Fork for library tinygl, assembly version.

Can draw lines, and do some matrix operations.

git-svn-id: svn://kolibrios.org@5153 a494cfbc-eb01-0410-851d-a64ba20cac60
This commit is contained in:
IgorA 2014-10-31 21:28:24 +00:00
parent 0be6fd256d
commit 62b33c4994
30 changed files with 11115 additions and 0 deletions

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,360 @@
VERTEX_ARRAY equ 0x0001
COLOR_ARRAY equ 0x0002
NORMAL_ARRAY equ 0x0004
TEXCOORD_ARRAY equ 0x0008
align 4
proc glopArrayElement uses eax ebx ecx edx, context:dword, param:dword
locals
p rd 5
endl
mov eax,[context]
mov ebx,[param]
mov ebx,[ebx+4] ;ebx = p[1]
bt dword[eax+offs_cont_client_states],1 ;2^1=COLOR_ARRAY
jnc @f
mov ecx,[eax+offs_cont_color_array_size]
add ecx,[eax+offs_cont_color_array_stride]
imul ecx,ebx
shl ecx,2
add ecx,eax
add ecx,offs_cont_color_array ;ecx = &context.color_array[i]
mov ebx,ebp
sub ebx,20 ;=sizeof(dd)*5
mov edx,[ecx]
mov [ebx+4],edx
mov edx,[ecx+4]
mov [ebx+8],edx
mov edx,[ecx+8]
mov [ebx+12],edx
cmp dword[eax+offs_cont_color_array_size],3
jg .l0
mov edx,1.0
jmp .l1
.l0:
mov edx,[ecx+12]
.l1:
mov [ebx+16],edx
stdcall glopColor, eax, ebx
@@:
bt dword[eax+offs_cont_client_states],2 ;2^2=NORMAL_ARRAY
jnc @f
mov esi,dword[eax+offs_cont_normal_array_stride]
add esi,3
imul esi,ebx
shl esi,2
add esi,eax
add esi,offs_cont_normal_array ;esi = &normal_array[ebx * (3 + c->normal_array_stride)]
mov edi,eax
add edi,offs_cont_current_normal
mov ecx,3
rep movsd
mov dword[edi],0.0
@@:
bt dword[eax+offs_cont_client_states],3 ;2^3=TEXCOORD_ARRAY
jnc @f
mov ecx,[eax+offs_cont_texcoord_array_size]
add ecx,[eax+offs_cont_texcoord_array_stride]
imul ecx,ebx
shl ecx,2
add ecx,eax
add ecx,offs_cont_texcoord_array ;ecx = &context.texcoord_array[i]
mov edx,[ecx]
mov [eax+offs_cont_current_tex_coord],edx
mov edx,[ecx+4]
mov [eax+offs_cont_current_tex_coord+4],edx
cmp dword[eax+offs_cont_texcoord_array_size],2
jg .l2
mov edx,0.0
jmp .l3
.l2:
mov edx,[ecx+8]
.l3:
mov [eax+offs_cont_current_tex_coord+8],edx
cmp dword[eax+offs_cont_texcoord_array_size],3
jg .l4
mov edx,1.0
jmp .l5
.l4:
mov edx,[ecx+12]
.l5:
mov [eax+offs_cont_current_tex_coord+12],edx
@@:
bt dword[eax+offs_cont_client_states],0 ;2^0=VERTEX_ARRAY
jnc @f
mov ecx,[eax+offs_cont_vertex_array_size]
add ecx,[eax+offs_cont_vertex_array_stride]
imul ecx,ebx
shl ecx,2
add ecx,eax
add ecx,offs_cont_vertex_array ;ecx = &context.vertex_array[i]
mov ebx,ebp
sub ebx,20 ;=sizeof(dd)*5
mov edx,[ecx]
mov [ebx+4],edx
mov edx,[ecx+4]
mov [ebx+8],edx
cmp dword[eax+offs_cont_vertex_array_size],2
jg .l6
mov edx,0.0
jmp .l7
.l6:
mov edx,[ecx+8]
.l7:
mov [ebx+12],edx
cmp dword[eax+offs_cont_vertex_array_size],3
jg .l8
mov edx,1.0
jmp .l9
.l8:
mov edx,[ecx+12]
.l9:
mov [ebx+16],edx
stdcall glopVertex, eax, ebx
@@:
ret
endp
align 4
proc glArrayElement uses eax, i:dword
locals
p rd 2
endl
mov dword[p],OP_ArrayElement
mov eax,[i]
mov dword[p+4],eax
mov eax,ebp
sub eax,8 ;=sizeof(dd)*2
stdcall gl_add_op,eax
ret
endp
align 4
proc glopEnableClientState uses eax ebx, context:dword, p:dword
mov eax,[context]
mov ebx,[p]
mov ebx,[ebx+4] ;ebx = p[1]
or dword[eax+offs_cont_client_states],ebx
ret
endp
align 4
proc glEnableClientState uses eax, array:dword
locals
p rd 2
endl
mov dword[p],OP_EnableClientState
cmp dword[array],GL_VERTEX_ARRAY
jne @f
mov dword[p+4],VERTEX_ARRAY
jmp .end_f
@@:
cmp dword[array],GL_NORMAL_ARRAY
jne @f
mov dword[p+4],NORMAL_ARRAY
jmp .end_f
@@:
cmp dword[array],GL_COLOR_ARRAY
jne @f
mov dword[p+4],COLOR_ARRAY
jmp .end_f
@@:
cmp dword[array],GL_TEXTURE_COORD_ARRAY
jne @f
mov dword[p+4],TEXCOORD_ARRAY
jmp .end_f
@@:
;assert(0);
.end_f:
mov eax,ebp
sub eax,8 ;=sizeof(dd)*2
stdcall gl_add_op,eax
ret
endp
align 4
proc glopDisableClientState uses eax ebx, context:dword, p:dword
mov eax,[context]
mov ebx,[p]
mov ebx,[ebx+4] ;ebx = p[1]
and dword[eax+offs_cont_client_states],ebx
ret
endp
align 4
proc glDisableClientState uses eax, array:dword
locals
p rd 2
endl
mov dword[p],OP_DisableClientState
cmp dword[array],GL_VERTEX_ARRAY
jne @f
mov dword[p+4], not VERTEX_ARRAY
jmp .end_f
@@:
cmp dword[array],GL_NORMAL_ARRAY
jne @f
mov dword[p+4], not NORMAL_ARRAY
jmp .end_f
@@:
cmp dword[array],GL_COLOR_ARRAY
jne @f
mov dword[p+4], not COLOR_ARRAY
jmp .end_f
@@:
cmp dword[array],GL_TEXTURE_COORD_ARRAY
jne @f
mov dword[p+4], not TEXCOORD_ARRAY
jmp .end_f
@@:
;assert(0);
.end_f:
mov eax,ebp
sub eax,8 ;=sizeof(dd)*2
stdcall gl_add_op,eax
ret
endp
align 4
proc glopVertexPointer uses eax ebx ecx, context:dword, p:dword
mov eax,[context]
mov ebx,[p]
mov ecx,[ebx+4] ;ecx = p[1]
mov dword[eax+offs_cont_vertex_array_size],ecx
mov ecx,[ebx+8] ;ecx = p[2]
mov dword[eax+offs_cont_vertex_array_stride],ecx
mov ecx,[ebx+12] ;ecx = p[3]
mov dword[eax+offs_cont_vertex_array],ecx
ret
endp
align 4
proc glVertexPointer uses eax, size:dword, type:dword, stride:dword, pointer:dword
locals
p rd 4
endl
; assert(type == GL_FLOAT);
mov dword[p],OP_TexCoordPointer
mov eax,[size]
mov dword[p+4],eax
mov eax,[stride]
mov dword[p+8],eax
mov eax,[pointer]
mov dword[p+12],eax
mov eax,ebp
sub eax,16 ;=sizeof(dd)*4
stdcall gl_add_op,eax
ret
endp
align 4
proc glopColorPointer uses eax ebx ecx, context:dword, p:dword
mov eax,[context]
mov ebx,[p]
mov ecx,[ebx+4] ;ecx = p[1]
mov dword[eax+offs_cont_color_array_size],ecx
mov ecx,[ebx+8] ;ecx = p[2]
mov dword[eax+offs_cont_color_array_stride],ecx
mov ecx,[ebx+12] ;ecx = p[3]
mov dword[eax+offs_cont_color_array],ecx
ret
endp
align 4
proc glColorPointer uses eax, size:dword, type:dword, stride:dword, pointer:dword
locals
p rd 4
endl
; assert(type == GL_FLOAT);
mov dword[p],OP_ColorPointer
mov eax,[size]
mov dword[p+4],eax
mov eax,[stride]
mov dword[p+8],eax
mov eax,[pointer]
mov dword[p+12],eax
mov eax,ebp
sub eax,16 ;=sizeof(dd)*4
stdcall gl_add_op,eax
ret
endp
align 4
proc glopNormalPointer uses eax ebx ecx, context:dword, p:dword
mov eax,[context]
mov ebx,[p]
mov ecx,[ebx+4] ;ecx = p[1]
mov dword[eax+offs_cont_normal_array_stride],ecx
mov ecx,[ebx+8] ;ecx = p[2]
mov dword[eax+offs_cont_normal_array],ecx
ret
endp
align 4
proc glNormalPointer uses eax, type:dword, stride:dword, pointer:dword
locals
p rd 3
endl
; assert(type == GL_FLOAT);
mov dword[p],OP_NormalPointer
mov eax,[stride]
mov dword[p+4],eax
mov eax,[pointer]
mov dword[p+8],eax
mov eax,ebp
sub eax,12 ;=sizeof(dd)*3
stdcall gl_add_op,eax
ret
endp
align 4
proc glopTexCoordPointer uses eax ebx ecx, context:dword, p:dword
mov eax,[context]
mov ebx,[p]
mov ecx,[ebx+4] ;ecx = p[1]
mov dword[eax+offs_cont_texcoord_array_size],ecx
mov ecx,[ebx+8] ;ecx = p[2]
mov dword[eax+offs_cont_texcoord_array_stride],ecx
mov ecx,[ebx+12] ;ecx = p[3]
mov dword[eax+offs_cont_texcoord_array],ecx
ret
endp
align 4
proc glTexCoordPointer uses eax, size:dword, type:dword, stride:dword, pointer:dword
locals
p rd 4
endl
; assert(type == GL_FLOAT);
mov dword[p],OP_TexCoordPointer
mov eax,[size]
mov dword[p+4],eax
mov eax,[stride]
mov dword[p+8],eax
mov eax,[pointer]
mov dword[p+12],eax
mov eax,ebp
sub eax,16 ;=sizeof(dd)*4
stdcall gl_add_op,eax
ret
endp

View File

@ -0,0 +1,4 @@
if not exist bin mkdir bin
@fasm.exe -m 16384 tinygl.asm bin\tinygl.obj
@kpack bin\tinygl.obj
pause

View File

@ -0,0 +1,34 @@
align 4
proc glopClearColor uses ecx esi edi, context:dword, p:dword
mov esi,[p]
add esi,4
mov edi,[context]
add edi,offs_cont_clear_color
mov ecx,4
rep movsd
endp
align 4
proc glopClearDepth uses eax ebx, context:dword, p:dword
mov eax,[context]
mov ebx,[p]
mov ebx,[ebx+4] ;ebx = p[1]
mov dword[eax+offs_cont_clear_depth],ebx
ret
endp
;void glopClear(GLContext *c,GLParam *p)
;{
; int mask=p[1].i;
; int z=0;
; int r=(int)(c->clear_color.v[0]*65535);
; int g=(int)(c->clear_color.v[1]*65535);
; int b=(int)(c->clear_color.v[2]*65535);
;
; /* TODO : correct value of Z */
;
; ZB_clear(c->zb,mask & GL_DEPTH_BUFFER_BIT,z,
; mask & GL_COLOR_BUFFER_BIT,r,g,b);
;}

View File

@ -0,0 +1,923 @@
; fill triangle profile
; #define PROFILE
CLIP_XMIN equ (1<<0)
CLIP_XMAX equ (1<<1)
CLIP_YMIN equ (1<<2)
CLIP_YMAX equ (1<<3)
CLIP_ZMIN equ (1<<4)
CLIP_ZMAX equ (1<<5)
offs_X equ 0
offs_Y equ 4
offs_Z equ 8
offs_W equ 12
align 4
proc gl_transform_to_viewport uses eax ebx ecx, context:dword,v:dword
locals
point dd ?
endl
mov eax,[context]
mov ebx,[v]
; coordinates
fld1
fdiv dword[ebx+offs_vert_pc+offs_W] ;st0 = 1/v.pc.W
fld dword[ebx+offs_vert_pc+offs_X] ;st0 = v.pc.X
fmul st0,st1
fmul dword[eax+offs_cont_viewport+offs_vpor_scale+offs_X]
fadd dword[eax+offs_cont_viewport+offs_vpor_trans+offs_X]
fistp dword[ebx+offs_vert_zp] ;v.zp.x = st0, st0 = st1
fld dword[ebx+offs_vert_pc+offs_Y] ;st0 = v.pc.Y
fmul st0,st1
fmul dword[eax+offs_cont_viewport+offs_vpor_scale+offs_Y]
fadd dword[eax+offs_cont_viewport+offs_vpor_trans+offs_Y]
fistp dword[ebx+offs_vert_zp+offs_zbup_y] ;v.zp.y = st0, st0 = st1
fld dword[ebx+offs_vert_pc+offs_Z] ;st0 = v.pc.Z
fmul st0,st1
fmul dword[eax+offs_cont_viewport+offs_vpor_scale+offs_Z]
fadd dword[eax+offs_cont_viewport+offs_vpor_trans+offs_Z]
fistp dword[ebx+offs_vert_zp+offs_zbup_z] ;v.zp.z = st0, st0 = st1
; color
bt dword[eax+offs_cont_lighting_enabled],0
jnc @f
mov ecx,ebx
add ecx,offs_vert_zp+offs_zbup_b
push ecx
add ecx,offs_zbup_g-offs_zbup_b
push ecx
add ecx,offs_zbup_r-offs_zbup_g
push ecx
stdcall RGBFtoRGBI, dword[ebx+offs_vert_color],dword[ebx+offs_vert_color+4],dword[ebx+offs_vert_color+8]
jmp .end_if
@@:
; no need to convert to integer if no lighting : take current color
push ecx
mov ecx,[eax+offs_cont_longcurrent_color]
mov dword[ebx+offs_vert_zp+offs_zbup_r],ecx
mov ecx,[eax+offs_cont_longcurrent_color+4]
mov dword[ebx+offs_vert_zp+offs_zbup_g],ecx
mov ecx,[eax+offs_cont_longcurrent_color+8]
mov dword[ebx+offs_vert_zp+offs_zbup_b],ecx
pop ecx
.end_if:
; texture
bt dword[eax+offs_cont_texture_2d_enabled],0
jnc @f
mov dword[point],dword(ZB_POINT_S_MAX - ZB_POINT_S_MIN)
fild dword[point]
fmul dword[ebx+offs_vert_tex_coord] ;st0 *= v.tex_coord.X
fistp dword[ebx+offs_vert_zp+offs_zbup_s]
add dword[ebx+offs_vert_zp+offs_zbup_s],ZB_POINT_S_MIN
mov dword[point],dword(ZB_POINT_T_MAX - ZB_POINT_T_MIN)
fild dword[point]
fmul dword[ebx+offs_vert_tex_coord+4] ;st0 *= v.tex_coord.Y
fistp dword[ebx+offs_vert_zp+offs_zbup_t]
add dword[ebx+offs_vert_zp+offs_zbup_s],ZB_POINT_T_MIN
@@:
if DEBUG ;gl_transform_to_viewport
push edi
mov ecx,80
mov eax,[ebx+offs_vert_zp]
lea edi,[buf_param]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_zp_sp,2
stdcall str_len,edi
add edi,eax
sub ecx,eax
mov eax,[ebx+offs_vert_zp+offs_zbup_y]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_zp_sp,2
stdcall str_len,edi
add edi,eax
sub ecx,eax
mov eax,[ebx+offs_vert_zp+offs_zbup_z]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_nl,2
stdcall dbg_print,f_ttv,buf_param
pop edi
end if
ret
endp
align 4
proc gl_add_select1 uses eax ebx ecx, context:dword, z1:dword,z2:dword,z3:dword
mov eax,[z1]
mov ebx,eax
cmp [z2],eax
jge @f
mov eax,[z2]
@@:
cmp [z3],eax
jge @f
mov eax,[z3]
@@:
cmp [z2],ebx
jle @f
mov ebx,[z2]
@@:
cmp [z3],ebx
jle @f
mov ebx,[z3]
@@:
mov ecx,0xffffffff
sub ecx,ebx
push ecx
mov ecx,0xffffffff
sub ecx,eax
push ecx
stdcall gl_add_select, [context] ;,0xffffffff-eax,0xffffffff-ebx
ret
endp
; point
align 4
proc gl_draw_point uses eax ebx, context:dword, p0:dword
mov ebx,[p0]
cmp dword[ebx+offs_vert_clip_code],0 ;if (p0.clip_code == 0)
jne @f
mov eax,[context]
cmp dword[eax+offs_cont_render_mode],GL_SELECT
jne .els
stdcall gl_add_select, eax,dword[ebx+offs_vert_zp+offs_zbup_z],dword[ebx+offs_vert_zp+offs_zbup_z] ;p0.zp.z,p0.zp.z
jmp @f
.els:
add ebx,offs_vert_zp
stdcall ZB_plot, dword[eax+offs_cont_zb],ebx
@@:
ret
endp
; line
align 4
proc interpolate uses eax ebx ecx, q:dword,p0:dword,p1:dword,t:dword
mov eax,[q]
mov ebx,[p0]
mov ecx,[p1]
fld dword[t]
; интерполяция по координатам
fld dword[ecx+offs_vert_pc]
fsub dword[ebx+offs_vert_pc]
fmul st0,st1
fadd dword[ebx+offs_vert_pc]
fstp dword[eax+offs_vert_pc]
fld dword[ecx+offs_vert_pc+4]
fsub dword[ebx+offs_vert_pc+4]
fmul st0,st1
fadd dword[ebx+offs_vert_pc+4]
fstp dword[eax+offs_vert_pc+4]
fld dword[ecx+offs_vert_pc+8]
fsub dword[ebx+offs_vert_pc+8]
fmul st0,st1
fadd dword[ebx+offs_vert_pc+8]
fstp dword[eax+offs_vert_pc+8]
fld dword[ecx+offs_vert_pc+12]
fsub dword[ebx+offs_vert_pc+12]
fmul st0,st1
fadd dword[ebx+offs_vert_pc+12]
fstp dword[eax+offs_vert_pc+12]
; интерполяция по цвету
fld dword[ecx+offs_vert_color]
fsub dword[ebx+offs_vert_color]
fmul st0,st1
fadd dword[ebx+offs_vert_color]
fstp dword[eax+offs_vert_color]
fld dword[ecx+offs_vert_color+4]
fsub dword[ebx+offs_vert_color+4]
fmul st0,st1
fadd dword[ebx+offs_vert_color+4]
fstp dword[eax+offs_vert_color+4]
fld dword[ecx+offs_vert_color+8]
fsub dword[ebx+offs_vert_color+8]
fmul st0,st1
fadd dword[ebx+offs_vert_color+8]
fstp dword[eax+offs_vert_color+8]
ret
endp
;
; Line Clipping
;
; Line Clipping algorithm from 'Computer Graphics', Principles and
; Practice
; tmin,tmax -> &float
align 4
proc ClipLine1 uses ebx, denom:dword,num:dword,tmin:dword,tmax:dword
fldz
fcom dword[denom]
fstsw ax
sahf
je .u2
jmp @f
.u2:
fcom dword[num]
fstsw ax
sahf
jb .r0 ;if (denom==0 && num>0) return 0
jmp .r1
@@:
fcom dword[denom]
fstsw ax
sahf
ja .els_0 ;if (0<denom)
fld dword[num]
fdiv dword[denom]
mov ebx,[tmax]
fcom dword[ebx]
fstsw ax
sahf
ja .r0 ;if (t>*tmax) return 0
mov ebx,[tmin]
fcom dword[ebx]
fstsw ax
sahf
jbe .r1
fstp dword[ebx] ;if (t>*tmin) *tmin=t
jmp .r1
.els_0: ;else if (0>denom)
fld dword[num]
fdiv dword[denom]
mov ebx,[tmin]
fcom dword[ebx]
fstsw ax
sahf
jb .r0 ;if (t<*tmin) return 0
mov ebx,[tmax]
fcom dword[ebx]
fstsw ax
sahf
jae .r1
fstp dword[ebx] ;if (t<*tmin) *tmax=t
jmp .r1
.r0: ;return 0
xor eax,eax
jmp .end_f
.r1: ;return 1
xor eax,eax
inc eax
.end_f:
if DEBUG ;ClipLine1
push edi
mov ecx,80
lea edi,[buf_param]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_nl,2
stdcall dbg_print,f_cl1,buf_param
pop edi
end if
ffree st0 ;профилактика для очистки стека
fincstp ;как минимум одно значение в стеке уже есть
ret
endp
align 4
proc gl_draw_line uses eax ebx edx edi esi, context:dword, p1:dword, p2:dword
locals
d_x dd ?
d_y dd ?
d_z dd ?
d_w dd ?
x1 dd ?
y1 dd ?
z1 dd ?
w1 dd ?
q1 GLVertex ?
q2 GLVertex ?
tmin dd ? ;ebp-8
tmax dd ? ;ebp-4
endl
mov edx,[context]
mov edi,[p1]
mov esi,[p2]
if DEBUG
jmp @f
f_1 db ' gl_draw_line',0
@@:
stdcall dbg_print,f_1,m_1
end if
cmp dword[edi+offs_vert_clip_code],0
jne .els_i
cmp dword[esi+offs_vert_clip_code],0
jne .els_i
;if ( (p1.clip_code | p2.clip_code) == 0)
cmp dword[edx+offs_cont_render_mode],GL_SELECT ;if (context.render_mode == GL_SELECT)
jne .els_1
stdcall gl_add_select1, edx,dword[edi+offs_vert_zp+offs_zbup_z],\
dword[esi+offs_vert_zp+offs_zbup_z],dword[esi+offs_vert_zp+offs_zbup_z]
jmp .end_f
.els_1:
add edi,offs_vert_zp
add esi,offs_vert_zp
push esi
push edi
push dword[edx+offs_cont_zb]
cmp dword[edx+offs_cont_depth_test],0
je .els_2
;if (context.depth_test)
call ZB_line_z ;, dword[edx+offs_cont_zb],edi,esi
jmp .end_f
.els_2:
call ZB_line ;, dword[edx+offs_cont_zb],edi,esi
jmp .end_f
.els_i:
;else if ( (p1.clip_code & p2.clip_code) != 0 )
mov eax,[edi+offs_vert_clip_code]
and eax,[esi+offs_vert_clip_code]
cmp eax,0
jne .end_f
.els_0:
if DEBUG
stdcall dbg_print,f_1,m_2
end if
finit
fld dword[esi+offs_vert_pc+offs_X]
fsub dword[edi+offs_vert_pc+offs_X]
fstp dword[d_x] ;d_x = p2.pc.X - p1.pc.X
fld dword[esi+offs_vert_pc+offs_Y]
fsub dword[edi+offs_vert_pc+offs_Y]
fstp dword[d_y] ;d_y = p2.pc.Y - p1.pc.Y
fld dword[esi+offs_vert_pc+offs_Z]
fsub dword[edi+offs_vert_pc+offs_Z]
fstp dword[d_z] ;d_z = p2.pc.Z - p1.pc.Z
fld dword[esi+offs_vert_pc+offs_W]
fsub dword[edi+offs_vert_pc+offs_W]
fstp dword[d_w] ;d_w = p2.pc.W - p1.pc.W
mov eax,[edi+offs_vert_pc+offs_X]
mov [x1],eax ;x1 = p1.pc.X
mov eax,[edi+offs_vert_pc+offs_Y]
mov [y1],eax ;y1 = p1.pc.Y
mov eax,[edi+offs_vert_pc+offs_Z]
mov [z1],eax ;z1 = p1.pc.Z
mov eax,[edi+offs_vert_pc+offs_W]
mov [w1],eax ;w1 = p1.pc.W
mov dword[tmin],0.0
mov dword[tmax],1.0
mov eax,ebp
sub eax,4
push eax ;толкаем в стек адрес &tmax
sub eax,4
push eax ;толкаем в стек адрес &tmin
fld dword[x1]
fadd dword[w1]
fchs
fstp dword[esp-4]
fld dword[d_x]
fadd dword[d_w]
fstp dword[esp-8]
sub esp,8
call ClipLine1 ;d_x+d_w,-x1-w1,&tmin,&tmax
bt eax,0
jnc .end_f
sub esp,8 ;толкаем в стек адреса переменных &tmin и &tmax
fld dword[x1]
fsub dword[w1]
fstp dword[esp-4]
fld dword[d_w]
fsub dword[d_x]
fstp dword[esp-8]
sub esp,8
call ClipLine1 ;-d_x+d_w,x1-w1,&tmin,&tmax
bt eax,0
jnc .end_f
sub esp,8 ;толкаем в стек адреса переменных &tmin и &tmax
fld dword[y1]
fadd dword[w1]
fchs
fstp dword[esp-4]
fld dword[d_y]
fadd dword[d_w]
fstp dword[esp-8]
sub esp,8
call ClipLine1 ;d_y+d_w,-y1-w1,&tmin,&tmax
bt eax,0
jnc .end_f
sub esp,8 ;толкаем в стек адреса переменных &tmin и &tmax
fld dword[y1]
fsub dword[w1]
fstp dword[esp-4]
fld dword[d_w]
fsub dword[d_y]
fstp dword[esp-8]
sub esp,8
call ClipLine1 ;-d_y+d_w,y1-w1,&tmin,&tmax
bt eax,0
jnc .end_f
sub esp,8 ;толкаем в стек адреса переменных &tmin и &tmax
fld dword[z1]
fadd dword[w1]
fchs
fstp dword[esp-4]
fld dword[d_z]
fadd dword[d_w]
fstp dword[esp-8]
sub esp,8
call ClipLine1 ;d_z+d_w,-z1-w1,&tmin,&tmax
bt eax,0
jnc .end_f
sub esp,8 ;толкаем в стек адреса переменных &tmin и &tmax
fld dword[z1]
fsub dword[w1]
fstp dword[esp-4]
fld dword[d_w]
fsub dword[d_z]
fstp dword[esp-8]
sub esp,8
call ClipLine1 ;-d_z+d_w,z1-w1,&tmin,&tmax
bt eax,0
jnc .end_f
mov eax,ebp
sub eax,8+2*sizeof.GLVertex ;eax = &q1
stdcall interpolate, eax,edi,esi,[tmin]
stdcall gl_transform_to_viewport, edx,eax
add eax,sizeof.GLVertex ;eax = &q2
stdcall interpolate, eax,edi,esi,[tmax]
stdcall gl_transform_to_viewport, edx,eax
sub eax,sizeof.GLVertex ;eax = &q1
mov ebx,eax
add ebx,offs_vert_zp+offs_zbup_b
push ebx
add ebx,offs_zbup_g-offs_zbup_b
push ebx
add ebx,offs_zbup_r-offs_zbup_g
push ebx
stdcall RGBFtoRGBI, dword[eax+offs_vert_color],dword[eax+offs_vert_color+4],dword[eax+offs_vert_color+8]
add eax,sizeof.GLVertex ;eax = &q2
mov ebx,eax
add ebx,offs_vert_zp+offs_zbup_b
push ebx
add ebx,offs_zbup_g-offs_zbup_b
push ebx
add ebx,offs_zbup_r-offs_zbup_g
push ebx
stdcall RGBFtoRGBI, dword[eax+offs_vert_color],dword[eax+offs_vert_color+4],dword[eax+offs_vert_color+8]
add eax,offs_vert_zp ;eax = &q2.zp
push eax
sub eax,sizeof.GLVertex ;eax = &q1.zp
push eax
push dword[edx+offs_cont_zb]
cmp dword[edx+offs_cont_depth_test],0
je .els_3
call ZB_line_z ;(context.zb,&q1.zp,&q2.zp)
jmp .end_f
.els_3:
call ZB_line ;(context.zb,&q1.zp,&q2.zp)
.end_f:
ret
endp
; triangle
;
; Clipping
;
; We clip the segment [a,b] against the 6 planes of the normal volume.
; We compute the point 'c' of intersection and the value of the parameter 't'
; of the intersection if x=a+t(b-a).
;
; sign: 0 -> '-', 1 -> '+'
macro clip_func sign,dir,dir1,dir2
{
locals
t dd ?
d_X dd ?
d_Y dd ?
d_Z dd ?
d_W dd ?
endl
mov edx,[a]
mov ebx,[b]
mov ecx,[c]
fld dword[ebx]
fsub dword[edx]
fstp dword[d_X] ;d_X = (b.X - a.X)
fld dword[ebx+4]
fsub dword[edx+4]
fstp dword[d_Y] ;d_Y = (b.Y - a.Y)
fld dword[ebx+8]
fsub dword[edx+8]
fstp dword[d_Z] ;d_Z = (b.Z - a.Z)
fld dword[ebx+12]
fsub dword[edx+12]
fst dword[d_W] ;d_W = (b.W - a.W)
if sign eq 0
fadd dword[d#dir]
else
fsub dword[d#dir]
end if
fldz
fcomp st1
fstsw ax
sahf
ja @f
fincstp
fst dword[t] ;t=0
jmp .e_zero
@@: ;else
fincstp
fld dword[edx+offs#dir]
if sign eq 0
fchs
end if
fsub dword[edx+offs_W]
fdiv st0,st1
fst dword[t] ;t = ( sign a.dir - a.W) / den
.e_zero:
fmul dword[d#dir1] ;st0 = t * d.dir1
fadd dword[edx+offs#dir1]
fstp dword[ecx+offs#dir1] ;c.dir1 = a.dir1 + t * d.dir1
fld dword[t]
fmul dword[d#dir2] ;st0 = t * d.dir2
fadd dword[edx+offs#dir2]
fstp dword[ecx+offs#dir2] ;c.dir2 = a.dir2 + t * d.dir2
fld dword[t]
fmul dword[d_W]
fadd dword[edx+offs_W]
fst dword[ecx+offs_W] ;c.W = a.W + t * d_W
if sign eq 0
fchs
end if
fstp dword[ecx+offs#dir] ;c.dir = sign c.W
mov eax,[t]
}
align 4
proc clip_xmin uses ebx ecx edx, c:dword, a:dword, b:dword
clip_func 0,_X,_Y,_Z
ret
endp
align 4
proc clip_xmax uses ebx ecx edx, c:dword, a:dword, b:dword
clip_func 1,_X,_Y,_Z
ret
endp
align 4
proc clip_ymin uses ebx ecx edx, c:dword, a:dword, b:dword
clip_func 0,_Y,_X,_Z
ret
endp
align 4
proc clip_ymax uses ebx ecx edx, c:dword, a:dword, b:dword
clip_func 1,_Y,_X,_Z
ret
endp
align 4
proc clip_zmin uses ebx ecx edx, c:dword, a:dword, b:dword
clip_func 0,_Z,_X,_Y
ret
endp
align 4
proc clip_zmax uses ebx ecx edx, c:dword, a:dword, b:dword
clip_func 1,_Z,_X,_Y
ret
endp
align 4
clip_proc dd clip_xmin,clip_xmax, clip_ymin,clip_ymax, clip_zmin,clip_zmax
;static inline void updateTmp(GLContext *c, GLVertex *q,GLVertex *p0,GLVertex *p1,float t)
;{
; if (c->current_shade_model == GL_SMOOTH) {
; q->color.v[0]=p0->color.v[0] + (p1->color.v[0]-p0->color.v[0])*t;
; q->color.v[1]=p0->color.v[1] + (p1->color.v[1]-p0->color.v[1])*t;
; q->color.v[2]=p0->color.v[2] + (p1->color.v[2]-p0->color.v[2])*t;
; } else {
; q->color.v[0]=p0->color.v[0];
; q->color.v[1]=p0->color.v[1];
; q->color.v[2]=p0->color.v[2];
; }
; if (c->texture_2d_enabled) {
; q->tex_coord.X=p0->tex_coord.X + (p1->tex_coord.X-p0->tex_coord.X)*t;
; q->tex_coord.Y=p0->tex_coord.Y + (p1->tex_coord.Y-p0->tex_coord.Y)*t;
; }
; q->clip_code=gl_clipcode(q->pc.X,q->pc.Y,q->pc.Z,q->pc.W);
; if (q->clip_code==0){
; gl_transform_to_viewport(c,q);
; RGBFtoRGBI(q->color.v[0],q->color.v[1],q->color.v[2],q->zp.r,q->zp.g,q->zp.b);
; }
;}
;static void gl_draw_triangle_clip(GLContext *c, GLVertex *p0,GLVertex *p1,GLVertex *p2,int clip_bit);
;void gl_draw_triangle(GLContext *c, GLVertex *p0,GLVertex *p1,GLVertex *p2)
;{
; int co,c_and,cc[3],front;
; float norm;
;
; cc[0]=p0->clip_code;
; cc[1]=p1->clip_code;
; cc[2]=p2->clip_code;
;
; co=cc[0] | cc[1] | cc[2];
;
; /* we handle the non clipped case here to go faster */
; if (co==0) {
;
; norm=(float)(p1->zp.x-p0->zp.x)*(float)(p2->zp.y-p0->zp.y)-
; (float)(p2->zp.x-p0->zp.x)*(float)(p1->zp.y-p0->zp.y);
;
; if (norm == 0) return;
;
; front = norm < 0.0;
; front = front ^ c->current_front_face;
;
; /* back face culling */
; if (c->cull_face_enabled) {
; /* most used case first */
; if (c->current_cull_face == GL_BACK) {
; if (front == 0) return;
; c->draw_triangle_front(c,p0,p1,p2);
; } else if (c->current_cull_face == GL_FRONT) {
; if (front != 0) return;
; c->draw_triangle_back(c,p0,p1,p2);
; } else {
; return;
; }
; } else {
; /* no culling */
; if (front) {
; c->draw_triangle_front(c,p0,p1,p2);
; } else {
; c->draw_triangle_back(c,p0,p1,p2);
; }
; }
; } else {
; c_and=cc[0] & cc[1] & cc[2];
; if (c_and==0) {
; gl_draw_triangle_clip(c,p0,p1,p2,0);
; }
; }
;}
;static void gl_draw_triangle_clip(GLContext *c, GLVertex *p0,GLVertex *p1,GLVertex *p2,int clip_bit)
;{
; int co,c_and,co1,cc[3],edge_flag_tmp,clip_mask;
; GLVertex tmp1,tmp2,*q[3];
; float tt;
; cc[0]=p0->clip_code;
; cc[1]=p1->clip_code;
; cc[2]=p2->clip_code;
; co=cc[0] | cc[1] | cc[2];
; if (co == 0) {
; gl_draw_triangle(c,p0,p1,p2);
; } else {
; c_and=cc[0] & cc[1] & cc[2];
; /* the triangle is completely outside */
; if (c_and!=0) return;
; /* find the next direction to clip */
; while (clip_bit < 6 && (co & (1 << clip_bit)) == 0) {
; clip_bit++;
; }
; /* this test can be true only in case of rounding errors */
; if (clip_bit == 6) {
;#if 0
; printf("Error:\n");
; printf("%f %f %f %f\n",p0->pc.X,p0->pc.Y,p0->pc.Z,p0->pc.W);
; printf("%f %f %f %f\n",p1->pc.X,p1->pc.Y,p1->pc.Z,p1->pc.W);
; printf("%f %f %f %f\n",p2->pc.X,p2->pc.Y,p2->pc.Z,p2->pc.W);
;#endif
; return;
; }
; clip_mask = 1 << clip_bit;
; co1=(cc[0] ^ cc[1] ^ cc[2]) & clip_mask;
; if (co1) {
; /* one point outside */
; if (cc[0] & clip_mask) { q[0]=p0; q[1]=p1; q[2]=p2; }
; else if (cc[1] & clip_mask) { q[0]=p1; q[1]=p2; q[2]=p0; }
; else { q[0]=p2; q[1]=p0; q[2]=p1; }
;
; tt=clip_proc[clip_bit](&tmp1.pc,&q[0]->pc,&q[1]->pc);
; updateTmp(c,&tmp1,q[0],q[1],tt);
;
; tt=clip_proc[clip_bit](&tmp2.pc,&q[0]->pc,&q[2]->pc);
; updateTmp(c,&tmp2,q[0],q[2],tt);
;
; tmp1.edge_flag=q[0]->edge_flag;
; edge_flag_tmp=q[2]->edge_flag;
; q[2]->edge_flag=0;
; gl_draw_triangle_clip(c,&tmp1,q[1],q[2],clip_bit+1);
;
; tmp2.edge_flag=0;
; tmp1.edge_flag=0;
; q[2]->edge_flag=edge_flag_tmp;
; gl_draw_triangle_clip(c,&tmp2,&tmp1,q[2],clip_bit+1);
; } else {
; /* two points outside */
; if ((cc[0] & clip_mask)==0) { q[0]=p0; q[1]=p1; q[2]=p2; }
; else if ((cc[1] & clip_mask)==0) { q[0]=p1; q[1]=p2; q[2]=p0; }
; else { q[0]=p2; q[1]=p0; q[2]=p1; }
; tt=clip_proc[clip_bit](&tmp1.pc,&q[0]->pc,&q[1]->pc);
; updateTmp(c,&tmp1,q[0],q[1],tt);
; tt=clip_proc[clip_bit](&tmp2.pc,&q[0]->pc,&q[2]->pc);
; updateTmp(c,&tmp2,q[0],q[2],tt);
; tmp1.edge_flag=1;
; tmp2.edge_flag=q[2]->edge_flag;
; gl_draw_triangle_clip(c,q[0],&tmp1,&tmp2,clip_bit+1);
; }
; }
;}
align 4
proc gl_draw_triangle_select uses eax, context:dword, p0:dword,p1:dword,p2:dword
mov eax,[p2]
push dword[eax+offs_vert_zp+offs_Z]
mov eax,[p1]
push dword[eax+offs_vert_zp+offs_Z]
mov eax,[p0]
push dword[eax+offs_vert_zp+offs_Z]
stdcall gl_add_select1, [context] ;,p0.zp.z, p1.zp.z, p2.zp.z
ret
endp
;#ifdef PROFILE
;int count_triangles,count_triangles_textured,count_pixels;
;#endif
align 4
proc gl_draw_triangle_fill uses eax edx, context:dword, p0:dword,p1:dword,p2:dword
;#ifdef PROFILE
; {
; int norm;
; assert(p0->zp.x >= 0 && p0->zp.x < c->zb->xsize);
; assert(p0->zp.y >= 0 && p0->zp.y < c->zb->ysize);
; assert(p1->zp.x >= 0 && p1->zp.x < c->zb->xsize);
; assert(p1->zp.y >= 0 && p1->zp.y < c->zb->ysize);
; assert(p2->zp.x >= 0 && p2->zp.x < c->zb->xsize);
; assert(p2->zp.y >= 0 && p2->zp.y < c->zb->ysize);
; norm=(p1->zp.x-p0->zp.x)*(p2->zp.y-p0->zp.y)-
; (p2->zp.x-p0->zp.x)*(p1->zp.y-p0->zp.y);
; count_pixels+=abs(norm)/2;
; count_triangles++;
; }
;#endif
mov edx,[context]
cmp dword[edx+offs_cont_texture_2d_enabled],0
je .els_i
;if (context.texture_2d_enabled)
;#ifdef PROFILE
; count_triangles_textured++;
;#endif
mov eax,dword[edx+offs_cont_current_texture]
mov eax,[eax] ;переход по указателю
;так как offs_text_images+offs_imag_pixmap = 0 то context.current_texture.images[0].pixmap = [eax]
stdcall ZB_setTexture, dword[edx+offs_cont_zb],dword[eax]
; ZB_fillTriangleMappingPerspective, dword[edx+offs_cont_zb],&p0->zp,&p1->zp,&p2->zp);
jmp .end_f
.els_i:
cmp dword[edx+offs_cont_current_shade_model],GL_SMOOTH
jne .els
;else if (context.current_shade_model == GL_SMOOTH)
; ZB_fillTriangleSmooth, dword[edx+offs_cont_zb],&p0->zp,&p1->zp,&p2->zp);
jmp .end_f
.els:
; ZB_fillTriangleFlat, dword[edx+offs_cont_zb],&p0->zp,&p1->zp,&p2->zp);
.end_f:
ret
endp
; Render a clipped triangle in line mode
align 4
proc gl_draw_triangle_line uses eax ebx ecx edx, context:dword, p0:dword,p1:dword,p2:dword
mov edx,[context]
cmp dword[edx+offs_cont_depth_test],0
je .els
lea ecx,[ZB_line_z]
jmp @f
.els:
lea ecx,[ZB_line]
@@:
;if (p0.edge_flag) ZB_line_z(context.zb,&p0.zp,&p1.zp)
mov eax,[p0]
cmp dword[eax+offs_vert_edge_flag],0
je @f
mov ebx,eax
add ebx,offs_vert_zp
mov eax,[p1]
add eax,offs_vert_zp
stdcall ecx,dword[edx+offs_cont_zb],ebx,eax
@@:
;if (p1.edge_flag) ZB_line_z(context.zb,&p1.zp,&p2.zp)
mov eax,[p1]
cmp dword[eax+offs_vert_edge_flag],0
je @f
mov ebx,eax
add ebx,offs_vert_zp
mov eax,[p2]
add eax,offs_vert_zp
stdcall ecx,dword[edx+offs_cont_zb],ebx,eax
@@:
;if (p2.edge_flag) ZB_line_z(context.zb,&p2.zp,&p0.zp);
mov eax,[p2]
cmp dword[eax+offs_vert_edge_flag],0
je @f
mov ebx,eax
add ebx,offs_vert_zp
mov eax,[p0]
add eax,offs_vert_zp
stdcall ecx,dword[edx+offs_cont_zb],ebx,eax
@@:
ret
endp
; Render a clipped triangle in point mode
align 4
proc gl_draw_triangle_point uses eax ebx edx, context:dword, p0:dword,p1:dword,p2:dword
mov edx,[context]
mov eax,[p0]
cmp dword[eax+offs_vert_edge_flag],0
je @f
mov ebx,eax
add ebx,offs_vert_zp
stdcall ZB_plot,dword[edx+offs_cont_zb],ebx
@@:
add eax,[p1]
cmp dword[eax+offs_vert_edge_flag],0
je @f
mov ebx,eax
add ebx,offs_vert_zp
stdcall ZB_plot,dword[edx+offs_cont_zb],ebx
@@:
add eax,[p2]
cmp dword[eax+offs_vert_edge_flag],0
je @f
mov ebx,eax
add ebx,offs_vert_zp
stdcall ZB_plot,dword[edx+offs_cont_zb],ebx
@@:
ret
endp

View File

@ -0,0 +1,164 @@
;
; Export functions (103)
;
E_LIB glEnable ;(int code)
E_LIB glDisable ;(int code)
E_LIB glShadeModel ;(int mode)
E_LIB glCullFace ;(int mode)
E_LIB glPolygonMode ;(int face,int mode)
E_LIB glBegin ;(int type)
E_LIB glEnd ;(void)
E_LIB glVertex2f ;(float ,float)
E_LIB glVertex2d ;(double ,double)
E_LIB glVertex2fv ;(float *)
E_LIB glVertex2dv ;(double *)
E_LIB glVertex3f ;(float ,float ,float)
E_LIB glVertex3d ;(double ,double ,double)
E_LIB glVertex3fv ;(float *)
E_LIB glVertex3dv ;(double *)
E_LIB glVertex4f ;(float ,float ,float, float )
E_LIB glVertex4d ;(double ,double ,double, double )
E_LIB glVertex4fv ;(float *)
E_LIB glVertex4dv ;(double *)
E_LIB glColor3f ;(float ,float ,float)
E_LIB glColor3d ;(double ,double ,double)
E_LIB glColor3fv ;(float *)
E_LIB glColor3dv ;(double *)
E_LIB glColor4f ;(float ,float ,float, float )
E_LIB glColor4d ;(double ,double ,double, double )
E_LIB glColor4fv ;(float *)
E_LIB glColor4dv ;(double *)
E_LIB glNormal3f ;(float ,float ,float)
E_LIB glNormal3d ;(double ,double ,double)
E_LIB glNormal3fv ;(float *)
E_LIB glNormal3dv ;(double *)
E_LIB glTexCoord1f ;(float)
E_LIB glTexCoord1d ;(double)
E_LIB glTexCoord1fv ;(float *)
E_LIB glTexCoord1dv ;(double *)
E_LIB glTexCoord2f ;(float ,float)
E_LIB glTexCoord2d ;(double ,double)
E_LIB glTexCoord2fv ;(float *)
E_LIB glTexCoord2dv ;(double *)
E_LIB glTexCoord3f ;(float ,float ,float)
E_LIB glTexCoord3d ;(double ,double ,double)
E_LIB glTexCoord3fv ;(float *)
E_LIB glTexCoord3dv ;(double *)
E_LIB glTexCoord4f ;(float ,float ,float, float )
E_LIB glTexCoord4d ;(double ,double ,double, double )
E_LIB glTexCoord4fv ;(float *)
E_LIB glTexCoord4dv ;(double *)
E_LIB glEdgeFlag ;(int flag)
; matrix
E_LIB glMatrixMode ;(int mode)
E_LIB glLoadMatrixf ;(const float *m)
E_LIB glLoadIdentity ;(void)
E_LIB glMultMatrixf ;(const float *m)
E_LIB glPushMatrix ;(void)
E_LIB glPopMatrix ;(void)
E_LIB glRotatef ;(float angle,float x,float y,float z)
E_LIB glTranslatef ;(float x,float y,float z)
E_LIB glScalef ;(float x,float y,float z)
E_LIB glViewport ;(int x,int y,int width,int height)
E_LIB glFrustum ;(double left,double right,double bottom,double top, double near_,double far_);
; lists
E_LIB glGenLists ;(int range)
E_LIB glIsList ;(unsigned int list)
E_LIB glNewList ;(unsigned int list,int mode)
E_LIB glEndList ;(void)
E_LIB glCallList ;(unsigned int list)
; clear
E_LIB glClear ;(int mask)
E_LIB glClearColor ;(float r,float g,float b,float a)
E_LIB glClearDepth ;(double depth)
; selection
E_LIB glRenderMode ;(int mode)
E_LIB glSelectBuffer ;(int size,unsigned int *buf)
E_LIB glInitNames ;(void)
E_LIB glPushName ;(unsigned int name)
E_LIB glPopName ;(void)
E_LIB glLoadName ;(unsigned int name)
; textures
E_LIB glGenTextures ;(int n, unsigned int *textures)
E_LIB glDeleteTextures ;(int n, const unsigned int *textures)
E_LIB glBindTexture ;(int target,int texture)
E_LIB glTexImage2D ;( int target, int level, int components, int width, int height, int border, int format, int type, void *pixels)
E_LIB glTexEnvi ;(int target,int pname,int param)
E_LIB glTexParameteri ;(int target,int pname,int param)
E_LIB glPixelStorei ;(int pname,int param)
; lighting
E_LIB glMaterialfv ;(int mode,int type,float *v)
E_LIB glMaterialf ;(int mode,int type,float v)
E_LIB glColorMaterial ;(int mode,int type)
E_LIB glLightfv ;(int light,int type,float *v)
E_LIB glLightf ;(int light,int type,float v)
E_LIB glLightModeli ;(int pname,int param)
E_LIB glLightModelfv ;(int pname,float *param)
; misc
E_LIB glFlush ;(void)
E_LIB glHint ;(int target,int mode)
E_LIB glGetIntegerv ;(int pname,int *params)
E_LIB glGetFloatv ;(int pname, float *v)
E_LIB glFrontFace ;(int mode)
; opengl 1.2 arrays
E_LIB glEnableClientState ;(GLenum array)
E_LIB glDisableClientState ;(GLenum array)
E_LIB glArrayElement ;(GLint i)
E_LIB glVertexPointer ;(GLint size, GLenum type, GLsizei stride, const GLvoid *pointer)
E_LIB glColorPointer ;(GLint size, GLenum type, GLsizei stride, const GLvoid *pointer)
E_LIB glNormalPointer ;(GLenum type, GLsizei stride, const GLvoid *pointer)
E_LIB glTexCoordPointer ;(GLint size, GLenum type, GLsizei stride, const GLvoid *pointer)
; opengl 1.2 polygon offset
E_LIB glPolygonOffset ;(GLfloat factor, GLfloat units)
; not implemented, just added to compile
;inline void glPointSize(float) {}
;inline void glLineWidth(float) {}
;inline void glDeleteLists(int, int) {}
;inline void glDepthFunc(int) {}
;inline void glBlendFunc(int, int) {}
;inline void glTexEnvf(int, int, int) {}
;inline void glOrtho(float,float,float,float,float,float){}
;inline void glVertex2i(int,int) {}
;inline void glDepthMask(int) {}
;inline void glFogi(int, int) {}
;inline void glFogfv(int, const float*) {}
;inline void glFogf(int, float) {}
;inline void glRasterPos2f(float, float) {}
;inline void glPolygonStipple(void*) {}
;inline void glTexParameterf(int, int, int) {};
; non compatible functions
E_LIB glDebug ;(int mode)
E_LIB glInit ;(void *zbuffer)
E_LIB glClose ;(void)
;
; Kolibri OS functions
;
E_LIB kosglMakeCurrent
E_LIB kosglSwapBuffers
purge E_LIB

View File

@ -0,0 +1,326 @@
;
; ä㭪樨 ¤«ï à ¡®âë á ç¨á« ¬¨ float
;
; Š®«¨ç¥á⢮ §­ ª®¢ ç¨á«  ¯®á«¥ § ¯ï⮩ (1-17)
NumberSymbolsAD DW 5
; Š®­áâ ­âë (10 ¢ á⥯¥­¨ N)
MConst DQ 1.0E1,1.0E2,1.0E3,1.0E4,1.0E5
DQ 1.0E6,1.0E7,1.0E8,1.0E9,1.0E10
DQ 1.0E11,1.0E12,1.0E13,1.0E14,1.0E15
DQ 1.0E16,1.0E17,1.0E18,1.0E19,1.0E20
DQ 1.0E21,1.0E22,1.0E23,1.0E24,1.0E25
DQ 1.0E26,1.0E27,1.0E28,1.0E29,1.0E30
DQ 1.0E31,1.0E32,1.0E33,1.0E34,1.0E35
DQ 1.0E36,1.0E37,1.0E38,1.0E39,1.0E40
DQ 1.0E41,1.0E42,1.0E43,1.0E44,1.0E45
DQ 1.0E46,1.0E47,1.0E48,1.0E49,1.0E50
DQ 1.0E51,1.0E52,1.0E53,1.0E54,1.0E55
DQ 1.0E56,1.0E57,1.0E58,1.0E59,1.0E60
DQ 1.0E61,1.0E62,1.0E63,1.0E64,1.0E65
DQ 1.0E66,1.0E67,1.0E68,1.0E69,1.0E70
DQ 1.0E71,1.0E72,1.0E73,1.0E74,1.0E75
DQ 1.0E76,1.0E77,1.0E78,1.0E79,1.0E80
DQ 1.0E81,1.0E82,1.0E83,1.0E84,1.0E85
DQ 1.0E86,1.0E87,1.0E88,1.0E89,1.0E90
DQ 1.0E91,1.0E92,1.0E93,1.0E94,1.0E95
DQ 1.0E96,1.0E97,1.0E98,1.0E99,1.0E100
DQ 1.0E101,1.0E102,1.0E103,1.0E104,1.0E105
DQ 1.0E106,1.0E107,1.0E108,1.0E109,1.0E110
DQ 1.0E111,1.0E112,1.0E113,1.0E114,1.0E115
DQ 1.0E116,1.0E117,1.0E118,1.0E119,1.0E120
DQ 1.0E121,1.0E122,1.0E123,1.0E124,1.0E125
DQ 1.0E126,1.0E127,1.0E128
; —¨á«® á ¯« ¢ î饩 § ¯ï⮩ ¤¢®©­®© â®ç­®áâ¨
Data_Double DQ ?
; —¨á«® ¢ BCD-ä®à¬ â¥
Data_BCD DT ?
; ‚ᯮ¬®£ â¥«ì­ë© ä« £
Data_Flag DB ?
; ‡­ ª १ã«ìâ â  (¥á«¨ ­¥ 0 - ®âà¨æ â¥«ì­®¥ ç¨á«®)
Data_Sign DB ?
db 0 ;㪠§ â¥«ì ­  ᤢ¨£ ¢ ¯ ¬ïâ¨
; ‘âப  ¤«ï åà ­¥­¨ï ç¨á«  ¢ ª®¤¥ ASCII
Data_String DB 32 DUP (?)
;*******************************************************
;* <EFBFBD><EFBFBD>…Ž<EFBFBD><EFBFBD>€‡Ž<EFBFBD>ˆ —ˆ‘‹€ <EFBFBD>€ž™…‰ ‡€<EFBFBD>ŸŽ‰ <EFBFBD>ŽŠ“ *
;* —¨á«® ¨¬¥¥â ä®à¬ â á 㤢®¥­­®© â®ç­®áâìî, १ã«ìâ â *
;* ¢ë¤ ¥âáï ¢ ¤¥áïâ¨ç­®¬ ª®¤¥, ¢ "¡ë⮢®¬" ä®à¬ â¥ á *
;* 䨪á¨à®¢ ­­ë¬ ª®«¨ç¥á⢮¬ §­ ª®¢ ¯®á«¥ § ¯ï⮩. *
;* ‚室­ë¥ ¯ à ¬¥âàë: *
;* Data_Double - ¯à¥®¡à §ã¥¬®¥ ç¨á«®; *
;* NumberSymbolsAD - ª®«¨ç¥á⢮ §­ ª®¢ ¯®á«¥ *
;* § ¯ï⮩ (0-17). *
;* ‚ë室­ë¥ ¯ à ¬¥âàë: *
;* Data_String - áâப -१ã«ìâ â. *
;*******************************************************
DoubleFloat_to_String:
pushad
; <EFBFBD>¥§ã«ìâ â § ¯¨á뢠âì ¢ áâபã Data_String
lea EDI, [Data_String]
; ‘¤¢¨£ ¥¬ ç¨á«® ¢«¥¢® ­  NumberSymbolsAD
; ¤¥áïâ¨ç­ëå à §à冷¢
fninit ;á¡à®á ᮯà®æ¥áá®à 
fld [Data_Double] ;§ £à㧨âì ç¨á«®
xor ebx,ebx
mov BX,[NumberSymbolsAD]
cmp BX, 0
je .NoShifts ;­¥â æ¨äà ¯®á«¥ § ¯ï⮩
jl .Error ;®è¨¡ª 
dec BX
shl BX, 3 ;㬭®¦ ¥¬ ­  8
lea eax,[MConst]
add EBX, eax
fmul qword [EBX] ;㬭®¦¨âì ­  ª®­áâ ­âã
.NoShifts:
; ˆ§¢«¥çì ç¨á«® ¢ ª®¤¥ BCD
fbstp [Data_BCD]
; <EFBFBD>஢¥à¨âì १ã«ìâ â ­  ¯¥à¥¯®«­¥­¨¥
mov AX,word [Data_BCD + 8]
cmp AX,0FFFFh ;"¤¥áïâ¨ç­®¥" ¯¥à¥¯®«­¥­¨¥?
je .Overflow
; ‚뤥«¨âì §­ ª ç¨á«  ¨ § ¯¨á âì ¥£® ¢ ASCII-ª®¤¥
mov AL, byte [Data_BCD + 9]
and AL,AL
jz .NoSign
mov AL,'-'
stosb
.NoSign:
; <EFBFBD> á¯ ª®¢ âì ç¨á«® ¢ ª®¤ ASCII
mov ebx,8 ;ᬥ饭¨¥ ¯®á«¥¤­¥© ¯ àë æ¨äà
mov ecx,9 ;áç¥â稪 ¯ à æ¨äà
; Ž¯à¥¤¥«¨âì ¯®§¨æ¨î ¤¥áïâ¨ç­®© â®çª¨ ¢ ç¨á«¥
mov DX,18
sub DX,[NumberSymbolsAD]
js .Error ;®è¨¡ª , ¥á«¨ ®âà¨æ â¥«ì­ ï
jz .Error ;¨«¨ ­ã«¥¢ ï ¯®§¨æ¨ï
.NextPair:
; ‡ £à㧨âì ®ç¥à¥¤­ãî ¯ àã à §à冷¢
mov AL, byte [ebx + Data_BCD]
mov AH,AL
; ‚뤥«¨âì, ¯¥à¥¢¥á⨠¢ ASCII ¨
; á®åà ­¨âì áâ àèãî â¥âà ¤ã
shr AL,4
add AL,'0'
stosb
dec DX
jnz .N0
mov AL,'.'
stosb
.N0: ; ‚뤥«¨âì, ¯¥à¥¢¥á⨠¢ ASCII ¨
; á®åà ­¨âì ¬« ¤èãî â¥âà ¤ã
mov AL,AH
and AL,0Fh
add AL,'0'
stosb
dec DX
jnz .N1
mov AL,'.'
stosb
.N1:
dec BX
loop .NextPair
mov AL,0
stosb
; “¡à âì ­¥§­ ç é¨¥ ­ã«¨ á«¥¢ 
lea EDI, [Data_String]
lea ESI, [Data_String]
; <EFBFBD>யãáâ¨âì §­ ª ç¨á« , ¥á«¨ ®­ ¥áâì
cmp byte [ESI],'-'
jne .N2
inc ESI
inc EDI
.N2: ; ‡ £à㧨âì ¢ áç¥â稪 横«  ª®«¨ç¥á⢮ à §à冷¢
; ç¨á«  ¯«îá 1 (¡ ©â ¤¥áïâ¨ç­®© â®çª¨)
mov ecx,18+1+1
; <EFBFBD>யãáâ¨âì ­¥§­ ç é¨¥ ­ã«¨
.N3:
cmp byte [ESI],'0'
jne .N4
cmp byte [ESI+1],'.'
je .N4
inc ESI
loop .N3
; Žè¨¡ª  - ­¥â §­ ç é¨å æ¨äà
jmp .Error
; ‘ª®¯¨à®¢ âì §­ ç éãî ç áâì ç¨á«  ¢ ­ ç «® áâப¨
.N4: rep movsb
jmp .End
; Žè¨¡ª 
.Error:
mov AL,'E'
stosb
mov AL,'R'
stosb
mov AL,'R'
stosb
xor AL,AL
stosb
jmp .End
; <EFBFBD>¥à¥¯®«­¥­¨¥ à §à來®© á¥âª¨
.Overflow:
mov AL,'#'
stosb
xor AL,AL
stosb
; Š®­¥æ ¯à®æ¥¤ãàë
.End:
popad
ret
;****************************************************
;* <EFBFBD><EFBFBD>…Ž<EFBFBD><EFBFBD>€‡Žœ <EFBFBD>ŽŠ“ —ˆ‘‹Ž <EFBFBD>€ž™…‰ ‡€<EFBFBD>ŸŽ‰ *
;* (ç¨á«® ¨¬¥¥â ®¡ëç­ë©, "¡ë⮢®©" ä®à¬ â) *
;* ‚室­ë¥ ¯ à ¬¥âàë: *
;* Data_String - ç¨á«® ¢ ª®¤¥ ASCII. *
;* ‚ë室­ë¥ ¯ à ¬¥âàë: *
;* Data_Double - ç¨á«® ¢ ¤¢®¨ç­®¬ ª®¤¥. *
;****************************************************
String_to_DoubleFloat:
pushad
cld
; Žç¨é ¥¬ Data_BCD
mov dword [Data_BCD],0
mov dword [Data_BCD+4],0
mov word [Data_BCD+8],0
; Žç¨é ¥¬ ¡ ©â §­ ª 
mov [Data_Sign],0
; ‡ ­®á¨¬ ¢ SI 㪠§ â¥«ì ­  áâபã
lea ESI, [Data_String]
; <EFBFBD>யã᪠¥¬ ¯à®¡¥«ë ¯¥à¥¤ ç¨á«®¬
mov ecx,64 ;§ é¨â  ®â § æ¨ª«¨¢ ­¨ï
.ShiftIgnore:
lodsb
cmp AL,' '
jne .ShiftIgnoreEnd
loop .ShiftIgnore
jmp .Error
.ShiftIgnoreEnd:
; <EFBFBD>஢¥à塞 §­ ª ç¨á« 
cmp AL,'-'
jne .Positive
mov [Data_Sign],80h
lodsb
.Positive:
mov [Data_Flag],0 ;¯à¨§­ ª ­ «¨ç¨ï â®çª¨
mov DX,0 ;¯®§¨æ¨ï â®çª¨
mov ecx,18 ;¬ ªá. ç¨á«® à §à冷¢
.ASCIItoBCDConversion:
cmp AL,'.' ;â®çª ?
jne .NotDot
cmp [Data_Flag],0 ;â®çª  ­¥ ¢áâà¥ç « áì?
jne .Error
mov [Data_Flag],1
lodsb
cmp AL,0 ;ª®­¥æ áâப¨?
jne .NotDot
jmp .ASCIItoBCDConversionEnd
.NotDot:
; “¢¥«¨ç¨âì ­  1 §­ ç¥­¨¥ ¯®§¨æ¨¨ â®çª¨,
; ¥á«¨ ®­  ¥é¥ ­¥ ¢áâà¥ç « áì
cmp [Data_Flag],0
jnz .Figures
inc DX
.Figures:
; ‘¨¬¢®«ë ç¨á«  ¤®«¦­ë ¡ëâì æ¨äà ¬¨
cmp AL,'0'
jb .Error
cmp AL,'9'
ja .Error
; <EFBFBD>¨è¥¬ ®ç¥à¥¤­ãî æ¨äàã ¢ ¬« ¤èãî â¥âà ¤ã BCD
and AL,0Fh
or byte [Data_BCD],AL
; <EFBFBD>஢¥àª  ­  ª®­¥æ áâப¨
cmp byte [ESI],0
je .ASCIItoBCDConversionEnd
; ‘¤¢¨£ ¥¬ BCD ­  4 à §à鸞 ¢«¥¢®
; (ᤢ¨£ ¥¬ áâ à訥 2 ¡ ©â )
mov AX,word [Data_BCD+6]
shld word [Data_BCD+8],AX,4
; (ᤢ¨£ ¥¬ á।­¨¥ 4 ¡ ©â )
mov EAX, dword [Data_BCD]
shld dword [Data_BCD+4],EAX,4
; (ᤢ¨£ ¥¬ ¬« ¤è¨¥ 4 ¡ ©â )
shl dword [Data_BCD],4
; ‡ £à㦠¥¬ á«¥¤ãî騩 ᨬ¢®« ¢ AL
lodsb
loop .ASCIItoBCDConversion
; …᫨ 19-© ᨬ¢®« ­¥ 0 ¨ ­¥ â®çª ,
; â® ®è¨¡ª  ¯¥à¥¯®«­¥­¨ï
cmp AL,'.'
jne .NotDot2
inc ecx
lodsb
.NotDot2:
cmp AL,0
jne .Error ;¯¥à¥¯®«­¥­¨¥ à §à來®© á¥âª¨
; <EFBFBD><EFBFBD>…Ž<EFBFBD><EFBFBD>€‡Žœ —ˆ‘‹Ž ˆ‡ ŠŽ„€ BCD …™…<EFBFBD><EFBFBD>Ž… —ˆ‘‹Ž
.ASCIItoBCDConversionEnd:
; ‚¯¨á âì §­ ª ¢ áâ à訩 ¡ ©â
mov AL,[Data_Sign]
mov byte [Data_BCD+9],AL
; ‘¡à®á¨âì ॣ¨áâàë ᮯà®æ¥áá®à 
fninit
; ‡ £à㧨âì ¢ ᮯà®æ¥áá®à ç¨á«® ¢ BCD-ä®à¬ â¥
fbld [Data_BCD]
; ‚ëç¨á«¨âì ­®¬¥à ¤¥«¨â¥«ï
mov EBX,18+1
sub BX,CX
sub BX,DX
cmp EBX,0
je .NoDiv
dec EBX
shl EBX,3 ;㬭®¦ ¥¬ ­  8
lea eax,[MConst]
add EBX,eax
fdiv qword [EBX] ;à §¤¥«¨âì ­  ª®­áâ ­âã
.NoDiv:; ‚ë£à㧨âì ç¨á«® ¢ ¤¢®¨ç­®¬ ä®à¬ â¥
fstp [Data_Double]
jmp .End
.Error:; <EFBFBD>ਠ«î¡®© ®è¨¡ª¥ ®¡­ã«¨âì १ã«ìâ â
fldz ;§ ­¥á⨠­®«ì á á⥪ ᮯà®æ¥áá®à 
fstp [Data_Double]
.End:
popad
ret
align 4
proc str_cat, str1:dword, str2:dword
push eax ecx edi esi
mov esi,dword[str2]
stdcall str_len,esi
mov ecx,eax
inc ecx
mov edi,dword[str1]
stdcall str_len,edi
add edi,eax
cld
repne movsb
pop esi edi ecx eax
ret
endp
;output:
; eax = strlen
align 4
proc str_len, str1:dword
mov eax,[str1]
@@:
cmp byte[eax],0
je @f
inc eax
jmp @b
@@:
sub eax,[str1]
ret
endp

View File

@ -0,0 +1,207 @@
align 4
proc initSharedState uses eax ebx, context:dword
mov ebx,[context]
stdcall gl_zalloc, 4*MAX_DISPLAY_LISTS
mov [ebx+offs_cont_shared_state],eax ;...lists=gl_zalloc(...)
stdcall gl_zalloc, 4*TEXTURE_HASH_TABLE_SIZE
mov [ebx+offs_cont_shared_state+4],eax ;...texture_hash_table=gl_zalloc(...)
stdcall alloc_texture, [context],0
ret
endp
align 4
proc endSharedState uses eax ebx, context:dword
mov ebx,[context]
mov ebx,[ebx+offs_cont_shared_state]
; int i;
; for(i=0;i<MAX_DISPLAY_LISTS;i++) {
; /* TODO */
; }
stdcall gl_free, dword[ebx] ;lists
stdcall gl_free, dword[ebx+4] ;texture_hash_table
ret
endp
align 4
proc glInit uses eax ebx ecx edx, zbuffer1:dword
; int i;
stdcall gl_zalloc,sizeof.GLContext
mov dword[gl_ctx],eax
mov edx,eax
mov ecx,[zbuffer1]
mov dword[edx+offs_cont_zb],ecx
; allocate GLVertex array
mov dword[edx+offs_cont_vertex_max],POLYGON_MAX_VERTEX
stdcall gl_malloc, POLYGON_MAX_VERTEX*sizeof.GLVertex
mov dword[edx+offs_cont_vertex],eax
; viewport
mov dword[edx+offs_cont_viewport+offs_vpor_xmin],0
mov dword[edx+offs_cont_viewport+offs_vpor_ymin],0
mov eax,[ecx+offs_zbuf_xsize]
mov dword[edx+offs_cont_viewport+offs_vpor_xsize], eax
mov eax,[ecx+offs_zbuf_ysize]
mov dword[edx+offs_cont_viewport+offs_vpor_ysize], eax
mov dword[edx+offs_cont_viewport+offs_vpor_updated],1
; shared state
stdcall initSharedState,edx
; lists
mov dword[edx+offs_cont_exec_flag],1
mov dword[edx+offs_cont_compile_flag],0
mov dword[edx+offs_cont_print_flag],0
mov dword[edx+offs_cont_in_begin],0
; lights
mov ecx,MAX_LIGHTS
mov eax,edx
add eax,offs_cont_lights
.cycle_0:
gl_V4_New eax+offs_ligh_ambient, 0.0,0.0,0.0,1.0
gl_V4_New eax+offs_ligh_diffuse, 1.0,1.0,1.0,1.0
gl_V4_New eax+offs_ligh_specular, 1.0,1.0,1.0,1.0
gl_V4_New eax+offs_ligh_position, 0.0,0.0,1.0,0.0
gl_V3_New eax+offs_ligh_norm_position, 0.0,0.0,1.0
gl_V3_New eax+offs_ligh_spot_direction, 0.0,0.0,-1.0
gl_V3_New eax+offs_ligh_norm_spot_direction, 0.0,0.0,-1.0
mov dword[eax+offs_ligh_spot_exponent],0.0
mov dword[eax+offs_ligh_spot_cutoff],180.0
mov dword[eax+offs_ligh_attenuation],1.0
mov dword[eax+offs_ligh_attenuation+4],0.0
mov dword[eax+offs_ligh_attenuation+8],0.0
mov dword[eax+offs_ligh_enabled],0
add eax,sizeof.GLLight
dec ecx
cmp ecx,0
jg .cycle_0
mov dword[edx+offs_cont_first_light],0 ;NULL
gl_V4_New edx+offs_cont_ambient_light_model, 0.2,0.2,0.2,1.0
mov dword[edx+offs_cont_local_light_model],0
mov dword[edx+offs_cont_lighting_enabled],0
mov dword[edx+offs_cont_light_model_two_side],0
; default materials
mov ecx,2 ;for(i=0;i<2;i++)
mov eax,edx
add eax,offs_cont_materials
@@:
gl_V4_New eax+offs_mate_emission, 0.0,0.0,0.0,1.0
gl_V4_New eax+offs_mate_ambient, 0.2,0.2,0.2,1.0
gl_V4_New eax+offs_mate_diffuse, 0.8,0.8,0.8,1.0
gl_V4_New eax+offs_mate_specular, 0.0,0.0,0.0,1.0
mov dword[eax+offs_mate_shininess], 0.0
add eax,sizeof.GLMaterial
loop @b
mov dword[edx+offs_cont_current_color_material_mode],GL_FRONT_AND_BACK
mov dword[edx+offs_cont_current_color_material_type],GL_AMBIENT_AND_DIFFUSE
mov dword[edx+offs_cont_color_material_enabled],0
; textures
stdcall glInitTextures,edx
; default state
mov dword[edx+offs_cont_current_color],1.0
mov dword[edx+offs_cont_current_color+4],1.0
mov dword[edx+offs_cont_current_color+8],1.0
mov dword[edx+offs_cont_current_color+12],1.0
mov dword[edx+offs_cont_longcurrent_color],65535
mov dword[edx+offs_cont_longcurrent_color+4],65535
mov dword[edx+offs_cont_longcurrent_color+8],65535
mov dword[edx+offs_cont_current_normal],1.0
mov dword[edx+offs_cont_current_normal+4],0.0
mov dword[edx+offs_cont_current_normal+8],0.0
mov dword[edx+offs_cont_current_normal+12],0.0
mov dword[edx+offs_cont_current_edge_flag],1
mov dword[edx+offs_cont_current_tex_coord],0.0
mov dword[edx+offs_cont_current_tex_coord+4],0.0
mov dword[edx+offs_cont_current_tex_coord+8],0.0
mov dword[edx+offs_cont_current_tex_coord+12],1.0
mov dword[edx+offs_cont_polygon_mode_front],GL_FILL
mov dword[edx+offs_cont_polygon_mode_back],GL_FILL
mov dword[edx+offs_cont_current_front_face],0 ;0 = GL_CCW 1 = GL_CW
mov dword[edx+offs_cont_current_cull_face],GL_BACK
mov dword[edx+offs_cont_current_shade_model],GL_SMOOTH
mov dword[edx+offs_cont_cull_face_enabled],0
; clear
mov dword[edx+offs_cont_clear_color],0.0
mov dword[edx+offs_cont_clear_color+4],0.0
mov dword[edx+offs_cont_clear_color+8],0.0
mov dword[edx+offs_cont_clear_color+12],0.0
mov dword[edx+offs_cont_clear_depth],0
; selection
mov dword[edx+offs_cont_render_mode],GL_RENDER
mov dword[edx+offs_cont_select_buffer],0 ;NULL
mov dword[edx+offs_cont_name_stack_size],0
; matrix
mov dword[edx+offs_cont_matrix_mode],0
mov dword[edx+offs_cont_matrix_stack_depth_max],MAX_MODELVIEW_STACK_DEPTH
mov dword[edx+offs_cont_matrix_stack_depth_max+4],MAX_PROJECTION_STACK_DEPTH
mov dword[edx+offs_cont_matrix_stack_depth_max+8],MAX_TEXTURE_STACK_DEPTH
mov ecx,3 ;for(i=0;i<3;i++)
mov ebx,edx
@@:
mov edi,[ebx+offs_cont_matrix_stack_depth_max]
shl edi,6 ;вместо imul edi,sizeof(M4)
stdcall gl_zalloc,edi
mov [ebx+offs_cont_matrix_stack],eax
mov [ebx+offs_cont_matrix_stack_ptr],eax
add ebx,4
loop @b
stdcall glMatrixMode,GL_PROJECTION
call glLoadIdentity
stdcall glMatrixMode,GL_TEXTURE
call glLoadIdentity
stdcall glMatrixMode,GL_MODELVIEW
call glLoadIdentity
mov dword[edx+offs_cont_matrix_model_projection_updated],1
; opengl 1.1 arrays
mov dword[edx+offs_cont_client_states],0
; opengl 1.1 polygon offset
mov dword[edx+offs_cont_offset_states],0
; clear the resize callback function pointer
mov dword[edx+offs_cont_gl_resize_viewport],0 ;NULL
; specular buffer
mov dword[edx+offs_cont_specbuf_first],0 ;NULL
mov dword[edx+offs_cont_specbuf_used_counter],0
mov dword[edx+offs_cont_specbuf_num_buffers],0
; depth test
mov dword[edx+offs_cont_depth_test],0
ret
endp
align 4
proc glClose uses eax
call gl_get_context
stdcall endSharedState,eax
stdcall gl_free,eax
ret
endp

View File

@ -0,0 +1,146 @@
; simple gl like driver for TinyGL and KolibriOS - porting iadn
struct TinyGLContext
gl_context dd ?
xsize dd ? ;+4
ysize dd ? ;+8
d_x dd ? ;+12
d_y dd ? ;+16
x dd ? ;+20
y dd ? ;+24
ends
;KOSGLContext kosglCreateContext(KOSGLContext shareList, int flags)
;{
; TinyGLContext *ctx;
;
; if (shareList != NULL) {
; gl_fatal_error("No sharing available in TinyGL");
; }
;
; ctx=gl_malloc(sizeof(TinyGLContext));
; if (!ctx)
; return NULL;
; ctx->gl_context=NULL;
; return (KOSGLContext) ctx;
;}
;void kosglDestroyContext( KOSGLContext ctx1 )
;{
; TinyGLContext *ctx = (TinyGLContext *) ctx1;
; if (ctx->gl_context != NULL) {
; glClose();
; }
; gl_free(ctx);
;}
; resize the glx viewport : we try to use the xsize and ysize
; given. We return the effective size which is guaranted to be smaller
align 4
proc gl_resize_viewport uses ebx ecx edx edi esi, context:dword, xsize_ptr:dword, ysize_ptr:dword
xor eax,eax
mov ecx,[xsize_ptr] ; ecx = &xsize
mov edi,[ecx] ; edi = xsize
mov esi,[ysize_ptr] ; esi = &ysize
mov esi,[esi] ; esi = ysize
; we ensure that xsize and ysize are multiples of 2 for the zbuffer.
; TODO: find a better solution
and edi, not 3
and esi, not 3
cmp edi,0
jne @f
cmp esi,0
jne @f
mov eax,-1
jmp .end_f
@@:
mov [ecx],edi
dec dword[ecx]
mov ecx,[ysize_ptr]
mov [ecx],esi
dec dword[ecx]
mov ebx,[context]
mov edx,[ebx+offs_cont_opaque] ; edx = (TinyGLContext *)context.opaque
mov [edx+4],edi
mov [edx+12],edi ;d_x = xsize
mov [edx+8],esi
mov [edx+16],esi ;d_y = ysize
; resize the Z buffer
stdcall ZB_resize, dword[ebx+offs_cont_zb],0,edi,esi
.end_f:
ret
endp
; we assume here that drawable is a window
align 4
proc kosglMakeCurrent uses ebx ecx, win_x0:dword, win_y0:dword, win_x:dword, win_y:dword, ctx1:dword
mov ebx,[ctx1]
cmp dword[ebx],0 ;if (ctx.gl_context == NULL)
jne .end_f
; create the TinyGL context
mov ecx,[win_x0]
mov [ebx+20],ecx ;ctx.x = win_x0
mov ecx,[win_y0]
mov [ebx+24],ecx ;ctx.y = win_y0
mov ecx,[win_x]
mov [ebx+12],ecx ;ctx.d_x = win_x
mov ecx,[win_y]
mov [ebx+16],ecx ;ctx.d_y = win_y
; currently, we only support 16 bit rendering
xor eax,eax
stdcall ZB_open, dword[win_x], dword[win_y], dword ZB_MODE_RGB24, eax,eax,eax,eax ;NULL,NULL,NULL
cmp eax,0
jne @f
stdcall dbg_print,f_kosgl_1,err_0
xor eax,eax
jmp .err_f
@@:
; initialisation of the TinyGL interpreter
stdcall glInit, eax
call gl_get_context
mov [ebx],eax ;ctx.gl_context = eax
mov [eax+offs_cont_opaque],ebx ;ctx.gl_context.opaque = ctx
mov dword[eax+offs_cont_gl_resize_viewport],gl_resize_viewport
; set the viewport : we force a call to gl_resize_viewport
dec dword[eax+offs_cont_viewport+offs_vpor_xsize]
dec dword[eax+offs_cont_viewport+offs_vpor_ysize]
stdcall glViewport, 0, 0, [win_x], [win_y]
.end_f:
xor eax,eax
inc eax
.err_f:
ret
endp
align 4
proc kosglSwapBuffers uses eax ebx ecx edx esi
; retrieve the current TinyGLContext
call gl_get_context
mov ebx,[eax+offs_cont_zb]
mov ebx,[ebx+offs_zbuf_pbuf]
mov esi,[eax+offs_cont_opaque] ;esi = &context.opaque
mov eax,7
mov ecx,[esi+12] ;d_x
shl ecx,16
mov cx,[esi+16] ;d_y
mov edx,[esi+20] ;x
shl edx,16
mov dx,[esi+24] ;y
int 0x40
ret
endp

View File

@ -0,0 +1,350 @@
;include 'msghandling.inc'
align 4
proc glopMaterial, context:dword, p:dword
; int mode=p[1].i;
; int type=p[2].i;
; float *v=&p[3].f;
; int i;
; GLMaterial *m;
; if (mode == GL_FRONT_AND_BACK) {
; p[1].i=GL_FRONT;
; glopMaterial(c,p);
; mode=GL_BACK;
; }
; if (mode == GL_FRONT) m=&c->materials[0];
; else m=&c->materials[1];
; switch(type) {
; case GL_EMISSION:
; for(i=0;i<4;i++)
; m->emission.v[i]=v[i];
; break;
; case GL_AMBIENT:
; for(i=0;i<4;i++)
; m->ambient.v[i]=v[i];
; break;
; case GL_DIFFUSE:
; for(i=0;i<4;i++)
; m->diffuse.v[i]=v[i];
; break;
; case GL_SPECULAR:
; for(i=0;i<4;i++)
; m->specular.v[i]=v[i];
; break;
; case GL_SHININESS:
; m->shininess=v[0];
; m->shininess_i = (v[0]/128.0f)*SPECULAR_BUFFER_RESOLUTION;
; break;
; case GL_AMBIENT_AND_DIFFUSE:
; for(i=0;i<4;i++)
; m->diffuse.v[i]=v[i];
; for(i=0;i<4;i++)
; m->ambient.v[i]=v[i];
; break;
; default:
; assert(0);
; }
ret
endp
align 4
proc glopColorMaterial uses eax ebx ecx, context:dword, p:dword
mov eax,[context]
mov ebx,[p]
mov ecx,[ebx+4] ;ecx = p[1]
mov dword[eax+offs_cont_current_color_material_mode],ecx
mov ecx,[ebx+8] ;ecx = p[2]
mov dword[eax+offs_cont_current_color_material_type],ecx
ret
endp
;void glopLight(GLContext *c,GLParam *p)
;{
; int light=p[1].i;
; int type=p[2].i;
; V4 v;
; GLLight *l;
; int i;
;
; assert(light >= GL_LIGHT0 && light < GL_LIGHT0+MAX_LIGHTS );
;
; l=&c->lights[light-GL_LIGHT0];
;
; for(i=0;i<4;i++) v.v[i]=p[3+i].f;
;
; switch(type) {
; case GL_AMBIENT:
; l->ambient=v;
; break;
; case GL_DIFFUSE:
; l->diffuse=v;
; break;
; case GL_SPECULAR:
; l->specular=v;
; break;
; case GL_POSITION:
; {
; V4 pos;
; gl_M4_MulV4(&pos,c->matrix_stack_ptr[0],&v);
;
; l->position=pos;
;
; if (l->position.v[3] == 0) {
; l->norm_position.X=pos.X;
; l->norm_position.Y=pos.Y;
; l->norm_position.Z=pos.Z;
;
; gl_V3_Norm(&l->norm_position);
; }
; }
; break;
; case GL_SPOT_DIRECTION:
; for(i=0;i<3;i++) {
; l->spot_direction.v[i]=v.v[i];
; l->norm_spot_direction.v[i]=v.v[i];
; }
; gl_V3_Norm(&l->norm_spot_direction);
; break;
; case GL_SPOT_EXPONENT:
; l->spot_exponent=v.v[0];
; break;
; case GL_SPOT_CUTOFF:
; {
; float a=v.v[0];
; assert(a == 180 || (a>=0 && a<=90));
; l->spot_cutoff=a;
; if (a != 180) l->cos_spot_cutoff=cos(a * M_PI / 180.0);
; }
; break;
; case GL_CONSTANT_ATTENUATION:
; l->attenuation[0]=v.v[0];
; break;
; case GL_LINEAR_ATTENUATION:
; l->attenuation[1]=v.v[0];
; break;
; case GL_QUADRATIC_ATTENUATION:
; l->attenuation[2]=v.v[0];
; break;
; default:
; assert(0);
; }
;}
align 4
proc glopLightModel uses ebx ecx esi edi, context:dword, p:dword
mov edi,[context]
mov ebx,[p]
mov esi,[ebx+8]
cmp dword[ebx+4],GL_LIGHT_MODEL_AMBIENT
jne @f
mov ecx,4
mov edi,dword[edi+offs_cont_ambient_light_model]
rep movsd ;for(i=0;i<4;i++) context.ambient_light_model.v[i]=v[i]
jmp .end_f
@@:
cmp dword[ebx+4],GL_LIGHT_MODEL_LOCAL_VIEWER
jne @f
fld dword[esi] ;st0 = p[2].v[0]
fistp dword[edi+offs_cont_local_light_model]
jmp .end_f
@@:
cmp dword[ebx+4],GL_LIGHT_MODEL_TWO_SIDE
jne @f
fld dword[esi] ;st0 = p[2].v[0]
fistp dword[edi+offs_cont_light_model_two_side]
jmp .end_f
@@: ;default:
; tgl_warning("glopLightModel: illegal pname: 0x%x\n", dword[ebx+4]);
; //assert(0);
.end_f:
ret
endp
;static inline float clampf(float a,float min,float max)
;{
; if (a<min) return min;
; else if (a>max) return max;
; else return a;
;}
align 4
proc gl_enable_disable_light uses eax ebx ecx, context:dword, light:dword, v:dword
mov eax,[context]
mov ebx,[light]
imul ebx,sizeof.GLLight
add ebx,[eax+offs_cont_lights]
xor ecx,ecx
cmp dword[ebx+offs_ligh_enabled],0
jne @f
not ecx
@@:
and ecx,[v]
cmp ecx,0
je @f
;if (v && !l.enabled)
mov dword[ebx+offs_ligh_enabled],1
mov ecx,[eax+offs_cont_first_light]
mov [ebx+offs_ligh_next],ecx
mov [eax+offs_cont_first_light],ebx ;context.first_light = l
mov dword[ebx+offs_ligh_prev],0 ;l.prev = NULL
jmp .end_f
@@:
xor ecx,ecx
cmp dword[v],0
jne @f
not ecx
@@:
and ecx,[ebx+offs_ligh_enabled]
cmp ecx,0
je .end_f
;else if (!v && l.enabled)
mov dword[ebx+offs_ligh_enabled],0 ;l.enabled = 0
mov ecx,[ebx+offs_ligh_next]
cmp dword[ebx+offs_ligh_prev],0 ;if (l.prev == NULL)
jne .els_0
mov [eax+offs_cont_first_light],ecx ;context.first_light = l.next
jmp @f
.els_0:
mov eax,[ebx+offs_ligh_prev]
mov [eax+offs_ligh_next],ecx ;l.prev.next = l.next
@@:
cmp dword[ebx+offs_ligh_next],0
je .end_f
mov ecx,[ebx+offs_ligh_prev]
mov eax,[ebx+offs_ligh_next]
mov [eax+offs_ligh_prev],ecx ;l.next.prev = l.prev
.end_f:
ret
endp
; non optimized lightening model
align 4
proc gl_shade_vertex, context:dword, v:dword
; float R,G,B,A;
; GLMaterial *m;
; GLLight *l;
; V3 n,s,d;
; float dist,tmp,att,dot,dot_spot,dot_spec;
; int twoside = c->light_model_two_side;
; m=&c->materials[0];
; n.X=v->normal.X;
; n.Y=v->normal.Y;
; n.Z=v->normal.Z;
; R=m->emission.v[0]+m->ambient.v[0]*c->ambient_light_model.v[0];
; G=m->emission.v[1]+m->ambient.v[1]*c->ambient_light_model.v[1];
; B=m->emission.v[2]+m->ambient.v[2]*c->ambient_light_model.v[2];
; A=clampf(m->diffuse.v[3],0,1);
; for(l=c->first_light;l!=NULL;l=l->next) {
; float lR,lB,lG;
; /* ambient */
; lR=l->ambient.v[0] * m->ambient.v[0];
; lG=l->ambient.v[1] * m->ambient.v[1];
; lB=l->ambient.v[2] * m->ambient.v[2];
; if (l->position.v[3] == 0) {
; /* light at infinity */
; d.X=l->position.v[0];
; d.Y=l->position.v[1];
; d.Z=l->position.v[2];
; att=1;
; } else {
; /* distance attenuation */
; d.X=l->position.v[0]-v->ec.v[0];
; d.Y=l->position.v[1]-v->ec.v[1];
; d.Z=l->position.v[2]-v->ec.v[2];
; dist=sqrt(d.X*d.X+d.Y*d.Y+d.Z*d.Z);
; if (dist>1E-3) {
; tmp=1/dist;
; d.X*=tmp;
; d.Y*=tmp;
; d.Z*=tmp;
; }
; att=1.0f/(l->attenuation[0]+dist*(l->attenuation[1]+
; dist*l->attenuation[2]));
; }
; dot=d.X*n.X+d.Y*n.Y+d.Z*n.Z;
; if (twoside && dot < 0) dot = -dot;
; if (dot>0) {
; /* diffuse light */
; lR+=dot * l->diffuse.v[0] * m->diffuse.v[0];
; lG+=dot * l->diffuse.v[1] * m->diffuse.v[1];
; lB+=dot * l->diffuse.v[2] * m->diffuse.v[2];
;
; /* spot light */
; if (l->spot_cutoff != 180) {
; dot_spot=-(d.X*l->norm_spot_direction.v[0]+
; d.Y*l->norm_spot_direction.v[1]+
; d.Z*l->norm_spot_direction.v[2]);
; if (twoside && dot_spot < 0) dot_spot = -dot_spot;
; if (dot_spot < l->cos_spot_cutoff) {
; /* no contribution */
; continue;
; } else {
; /* TODO: optimize */
; if (l->spot_exponent > 0) {
; att=att*pow(dot_spot,l->spot_exponent);
; }
; }
; }
; /* specular light */
; if (c->local_light_model) {
; V3 vcoord;
; vcoord.X=v->ec.X;
; vcoord.Y=v->ec.Y;
; vcoord.Z=v->ec.Z;
; gl_V3_Norm(&vcoord);
; s.X=d.X-vcoord.X;
; s.Y=d.Y-vcoord.X;
; s.Z=d.Z-vcoord.X;
; } else {
; s.X=d.X;
; s.Y=d.Y;
; s.Z=d.Z+1.0;
; }
; dot_spec=n.X*s.X+n.Y*s.Y+n.Z*s.Z;
; if (twoside && dot_spec < 0) dot_spec = -dot_spec;
; if (dot_spec>0) {
; GLSpecBuf *specbuf;
; int idx;
; tmp=sqrt(s.X*s.X+s.Y*s.Y+s.Z*s.Z);
; if (tmp > 1E-3) {
; dot_spec=dot_spec / tmp;
; }
; /* TODO: optimize */
; /* testing specular buffer code */
; /* dot_spec= pow(dot_spec,m->shininess);*/
; specbuf = specbuf_get_buffer(c, m->shininess_i, m->shininess);
; idx = (int)(dot_spec*SPECULAR_BUFFER_SIZE);
; if (idx > SPECULAR_BUFFER_SIZE) idx = SPECULAR_BUFFER_SIZE;
; dot_spec = specbuf->buf[idx];
; lR+=dot_spec * l->specular.v[0] * m->specular.v[0];
; lG+=dot_spec * l->specular.v[1] * m->specular.v[1];
; lB+=dot_spec * l->specular.v[2] * m->specular.v[2];
; }
; }
; R+=att * lR;
; G+=att * lG;
; B+=att * lB;
; }
; v->color.v[0]=clampf(R,0,1);
; v->color.v[1]=clampf(G,0,1);
; v->color.v[2]=clampf(B,0,1);
; v->color.v[3]=A;
ret
endp

View File

@ -0,0 +1,329 @@
;строки с именами функций
op_table_str:
macro ADD_OP a,b,c
{
db 'gl',`a,' ',c,0
}
include 'opinfo.inc'
;указатели на функции ;static void (*op_table_func[])(GLContext *,GLParam *)=
op_table_func:
macro ADD_OP a,b,c
{
dd glop#a
}
include 'opinfo.inc'
;число параметров в функциях
op_table_size:
macro ADD_OP a,b,c
{
dd b+1
}
include 'opinfo.inc'
;output:
; eax = context.shared_state.lists[list]
align 4
proc find_list uses ebx, context:dword, list:dword
mov eax,[context]
mov eax,[eax+offs_cont_shared_state]
mov ebx,[list]
shl ebx,2
add eax,ebx
mov eax,[eax]
ret
endp
;static void delete_list(GLContext *c,int list)
;{
; GLParamBuffer *pb,*pb1;
; GLList *l;
; l=find_list(c,list);
; assert(l != NULL);
; /* free param buffer */
; pb=l->first_op_buffer;
; while (pb!=NULL) {
; pb1=pb->next;
; gl_free(pb);
; pb=pb1;
; }
; gl_free(l);
; c->shared_state.lists[list]=NULL;
;}
;static GLList *alloc_list(GLContext *c,int list)
;{
; GLList *l;
; GLParamBuffer *ob;
; l=gl_zalloc(sizeof(GLList));
; ob=gl_zalloc(sizeof(GLParamBuffer));
; ob->next=NULL;
; l->first_op_buffer=ob;
; ob->ops[0].op=OP_EndList;
; c->shared_state.lists[list]=l;
; return l;
;}
;void gl_print_op(FILE *f,GLParam *p)
;{
; int op;
; char *s;
; op=p[0].op;
; p++;
; s=op_table_str[op];
; while (*s != 0) {
; if (*s == '%') {
; s++;
; switch (*s++) {
; case 'f':
; fprintf(f,"%g",p[0].f);
; break;
; default:
; fprintf(f,"%d",p[0].i);
; break;
; }
; p++;
; } else {
; fputc(*s,f);
; s++;
; }
; }
; fprintf(f,"\n");
;}
align 4
proc gl_compile_op uses eax ebx, context:dword, p:dword
mov eax,[context]
; int op,op_size;
; GLParamBuffer *ob,*ob1;
; int index,i;
; op=p[0].op;
; op_size=op_table_size[op];
; index=c->current_op_buffer_index;
; ob=c->current_op_buffer;
; /* we should be able to add a NextBuffer opcode */
; if ((index + op_size) > (OP_BUFFER_MAX_SIZE-2)) {
; ob1=gl_zalloc(sizeof(GLParamBuffer));
; ob1->next=NULL;
; ob->next=ob1;
; ob->ops[index].op=OP_NextBuffer;
; ob->ops[index+1].p=(void *)ob1;
; c->current_op_buffer=ob1;
; ob=ob1;
; index=0;
; }
; for(i=0;i<op_size;i++) {
; ob->ops[index]=p[i];
; index++;
; }
; c->current_op_buffer_index=index;
ret
endp
align 4
proc gl_add_op uses eax ebx ecx, p:dword ;GLParam*
if DEBUG
push edi esi
mov ebx,[p]
mov ebx,[ebx]
lea eax,[op_table_str]
@@:
cmp ebx,0
je @f
cmp byte[eax],0
jne .no_dec
dec ebx
.no_dec:
inc eax
jmp @b
@@:
stdcall dbg_print,eax,txt_nl
mov esi,eax
mov word[NumberSymbolsAD],3
mov ebx,[p]
lea edi,[buf_param]
mov byte[edi],0
mov ecx,80
.cycle_0:
cmp byte[esi],'%'
jne .no_param
cmp ebx,[p]
je @f
stdcall str_n_cat,edi,txt_zp_sp,2
stdcall str_len,edi
add edi,eax
@@:
add ebx,4
inc esi
cmp byte[esi],'f'
jne @f
fld dword[ebx]
fstp qword[Data_Double]
call DoubleFloat_to_String
stdcall str_cat, edi,Data_String
@@:
cmp byte[esi],'d'
jne @f
stdcall str_len,edi
add edi,eax
sub ecx,eax
mov eax,dword[ebx]
stdcall convert_int_to_str,ecx
@@:
.no_param:
inc esi
cmp byte[esi],0
jne .cycle_0
stdcall str_cat, edi,txt_nl
stdcall dbg_print,txt_sp,buf_param
pop esi edi
end if
call gl_get_context
mov ebx,[p]
cmp dword[eax+offs_cont_exec_flag],0
je @f
push ebx
push eax
mov ecx,dword[ebx] ;ecx = OP_...
shl ecx,2
lea ebx,[op_table_func]
add ecx,ebx
call dword[ecx] ;op_table_func[op](c,p)
@@:
cmp dword[eax+offs_cont_compile_flag],0
je @f
stdcall gl_compile_op,eax,[p]
@@:
cmp dword[eax+offs_cont_print_flag],0
je @f
;gl_print_op(stderr,p);
@@:
ret
endp
; this opcode is never called directly
align 4
proc glopEndList, context:dword, p:dword
; assert(0);
ret
endp
; this opcode is never called directly
align 4
proc glopNextBuffer, context:dword, p:dword
; assert(0);
ret
endp
;void glopCallList(GLContext *c,GLParam *p)
;{
; GLList *l;
; int list,op;
; list=p[1].ui;
; l=find_list(c,list);
; if (l == NULL) gl_fatal_error("list %d not defined",list);
; p=l->first_op_buffer->ops;
; while (1) {
; op=p[0].op;
; if (op == OP_EndList) break;
; if (op == OP_NextBuffer) {
; p=(GLParam *)p[1].p;
; } else {
; op_table_func[op](c,p);
; p+=op_table_size[op];
; }
; }
;}
;void glNewList(unsigned int list,int mode)
;{
; GLList *l;
; GLContext *c=gl_get_context();
;
; assert(mode == GL_COMPILE || mode == GL_COMPILE_AND_EXECUTE);
; assert(c->compile_flag == 0);
;
; l=find_list(c,list);
; if (l!=NULL) delete_list(c,list);
; l=alloc_list(c,list);
;
; c->current_op_buffer=l->first_op_buffer;
; c->current_op_buffer_index=0;
;
; c->compile_flag=1;
; c->exec_flag=(mode == GL_COMPILE_AND_EXECUTE);
;}
;void glEndList(void)
;{
; GLContext *c=gl_get_context();
; GLParam p[1];
; assert(c->compile_flag == 1);
; /* end of list */
; p[0].op=OP_EndList;
; gl_compile_op(c,p);
; c->compile_flag=0;
; c->exec_flag=1;
;}
;output:
; eax = (find_list(gl_get_context,list) != NULL)
align 4
proc glIsList, list:dword
call gl_get_context
stdcall find_list, eax,[list]
cmp eax,0 ;NULL
je @f
mov eax,1
@@:
ret
endp
;unsigned int glGenLists(int range)
;{
; GLContext *c=gl_get_context();
; int count,i,list;
; GLList **lists;
; lists=c->shared_state.lists;
; count=0;
; for(i=0;i<MAX_DISPLAY_LISTS;i++) {
; if (lists[i]==NULL) {
; count++;
; if (count == range) {
; list=i-range+1;
; for(i=0;i<range;i++) {
; alloc_list(c,list+i);
; }
; return list;
; }
; } else {
; count=0;
; }
; }
; return 0;
;}

View File

@ -0,0 +1,521 @@
if DEBUG
align 4
proc gl_print_matrix uses eax ebx ecx edi, m:dword, rows:dword
mov ecx,[rows]
cmp ecx,1
jl .end_f
mov ebx,[m]
mov word[NumberSymbolsAD],3
finit
@@:
lea edi,[buf_param]
mov byte[edi],0
fld dword[ebx]
fstp qword[Data_Double]
call DoubleFloat_to_String
stdcall str_cat, edi,Data_String
stdcall str_n_cat,edi,txt_zp_sp,2
stdcall str_len,edi
add edi,eax
fld dword[ebx+4]
fstp qword[Data_Double]
call DoubleFloat_to_String
stdcall str_cat, edi,Data_String
stdcall str_n_cat,edi,txt_zp_sp,2
stdcall str_len,edi
add edi,eax
fld dword[ebx+8]
fstp qword[Data_Double]
call DoubleFloat_to_String
stdcall str_cat, edi,Data_String
stdcall str_n_cat,edi,txt_zp_sp,2
stdcall str_len,edi
add edi,eax
fld dword[ebx+12]
fstp qword[Data_Double]
call DoubleFloat_to_String
stdcall str_cat, edi,Data_String
stdcall str_n_cat,edi,txt_nl,2
stdcall dbg_print,txt_sp,buf_param
add ebx,16
dec ecx
cmp ecx,0
jg @b
.end_f:
ret
endp
end if
macro gl_matrix_update context, reg
{
local .end_0
xor reg,reg
cmp dword[context+offs_cont_matrix_mode],1
jg .end_0
inc reg
.end_0:
mov dword[context+offs_cont_matrix_model_projection_updated],reg
}
align 4
proc glopMatrixMode uses eax ebx, context:dword, p:dword
mov eax,[context]
mov ebx,[p]
cmp dword[ebx+4],GL_MODELVIEW ;cmp p[1],...
jne @f
mov dword[eax+offs_cont_matrix_mode],0
jmp .end_f
@@:
cmp dword[ebx+4],GL_PROJECTION
jne @f
mov dword[eax+offs_cont_matrix_mode],1
jmp .end_f
@@:
cmp dword[ebx+4],GL_TEXTURE
jne .def
mov dword[eax+offs_cont_matrix_mode],2
jmp .end_f
.def:
;assert(0);
.end_f:
ret
endp
align 4
proc glopLoadMatrix uses eax edi esi, context:dword, p:dword
mov eax,[context]
mov edi,[eax+offs_cont_matrix_mode]
shl edi,2
add edi,eax
mov edi,dword[edi+offs_cont_matrix_stack_ptr]
mov esi,[p]
add esi,4
stdcall gl_M4_Transpose,edi,esi ;транспонируем входную матрицу в матрицу context.matrix_stack_ptr[context.matrix_mode]
gl_matrix_update eax,edi
ret
endp
align 4
proc glopLoadIdentity uses eax ebx, context:dword, p:dword
mov eax,[context]
mov ebx,[eax+offs_cont_matrix_mode]
shl ebx,2
add ebx,eax
stdcall gl_M4_Id,[ebx+offs_cont_matrix_stack_ptr]
if DEBUG ;glopLoadIdentity
stdcall gl_print_matrix,[ebx+offs_cont_matrix_stack_ptr],4
end if
gl_matrix_update eax,ebx
ret
endp
align 4
proc glopMultMatrix uses eax edi esi, context:dword, p:dword
locals
m M4
endl
mov esi,[p]
add esi,4
mov edi,ebp
sub edi,sizeof.M4
stdcall gl_M4_Transpose,edi,esi ;транспонируем входную матрицу в локальную матрицу m
mov eax,[context]
mov esi,[eax+offs_cont_matrix_mode]
shl esi,2
add esi,eax
stdcall gl_M4_MulLeft,dword[esi+offs_cont_matrix_stack_ptr],edi
gl_matrix_update eax,edi
ret
endp
align 4
proc glopPushMatrix uses eax ebx, context:dword, p:dword
mov eax,[context]
mov ebx,[eax+offs_cont_matrix_mode]
; assert( (c->matrix_stack_ptr[ebx] - c->matrix_stack[ebx] + 1 )
; < c->matrix_stack_depth_max[ebx] );
shl ebx,2
add ebx,eax
add ebx,offs_cont_matrix_stack_ptr
add dword[ebx],sizeof.M4
mov ebx,[ebx] ;ebx = ++context.matrix_stack_ptr[context.matrix_mode]
sub ebx,sizeof.M4
push ebx
add ebx,sizeof.M4
stdcall gl_M4_Move, ebx
gl_matrix_update eax,ebx
ret
endp
align 4
proc glopPopMatrix uses eax ebx, context:dword, p:dword
mov eax,[context]
mov ebx,[eax+offs_cont_matrix_mode]
; assert( c->matrix_stack_ptr[n] > c->matrix_stack[n] );
shl ebx,2
add ebx,eax
sub dword[ebx+offs_cont_matrix_stack_ptr],sizeof.M4
gl_matrix_update eax,ebx
ret
endp
align 4
proc glopRotate uses eax ebx ecx, context:dword, p:dword
locals
u0 dd ?
u1 dd ?
u2 dd ?
angle dd ?
cost dd ?
sint dd ?
m M4
endl
mov eax,[context]
mov ebx,[p]
mov ecx,ebp
sub ecx,sizeof.M4 ;ecx=&m
finit
fldpi
fmul dword[ebx+4]
fdiv dword[an180f]
fst dword[angle] ;angle = p[1].f * M_PI / 180.0
;st0 = angle
fldz
fild dword[ebx+8]
fstp dword[u0]
fild dword[ebx+12]
fstp dword[u1]
fild dword[ebx+16]
fst dword[u2]
; simple case detection
xor ebx,ebx
fcomp st1 ;u2 ... 0
fstsw ax
sahf
je @f
inc ebx
@@:
fcom dword[u1] ;0 ... u1
fstsw ax
sahf
je @f
or ebx,2
@@:
fcom dword[u0] ;0 ... u0
fstsw ax
sahf
je @f
or ebx,4
@@:
;st0 = 0, st1 = angle
;ebx = ((u0 != 0)<<2) | ((u1 != 0)<<1) | (u2 != 0)
cmp ebx,0
je .end_f ;если нет поворотов выход из функции
cmp ebx,4
jne @f
fcomp dword[u0] ;0 ... u0
fstsw ax
sahf
jae .u0ch
fchs
fstp dword[angle] ;if (u0 < 0) angle *= -1
.u0ch:
stdcall gl_M4_Rotate, ecx,[angle],0
jmp .end_sw
@@:
cmp ebx,2
jne @f
fcomp dword[u1] ;0 ... u1
fstsw ax
sahf
jae .u1ch
fchs
fstp dword[angle] ;if (u1 < 0) angle *= -1
.u1ch:
stdcall gl_M4_Rotate, ecx,[angle],1
jmp .end_sw
@@:
cmp ebx,1
jne @f
fcomp dword[u2] ;0 ... u2
fstsw ax
sahf
jae .u2ch
fchs
fstp dword[angle] ;if (u2 < 0) angle *= -1
.u2ch:
stdcall gl_M4_Rotate, ecx,[angle],2
jmp .end_sw
@@: ;default:
if DEBUG ;glopRotete
stdcall dbg_print,txt_sp,m_1
end if
; normalize vector
fld dword[u0]
fmul st0,st0
fld dword[u1]
fmul st0,st0
fld dword[u2]
fmul st0,st0
fadd st0,st1
fadd st0,st2
; fst dword[len] ;len = u0*u0+u1*u1+u2*u2
fcom st1
fstsw ax
sahf
je .end_f ;if (len == 0.0f) return
fsqrt
fld1
fdiv st0,st1
; fst dword[len] ;len = 1.0f / sqrt(len)
fld dword[u0]
fmul st0,st1
fstp dword[u0] ;u0 *= len
fld dword[u1]
fmul st0,st1
fstp dword[u1] ;u1 *= len
fld dword[u2]
fmul st0,st1
fstp dword[u2] ;u2 *= len
;st0 = len, st1=..., st2=..., st3 = 0, st4 = angle
; store cos and sin values
finit
fld dword[angle]
fcos
fst dword[cost] ;cost=cos(angle)
fld dword[angle]
fsin
fst dword[sint] ;sint=sin(angle)
; fill in the values
mov ebx,0.0
mov [ecx+3*16 ],ebx ;m[3][0]
mov [ecx+3*16 +4],ebx ;m[3][1]
mov [ecx+3*16 +8],ebx ;m[3][2]
mov [ecx+ 12],ebx ;m[0][3]
mov [ecx+ 16+12],ebx ;m[1][3]
mov [ecx+2*16+12],ebx ;m[2][3]
mov ebx,1.0
mov [ecx+3*16+12],ebx ;m[3][3]
; do the math
; m.m[0][0]=u[0]*u[0]+cost*(1-u[0]*u[0]);
; m.m[1][0]=u[0]*u[1]*(1-cost)-u[2]*sint;
; m.m[2][0]=u[2]*u[0]*(1-cost)+u[1]*sint;
; m.m[0][1]=u[0]*u[1]*(1-cost)+u[2]*sint;
; m.m[1][1]=u[1]*u[1]+cost*(1-u[1]*u[1]);
; m.m[2][1]=u[1]*u[2]*(1-cost)-u[0]*sint;
; m.m[0][2]=u[2]*u[0]*(1-cost)-u[1]*sint;
; m.m[1][2]=u[1]*u[2]*(1-cost)+u[0]*sint;
; m.m[2][2]=u[2]*u[2]+cost*(1-u[2]*u[2]);
.end_sw:
mov eax,[context]
mov ebx,[eax+offs_cont_matrix_mode]
shl ebx,2
add ebx,eax
stdcall gl_M4_MulLeft,dword[ebx+offs_cont_matrix_stack_ptr],ecx
if DEBUG ;glopRotete
stdcall gl_print_matrix,ecx,4
end if
gl_matrix_update eax,ebx
.end_f:
ret
endp
align 4
proc glopScale uses eax ebx ecx, context:dword, p:dword
mov ecx,[p]
mov eax,[context]
mov ebx,[eax+offs_cont_matrix_mode]
shl ebx,2
add ebx,eax
mov ebx,[ebx+offs_cont_matrix_stack_ptr] ;ebx = &m[0]
fld dword[ecx+ 4] ;x
fld dword[ecx+ 8] ;y
fld dword[ecx+12] ;z
mov ecx,4
@@:
fld dword[ebx] ;m[0]
fmul st0,st3 ;m[0] * x
fstp dword[ebx] ;m[0] *= x
fld dword[ebx+4] ;m[1]
fmul st0,st2 ;m[1] * y
fstp dword[ebx+4];m[1] *= y
fld dword[ebx+8] ;m[2]
fmul st0,st1 ;m[2] * z
fstp dword[ebx+8];m[2] *= z
add ebx,16
loop @b
if DEBUG ;glopScale
mov ebx,[eax+offs_cont_matrix_mode]
shl ebx,2
add ebx,eax
stdcall gl_print_matrix,[ebx+offs_cont_matrix_stack_ptr],4
end if
gl_matrix_update eax,ebx
ret
endp
align 4
proc glopTranslate uses eax ebx ecx, context:dword, p:dword
mov ecx,[p]
mov eax,[context]
mov ebx,[eax+offs_cont_matrix_mode]
shl ebx,2
add ebx,eax
mov ebx,[ebx+offs_cont_matrix_stack_ptr] ;ebx = &m[0]
fld dword[ecx+ 4] ;x
fld dword[ecx+ 8] ;y
fld dword[ecx+12] ;z
mov ecx,4
@@:
fld dword[ebx] ;m[0]
fmul st0,st3 ;m[0] * x
fld dword[ebx+4] ;m[1]
fmul st0,st3 ;m[1] * y
fld dword[ebx+8] ;m[2]
fmul st0,st3 ;m[2] * z
fadd st0,st1
fadd st0,st2
fadd dword[ebx+12] ;m[3]
fstp dword[ebx+12] ;m[3] = m[0] * x + m[1] * y + m[2] * z + m[3]
ffree st0
fincstp
ffree st0
fincstp
add ebx,16
loop @b
if DEBUG ;glopTranslate
mov ebx,[eax+offs_cont_matrix_mode]
shl ebx,2
add ebx,eax
stdcall gl_print_matrix,[ebx+offs_cont_matrix_stack_ptr],4
end if
gl_matrix_update eax,ebx
ret
endp
align 4
proc glopFrustum uses eax ebx ecx, context:dword, p:dword
locals
x dd ?
y dd ?
A dd ?
B dd ?
C dd ?
D dd ?
m M4
endl
mov eax,[context]
mov ebx,[p]
fld dword[ebx+8]
fsub dword[ebx+4] ;st0 = (right-left)
fld dword[ebx+20] ;st0 = near
fadd st0,st0
fdiv st0,st1
fstp dword[x] ;x = (2.0*near) / (right-left)
fld dword[ebx+16]
fsub dword[ebx+12] ;st0 = (top-bottom)
fld dword[ebx+20] ;st0 = near
fadd st0,st0
fdiv st0,st1
fstp dword[y] ;y = (2.0*near) / (top-bottom)
fld dword[ebx+8]
fadd dword[ebx+4] ;st0 = (right+left)
fdiv st0,st2 ;st2 = (right-left)
fstp dword[A] ;A = (right+left) / (right-left)
fld dword[ebx+16]
fadd dword[ebx+12] ;st0 = (top+bottom)
fdiv st0,st1 ;st1 = (top-bottom)
fstp dword[B] ;B = (top+bottom) / (top-bottom)
fld dword[ebx+24]
fsub dword[ebx+20] ;st0 = (farp-near)
fldz
fsub dword[ebx+24]
fsub dword[ebx+20] ;st0 = -(farp+near)
fdiv st0,st1
fstp dword[C] ;C = -(farp+near) / (farp-near)
fld dword[ebx+24]
fmul dword[ebx+20] ;st0 = farp*near
fadd st0,st0
fchs ;st0 = -(2.0*farp*near)
fdiv st0,st1
fstp dword[D] ;D = -(2.0*farp*near) / (farp-near)
mov ecx,ebp
sub ecx,sizeof.M4
mov ebx,[x]
mov dword[ecx],ebx
mov dword[ecx+4],0.0
mov ebx,[A]
mov dword[ecx+8],ebx
mov dword[ecx+12],0.0
mov dword[ecx+16],0.0
mov ebx,[y]
mov dword[ecx+20],ebx
mov ebx,[B]
mov dword[ecx+24],ebx
mov dword[ecx+28],0.0
mov dword[ecx+32],0.0
mov dword[ecx+36],0.0
mov ebx,[C]
mov dword[ecx+40],ebx
mov ebx,[D]
mov dword[ecx+44],ebx
mov dword[ecx+48],0.0
mov dword[ecx+52],0.0
mov dword[ecx+56],-1.0
mov dword[ecx+60],0.0
mov ebx,[eax+offs_cont_matrix_mode]
shl ebx,2
add ebx,eax
stdcall gl_M4_MulLeft,dword[ebx+offs_cont_matrix_stack_ptr],ecx
if DEBUG ;glopFrustum
stdcall gl_print_matrix,ecx,4
stdcall gl_print_matrix,dword[ebx+offs_cont_matrix_stack_ptr],4
end if
gl_matrix_update eax,ebx
ret
endp

View File

@ -0,0 +1,273 @@
align 4
proc glopViewport uses eax ebx ecx edx, context:dword, p:dword
locals
xsize dd ? ;int
ysize dd ? ;int
xmin dd ? ;int
ymin dd ? ;int
xsize_req dd ? ;int
ysize_req dd ? ;int
endl
mov edx,[context]
mov ebx,[p]
mov ecx,[ebx+4]
mov [xmin],ecx
mov ecx,[ebx+8]
mov [ymin],ecx
mov ecx,[ebx+12]
mov [xsize],ecx
mov ecx,[ebx+16]
mov [ysize],ecx
; we may need to resize the zbuffer
cmp dword[edx+offs_cont_viewport+offs_vpor_ysize],ecx
jne @f
mov ecx,[xmin]
cmp dword[edx+offs_cont_viewport+offs_vpor_xmin],ecx
jne @f
mov ecx,[ymin]
cmp dword[edx+offs_cont_viewport+offs_vpor_ymin],ecx
jne @f
mov ecx,[xsize]
cmp dword[edx+offs_cont_viewport+offs_vpor_xsize],ecx
jne @f
jmp .end_f
@@:
mov ecx,[xmin]
add ecx,[xsize]
mov [xsize_req],ecx ;xsize_req = xmin + xsize
mov ecx,[ymin]
add ecx,[ysize]
mov [ysize_req],ecx ;ysize_req = ymin + ysize
cmp dword[edx+offs_cont_gl_resize_viewport],0
je @f
mov eax,ebp
sub eax,4
push eax
sub eax,4
push eax
stdcall dword[edx+offs_cont_gl_resize_viewport], edx ;gl_resize_viewport(context,&xsize_req,&ysize_req)
cmp eax,0
je @f
stdcall dbg_print,f_vp,err_4
@@:
mov ecx,[xsize_req]
sub ecx,[xmin]
mov [xsize],ecx
mov ecx,[ysize_req]
sub ecx,[ymin]
mov [ysize],ecx
cmp ecx,0
jg @f
cmp dword[xsize],0
jg @f
stdcall dbg_print,f_vp,err_5
@@:
if DEBUG ;glopViewport
push edi
mov ecx,80
mov eax,[xmin]
lea edi,[buf_param]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_zp_sp,2
stdcall str_len,edi
add edi,eax
sub ecx,eax
mov eax,[ymin]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_zp_sp,2
stdcall str_len,edi
add edi,eax
sub ecx,eax
mov eax,[xsize]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_zp_sp,2
stdcall str_len,edi
add edi,eax
sub ecx,eax
mov eax,[ysize]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_nl,2
stdcall dbg_print,f_vp,buf_param
pop edi
end if
mov ecx,[xmin]
mov dword[edx+offs_cont_viewport+offs_vpor_xmin],ecx
mov ecx,[ymin]
mov dword[edx+offs_cont_viewport+offs_vpor_ymin],ecx
mov ecx,[xsize]
mov dword[edx+offs_cont_viewport+offs_vpor_xsize],ecx
mov ecx,[ysize]
mov dword[edx+offs_cont_viewport+offs_vpor_ysize],ecx
mov dword[edx+offs_cont_viewport+offs_vpor_updated],1
.end_f:
ret
endp
align 4
proc glopEnableDisable uses eax ebx ecx, context:dword, p:dword
mov eax,[context]
mov ebx,[p]
mov ecx,[ebx+8]
mov ebx,[ebx+4]
cmp ebx,GL_CULL_FACE
jne @f
mov [eax+offs_cont_cull_face_enabled],ecx
jmp .end_f
@@:
cmp ebx,GL_LIGHTING
jne @f
mov [eax+offs_cont_lighting_enabled],ecx
jmp .end_f
@@:
cmp ebx,GL_COLOR_MATERIAL
jne @f
mov [eax+offs_cont_color_material_enabled],ecx
jmp .end_f
@@:
cmp ebx,GL_TEXTURE_2D
jne @f
mov [eax+offs_cont_texture_2d_enabled],ecx
jmp .end_f
@@:
cmp ebx,GL_NORMALIZE
jne @f
mov [eax+offs_cont_normalize_enabled],ecx
jmp .end_f
@@:
cmp ebx,GL_DEPTH_TEST
jne @f
mov [eax+offs_cont_depth_test],ecx
jmp .end_f
@@:
cmp ebx,GL_POLYGON_OFFSET_FILL
jne .polygon_offset_fill
cmp ecx,0
je @f
or dword[eax+offs_cont_offset_states],TGL_OFFSET_FILL
jmp .end_f
@@:
and dword[eax+offs_cont_offset_states],not TGL_OFFSET_FILL
jmp .end_f
.polygon_offset_fill:
cmp ebx,GL_POLYGON_OFFSET_POINT
jne .polygon_offset_point
cmp ecx,0
je @f
or dword[eax+offs_cont_offset_states],TGL_OFFSET_POINT
jmp .end_f
@@:
and dword[eax+offs_cont_offset_states],not TGL_OFFSET_POINT
jmp .end_f
.polygon_offset_point:
cmp ebx,GL_POLYGON_OFFSET_LINE
jne .polygon_offset_line
cmp ecx,0
je @f
or dword[eax+offs_cont_offset_states],TGL_OFFSET_LINE
jmp .end_f
@@:
and dword[eax+offs_cont_offset_states],not TGL_OFFSET_LINE
jmp .end_f
.polygon_offset_line: ;default:
cmp ebx,GL_LIGHT0
jl .els_0
cmp ebx,GL_LIGHT0+MAX_LIGHTS
jge .els_0 ;if (GL_LIGHT0 <= ebx < GL_LIGHT0+MAX_LIGHTS)
stdcall gl_enable_disable_light, eax,ebx-GL_LIGHT0,ecx
jmp .end_f
.els_0:
;//fprintf(stderr,"glEnableDisable: 0x%X not supported.\n",code);
.end_f:
ret
endp
align 4
proc glopShadeModel uses eax ebx, context:dword,p:dword
mov eax,[context]
mov ebx,[p]
mov ebx,[ebx+4]
mov [eax+offs_cont_current_shade_model],ebx
ret
endp
align 4
proc glopCullFace uses eax ebx, context:dword,p:dword
mov eax,[context]
mov ebx,[p]
mov ebx,[ebx+4]
mov [eax+offs_cont_current_cull_face],ebx
ret
endp
align 4
proc glopFrontFace uses eax ebx, context:dword,p:dword
mov eax,[context]
mov ebx,[p]
mov ebx,[ebx+4]
mov [eax+offs_cont_current_front_face],ebx
ret
endp
align 4
proc glopPolygonMode uses eax ebx, context:dword,p:dword
mov eax,[context]
mov ebx,[p]
cmp dword[ebx+4],GL_BACK
jne @f
mov ebx,[ebx+8]
mov [eax+offs_cont_polygon_mode_back],ebx
jmp .end_f
@@:
cmp dword[ebx+4],GL_FRONT
jne @f
mov ebx,[ebx+8]
mov [eax+offs_cont_polygon_mode_front],ebx
jmp .end_f
@@:
cmp dword[ebx+4],GL_FRONT_AND_BACK
jne @f
mov ebx,[ebx+8]
mov [eax+offs_cont_polygon_mode_front],ebx
mov [eax+offs_cont_polygon_mode_back],ebx
jmp .end_f
@@:
; assert(0);
.end_f:
ret
endp
align 4
proc glopHint, context:dword,p:dword
if 0
; int target=p[1].i;
; int mode=p[2].i;
; do nothing
end if
ret
endp
align 4
proc glopPolygonOffset uses eax ebx ecx, context:dword,p:dword
mov eax,[context]
mov ebx,[p]
mov ecx,[ebx+4]
mov [eax+offs_cont_offset_factor],ecx
mov ecx,[ebx+8]
mov [eax+offs_cont_offset_units],ecx
ret
endp

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,70 @@
ADD_OP Color,7,'%f %f %f %f %d %d %d'
ADD_OP TexCoord,4,'%f %f %f %f'
ADD_OP EdgeFlag,1,'%d'
ADD_OP Normal,3,'%f %f %f'
ADD_OP Begin,1,'%C'
ADD_OP Vertex,4,'%f %f %f %f'
ADD_OP End,0,''
ADD_OP EnableDisable,2,'%C %d'
ADD_OP MatrixMode,1,'%C'
ADD_OP LoadMatrix,16,''
ADD_OP LoadIdentity,0,''
ADD_OP MultMatrix,16,''
ADD_OP PushMatrix,0,''
ADD_OP PopMatrix,0,''
ADD_OP Rotate,4,'%f %f %f %f'
ADD_OP Translate,3,'%f %f %f'
ADD_OP Scale,3,'%f %f %f'
ADD_OP Viewport,4,'%d %d %d %d'
ADD_OP Frustum,6,'%f %f %f %f %f %f'
ADD_OP Material,6,'%C %C %f %f %f %f'
ADD_OP ColorMaterial,2,'%C %C'
ADD_OP Light,6,'%C %C %f %f %f %f'
ADD_OP LightModel,5,'%C %f %f %f %f'
ADD_OP Clear,1,'%d'
ADD_OP ClearColor,4,'%f %f %f %f'
ADD_OP ClearDepth,1,'%f'
ADD_OP InitNames,0,''
ADD_OP PushName,1,'%d'
ADD_OP PopName,0,''
ADD_OP LoadName,1,'%d'
ADD_OP TexImage2D,9,'%d %d %d %d %d %d %d %d %d'
ADD_OP BindTexture,2,'%C %d'
ADD_OP TexEnv,7,'%C %C %C %f %f %f %f'
ADD_OP TexParameter,7,'%C %C %C %f %f %f %f'
ADD_OP PixelStore,2,'%C %C'
ADD_OP ShadeModel,1,'%C'
ADD_OP CullFace,1,'%C'
ADD_OP FrontFace,1,'%C'
ADD_OP PolygonMode,2,'%C %C'
ADD_OP CallList,1,'%d'
ADD_OP Hint,2,'%C %C'
; special opcodes
ADD_OP EndList,0,''
ADD_OP NextBuffer,1,'%p'
; opengl 1.1 arrays
ADD_OP ArrayElement, 1, '%d'
ADD_OP EnableClientState, 1, '%C'
ADD_OP DisableClientState, 1, '%C'
ADD_OP VertexPointer, 4, '%d %C %d %p'
ADD_OP ColorPointer, 4, '%d %C %d %p'
ADD_OP NormalPointer, 3, '%C %d %p'
ADD_OP TexCoordPointer, 4, '%d %C %d %p'
; opengl 1.1 polygon offset
ADD_OP PolygonOffset, 2, '%f %f'
purge ADD_OP

View File

@ -0,0 +1,168 @@
align 4
proc glRenderMode uses ebx ecx, mode:dword
call gl_get_context
xor ebx,ebx
cmp dword[eax+offs_cont_render_mode],GL_RENDER
je .e_sw_1
cmp dword[eax+offs_cont_render_mode],GL_SELECT
jne .def_1
cmp dword[eax+offs_cont_select_overflow],0
je @f
sub ebx,[eax+offs_cont_select_hits]
jmp .else_e
@@:
mov ebx,[eax+offs_cont_select_hits]
.else_e:
mov dword[eax+offs_cont_select_overflow],0
mov ecx,[eax+offs_cont_select_buffer]
mov dword[eax+offs_cont_select_ptr],ecx
mov dword[eax+offs_cont_name_stack_size],0
jmp .e_sw_1
.def_1:
; assert(0);
.e_sw_1:
cmp dword[mode],GL_RENDER
jne @f
mov dword[eax+offs_cont_render_mode],GL_RENDER
jmp .e_sw_2
@@:
cmp dword[mode],GL_SELECT
jne .def_2
mov dword[eax+offs_cont_render_mode],GL_SELECT
; assert( c->select_buffer != NULL);
mov ecx,[eax+offs_cont_select_buffer]
mov dword[eax+offs_cont_select_ptr],ecx
mov dword[eax+offs_cont_select_hits],0
mov dword[eax+offs_cont_select_overflow],0
mov dword[eax+offs_cont_select_hit],0 ;NULL
jmp .e_sw_2
.def_2:
; assert(0);
.e_sw_2:
mov eax,ebx
ret
endp
align 4
proc glSelectBuffer uses eax ebx, size:dword, buf:dword
call gl_get_context
; assert(c->render_mode != GL_SELECT);
mov ebx,[buf]
mov dword[eax+offs_cont_select_buffer],ebx
mov ebx,[size]
mov dword[eax+offs_cont_select_size],ebx
ret
endp
align 4
proc glopInitNames uses eax, context:dword, p:dword
mov eax,[context]
cmp dword[eax+offs_cont_render_mode],GL_SELECT
jne @f
mov dword[eax+offs_cont_name_stack_size],0
mov dword[eax+offs_cont_select_hit],0 ;=NULL
@@:
ret
endp
align 4
proc glopPushName uses eax ebx, context:dword, p:dword
mov eax,[context]
cmp dword[eax+offs_cont_render_mode],GL_SELECT
jne @f
; assert(c->name_stack_size<MAX_NAME_STACK_DEPTH);
mov dword[eax+offs_cont_select_hit],0 ;=NULL
inc dword[eax+offs_cont_name_stack_size]
mov ebx,dword[eax+offs_cont_name_stack_size]
shl ebx,2
add ebx,eax
mov eax,[p]
mov eax,[eax+4]
mov dword[ebx+offs_cont_name_stack],eax ;context.name_stack[context.name_stack_size++]=p[1]
@@:
ret
endp
align 4
proc glopPopName uses eax, context:dword, p:dword
mov eax,[context]
cmp dword[eax+offs_cont_render_mode],GL_SELECT
jne @f
; assert(c->name_stack_size>0);
dec dword[eax+offs_cont_name_stack_size]
mov dword[eax+offs_cont_select_hit],0 ;=NULL
@@:
ret
endp
align 4
proc glopLoadName uses eax ebx, context:dword, p:dword
mov eax,[context]
cmp dword[eax+offs_cont_render_mode],GL_SELECT
jne @f
; assert(c->name_stack_size>0);
mov dword[eax+offs_cont_select_hit],0 ;=NULL
mov ebx,dword[eax+offs_cont_name_stack_size]
dec ebx
shl ebx,2
add ebx,eax
mov eax,[p]
mov eax,[eax+4]
mov dword[ebx+offs_cont_name_stack],eax ;context.name_stack[context.name_stack_size-1]=p[1]
@@:
ret
endp
align 4
proc gl_add_select uses eax ebx ecx edx, context:dword, zmin:dword, zmax:dword
; unsigned int *ptr;
; int i;
mov eax,[context]
cmp dword[eax+offs_cont_select_overflow],0
jne .end_f ;if (!context.select_overflow)
cmp dword[eax+offs_cont_select_hit],0 ;if (context.select_hit==NULL)
jne .els_0
mov ecx,[eax+offs_cont_name_stack_size]
mov ebx,[eax+offs_cont_select_ptr]
sub ebx,[eax+offs_cont_select_buffer]
sub ebx,3
sub ebx,ecx
cmp ebx,[eax+offs_cont_select_size]
jle .els_1
mov dword[eax+offs_cont_select_overflow],1
jmp .end_f
.els_1:
mov ebx,[eax+offs_cont_select_ptr]
mov [eax+offs_cont_select_hit],ebx
mov edx,[eax+offs_cont_name_stack_size]
mov [ebx],edx
add ebx,4
mov edx,[zmin]
mov [ebx],edx
add ebx,4
mov edx,[zmax]
mov [ebx],edx
add ebx,4
; for(i=0;i<ecx;i++) *ptr++=c->name_stack[i];
mov [eax+offs_cont_select_ptr],ebx
inc dword[eax+offs_cont_select_hits]
jmp .end_f
.els_0:
mov ebx,[zmin]
cmp dword[eax+offs_cont_select_hit+4],ebx
jle @f
mov dword[eax+offs_cont_select_hit+4],ebx
@@:
mov ebx,[zmax]
cmp dword[eax+offs_cont_select_hit+8],ebx
jge .end_f
mov dword[eax+offs_cont_select_hit+8],ebx
.end_f:
ret
endp

View File

@ -0,0 +1,260 @@
;
; Texture Manager
;
align 4
proc find_texture uses ebx ecx, context:dword, h:dword
mov ebx,[context]
mov ebx,[ebx+offs_cont_shared_state+4] ;ebx = &texture_hash_table
mov eax,[h]
and eax,0xff
shl eax,2
add eax,[ebx] ;eax = &context.shared_state.texture_hash_table[h % TEXTURE_HASH_TABLE_SIZE]
; [eax] - указатель на текстуру, получаемую через хеш таблицу
mov ecx,[h] ; ecx - указатель на искомую текстуру
@@:
cmp dword[eax],0
je .no_found
mov ebx,[eax]
cmp dword[ebx+offs_text_handle],ecx
je .found
mov eax,[ebx+offs_text_next]
jmp @b
.no_found:
xor eax,eax ;ret NULL
.found:
ret
endp
;static void free_texture(GLContext *c,int h)
;{
; GLTexture *t,**ht;
; GLImage *im;
; int i;
;
; t=find_texture(c,h);
; if (t->prev==NULL) {
; ht=&c->shared_state.texture_hash_table
; [t->handle % TEXTURE_HASH_TABLE_SIZE];
; *ht=t->next;
; } else {
; t->prev->next=t->next;
; }
; if (t->next!=NULL) t->next->prev=t->prev;
;
; for(i=0;i<MAX_TEXTURE_LEVELS;i++) {
; im=&t->images[i];
; if (im->pixmap != NULL) gl_free(im->pixmap);
; }
;
; gl_free(t);
;}
;output:
; eax - указатель на память
align 4
proc alloc_texture uses ebx ecx, context:dword, h:dword
stdcall gl_zalloc,sizeof.GLTexture
mov ebx,[context]
mov ebx,[ebx+offs_cont_shared_state+4] ;ebx = &texture_hash_table
mov ecx,[h]
and ecx,0xff
shl ecx,2
add ecx,[ebx] ;ecx = &context.shared_state.texture_hash_table[h % TEXTURE_HASH_TABLE_SIZE]
mov ebx,[ecx]
mov [eax+offs_text_next],ebx
mov dword[eax+offs_text_prev],0 ;NULL
cmp dword[eax+offs_text_next],0 ;NULL
je @f
mov [eax+offs_text_prev],eax
@@:
mov [ecx],eax
mov ebx,[h]
mov [eax+offs_text_handle],ebx
ret
endp
align 4
proc glInitTextures uses eax edx, context:dword
; textures
mov edx,[context]
mov dword[edx+offs_cont_texture_2d_enabled],0
stdcall find_texture,edx,0
mov dword[edx+offs_cont_current_texture],eax
ret
endp
;void glGenTextures(int n, unsigned int *textures)
;{
; GLContext *c=gl_get_context();
; int max,i;
; GLTexture *t;
;
; max=0;
; for(i=0;i<TEXTURE_HASH_TABLE_SIZE;i++) {
; t=c->shared_state.texture_hash_table[i];
; while (t!=NULL) {
; if (t->handle>max) max=t->handle;
; t=t->next;
; }
;
; }
; for(i=0;i<n;i++) {
; textures[i]=max+i+1;
; }
;}
;
;
;void glDeleteTextures(int n, const unsigned int *textures)
;{
; GLContext *c=gl_get_context();
; int i;
; GLTexture *t;
;
; for(i=0;i<n;i++) {
; t=find_texture(c,textures[i]);
; if (t!=NULL && t!=0) {
; if (t==c->current_texture) {
; glBindTexture(GL_TEXTURE_2D,0);
; }
; free_texture(c,textures[i]);
; }
; }
;}
align 4
proc glopBindTexture uses eax ebx edx, context:dword, p:dword
mov ebx,[p]
mov edx,[context]
; assert(p[1].i == GL_TEXTURE_2D && texture >= 0);
;[ebx+8] = p[2]
stdcall find_texture, edx,dword[ebx+8]
cmp eax,0 ;NULL
jne @f
stdcall alloc_texture, edx,dword[ebx+8]
@@:
mov [edx+offs_cont_current_texture],eax
ret
endp
align 4
proc glopTexImage2D, context:dword, p:dword
;{
; int target=p[1].i;
; int level=p[2].i;
; int components=p[3].i;
; int width=p[4].i;
; int height=p[5].i;
; int border=p[6].i;
; int format=p[7].i;
; int type=p[8].i;
; void *pixels=p[9].p;
; GLImage *im;
; unsigned char *pixels1;
; int do_free;
;
; if (!(target == GL_TEXTURE_2D && level == 0 && components == 3 &&
; border == 0 && format == GL_RGB &&
; type == GL_UNSIGNED_BYTE)) {
; gl_fatal_error("glTexImage2D: combinaison of parameters not handled");
; }
;
; do_free=0;
; if (width != 256 || height != 256) {
; pixels1 = gl_malloc(256 * 256 * 3);
; /* no interpolation is done here to respect the original image aliasing ! */
; gl_resizeImageNoInterpolate(pixels1,256,256,pixels,width,height);
; do_free=1;
; width=256;
; height=256;
; } else {
; pixels1=pixels;
; }
;
; im=&c->current_texture->images[level];
; im->xsize=width;
; im->ysize=height;
; if (im->pixmap!=NULL) gl_free(im->pixmap);
;#if TGL_FEATURE_RENDER_BITS == 24
; im->pixmap=gl_malloc(width*height*3);
; if(im->pixmap) {
; memcpy(im->pixmap,pixels1,width*height*3);
; }
;#elif TGL_FEATURE_RENDER_BITS == 32
; im->pixmap=gl_malloc(width*height*4);
; if(im->pixmap) {
; gl_convertRGB_to_8A8R8G8B(im->pixmap,pixels1,width,height);
; }
;#elif TGL_FEATURE_RENDER_BITS == 16
; im->pixmap=gl_malloc(width*height*2);
; if(im->pixmap) {
; gl_convertRGB_to_5R6G5B(im->pixmap,pixels1,width,height);
; }
;#else
;#error TODO
;#endif
; if (do_free) gl_free(pixels1);
ret
endp
; TODO: not all tests are done
align 4
proc glopTexEnv, context:dword, p:dword
; int target=p[1].i;
; int pname=p[2].i;
; int param=p[3].i;
;
; if (target != GL_TEXTURE_ENV) {
; error:
; gl_fatal_error("glTexParameter: unsupported option");
; }
;
; if (pname != GL_TEXTURE_ENV_MODE) goto error;
;
; if (param != GL_DECAL) goto error;
ret
endp
; TODO: not all tests are done
align 4
proc glopTexParameter, context:dword, p:dword
; int target=p[1].i;
; int pname=p[2].i;
; int param=p[3].i;
;
; if (target != GL_TEXTURE_2D) {
; error:
; gl_fatal_error("glTexParameter: unsupported option");
; }
;
; switch(pname) {
; case GL_TEXTURE_WRAP_S:
; case GL_TEXTURE_WRAP_T:
; if (param != GL_REPEAT) goto error;
; break;
; }
ret
endp
align 4
proc glopPixelStore, context:dword, p:dword
; int pname=p[1].i;
; int param=p[2].i;
;
; if (pname != GL_UNPACK_ALIGNMENT ||
; param != 1) {
; gl_fatal_error("glPixelStore: unsupported option");
; }
ret
endp

View File

@ -0,0 +1,204 @@
format MS COFF
public EXPORTS
section '.flat' code readable align 16
include '../../../../../programs/proc32.inc'
include '../../../../../programs/macros.inc'
DEBUG equ 0
include 'zgl.inc'
include 'zmath.asm'
include 'clip.asm'
include 'vertex.asm'
include 'api.asm'
include 'list.asm'
include 'init.asm'
include 'matrix.asm'
include 'texture.asm'
include 'misc.asm'
include 'clear.asm'
include 'light.asm'
include 'select.asm'
;include 'get.asm'
;include 'error.asm'
include 'zbuffer.asm'
include 'zline.asm'
;include 'zdither.asm'
include 'ztriangle.asm'
;include 'image_util.asm'
;include 'msghandling.asm'
include 'arrays.asm'
include 'kosgl.asm'
if DEBUG
include 'info_fun_float.inc'
end if
; ***
glVertex2d: ;(double ,double)
glVertex2fv: ;(float *)
glVertex2dv: ;(double *)
glVertex3d: ;(double ,double ,double)
glVertex3dv: ;(double *)
glVertex4d: ;(double ,double ,double, double )
glVertex4fv: ;(float *)
glVertex4dv: ;(double *)
glColor3d: ;(double ,double ,double)
glColor3dv: ;(double *)
glColor4d: ;(double ,double ,double, double )
glColor4dv: ;(double *)
glNormal3d: ;(double ,double ,double)
glNormal3dv: ;(double *)
glTexCoord1f: ;(float)
glTexCoord1d: ;(double)
glTexCoord1fv: ;(float *)
glTexCoord1dv: ;(double *)
glTexCoord2d: ;(double ,double)
glTexCoord2dv: ;(double *)
glTexCoord3f: ;(float ,float ,float)
glTexCoord3d: ;(double ,double ,double)
glTexCoord3fv: ;(float *)
glTexCoord3dv: ;(double *)
glTexCoord4d: ;(double ,double ,double, double )
glTexCoord4fv: ;(float *)
glTexCoord4dv: ;(double *)
glGenLists: ;(int range)
glNewList: ;(unsigned int list,int mode)
glEndList: ;(void)
glGenTextures: ;(int n, unsigned int *textures)
glDeleteTextures: ;(int n, const unsigned int *textures)
glGetIntegerv: ;(int pname,int *params)
glGetFloatv: ;(int pname, float *v)
; ***
glopLight:
glopClear:
glopCallList:
if DEBUG
align 4
txt_nl db 13,10,0
txt_sp db ' ',0
txt_zp_sp db ', ',0
m_1 db '(1)',13,10,0
m_2 db '(2)',13,10,0
m_3 db '(3)',13,10,0
m_4 db '(4)',13,10,0
m_5 db '(5)',13,10,0
buf_param rb 80
align 4
proc str_n_cat uses eax ecx edi esi, str1:dword, str2:dword, n:dword
mov esi,dword[str2]
mov ecx,dword[n]
mov edi,dword[str1]
stdcall str_len,edi
add edi,eax
cld
repne movsb
mov byte[edi],0
ret
endp
;input:
; eax - число
; edi - буфер для строки
; len - длинна буфера
;output:
align 4
proc convert_int_to_str, len:dword
pushad
mov esi,[len]
add esi,edi
dec esi
call .str
popad
ret
endp
align 4
.str:
mov ecx,0x0a ;задается система счисления изменяются регистры ebx,eax,ecx,edx входные параметры eax - число
;преревод числа в ASCII строку взодные данные ecx=система счисленя edi адрес куда записывать, будем строку, причем конец переменной
cmp eax,ecx ;сравнить если в eax меньше чем в ecx то перейти на @@-1 т.е. на pop eax
jb @f
xor edx,edx ;очистить edx
div ecx ;разделить - остаток в edx
push edx ;положить в стек
;dec edi ;смещение необходимое для записи с конца строки
call .str ;перейти на саму себя т.е. вызвать саму себя и так до того момента пока в eax не станет меньше чем в ecx
pop eax
@@: ;cmp al,10 ;проверить не меньше ли значение в al чем 10 (для системы счисленя 10 данная команда - лишная))
cmp edi,esi
jge @f
or al,0x30 ;данная команда короче чем две выше
stosb ;записать элемент из регистра al в ячеку памяти es:edi
mov byte[edi],0 ;в конец строки ставим 0, что-бы не вылазил мусор
@@:
ret ;пока в стеке храниться кол-во вызовов то столько раз мы и будем вызываться
end if
align 4
f_kosgl_1 db 'kosglMakeCurrent',0
err_0 db 'Error while initializing Z buffer',13,10,0
f_zb_opn db ' ZB_open',0
err_1 db 'gl_malloc(sizeof.ZBuffer)==0',13,10,0
err_2 db 'gl_malloc(xsize*ysize*4)==0',13,10,0
err_3 db 'bit mode not correct',13,10,0
f_vp db ' glViewport',0
err_4 db 'error while resizing display',13,10,0
err_5 db 'size too small',13,10,0
f_clipcode db ' gl_clipcode',0
f_ttv db ' gl_transform_to_viewport',0
f_vt db ' gl_vertex_transform',0
f_ev db ' gl_eval_viewport',0
f_zbz db ' ZB_line_z',0
f_zb db ' ZB_line',0
f_cl1 db ' ClipLine1',0
f_m4m db 'gl_M4_Mul',0
f_m4ml db 'gl_M4_MulLeft',0
align 4
proc dbg_print, fun:dword, mes:dword
pushad
mov eax,63
mov ebx,1
mov esi,[fun]
@@:
mov cl,byte[esi]
int 0x40
inc esi
cmp byte[esi],0
jne @b
mov cl,':'
int 0x40
mov cl,' '
int 0x40
mov esi,[mes]
@@:
mov cl,byte[esi]
int 0x40
inc esi
cmp byte[esi],0
jne @b
popad
ret
endp
align 16
EXPORTS:
macro E_LIB n
{
dd sz_#n, n
}
include 'export.inc'
dd 0,0
macro E_LIB n
{
sz_#n db `n,0
}
include 'export.inc'

View File

@ -0,0 +1,651 @@
align 4
proc glopNormal uses ecx esi edi, context:dword, p:dword
mov esi,[p]
add esi,4
mov edi,[context]
add edi,offs_cont_current_normal
mov ecx,4
rep movsd
mov dword[esi],0.0 ;context.current_normal.W = 0.0
ret
endp
align 4
proc glopTexCoord uses ecx esi edi, context:dword, p:dword
mov esi,[p]
add esi,4
mov edi,[context]
add edi,offs_cont_current_tex_coord
mov ecx,4
rep movsd
ret
endp
align 4
proc glopEdgeFlag uses eax ebx, context:dword, p:dword
mov eax,[context]
mov ebx,[p]
mov ebx,[ebx+4] ;ebx = p[1]
mov dword[eax+offs_cont_current_edge_flag],ebx
ret
endp
align 4
proc glopColor uses eax ecx esi edi, context:dword, p:dword
locals
q rd 7
endl
;current_color[3] = p[1-4]
;longcurrent_color[2] = p[5-7]
mov esi,[p]
add esi,4
mov edi,[context]
add edi,offs_cont_current_color
mov ecx,7
rep movsd
mov eax,[context]
cmp dword[eax+offs_cont_color_material_enabled],1
jne @f
mov dword[q],OP_Material
mov ecx,[eax+offs_cont_current_color_material_mode]
mov dword[q+4],ecx
mov ecx,[eax+offs_cont_current_color_material_type]
mov dword[q+8],ecx
mov esi,[p]
add esi,4
mov edi,dword[q+12] ;edi = [q3]
mov ecx,4
rep movsd
stdcall glopMaterial, eax,[q]
@@:
ret
endp
align 4
proc gl_eval_viewport uses eax, context:dword
locals
zsize dd ? ;float
endl
mov eax,[context]
add eax,offs_cont_viewport ;eax = (GLViewport*) v
mov dword[zsize],(1 shl (ZB_Z_BITS + ZB_POINT_Z_FRAC_BITS))
fild dword[zsize]
fstp dword[zsize]
fld1
fld1
fadd st1,st0 ;st1 = 2.0
fdiv st0,st1 ;st0 = 0.5
fild dword[eax+offs_vpor_xsize]
fsub st0,st1
fdiv st0,st2
fst dword[eax+offs_vpor_scale+offs_X]
fiadd dword[eax+offs_vpor_xmin]
fstp dword[eax+offs_vpor_trans+offs_X]
fild dword[eax+offs_vpor_ysize]
fsub st0,st1
fdiv st0,st2
fchs
fst dword[eax+offs_vpor_scale+offs_Y]
fchs
fiadd dword[eax+offs_vpor_ymin]
fstp dword[eax+offs_vpor_trans+offs_Y]
fld dword[zsize]
fsub st0,st1
fdiv st0,st2
fchs
fst dword[eax+offs_vpor_scale+offs_Z]
fchs
mov dword[zsize],(1 shl ZB_POINT_Z_FRAC_BITS) / 2
fiadd dword[zsize]
fstp dword[eax+offs_vpor_trans+offs_Z]
if DEBUG ;gl_eval_viewport
stdcall dbg_print,f_ev,txt_nl
add eax,offs_vpor_scale
stdcall gl_print_matrix,eax,1
add eax,8
stdcall gl_print_matrix,eax,1
end if
ret
endp
align 4
proc glopBegin uses eax ebx ecx edx, context:dword, p:dword
locals
tmp M4
endl
; assert(c->in_begin == 0);
mov edx,[context]
mov ebx,[p]
mov ebx,[ebx+4] ;ebx = p[1]
mov [edx+offs_cont_begin_type],ebx
mov dword[edx+offs_cont_in_begin],1
mov dword[edx+offs_cont_vertex_n],0
mov dword[edx+offs_cont_vertex_cnt],0
bt dword[edx+offs_cont_matrix_model_projection_updated],0
jnc .end_mmpu
cmp dword[edx+offs_cont_lighting_enabled],0 ;if(context.lighting_enabled)
je @f
; precompute inverse modelview
mov ebx,ebp
sub ebx,64
stdcall gl_M4_Inv, ebx, edx+offs_cont_matrix_stack_ptr
stdcall gl_M4_Transpose, edx+offs_cont_matrix_model_view_inv, ebx
jmp .end_if_0
@@:
mov ecx,edx
add ecx,offs_cont_matrix_model_projection
; precompute projection matrix
stdcall gl_M4_Mul, ecx,dword[edx+offs_cont_matrix_stack_ptr+4],dword[edx+offs_cont_matrix_stack_ptr]
;if DEBUG ;glopBegin
;stdcall gl_print_matrix,ecx,4
;stdcall gl_print_matrix,[edx+offs_cont_matrix_stack_ptr+4],4
;stdcall gl_print_matrix,[edx+offs_cont_matrix_stack_ptr],4
;end if
; test to accelerate computation
mov dword[edx+offs_cont_matrix_model_projection_no_w_transform],0
fldz
fld dword[ecx+12*4]
fcomp st1
fstsw ax
sahf
jne .end_if_0
fld dword[ecx+13*4]
fcomp st1
fstsw ax
sahf
jne .end_if_0
fld dword[ecx+14*4]
fcomp st1
fstsw ax
sahf
jne .end_if_0
mov dword[edx+offs_cont_matrix_model_projection_no_w_transform],1
.end_if_0:
; test if the texture matrix is not Identity
stdcall gl_M4_IsId,edx+offs_cont_matrix_stack_ptr+8
xor edx,1
mov ebx,[context]
mov dword[ebx+offs_cont_apply_texture_matrix],edx
mov edx,[context]
mov dword[edx+offs_cont_matrix_model_projection_updated],0
.end_mmpu:
; viewport
cmp dword[edx+offs_cont_viewport+offs_vpor_updated],0 ;if (context.viewport.updated)
je @f
stdcall gl_eval_viewport,edx
mov dword[edx+offs_cont_viewport+offs_vpor_updated],0
@@:
; triangle drawing functions
cmp dword[edx+offs_cont_render_mode],GL_SELECT
jne @f
mov dword[edx+offs_cont_draw_triangle_front],gl_draw_triangle_select
mov dword[edx+offs_cont_draw_triangle_back],gl_draw_triangle_select
jmp .end_if_2
@@:
cmp dword[edx+offs_cont_polygon_mode_front],GL_POINT
jne @f
mov dword[edx+offs_cont_draw_triangle_front],gl_draw_triangle_point
jmp .end_if_1
@@:
cmp dword[edx+offs_cont_polygon_mode_front],GL_LINE
jne @f
mov dword[edx+offs_cont_draw_triangle_front],gl_draw_triangle_line
jmp .end_if_1
@@: ;default:
mov dword[edx+offs_cont_draw_triangle_front],gl_draw_triangle_fill
.end_if_1:
cmp dword[edx+offs_cont_polygon_mode_back],GL_POINT
jne @f
mov dword[edx+offs_cont_draw_triangle_back],gl_draw_triangle_point
jmp .end_if_2
@@:
cmp dword[edx+offs_cont_polygon_mode_back],GL_LINE
jne @f
mov dword[edx+offs_cont_draw_triangle_back],gl_draw_triangle_line
jmp .end_if_2
@@: ;default:
mov dword[edx+offs_cont_draw_triangle_back],gl_draw_triangle_fill
.end_if_2:
ret
endp
; coords, tranformation , clip code and projection
; TODO : handle all cases
align 4
proc gl_vertex_transform, context:dword, v:dword
pushad
mov eax,[context]
mov edx,[v]
cmp dword[eax+offs_cont_lighting_enabled],0 ;if (context.lighting_enabled)
je .els_0
; eye coordinates needed for lighting
mov ebx,dword[eax+offs_cont_matrix_stack_ptr]
;;;mov edx,[v]
finit
fld dword[edx+offs_vert_coord+offs_X]
fld dword[edx+offs_vert_coord+offs_Y]
fld dword[edx+offs_vert_coord+offs_Z]
mov ecx,4
.cycle_0:
fld dword[ebx] ;st0 = m[0]
fmul st0,st3 ;st0 *= v.coord.X
fld dword[ebx+4] ;st0 = m[1]
fmul st0,st3 ;st0 *= v.coord.Y
fld dword[ebx+8] ;st0 = m[2]
fmul st0,st3 ;st0 *= v.coord.Z
fadd dword[ebx+12] ;st0 += m[3]
fadd st0,st1 ;st0 += v.coord.Z * m[2]
fadd st0,st2 ;st0 += v.coord.Y * m[1]
fstp dword[edx+offs_vert_ec] ;v.ec.X = v.coord.X * m[0] + v.coord.Y * m[1] + v.coord.Z * m[2] + m[3]
ffree st0
fincstp
ffree st0
fincstp
add ebx,16 ;следущая строка матрицы
add edx,4 ;следущая координата вектора
loop .cycle_0
; projection coordinates
mov ebx,dword[eax+offs_cont_matrix_stack_ptr+4]
mov edx,[v]
finit
fld dword[edx+offs_vert_ec+offs_X]
fld dword[edx+offs_vert_ec+offs_Y]
fld dword[edx+offs_vert_ec+offs_Z]
mov ecx,4
.cycle_1:
fld dword[ebx] ;st0 = m[0]
fmul st0,st3 ;st0 *= v.ec.X
fld dword[ebx+4] ;st0 = m[1]
fmul st0,st3 ;st0 *= v.ec.Y
fld dword[ebx+8] ;st0 = m[2]
fmul st0,st3 ;st0 *= v.ec.Z
fadd dword[ebx+12] ;st0 += m[3]
fadd st0,st1 ;st0 += v.ec.Z * m[2]
fadd st0,st2 ;st0 += v.ec.Y * m[1]
fstp dword[edx+offs_vert_pc] ;v.pc.X = v.ec.X * m[0] + v.ec.Y * m[1] + v.ec.Z * m[2] + m[3]
ffree st0
fincstp
ffree st0
fincstp
add ebx,16 ;следущая строка матрицы
add edx,4 ;следущая координата вектора
loop .cycle_1
mov ebx,eax
add ebx,offs_cont_matrix_model_view_inv
mov edi,eax
add edi,offs_cont_current_normal
mov edx,[v]
finit
fld dword[edi+offs_X]
fld dword[edi+offs_Y]
fld dword[edi+offs_Z]
mov ecx,3
.cycle_2:
fld dword[ebx] ;st0 = m[0]
fmul st0,st3 ;st0 *= n.X
fld dword[ebx+4] ;st0 = m[1]
fmul st0,st3 ;st0 *= n.Y
fld dword[ebx+8] ;st0 = m[2]
fmul st0,st3 ;st0 *= n.Z
fadd st0,st1 ;st0 += n.Z * m[2]
fadd st0,st2 ;st0 += n.Y * m[1]
fstp dword[edx+offs_vert_normal] ;v.normal.X = n.X * m[0] + n.Y * m[1] + n.Z * m[2]
ffree st0
fincstp
ffree st0
fincstp
add ebx,16 ;следущая строка матрицы
add edx,4 ;следущая координата вектора
loop .cycle_2
cmp dword[eax+offs_cont_normalize_enabled],0
je .end_els
;stdcall gl_V3_Norm(&v->normal)
jmp .end_els
.els_0:
; no eye coordinates needed, no normal
; NOTE: W = 1 is assumed
mov ebx,eax
add ebx,offs_cont_matrix_model_projection
;;;mov edx,[v]
finit
fld dword[edx+offs_vert_coord+offs_X]
fld dword[edx+offs_vert_coord+offs_Y]
fld dword[edx+offs_vert_coord+offs_Z]
mov esi,edx
add esi,offs_vert_pc
fld dword[ebx] ;st0 = m[0]
fmul st0,st3 ;st0 *= v.coord.X
fld dword[ebx+4] ;st0 = m[1]
fmul st0,st3 ;st0 *= v.coord.Y
fld dword[ebx+8] ;st0 = m[2]
fmul st0,st3 ;st0 *= v.coord.Z
fadd dword[ebx+12] ;st0 += m[3]
fadd st0,st1 ;st0 += v.coord.Z * m[2]
fadd st0,st2 ;st0 += v.coord.Y * m[1]
fstp dword[esi] ;v.pc.X = v.coord.X * m[0] + v.coord.Y * m[1] + v.coord.Z * m[2] + m[3]
ffree st0
fincstp
ffree st0
fincstp
fld dword[ebx+16] ;st0 = m[4]
fmul st0,st3 ;st0 *= v.coord.X
fld dword[ebx+20] ;st0 = m[5]
fmul st0,st3 ;st0 *= v.coord.Y
fld dword[ebx+24] ;st0 = m[6]
fmul st0,st3 ;st0 *= v.coord.Z
fadd dword[ebx+28] ;st0 += m[7]
fadd st0,st1 ;st0 += v.coord.Z * m[6]
fadd st0,st2 ;st0 += v.coord.Y * m[5]
fstp dword[esi+4] ;v.pc.X = v.coord.X * m[4] + v.coord.Y * m[5] + v.coord.Z * m[6] + m[7]
ffree st0
fincstp
ffree st0
fincstp
fld dword[ebx+32] ;st0 = m[8]
fmul st0,st3 ;st0 *= v.coord.X
fld dword[ebx+36] ;st0 = m[9]
fmul st0,st3 ;st0 *= v.coord.Y
fld dword[ebx+40] ;st0 = m[10]
fmul st0,st3 ;st0 *= v.coord.Z
fadd dword[ebx+44] ;st0 += m[11]
fadd st0,st1 ;st0 += v.coord.Z * m[10]
fadd st0,st2 ;st0 += v.coord.Y * m[9]
fstp dword[esi+8] ;v.pc.X = v.coord.X * m[8] + v.coord.Y * m[9] + v.coord.Z * m[10] + m[11]
cmp dword[eax+offs_cont_matrix_model_projection_no_w_transform],0
je .els_1
;if (context.matrix_model_projection_no_w_transform)
mov ebx,dword[ebx+60] ;ebx = m[15]
mov dword[esi+12],ebx ;v.pc.W = m[15]
jmp .end_els
.els_1:
ffree st0
fincstp
ffree st0
fincstp
fld dword[ebx+48] ;st0 = m[12]
fmul st0,st3 ;st0 *= v.coord.X
fld dword[ebx+52] ;st0 = m[13]
fmul st0,st3 ;st0 *= v.coord.Y
fld dword[ebx+56] ;st0 = m[14]
fmul st0,st3 ;st0 *= v.coord.Z
fadd dword[ebx+60] ;st0 += m[15]
fadd st0,st1 ;st0 += v.coord.Z * m[14]
fadd st0,st2 ;st0 += v.coord.Y * m[13]
fstp dword[esi+12] ;v.pc.W = v.coord.X * m[12] + v.coord.Y * m[13] + v.coord.Z * m[14] + m[15]
.end_els:
if DEBUG ;gl_vertex_transform
stdcall dbg_print,f_vt,txt_nl
mov edx,[v]
add edx,offs_vert_pc
stdcall gl_print_matrix,edx,1
end if
mov edx,[v]
stdcall gl_clipcode, dword[edx+offs_vert_pc+offs_X], dword[edx+offs_vert_pc+offs_Y],\
dword[edx+offs_vert_pc+offs_Z], dword[edx+offs_vert_pc+offs_W]
mov dword[edx+offs_vert_clip_code],eax
popad
ret
endp
align 4
proc glopVertex, context:dword, p:dword
locals
;ebx = GLVertex * v
n dd ? ;ebp-4
endl
pushad
mov edx,[context]
; assert(c->in_begin != 0);
mov ecx,[edx+offs_cont_vertex_n]
mov [n],ecx
inc dword[edx+offs_cont_vertex_cnt]
; quick fix to avoid crashes on large polygons
mov ecx,[edx+offs_cont_vertex_max]
cmp dword[n],ecx
jl @f
shl dword[edx+offs_cont_vertex_max],1 ; just double size
imul ecx,2*sizeof.GLVertex
stdcall gl_malloc,ecx
cmp eax,0
jne .no_err
;gl_fatal_error("unable to allocate GLVertex array.\n");
.no_err:
mov edi,eax
mov ebx,eax
mov esi,[edx+offs_cont_vertex]
mov ecx,[n]
imul ecx,(sizeof.GLVertex)/4 ;((...)/4) что-бы использовать movsd вместо movsb
rep movsd
stdcall gl_free,dword[edx+offs_cont_vertex]
mov dword[edx+offs_cont_vertex],ebx
@@:
; new vertex entry
mov ebx,[n]
imul ebx,sizeof.GLVertex
add ebx,[edx+offs_cont_vertex]
inc dword[n]
mov esi,[p]
add esi,4
mov edi,ebx
add edi,offs_vert_coord ;edi = &v.coord
mov ecx,4
rep movsd
stdcall gl_vertex_transform, edx, ebx
; color
cmp dword[edx+offs_cont_lighting_enabled],0
je .els_0
stdcall gl_shade_vertex, edx,ebx
jmp @f
.els_0:
mov eax,[edx+offs_cont_current_color]
mov [ebx+offs_vert_color],eax
@@:
; tex coords
cmp dword[edx+offs_cont_texture_2d_enabled],0
je @f
cmp dword[edx+offs_cont_apply_texture_matrix],0
je .els_1
; gl_M4_MulV4(&v->tex_coord, c->matrix_stack_ptr[2], &c->current_tex_coord);
jmp @f
.els_1:
mov eax,[edx+offs_cont_current_tex_coord]
mov [ebx+offs_vert_tex_coord],eax
@@:
; precompute the mapping to the viewport
cmp dword[ebx+offs_vert_clip_code],0
jne @f
stdcall gl_transform_to_viewport, edx,ebx
@@:
; edge flag
mov eax,[edx+offs_cont_current_edge_flag]
mov dword[ebx+offs_vert_edge_flag],eax ;v.edge_flag = context.current_edge_flag
cmp dword[edx+offs_cont_begin_type],GL_POINTS
jne @f
stdcall gl_draw_point, edx, dword[edx+offs_cont_vertex] ;dword[edx+...] = &context.vertex[0]
mov dword[n],0
jmp .end_f
@@:
cmp dword[edx+offs_cont_begin_type],GL_LINES
jne @f
cmp dword[n],2
jne .end_f
mov eax,[edx+offs_cont_vertex]
push eax
add eax,sizeof.GLVertex
push eax
stdcall gl_draw_line, edx
xor eax,eax
mov dword[n],eax
jmp .end_f
@@:
cmp dword[edx+offs_cont_begin_type],GL_LINE_STRIP
je .li_loop
cmp dword[edx+offs_cont_begin_type],GL_LINE_LOOP
jne @f
.li_loop:
cmp dword[n],1
jne .els_2
mov esi,[edx+offs_cont_vertex]
mov edi,esi
add edi,2*sizeof.GLVertex
mov ecx,(sizeof.GLVertex)/4 ;((...)/4) что-бы использовать movsd вместо movsb
rep movsd ;context.vertex[2] = context.vertex[0]
jmp .end_f
.els_2:
cmp dword[n],2
jne .end_f ;else if (n == 2)
mov eax,[edx+offs_cont_vertex]
push eax
add eax,sizeof.GLVertex
push eax
stdcall gl_draw_line, edx
mov edi,[edx+offs_cont_vertex]
mov esi,edi
add esi,sizeof.GLVertex
mov ecx,(sizeof.GLVertex)/4 ;((...)/4) что-бы использовать movsd вместо movsb
rep movsd ;context.vertex[0] = context.vertex[1]
mov dword[n],1
jmp .end_f
@@:
cmp dword[edx+offs_cont_begin_type],GL_TRIANGLES
jne @f
cmp dword[n],3
jne .end_f
; gl_draw_triangle(c, &c->vertex[0], &c->vertex[1], &c->vertex[2]);
xor eax,eax
mov dword[n],eax
jmp .end_f
@@:
cmp dword[edx+offs_cont_begin_type],GL_TRIANGLE_STRIP
jne @f
; if (c->vertex_cnt >= 3) {
; if (n == 3)
; n = 0;
; /* needed to respect triangle orientation */
; switch(c->vertex_cnt & 1) {
; case 0:
; gl_draw_triangle(c,&c->vertex[2],&c->vertex[1],&c->vertex[0]);
; break;
; default:
; case 1:
; gl_draw_triangle(c,&c->vertex[0],&c->vertex[1],&c->vertex[2]);
; break;
; }
; }
jmp .end_f
@@:
cmp dword[edx+offs_cont_begin_type],GL_TRIANGLE_FAN
jne @f
cmp dword[n],2
jne .end_f
; gl_draw_triangle(c, &c->vertex[0], &c->vertex[1], &c->vertex[2]);
; c->vertex[1] = c->vertex[2];
mov dword[n],2
jmp .end_f
@@:
cmp dword[edx+offs_cont_begin_type],GL_QUADS
jne @f
cmp dword[n],4
jne .end_f
; c->vertex[2].edge_flag = 0;
; gl_draw_triangle(c, &c->vertex[0], &c->vertex[1], &c->vertex[2]);
; c->vertex[2].edge_flag = 1;
; c->vertex[0].edge_flag = 0;
; gl_draw_triangle(c, &c->vertex[0], &c->vertex[2], &c->vertex[3]);
xor eax,eax
mov dword[n],eax
jmp .end_f
@@:
cmp dword[edx+offs_cont_begin_type],GL_QUAD_STRIP
jne @f
cmp dword[n],2
jne .end_f
; gl_draw_triangle(c, &c->vertex[0], &c->vertex[1], &c->vertex[2]);
; gl_draw_triangle(c, &c->vertex[1], &c->vertex[3], &c->vertex[2]);
; for (i = 0; i < 2; i++)
; c->vertex[i] = c->vertex[i + 2];
mov dword[n],2
jmp .end_f
@@:
cmp dword[edx+offs_cont_begin_type],GL_POLYGON
jne @f
;...
jmp .end_f
@@:
; default:
; gl_fatal_error("glBegin: type %x not handled\n", c->begin_type);
; }
.end_f:
mov ecx,[n]
mov [edx+offs_cont_vertex_n],ecx
popad
ret
endp
align 4
proc glopEnd uses eax ebx, context:dword, p:dword
mov eax,[context]
; assert(c->in_begin == 1);
cmp dword[eax+offs_cont_begin_type],GL_LINE_LOOP
jne .else_i
cmp dword[eax+offs_cont_vertex_cnt],3
jl .end_i
mov ebx,[eax+offs_cont_vertex]
push ebx
add ebx,2*sizeof.GLVertex
push ebx
stdcall gl_draw_line, eax
jmp .end_i
.else_i:
cmp dword[eax+offs_cont_begin_type],GL_POLYGON
jne .end_i
mov ebx,dword[eax+offs_cont_vertex_cnt]
@@: ;while (ebx >= 3)
cmp ebx,3
jl .end_i
dec ebx
; gl_draw_triangle(c, &c->vertex[i], &c->vertex[0], &c->vertex[i - 1]);
jmp @b
.end_i:
mov dword[eax+offs_cont_in_begin],0
ret
endp

View File

@ -0,0 +1,545 @@
;
;
; Z buffer: 16 bits Z / 16 bits color
;
;
;include 'zbuffer.inc'
;output:
; eax - указатель на ZBuffer (0 если не удача)
align 4
proc ZB_open uses ecx edi, xsize:dword, ysize:dword, mode:dword,\
nb_colors:dword, color_indexes:dword, color_table:dword, frame_buffer:dword
stdcall gl_malloc, sizeof.ZBuffer
cmp eax,0
jne @f
stdcall dbg_print,f_zb_opn,err_1
jmp .end_f
@@:
mov edi,eax
mov eax,[ysize]
mov [edi+offs_zbuf_ysize],eax
mov eax,[xsize]
mov [edi+offs_zbuf_xsize],eax
imul eax,PSZB
add eax,3
and eax,not 3
mov [edi+offs_zbuf_linesize],eax
mov eax,[mode]
mov [edi+offs_zbuf_mode],eax
if TGL_FEATURE_8_BITS eq 1
cmp eax,ZB_MODE_INDEX
jne @f
;ZB_initDither(edi, nb_colors, color_indexes, color_table);
jmp .end_s
@@:
end if
if TGL_FEATURE_32_BITS eq 1
cmp eax,ZB_MODE_RGBA
je .correct
end if
if TGL_FEATURE_24_BITS eq 1
cmp eax,ZB_MODE_RGB24
je .correct
end if
cmp eax,ZB_MODE_5R6G5B
jne @f
.correct:
mov dword[edi+offs_zbuf_nb_colors],0
jmp .end_s
@@: ;default:
stdcall dbg_print,f_zb_opn,err_3
jmp .error
.end_s:
mov ecx,[edi+offs_zbuf_xsize]
imul ecx,[edi+offs_zbuf_ysize]
shl ecx,2 ;*= sizeof(unsigned short)
stdcall gl_malloc, ecx
mov [edi+offs_zbuf_zbuf],eax
cmp eax,0
jne @f
stdcall dbg_print,f_zb_opn,err_2
jmp .error
@@:
mov dword[edi+offs_zbuf_frame_buffer_allocated],0
mov dword[edi+offs_zbuf_pbuf],0 ;NULL
mov dword[edi+offs_zbuf_current_texture],0 ;NULL
mov eax,edi
jmp .end_f
.error:
stdcall gl_free,edi
xor eax,eax
.end_f:
ret
endp
;void ZB_close(ZBuffer * zb)
;{
if TGL_FEATURE_8_BITS eq 1
; if (zb->mode == ZB_MODE_INDEX)
; ZB_closeDither(zb);
end if
;
; if (zb->frame_buffer_allocated)
; gl_free(zb->pbuf);
;
; gl_free(zb->zbuf);
; gl_free(zb);
;}
align 4
proc ZB_resize uses eax ebx ecx edi esi, zb:dword, frame_buffer:dword, xsize:dword, ysize:dword
mov ebx,[zb]
; xsize must be a multiple of 4
mov edi,[xsize]
and edi,not 3
mov esi,[ysize]
mov [ebx+offs_zbuf_xsize], edi
mov [ebx+offs_zbuf_ysize], esi
mov eax,edi
imul eax,PSZB
add eax,3
and eax,not 3
mov [ebx+offs_zbuf_linesize],eax ;zb.linesize = (xsize * PSZB + 3) & ~3
mov ecx,edi
imul ecx,esi
shl ecx,2 ;*= sizeof(unsigned short)
stdcall gl_free,dword[ebx+offs_zbuf_zbuf]
stdcall gl_malloc,ecx
mov [ebx+offs_zbuf_zbuf],eax
cmp dword[ebx+offs_zbuf_frame_buffer_allocated],0
je @f
stdcall gl_free,dword[ebx+offs_zbuf_pbuf]
@@:
cmp dword[frame_buffer],0
jne .els_0
inc esi
imul esi,dword[ebx+offs_zbuf_linesize]
stdcall gl_malloc,esi
mov dword[ebx+offs_zbuf_pbuf],eax
mov dword[ebx+offs_zbuf_frame_buffer_allocated],1
jmp @f
.els_0:
mov eax,[frame_buffer]
mov dword[ebx+offs_zbuf_pbuf],eax
mov dword[ebx+offs_zbuf_frame_buffer_allocated],0
@@:
ret
endp
;static void ZB_copyBuffer(ZBuffer * zb,
; void *buf,
; int linesize)
;{
; unsigned char *p1;
; PIXEL *q;
; int y, n;
;
; q = zb->pbuf;
; p1 = buf;
; n = zb->xsize * PSZB;
; for (y = 0; y < zb->ysize; y++) {
; memcpy(p1, q, n);
; p1 += linesize;
; q = (PIXEL *) ((char *) q + zb->linesize);
; }
;}
;
;#if TGL_FEATURE_RENDER_BITS == 16
;/* 32 bpp copy */
;#ifdef TGL_FEATURE_32_BITS
;#define RGB16_TO_RGB32(p0,p1,v)\
;{\
; unsigned int g,b,gb;\
; g = (v & 0x07E007E0) << 5;\
; b = (v & 0x001F001F) << 3;\
; gb = g | b;\
; p0 = (gb & 0x0000FFFF) | ((v & 0x0000F800) << 8);\
; p1 = (gb >> 16) | ((v & 0xF8000000) >> 8);\
;}
;static void ZB_copyFrameBufferRGB32(ZBuffer * zb,
; void *buf,
; int linesize)
;{
; unsigned short *q;
; unsigned int *p, *p1, v, w0, w1;
; int y, n;
;
; q = zb->pbuf;
; p1 = (unsigned int *) buf;
;
; for (y = 0; y < zb->ysize; y++) {
; p = p1;
; n = zb->xsize >> 2;
; do {
; v = *(unsigned int *) q;
;#if BYTE_ORDER == BIG_ENDIAN
; RGB16_TO_RGB32(w1, w0, v);
;#else
; RGB16_TO_RGB32(w0, w1, v);
;#endif
; p[0] = w0;
; p[1] = w1;
;
; v = *(unsigned int *) (q + 2);
;#if BYTE_ORDER == BIG_ENDIAN
; RGB16_TO_RGB32(w1, w0, v);
;#else
; RGB16_TO_RGB32(w0, w1, v);
;#endif
; p[2] = w0;
; p[3] = w1;
;
; q += 4;
; p += 4;
; } while (--n > 0);
;
; p1 += linesize;
; }
;}
;#endif
;/* 24 bit packed pixel handling */
;#ifdef TGL_FEATURE_24_BITS
;/* order: RGBR GBRG BRGB */
;/* XXX: packed pixel 24 bit support not tested */
;/* XXX: big endian case not optimised */
;#if BYTE_ORDER == BIG_ENDIAN
;#define RGB16_TO_RGB24(p0,p1,p2,v1,v2)\
;{\
; unsigned int r1,g1,b1,gb1,g2,b2,gb2;\
; v1 = (v1 << 16) | (v1 >> 16);\
; v2 = (v2 << 16) | (v2 >> 16);\
; r1 = (v1 & 0xF800F800);\
; g1 = (v1 & 0x07E007E0) << 5;\
; b1 = (v1 & 0x001F001F) << 3;\
; gb1 = g1 | b1;\
; p0 = ((gb1 & 0x0000FFFF) << 8) | (r1 << 16) | (r1 >> 24);\
; g2 = (v2 & 0x07E007E0) << 5;\
; b2 = (v2 & 0x001F001F) << 3;\
; gb2 = g2 | b2;\
; p1 = (gb1 & 0xFFFF0000) | (v2 & 0xF800) | ((gb2 >> 8) & 0xff);\
; p2 = (gb2 << 24) | ((v2 & 0xF8000000) >> 8) | (gb2 >> 16);\
;}
;#else
;#define RGB16_TO_RGB24(p0,p1,p2,v1,v2)\
;{\
; unsigned int r1,g1,b1,gb1,g2,b2,gb2;\
; r1 = (v1 & 0xF800F800);\
; g1 = (v1 & 0x07E007E0) << 5;\
; b1 = (v1 & 0x001F001F) << 3;\
; gb1 = g1 | b1;\
; p0 = ((gb1 & 0x0000FFFF) << 8) | (r1 << 16) | (r1 >> 24);\
; g2 = (v2 & 0x07E007E0) << 5;\
; b2 = (v2 & 0x001F001F) << 3;\
; gb2 = g2 | b2;\
; p1 = (gb1 & 0xFFFF0000) | (v2 & 0xF800) | ((gb2 >> 8) & 0xff);\
; p2 = (gb2 << 24) | ((v2 & 0xF8000000) >> 8) | (gb2 >> 16);\
;}
;#endif
;static void ZB_copyFrameBufferRGB24(ZBuffer * zb,
; void *buf, int linesize)
;{
; unsigned short *q;
; unsigned int *p, *p1, w0, w1, w2, v0, v1;
; int y, n;
;
; q = zb->pbuf;
; p1 = (unsigned int *) buf;
; linesize = linesize * 3;
;
; for (y = 0; y < zb->ysize; y++) {
; p = p1;
; n = zb->xsize >> 2;
; do {
; v0 = *(unsigned int *) q;
; v1 = *(unsigned int *) (q + 2);
; RGB16_TO_RGB24(w0, w1, w2, v0, v1);
; p[0] = w0;
; p[1] = w1;
; p[2] = w2;
; q += 4;
; p += 3;
; } while (--n > 0);
;
; (char *) p1 += linesize;
; }
;}
;#endif
;void ZB_copyFrameBuffer(ZBuffer * zb, void *buf,
; int linesize)
;{
; switch (zb->mode) {
;#ifdef TGL_FEATURE_8_BITS
; case ZB_MODE_INDEX:
; ZB_ditherFrameBuffer(zb, buf, linesize >> 1);
; break;
;#endif
;#ifdef TGL_FEATURE_16_BITS
; case ZB_MODE_5R6G5B:
; ZB_copyBuffer(zb, buf, linesize);
; break;
;#endif
;#ifdef TGL_FEATURE_32_BITS
; case ZB_MODE_RGBA:
; ZB_copyFrameBufferRGB32(zb, buf, linesize >> 1);
; break;
;#endif
;#ifdef TGL_FEATURE_24_BITS
; case ZB_MODE_RGB24:
; ZB_copyFrameBufferRGB24(zb, buf, linesize >> 1);
; break;
;#endif
; default:
; assert(0);
; }
;}
;#endif /* TGL_FEATURE_RENDER_BITS == 16 */
;#if TGL_FEATURE_RENDER_BITS == 24
;#define RGB24_TO_RGB16(r, g, b) \
; ((((r) >> 3) << 11) | (((g) >> 2) << 5) | ((b) >> 3))
;/* XXX: not optimized */
;static void ZB_copyFrameBuffer5R6G5B(ZBuffer * zb,
; void *buf, int linesize)
;{
; PIXEL *q;
; unsigned short *p, *p1;
; int y, n;
;
; q = zb->pbuf;
; p1 = (unsigned short *) buf;
;
; for (y = 0; y < zb->ysize; y++) {
; p = p1;
; n = zb->xsize >> 2;
; do {
; p[0] = RGB24_TO_RGB16(q[0], q[1], q[2]);
; p[1] = RGB24_TO_RGB16(q[3], q[4], q[5]);
; p[2] = RGB24_TO_RGB16(q[6], q[7], q[8]);
; p[3] = RGB24_TO_RGB16(q[9], q[10], q[11]);
; q = (PIXEL *)((char *)q + 4 * PSZB);
; p += 4;
; } while (--n > 0);
; p1 = (unsigned short *)((char *)p1 + linesize);
; }
;}
;void ZB_copyFrameBuffer(ZBuffer * zb, void *buf,
; int linesize)
;{
; switch (zb->mode) {
;#ifdef TGL_FEATURE_16_BITS
; case ZB_MODE_5R6G5B:
; ZB_copyFrameBuffer5R6G5B(zb, buf, linesize);
; break;
;#endif
;#ifdef TGL_FEATURE_24_BITS
; case ZB_MODE_RGB24:
; ZB_copyBuffer(zb, buf, linesize);
; break;
;#endif
; default:
; assert(0);
; }
;}
;#endif /* TGL_FEATURE_RENDER_BITS == 24 */
;#if TGL_FEATURE_RENDER_BITS == 32
;#define RGB32_TO_RGB16(v) \
; (((v >> 8) & 0xf800) | (((v) >> 5) & 0x07e0) | (((v) & 0xff) >> 3))
;/* XXX: not optimized */
;static void ZB_copyFrameBuffer5R6G5B(ZBuffer * zb,
; void *buf, int linesize)
;{
; PIXEL *q;
; unsigned short *p, *p1;
; int y, n;
;
; q = zb->pbuf;
; p1 = (unsigned short *) buf;
;
; for (y = 0; y < zb->ysize; y++) {
; p = p1;
; n = zb->xsize >> 2;
; do {
; p[0] = RGB32_TO_RGB16(q[0]);
; p[1] = RGB32_TO_RGB16(q[1]);
; p[2] = RGB32_TO_RGB16(q[2]);
; p[3] = RGB32_TO_RGB16(q[3]);
; q += 4;
; p += 4;
; } while (--n > 0);
; p1 = (unsigned short *)((char *)p1 + linesize);
; }
;}
;
;void ZB_copyFrameBuffer(ZBuffer * zb, void *buf,
; int linesize)
;{
; switch (zb->mode) {
;#ifdef TGL_FEATURE_16_BITS
; case ZB_MODE_5R6G5B:
; ZB_copyFrameBuffer5R6G5B(zb, buf, linesize);
; break;
;#endif
;#ifdef TGL_FEATURE_32_BITS
; case ZB_MODE_RGBA:
; ZB_copyBuffer(zb, buf, linesize);
; break;
;#endif
; default:
; assert(0);
; }
;}
;
;#endif /* TGL_FEATURE_RENDER_BITS == 32 */
;
;
;/*
; * adr must be aligned on an 'int'
; */
;void memset_s(void *adr, int val, int count)
;{
; int i, n, v;
; unsigned int *p;
; unsigned short *q;
;
; p = adr;
; v = val | (val << 16);
;
; n = count >> 3;
; for (i = 0; i < n; i++) {
; p[0] = v;
; p[1] = v;
; p[2] = v;
; p[3] = v;
; p += 4;
; }
;
; q = (unsigned short *) p;
; n = count & 7;
; for (i = 0; i < n; i++)
; *q++ = val;
;}
;
;void memset_l(void *adr, int val, int count)
;{
; int i, n, v;
; unsigned int *p;
;
; p = adr;
; v = val;
; n = count >> 2;
; for (i = 0; i < n; i++) {
; p[0] = v;
; p[1] = v;
; p[2] = v;
; p[3] = v;
; p += 4;
; }
;
; n = count & 3;
; for (i = 0; i < n; i++)
; *p++ = val;
;}
;
;/* count must be a multiple of 4 and >= 4 */
;void memset_RGB24(void *adr,int r, int v, int b,long count)
;{
; long i, n;
; register long v1,v2,v3,*pt=(long *)(adr);
; unsigned char *p,R=(unsigned char)r,V=(unsigned char)v,B=(unsigned char)b;
;
; p=(unsigned char *)adr;
; *p++=R;
; *p++=V;
; *p++=B;
; *p++=R;
; *p++=V;
; *p++=B;
; *p++=R;
; *p++=V;
; *p++=B;
; *p++=R;
; *p++=V;
; *p++=B;
; v1=*pt++;
; v2=*pt++;
; v3=*pt++;
; n = count >> 2;
; for(i=1;i<n;i++) {
; *pt++=v1;
; *pt++=v2;
; *pt++=v3;
; }
;}
;
;void ZB_clear(ZBuffer * zb, int clear_z, int z,
; int clear_color, int r, int g, int b)
;{
;#if TGL_FEATURE_RENDER_BITS != 24
; int color;
;#endif
; int y;
; PIXEL *pp;
;
; if (clear_z) {
; memset_s(zb->zbuf, z, zb->xsize * zb->ysize);
; }
; if (clear_color) {
; pp = zb->pbuf;
; for (y = 0; y < zb->ysize; y++) {
;#if TGL_FEATURE_RENDER_BITS == 15 || TGL_FEATURE_RENDER_BITS == 16
; color = RGB_TO_PIXEL(r, g, b);
; memset_s(pp, color, zb->xsize);
;#elif TGL_FEATURE_RENDER_BITS == 32
; color = RGB_TO_PIXEL(r, g, b);
; memset_l(pp, color, zb->xsize);
;#elif TGL_FEATURE_RENDER_BITS == 24
; memset_RGB24(pp,r>>8,g>>8,b>>8,zb->xsize);
;#else
;#error TODO
;#endif
; pp = (PIXEL *) ((char *) pp + zb->linesize);
; }
; }
;}

View File

@ -0,0 +1,178 @@
;
; Z buffer
;
include 'zfeatures.inc'
ZB_Z_BITS equ 16
ZB_POINT_Z_FRAC_BITS equ 14
ZB_POINT_S_MIN equ ( (1 shl 13) )
ZB_POINT_S_MAX equ ( (1 shl 22)-(1 shl 13) )
ZB_POINT_T_MIN equ ( (1 shl 21) )
ZB_POINT_T_MAX equ ( (1 shl 30)-(1 shl 21) )
ZB_POINT_RED_MIN equ ( (1 shl 10) )
ZB_POINT_RED_MAX equ ( (1 shl 16)-(1 shl 10) )
ZB_POINT_GREEN_MIN equ ( (1 shl 9) )
ZB_POINT_GREEN_MAX equ ( (1 shl 16)-(1 shl 9) )
ZB_POINT_BLUE_MIN equ ( (1 shl 10) )
ZB_POINT_BLUE_MAX equ ( (1 shl 16)-(1 shl 10) )
; display modes
ZB_MODE_5R6G5B equ 1 ; true color 16 bits
ZB_MODE_INDEX equ 2 ; color index 8 bits
ZB_MODE_RGBA equ 3 ; 32 bit rgba mode
ZB_MODE_RGB24 equ 4 ; 24 bit rgb mode
ZB_NB_COLORS equ 225 ; number of colors for 8 bit display
if TGL_FEATURE_RENDER_BITS eq 15
;#define RGB_TO_PIXEL(r,g,b) \
; ((((r) >> 1) & 0x7c00) | (((g) >> 6) & 0x03e0) | ((b) >> 11))
;typedef unsigned short PIXEL;
;/* bytes per pixel */
;PSZB equ 2
;/* bits per pixel = (1 << PSZH) */
;PSZSH equ 4
else if TGL_FEATURE_RENDER_BITS eq 16
;/* 16 bit mode */
;#define RGB_TO_PIXEL(r,g,b) \
; (((r) & 0xF800) | (((g) >> 5) & 0x07E0) | ((b) >> 11))
;typedef unsigned short PIXEL;
;PSZB equ 2
;PSZSH equ 4
else if TGL_FEATURE_RENDER_BITS eq 24
macro RGB_TO_PIXEL r,g,b
{
mov eax,b
shr eax,8
push eax
mov eax,g
and eax,0xff00
or dword[esp],eax
mov eax,r
shl eax,8
or dword[esp],eax
pop eax
}
;typedef unsigned char PIXEL;
PSZB equ 3
PSZSH equ 5
else if TGL_FEATURE_RENDER_BITS eq 32
;#define RGB_TO_PIXEL(r,g,b) \
; ((((r) << 8) & 0xff0000) | ((g) & 0xff00) | ((b) >> 8))
;typedef unsigned int PIXEL;
;PSZB equ 4
;PSZSH equ 5
else
;#error Incorrect number of bits per pixel
end if
struct ZBuffer
xsize dd ? ;int
ysize dd ? ;int
linesize dd ? ;int ;line size, in bytes
mode dd ? ;int
zbuf dd ? ;*unsigned short
pbuf dd ? ;*PIXEL
frame_buffer_allocated dd ? ;int
nb_colors dd ? ;int
dctable dd ? ;*unsigned char
ctable dd ? ;*int
current_texture dd ? ;*PIXEL
ends
offs_zbuf_xsize equ 0
offs_zbuf_ysize equ 4
offs_zbuf_linesize equ 8
offs_zbuf_mode equ 16
offs_zbuf_zbuf equ 20
offs_zbuf_pbuf equ 24
offs_zbuf_frame_buffer_allocated equ 28
offs_zbuf_nb_colors equ 32
offs_zbuf_dctable equ 36
offs_zbuf_ctable equ 40
offs_zbuf_current_texture equ 44
struct ZBufferPoint
x dd ? ;int ;integer coordinates in the zbuffer
y dd ? ;int
z dd ? ;int
s dd ? ;int ;coordinates for the mapping
t dd ? ;int
r dd ? ;int ;color indexes
g dd ? ;int
b dd ? ;int
fsz dd ? ;float ;temporary coordinates for mapping
tz dd ? ;float
ends
offs_zbup_x equ 0
offs_zbup_y equ 4
offs_zbup_z equ 8
offs_zbup_s equ 12
offs_zbup_t equ 16
offs_zbup_r equ 20
offs_zbup_g equ 24
offs_zbup_b equ 28
offs_zbup_sz equ 32
offs_zbup_tz equ 36
; ztriangle.c
;
; Memory allocator for TinyGL
;
; modify these functions so that they suit your needs
align 4
proc gl_free uses ebx ecx, mptr:dword
mov ecx,[mptr]
or ecx,ecx
jz @f
@@:
mcall 68, 13
ret
endp
;description:
; выделение памяти
align 4
proc gl_malloc uses ebx ecx, size:dword
mcall 68, 12, [size]
ret
endp
;description:
; выделение очищеной памяти
align 4
proc gl_zalloc uses ebx ecx edi, size:dword
mov ecx,[size]
stdcall gl_malloc,ecx
cmp eax,0
je @f
mov ebx,eax
mov edi,eax
xor eax,eax
shr ecx,2
rep stosd ;очистка памяти (пишем везде 0)
mov eax,ebx
@@:
ret
endp

View File

@ -0,0 +1,43 @@
;
; If not debugging, assert does nothing.
;
;#define assert(x) ((void)0) /* debugging disabled */
;#include <assert.h> /* debugging enabled */
; It is possible to enable/disable (compile time) features in this
; header file.
;TGL_FEATURE_ARRAYS equ 1
;TGL_FEATURE_DISPLAYLISTS equ 1
;TGL_FEATURE_POLYGON_OFFSET equ 1
;
; Matrix of internal and external pixel formats supported. 'Y' means
; supported.
;
; External 8 16 24 32
; Internal
; 15 . . . .
; 16 Y Y Y Y
; 24 . Y Y .
; 32 . Y . Y
;
;
; 15 bpp does not work yet (although it is easy to add it - ask me if
; you need it).
;
; Internal pixel format: see TGL_FEATURE_RENDER_BITS
; External pixel format: see TGL_FEATURE_xxx_BITS
;
; enable various convertion code from internal pixel format (usually
; 16 bits per pixel) to any external format */
;TGL_FEATURE_16_BITS equ 1
;TGL_FEATURE_8_BITS equ 1
TGL_FEATURE_24_BITS equ 1
;TGL_FEATURE_32_BITS equ 1
;TGL_FEATURE_RENDER_BITS equ 15
;TGL_FEATURE_RENDER_BITS equ 16
TGL_FEATURE_RENDER_BITS equ 24
;TGL_FEATURE_RENDER_BITS equ 32

View File

@ -0,0 +1,515 @@
include 'opengl_const.inc'
include 'zbuffer.inc'
include 'zmath.inc'
;#define fputc(...) /*nothing*/
;#define fprintf(...) /*nothing*/
;#define vfprintf(...) /*nothing*/
;#undef stderr
;#define stderr ((FILE*)-1)
;enum { OP_ ## a , ... }
s1 equ 0
macro ADD_OP a,b,c
{
OP_#a equ s1
s1 equ (s1+1)
}
include 'opinfo.inc'
;initially # of allocated GLVertexes (will grow when necessary)
POLYGON_MAX_VERTEX equ 16
;Max # of specular light pow buffers
MAX_SPECULAR_BUFFERS equ 8
;# of entries in specular buffer
SPECULAR_BUFFER_SIZE equ 1024
;specular buffer granularity
SPECULAR_BUFFER_RESOLUTION equ 1024
MAX_MODELVIEW_STACK_DEPTH equ 32
MAX_PROJECTION_STACK_DEPTH equ 8
MAX_TEXTURE_STACK_DEPTH equ 8
MAX_NAME_STACK_DEPTH equ 64
MAX_TEXTURE_LEVELS equ 11
MAX_LIGHTS equ 16
VERTEX_HASH_SIZE equ 1031
MAX_DISPLAY_LISTS equ 1024
OP_BUFFER_MAX_SIZE equ 512
TGL_OFFSET_FILL equ 0x1
TGL_OFFSET_LINE equ 0x2
TGL_OFFSET_POINT equ 0x4
struct GLSpecBuf
shininess_i dd ? ;int
last_used dd ? ;int
buf rd SPECULAR_BUFFER_SIZE+1 ;float[SPECULAR_BUFFER_SIZE+1]
next dd ? ;struct GLSpecBuf*
ends
struct GLLight
ambient V4
diffuse V4
specular V4
position V4
spot_direction V3
spot_exponent dd ? ;float
spot_cutoff dd ? ;float
attenuation rd 3 ;float[3]
; precomputed values
cos_spot_cutoff dd ? ;float
norm_spot_direction V3
norm_position V3
; we use a linked list to know which are the enabled lights
enabled dd ? ;int
next dd ? ;struct GLLight*
prev dd ? ;struct GLLight*
ends
offs_ligh_ambient equ 0 ;V4
offs_ligh_diffuse equ 16 ;V4
offs_ligh_specular equ 32 ;V4
offs_ligh_position equ 48 ;V4
offs_ligh_spot_direction equ 64 ;V3
offs_ligh_spot_exponent equ 76 ;dd ?
offs_ligh_spot_cutoff equ 80 ;dd ?
offs_ligh_attenuation equ 84 ;rd 3
offs_ligh_cos_spot_cutoff equ 96 ;dd ?
offs_ligh_norm_spot_direction equ 100 ;V3
offs_ligh_norm_position equ 112 ;V3
offs_ligh_enabled equ 124 ;dd ?
offs_ligh_next equ 128 ;dd ?
offs_ligh_prev equ 132 ;dd ?
struct GLMaterial
emission V4
ambient V4
diffuse V4
specular V4
shininess dd ? ;float
; computed values
shininess_i dd ? ;int
do_specular dd ? ;int
ends
offs_mate_emission equ 0 ;V4
offs_mate_ambient equ 16 ;V4
offs_mate_diffuse equ 32 ;V4
offs_mate_specular equ 48 ;V4
offs_mate_shininess equ 64 ;dd
offs_mate_shininess_i equ 68 ;dd
offs_mate_do_specular equ 72 ;dd
struct GLViewport
xmin dd ? ;int
ymin dd ? ;int
xsize dd ? ;int
ysize dd ? ;int
scale V3
trans V3
updated dd ? ;int
ends
offs_vpor_xmin equ 0
offs_vpor_ymin equ 4
offs_vpor_xsize equ 8
offs_vpor_ysize equ 12
offs_vpor_scale equ 16
offs_vpor_trans equ 28
offs_vpor_updated equ 40
struct GLParamBuffer
ops rd OP_BUFFER_MAX_SIZE ;GLParam[OP_BUFFER_MAX_SIZE]
next dd ? ;struct GLParamBuffer*
ends
struct GLList
first_op_buffer dd ? ;GLParamBuffer*
; /* TODO: extensions for an hash table or a better allocating scheme */
ends
struct GLVertex
edge_flag dd ? ;int
normal V3
coord V4
tex_coord V4
color V4
; computed values
ec V4 ; eye coordinates
pc V4 ; coordinates in the normalized volume
clip_code dd ? ;int ; clip code
zp ZBufferPoint ; integer coordinates for the rasterization
ends
offs_vert_edge_flag equ 0
offs_vert_normal equ 4
offs_vert_coord equ 16
offs_vert_tex_coord equ 32
offs_vert_color equ 48
offs_vert_ec equ 64
offs_vert_pc equ 80
offs_vert_clip_code equ 96
offs_vert_zp equ 100
struct GLImage
pixmap dd ? ;void*
xsize dd ? ;int
ysize dd ? ;int
ends
offs_imag_pixmap equ 0
; textures
TEXTURE_HASH_TABLE_SIZE equ 256 ;должно быть кратное 2, в коде берется остаток от деления (через and быстрее чем div)
struct GLTexture
images rb sizeof.GLImage * MAX_TEXTURE_LEVELS ;GLImage[MAX_TEXTURE_LEVELS]
handle dd ? ;int
next dd ? ;struct GLTexture*
prev dd ? ;struct GLTexture*
ends
offs_text_images equ 0
offs_text_handle equ sizeof.GLImage*MAX_TEXTURE_LEVELS
offs_text_next equ 4+offs_text_handle
offs_text_prev equ 8+offs_text_handle
; shared state
struct GLSharedState
lists dd ? ;GLList**
texture_hash_table dd ? ;GLTexture**
ends
; display context
struct GLContext
; Z buffer
zb dd ? ;ZBuffer*
; lights
lights rb sizeof.GLLight * MAX_LIGHTS ;GLLight[MAX_LIGHTS]
first_light dd ? ;GLLight*
ambient_light_model V4
local_light_model dd ? ;int
lighting_enabled dd ? ;int
light_model_two_side dd ? ;int
; materials
materials rb sizeof.GLMaterial * 2 ;GLMaterial[2]
color_material_enabled dd ? ;int
current_color_material_mode dd ? ;int
current_color_material_type dd ? ;int
; textures
current_texture dd ? ;GLTexture*
texture_2d_enabled dd ? ;int
; shared state
shared_state GLSharedState
; current list
current_op_buffer dd ? ;GLParamBuffer*
current_op_buffer_index dd ? ;int
exec_flag dd ? ;int
compile_flag dd ? ;int
print_flag dd ? ;int
; matrix
matrix_mode dd ? ;int режим активного вида матрицы (один из 3-х: GL_MODELVIEW, GL_PROJECTION, GL_TEXTURE)
matrix_stack rd 3 ;*M4[3] указатель на начало массива матриц
matrix_stack_ptr rd 3 ;*M4[3] указатель на активную матрицу из массива
matrix_stack_depth_max rd 3 ;int[3] максимальное число матриц в массивах matrix_stack
matrix_model_view_inv M4
matrix_model_projection M4
matrix_model_projection_updated dd ? ;int
matrix_model_projection_no_w_transform dd ? ;int
apply_texture_matrix dd ? ;int
; viewport
viewport GLViewport
; current state
polygon_mode_back dd ? ;int
polygon_mode_front dd ? ;int
current_front_face dd ? ;int
current_shade_model dd ? ;int
current_cull_face dd ? ;int
cull_face_enabled dd ? ;int
normalize_enabled dd ? ;int
draw_triangle_front dd ? ;gl_draw_triangle_func
draw_triangle_back dd ? ;gl_draw_triangle_func
; selection
render_mode dd ? ;int
select_buffer dd ? ;unsigned int*
select_size dd ? ;int
select_ptr dd ? ;unsigned int*
select_hit dd ? ;unsigned int*
select_overflow dd ? ;int
select_hits dd ? ;int
; names
name_stack rd MAX_NAME_STACK_DEPTH ;unsigned int[MAX_NAME_STACK_DEPTH]
name_stack_size dd ? ;int
; clear
clear_depth dd ? ;float
clear_color V4
; current vertex state
current_color V4
longcurrent_color rd 3 ;unsigned int[3] ;precomputed integer color
current_normal V4
current_tex_coord V4
current_edge_flag dd ? ;int
; glBegin / glEnd
in_begin dd ? ;int
begin_type dd ? ;int
vertex_n dd ? ;int
vertex_cnt dd ? ;int
vertex_max dd ? ;int
vertex dd ? ;GLVertex*
; opengl 1.1 arrays
vertex_array dd ? ;float*
vertex_array_size dd ? ;int
vertex_array_stride dd ? ;int
normal_array dd ? ;float*
normal_array_stride dd ? ;int
color_array dd ? ;float*
color_array_size dd ? ;int
color_array_stride dd ? ;int
texcoord_array dd ? ;float*
texcoord_array_size dd ? ;int
texcoord_array_stride dd ? ;int
client_states dd ? ;int
; opengl 1.1 polygon offset
offset_factor dd ? ;float
offset_units dd ? ;float
offset_states dd ? ;int
; specular buffer. could probably be shared between contexts,
; but that wouldn't be 100% thread safe
specbuf_first dd ? ;GLSpecBuf*
specbuf_used_counter dd ? ;int
specbuf_num_buffers dd ? ;int
; opaque structure for user's use
opaque dd ? ;void*
; resize viewport function
gl_resize_viewport dd ? ;(struct GLContext *c,int *xsize,int *ysize)
; depth test
depth_test dd ? ;int
ends
offs_cont_s0 equ (4 + sizeof.GLLight * MAX_LIGHTS)
offs_cont_s1 equ (32 + offs_cont_s0 + sizeof.GLMaterial * 2)
offs_cont_s2 equ (228 + offs_cont_s1 + sizeof.GLViewport)
offs_cont_s3 equ (64 + offs_cont_s2 + MAX_NAME_STACK_DEPTH * 4)
offs_cont_zb equ 0 ;ZBuffer*
offs_cont_lights equ 4 ;GLLight[MAX_LIGHTS]
offs_cont_first_light equ offs_cont_s0 ;GLLight*
offs_cont_ambient_light_model equ 4+offs_cont_s0 ;V4
offs_cont_local_light_model equ 20+offs_cont_s0 ;int
offs_cont_lighting_enabled equ 24+offs_cont_s0 ;int
offs_cont_light_model_two_side equ 28+offs_cont_s0 ;int
offs_cont_materials equ 32+offs_cont_s0 ;GLMaterial[2]
offs_cont_color_material_enabled equ offs_cont_s1 ;int
offs_cont_current_color_material_mode equ 4+offs_cont_s1 ;int
offs_cont_current_color_material_type equ 8+offs_cont_s1 ;int
offs_cont_current_texture equ 12+offs_cont_s1 ;GLTexture*
offs_cont_texture_2d_enabled equ 16+offs_cont_s1 ;int
offs_cont_shared_state equ 20+offs_cont_s1 ;GLSharedState
offs_cont_current_op_buffer equ 28+offs_cont_s1 ;GLParamBuffer*
offs_cont_current_op_buffer_index equ 32+offs_cont_s1 ;int
offs_cont_exec_flag equ 36+offs_cont_s1 ;int
offs_cont_compile_flag equ 40+offs_cont_s1 ;int
offs_cont_print_flag equ 44+offs_cont_s1 ;int
offs_cont_matrix_mode equ 48+offs_cont_s1 ;int
offs_cont_matrix_stack equ 52+offs_cont_s1 ;*M4[3]
offs_cont_matrix_stack_ptr equ 64+offs_cont_s1 ;*M4[3]
offs_cont_matrix_stack_depth_max equ 76+offs_cont_s1 ;int[3]
offs_cont_matrix_model_view_inv equ 88+offs_cont_s1 ;M4
offs_cont_matrix_model_projection equ 152+offs_cont_s1 ;M4
offs_cont_matrix_model_projection_updated equ 216+offs_cont_s1 ;int
offs_cont_matrix_model_projection_no_w_transform equ 220+offs_cont_s1 ;int
offs_cont_apply_texture_matrix equ 224+offs_cont_s1 ;int
offs_cont_viewport equ 228+offs_cont_s1 ;GLViewport
offs_cont_polygon_mode_back equ offs_cont_s2 ;int
offs_cont_polygon_mode_front equ 4+offs_cont_s2 ;int
offs_cont_current_front_face equ 8+offs_cont_s2 ;int
offs_cont_current_shade_model equ 12+offs_cont_s2 ;int
offs_cont_current_cull_face equ 16+offs_cont_s2 ;int
offs_cont_cull_face_enabled equ 20+offs_cont_s2 ;int
offs_cont_normalize_enabled equ 24+offs_cont_s2 ;int
offs_cont_draw_triangle_front equ 28+offs_cont_s2 ;gl_draw_triangle_func
offs_cont_draw_triangle_back equ 32+offs_cont_s2 ;gl_draw_triangle_func
offs_cont_render_mode equ 36+offs_cont_s2 ;int
offs_cont_select_buffer equ 40+offs_cont_s2 ;unsigned int*
offs_cont_select_size equ 44+offs_cont_s2 ;int
offs_cont_select_ptr equ 48+offs_cont_s2 ;unsigned int*
offs_cont_select_hit equ 52+offs_cont_s2 ;unsigned int*
offs_cont_select_overflow equ 56+offs_cont_s2 ;int
offs_cont_select_hits equ 60+offs_cont_s2 ;int
offs_cont_name_stack equ 64+offs_cont_s2 ;unsigned int[MAX_NAME_STACK_DEPTH]
offs_cont_name_stack_size equ offs_cont_s3 ;int
offs_cont_clear_depth equ 4+offs_cont_s3 ;float
offs_cont_clear_color equ 8+offs_cont_s3 ;V4
offs_cont_current_color equ 24+offs_cont_s3 ;V4
offs_cont_longcurrent_color equ 40+offs_cont_s3 ;unsigned int[3]
offs_cont_current_normal equ 52+offs_cont_s3 ;V4
offs_cont_current_tex_coord equ 68+offs_cont_s3 ;V4
offs_cont_current_edge_flag equ 84+offs_cont_s3 ;int
offs_cont_in_begin equ 88+offs_cont_s3 ;int
offs_cont_begin_type equ 92+offs_cont_s3 ;int
offs_cont_vertex_n equ 96+offs_cont_s3 ;int
offs_cont_vertex_cnt equ 100+offs_cont_s3 ;int
offs_cont_vertex_max equ 104+offs_cont_s3 ;int
offs_cont_vertex equ 108+offs_cont_s3 ;GLVertex*
offs_cont_vertex_array equ 112+offs_cont_s3 ;float*
offs_cont_vertex_array_size equ 116+offs_cont_s3 ;int
offs_cont_vertex_array_stride equ 120+offs_cont_s3 ;int
offs_cont_normal_array equ 124+offs_cont_s3 ;float*
offs_cont_normal_array_stride equ 128+offs_cont_s3 ;int
offs_cont_color_array equ 132+offs_cont_s3 ;float*
offs_cont_color_array_size equ 136+offs_cont_s3 ;int
offs_cont_color_array_stride equ 140+offs_cont_s3 ;int
offs_cont_texcoord_array equ 144+offs_cont_s3 ;float*
offs_cont_texcoord_array_size equ 148+offs_cont_s3 ;int
offs_cont_texcoord_array_stride equ 152+offs_cont_s3 ;int
offs_cont_client_states equ 156+offs_cont_s3 ;int
offs_cont_offset_factor equ 160+offs_cont_s3 ;float
offs_cont_offset_units equ 164+offs_cont_s3 ;float
offs_cont_offset_states equ 168+offs_cont_s3 ;int
offs_cont_specbuf_first equ 172+offs_cont_s3 ;GLSpecBuf*
offs_cont_specbuf_used_counter equ 176+offs_cont_s3 ;int
offs_cont_specbuf_num_buffers equ 180+offs_cont_s3 ;int
offs_cont_opaque equ 184+offs_cont_s3 ;void*
offs_cont_gl_resize_viewport equ 188+offs_cont_s3 ;(struct GLContext *c,int *xsize,int *ysize)
offs_cont_depth_test equ 192+offs_cont_s3 ;int
align 16
gl_ctx dd ? ;extern GLContext*
align 16
proc gl_get_context
mov eax,[gl_ctx]
ret
endp
; this clip epsilon is needed to avoid some rounding errors after
; several clipping stages
CLIP_EPSILON dd 1.0e-5
align 4
proc gl_clipcode uses ebx, x:dword, y:dword, z:dword, w1:dword
xor ebx,ebx
;ffree st0
;fincstp
fld1
fadd dword[CLIP_EPSILON]
fmul dword[w1]
fcom dword[x]
fstsw ax
sahf
ja @f
or ebx,2
@@:
fcom dword[y]
fstsw ax
sahf
ja @f
or ebx,8
@@:
fcom dword[z]
fstsw ax
sahf
ja @f
or ebx,32
@@:
fchs
fcom dword[x]
fstsw ax
sahf
jbe @f
or ebx,1
@@:
fcom dword[y]
fstsw ax
sahf
jbe @f
or ebx,4
@@:
fcom dword[z]
fstsw ax
sahf
jbe @f
or ebx,16
@@:
mov eax,ebx
if DEBUG ;gl_clipcode
push edi
mov ecx,80
lea edi,[buf_param]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_nl,2
stdcall dbg_print,f_clipcode,buf_param
pop edi
end if
ret
endp
;input:
; rf,gf,bf - значения float
; ri,gi,bi - адреса куда будут записаны rf,gf,bf преобразованые в int
align 4
proc RGBFtoRGBI uses eax, rf:dword,gf:dword,bf:dword, ri:dword,gi:dword,bi:dword
locals
s dd ?
endl
mov dword[s],(ZB_POINT_RED_MAX - ZB_POINT_RED_MIN)
fild dword[s]
fmul dword[rf]
mov eax,[ri]
fistp dword[eax]
add dword[eax],ZB_POINT_RED_MIN
mov dword[s],(ZB_POINT_GREEN_MAX - ZB_POINT_GREEN_MIN)
fild dword[s]
fmul dword[gf]
mov eax,[gi]
fistp dword[eax]
add dword[eax],ZB_POINT_GREEN_MIN
;bi = (unsigned int) (bf * (ZB_POINT_BLUE_MAX - ZB_POINT_BLUE_MIN) + ZB_POINT_BLUE_MIN);
mov dword[s],(ZB_POINT_BLUE_MAX - ZB_POINT_BLUE_MIN)
fild dword[s]
fmul dword[bf]
mov eax,[bi]
fistp dword[eax]
add dword[eax],ZB_POINT_BLUE_MIN
ret
endp

View File

@ -0,0 +1,164 @@
align 4
proc ZB_plot uses eax ebx ecx edx edi, zb:dword, p:dword
mov eax,[zb]
mov ebx,[p]
mov ecx,[ebx+offs_zbup_y]
imul ecx,[eax+offs_zbuf_xsize]
add ecx,[ebx+offs_zbup_x]
add ecx,[eax+offs_zbuf_zbuf]
mov edx,[eax+offs_zbuf_linesize]
imul edx,[ebx+offs_zbup_y]
mov edi,[ebx+offs_zbup_x]
imul edi,PSZB
add edx,edi
add edx,[eax+offs_zbuf_pbuf]
mov edi,[ebx+offs_zbup_z]
shr edi,ZB_POINT_Z_FRAC_BITS
cmp edi,[ecx]
jl .end_f
if TGL_FEATURE_RENDER_BITS eq 24
mov eax,[ebx+offs_zbup_r]
mov byte[edx],ah
mov eax,[ebx+offs_zbup_g]
mov byte[edx+1],ah
mov eax,[ebx+offs_zbup_b]
mov byte[edx+2],ah
else
; *pp = RGB_TO_PIXEL(p->r, p->g, p->b);
end if
mov [ecx],edi
.end_f:
ret
endp
INTERP_Z equ 1
align 4
proc ZB_line_flat_z, zb:dword, p1:dword, p2:dword, color:dword
include 'zline.inc'
; line with color interpolation
INTERP_Z equ 1
align 4
proc ZB_line_interp_z, zb:dword, p1:dword, p2:dword
include 'zline_r.inc'
; no Z interpolation
align 4
proc ZB_line_flat, zb:dword, p1:dword, p2:dword, color:dword
include 'zline.inc'
align 4
proc ZB_line_interp, zb:dword, p1:dword, p2:dword
include 'zline_r.inc'
align 4
proc ZB_line_z uses eax ebx ecx, zb:dword, p1:dword, p2:dword
if DEBUG ;ZB_line_z
push edi
mov ecx,80
mov eax,[p1]
mov eax,[eax+offs_zbup_x]
lea edi,[buf_param]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_zp_sp,2
stdcall str_len,edi
add edi,eax
sub ecx,eax
mov eax,[p1]
mov eax,[eax+offs_zbup_y]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_zp_sp,2
stdcall str_len,edi
add edi,eax
sub ecx,eax
mov eax,[p2]
mov eax,[eax+offs_zbup_x]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_zp_sp,2
stdcall str_len,edi
add edi,eax
sub ecx,eax
mov eax,[p2]
mov eax,[eax+offs_zbup_y]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_nl,2
stdcall dbg_print,f_zbz,buf_param
pop edi
end if
mov ebx,[p1]
RGB_TO_PIXEL dword[ebx+offs_zbup_r],dword[ebx+offs_zbup_g],dword[ebx+offs_zbup_b]
mov ecx,eax
mov ebx,[p2]
RGB_TO_PIXEL dword[ebx+offs_zbup_r],dword[ebx+offs_zbup_g],dword[ebx+offs_zbup_b]
; choose if the line should have its color interpolated or not
cmp ecx,eax
jne .els
stdcall ZB_line_flat_z, dword[zb], dword[p1], ebx, ecx
jmp @f
.els:
stdcall ZB_line_interp_z, dword[zb], dword[p1], ebx
@@:
ret
endp
align 4
proc ZB_line uses eax ebx ecx, zb:dword, p1:dword, p2:dword
if DEBUG ;ZB_line
push edi
mov ecx,80
mov eax,[p1]
mov eax,[eax+offs_zbup_x]
lea edi,[buf_param]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_zp_sp,2
stdcall str_len,edi
add edi,eax
sub ecx,eax
mov eax,[p1]
mov eax,[eax+offs_zbup_y]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_zp_sp,2
stdcall str_len,edi
add edi,eax
sub ecx,eax
mov eax,[p2]
mov eax,[eax+offs_zbup_x]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_zp_sp,2
stdcall str_len,edi
add edi,eax
sub ecx,eax
mov eax,[p2]
mov eax,[eax+offs_zbup_y]
stdcall convert_int_to_str,ecx
stdcall str_n_cat,edi,txt_nl,2
stdcall dbg_print,f_zb,buf_param
pop edi
end if
mov ebx,[p1]
RGB_TO_PIXEL dword[ebx+offs_zbup_r],dword[ebx+offs_zbup_g],dword[ebx+offs_zbup_b]
mov ecx,eax
mov ebx,[p2]
RGB_TO_PIXEL dword[ebx+offs_zbup_r],dword[ebx+offs_zbup_g],dword[ebx+offs_zbup_b]
; choose if the line should have its color interpolated or not
cmp ecx,eax
jne .els
stdcall ZB_line_flat, dword[zb], dword[p1], ebx, ecx
jmp @f
.els:
stdcall ZB_line_interp, dword[zb], dword[p1], ebx
@@:
ret
endp

View File

@ -0,0 +1,226 @@
;PUTPIXEL -> RGBPIXEL
locals
n dd ?
d_x dd ?
d_y dd ?
sx dd ? ;ширина буфера в пикселях
pp_inc_1 dd ?
pp_inc_2 dd ?
a dd ? ;register int
if TGL_FEATURE_RENDER_BITS eq 24
r dd ? ;register unsigned int
g dd ?
b dd ?
end if
if INTERP_Z eq 1
pz dd ? ;register unsigned short *
zinc dd ?
z dd ? ;register int
zz dd ?
end if
endl
pushad
mov eax,[p1]
mov ebx,[p2]
mov ecx,[ebx+offs_zbup_y]
cmp [eax+offs_zbup_y], ecx ;if (p1.y > p2.y)
jg @f
jl .end_0 ;if (p1.y != p2.y)
mov ecx,[ebx+offs_zbup_x]
cmp [eax+offs_zbup_x], ecx ;if (p1.x > p2.x)
jle .end_0 ;if (p1.x <= p2.x)
@@: ;if (p1.y > p2.y || (p1.y == p2.y && p1.x > p2.x))
mov [p1],ebx
mov [p2],eax
.end_0:
mov eax,[zb]
mov edx,[eax+offs_zbuf_xsize]
mov [sx],edx
mov ecx,[p1]
mov edi,[eax+offs_zbuf_linesize]
imul edi,[ecx+offs_zbup_y]
mov edx,[ecx+offs_zbup_x]
imul edx,PSZB
add edi,edx
add edi,[eax+offs_zbuf_pbuf] ;edi = (zb.pbuf + zb.linesize*p1.y + p1.x*PSZB)
if INTERP_Z eq 1
mov edx,[ecx+offs_zbup_y]
imul edx,[sx]
add edx,[ecx+offs_zbup_x]
add edx,[eax+offs_zbuf_zbuf]
mov [pz],edx ;pz = zb.zbuf + (p1.y*sx + p1.x)
mov edx,[ecx+offs_zbup_z]
mov [z],edx ;z = p1.z
end if
mov ebx,[p2]
mov eax,[ebx+offs_zbup_x]
sub eax,[ecx+offs_zbup_x]
mov [d_x],eax ;d_x = p2.x - p1.x
mov eax,[ebx+offs_zbup_y]
sub eax,[ecx+offs_zbup_y]
mov [d_y],eax ;d_y = p2.y - p1.y
if TGL_FEATURE_RENDER_BITS eq 24
; for 24 bits, we store the colors in different variables
mov eax,[ebx+offs_zbup_r]
shr eax,8
mov [r],eax ;r = p2.r >> 8
mov eax,[ebx+offs_zbup_g]
shr eax,8
mov [g],eax ;g = p2.g >> 8
mov eax,[ebx+offs_zbup_b]
shr eax,8
mov [b],eax ;b = p2.b >> 8
end if
macro RGBPIXEL
{
if TGL_FEATURE_RENDER_BITS eq 24
mov eax,[r]
mov byte[edi],al
mov eax,[g]
mov byte[edi+1],al
mov eax,[b]
mov byte[edi+2],al
;;; else
;;; mov eax,[color]
;;; mov [edi],eax
end if
}
macro PUTPIXEL
{
if INTERP_Z eq 1
local .end_0
mov eax,[z]
shr eax, ZB_POINT_Z_FRAC_BITS
mov [zz],eax
cmp eax,[pz]
jl .end_0
RGBPIXEL
mov eax,dword[zz]
mov [pz],eax
.end_0:
else ; INTERP_Z
RGBPIXEL
end if ; INTERP_Z
}
macro DRAWLINE d_x,d_y,inc_1,inc_2
{
mov eax,d_x
mov [n],eax
if INTERP_Z eq 1
mov ebx,[p1]
mov eax,[p2]
mov eax,[eax+offs_zbup_z]
sub eax,[ebx+offs_zbup_z]
xor edx,edx
div dword[n]
mov [zinc],eax ;zinc=(p2.z-p1.z)/n
end if
shl dword d_y,1
mov eax, d_y
sub eax, d_x
mov [a],eax ;a=2*d_y-d_x
shl dword d_x,1
mov eax, d_y
sub d_x,eax
mov eax,inc_1
imul eax,PSZB
mov [pp_inc_1],eax ;pp_inc_1 = inc_1*PSZB
mov eax,inc_2
imul eax,PSZB
mov [pp_inc_2],eax ;pp_inc_2 = inc_2*PSZB
local .do_cycle
local .els_0
local .end_0
align 4
.do_cycle:
PUTPIXEL
if INTERP_Z eq 1
mov eax,[zinc]
add [z],eax
end if
cmp dword[a],0
jle .els_0
add edi,[pp_inc_1]
if INTERP_Z eq 1
mov eax,inc_1
add [pz],eax
end if
mov eax,d_x
sub [a],eax
jmp .end_0
.els_0:
add edi,[pp_inc_2]
if INTERP_Z eq 1
mov eax,inc_2
add [pz],eax
end if
mov eax,d_y
add [a],eax
.end_0:
dec dword[n]
cmp dword[n],0
jge .do_cycle
}
; fin macro
mov eax,[d_x]
cmp eax,0
jne .els_0
cmp dword[d_y],0
jne .els_0
;if (d_x==0 && d_y==0)
PUTPIXEL
jmp .end_2
.els_0:
cmp eax,0
jle .els_3
;if (d_x > 0)
mov esi,[sx]
inc esi
cmp eax,[d_y]
jl .els_2
;if (d_x >= d_y)
DRAWLINE [d_x], [d_y], esi, 1
jmp .end_2
.els_2:
DRAWLINE [d_y], [d_x], esi, [sx]
jmp .end_2
.els_3:
xor eax,eax
sub eax,[d_x]
mov [d_x],eax
mov esi,[sx]
dec esi
cmp eax,[d_y]
jl .els_4
;if (d_x >= d_y)
DRAWLINE [d_x], [d_y], esi, -1
jmp .end_2
.els_4:
DRAWLINE [d_y], [d_x], esi, [sx]
.end_2:
popad
ret
endp
restore INTERP_Z
; internal defines
purge DRAWLINE
purge PUTPIXEL
purge RGBPIXEL

View File

@ -0,0 +1,257 @@
;PUTPIXEL -> RGBPIXEL
locals
n dd ?
d_x dd ?
d_y dd ?
sx dd ? ;ширина буфера в пикселях
pp_inc_1 dd ?
pp_inc_2 dd ?
a dd ? ;register int
r dd ? ;register unsigned int
g dd ?
b dd ?
rinc dd ? ;register unsigned int
ginc dd ?
binc dd ?
if INTERP_Z eq 1
pz dd ? ;register unsigned short *
zinc dd ?
z dd ? ;register int
zz dd ?
end if
endl
pushad
mov eax,[p1]
mov ebx,[p2]
mov ecx,[ebx+offs_zbup_y]
cmp [eax+offs_zbup_y], ecx ;if (p1.y > p2.y)
jg @f
jl .end_0 ;if (p1.y != p2.y)
mov ecx,[ebx+offs_zbup_x]
cmp [eax+offs_zbup_x], ecx ;if (p1.x > p2.x)
jle .end_0 ;if (p1.x <= p2.x)
@@: ;if (p1.y > p2.y || (p1.y == p2.y && p1.x > p2.x))
mov [p1],ebx
mov [p2],eax
.end_0:
mov eax,[zb]
mov edx,[eax+offs_zbuf_xsize]
mov [sx],edx
mov ecx,[p1]
mov edi,[eax+offs_zbuf_linesize]
imul edi,[ecx+offs_zbup_y]
mov edx,[ecx+offs_zbup_x]
imul edx,PSZB
add edi,edx
add edi,[eax+offs_zbuf_pbuf] ;edi = (zb.pbuf + zb.linesize*p1.y + p1.x*PSZB)
if INTERP_Z eq 1
mov edx,[ecx+offs_zbup_y]
imul edx,[sx]
add edx,[ecx+offs_zbup_x]
add edx,[eax+offs_zbuf_zbuf]
mov [pz],edx ;pz = zb.zbuf + (p1.y*sx + p1.x)
mov edx,[ecx+offs_zbup_z]
mov [z],edx ;z = p1.z
end if
mov ebx,[p2]
mov eax,[ebx+offs_zbup_x]
sub eax,[ecx+offs_zbup_x]
mov [d_x],eax ;d_x = p2.x - p1.x
mov eax,[ebx+offs_zbup_y]
sub eax,[ecx+offs_zbup_y]
mov [d_y],eax ;d_y = p2.y - p1.y
mov eax,[ecx+offs_zbup_r]
shl eax,8
mov [r],eax ;r = p1.r << 8
mov eax,[ecx+offs_zbup_g]
shl eax,8
mov [g],eax ;g = p1.g << 8
mov eax,[ecx+offs_zbup_b]
shl eax,8
mov [b],eax ;b = p1.b << 8
macro RGBPIXEL
{
if TGL_FEATURE_RENDER_BITS eq 24
mov eax,[r]
shr eax,16
mov byte[edi],al
mov eax,[g]
shr eax,16
mov byte[edi+1],al
mov eax,[b]
shr eax,16
mov byte[edi+2],al
;;; else
;*pp = RGB_TO_PIXEL(r >> 8,g >> 8,b >> 8)
end if
}
macro PUTPIXEL
{
if INTERP_Z eq 1
local .end_0
mov eax,[z]
shr eax, ZB_POINT_Z_FRAC_BITS
mov [zz],eax
cmp eax,[pz]
jl .end_0
RGBPIXEL
mov eax,dword[zz]
mov [pz],eax
.end_0:
else ; INTERP_Z
RGBPIXEL
end if ; INTERP_Z
}
macro DRAWLINE d_x,d_y,inc_1,inc_2
{
mov eax,d_x
mov [n],eax
mov ebx,[p1]
mov ecx,[p2]
if INTERP_Z eq 1
mov eax,[ecx+offs_zbup_z]
sub eax,[ebx+offs_zbup_z]
xor edx,edx
div dword[n]
mov [zinc],eax ;zinc=(p2.z-p1.z)/n
end if
;ebx=&p1, ecx=&p2
mov eax,[ecx+offs_zbup_r]
sub eax,[ebx+offs_zbup_r]
shl eax,8
xor edx,edx
div dword[n]
mov [rinc],eax ;rinc=((p2.r-p1.r)<<8)/n
mov eax,[ecx+offs_zbup_g]
sub eax,[ebx+offs_zbup_g]
shl eax,8
xor edx,edx
div dword[n]
mov [ginc],eax ;ginc=((p2.g-p1.g)<<8)/n
mov eax,[ecx+offs_zbup_b]
sub eax,[ebx+offs_zbup_b]
shl eax,8
xor edx,edx
div dword[n]
mov [binc],eax ;binc=((p2.b-p1.b)<<8)/n
shl dword d_y,1
mov eax, d_y
sub eax, d_x
mov [a],eax ;a=2*d_y-d_x
shl dword d_x,1
mov eax, d_y
sub d_x,eax
mov eax,inc_1
imul eax,PSZB
mov [pp_inc_1],eax ;pp_inc_1 = inc_1*PSZB
mov eax,inc_2
imul eax,PSZB
mov [pp_inc_2],eax ;pp_inc_2 = inc_2*PSZB
local .do_cycle
local .els_0
local .end_0
align 4
.do_cycle:
PUTPIXEL
if INTERP_Z eq 1
mov eax,[zinc]
add [z],eax
end if
mov eax,[rinc]
add [r],eax
mov eax,[ginc]
add [g],eax
mov eax,[binc]
add [b],eax
cmp dword[a],0
jle .els_0
add edi,[pp_inc_1]
if INTERP_Z eq 1
mov eax,inc_1
add [pz],eax
end if
mov eax,d_x
sub [a],eax
jmp .end_0
.els_0:
add edi,[pp_inc_2]
if INTERP_Z eq 1
mov eax,inc_2
add [pz],eax
end if
mov eax,d_y
add [a],eax
.end_0:
dec dword[n]
cmp dword[n],0
jge .do_cycle
}
; fin macro
mov eax,[d_x]
cmp eax,0
jne .els_0
cmp dword[d_y],0
jne .els_0
;if (d_x==0 && d_y==0)
PUTPIXEL
jmp .end_2
.els_0:
cmp eax,0
jle .els_3
;if (d_x > 0)
mov esi,[sx]
inc esi
cmp eax,[d_y]
jl .els_2
;if (d_x >= d_y)
DRAWLINE [d_x], [d_y], esi, 1
jmp .end_2
.els_2:
DRAWLINE [d_y], [d_x], esi, [sx]
jmp .end_2
.els_3:
xor eax,eax
sub eax,[d_x]
mov [d_x],eax
mov esi,[sx]
dec esi
cmp eax,[d_y]
jl .els_4
;if (d_x >= d_y)
DRAWLINE [d_x], [d_y], esi, -1
jmp .end_2
.els_4:
DRAWLINE [d_y], [d_x], esi, [sx]
.end_2:
popad
ret
endp
restore INTERP_Z
; internal defines
purge DRAWLINE
purge PUTPIXEL
purge RGBPIXEL

View File

@ -0,0 +1,428 @@
; Some simple mathematical functions. Don't look for some logic in
; the function names :-)
; ******* Gestion des matrices 4x4 ******
align 4
proc gl_M4_Id uses eax ecx edi, a:dword
mov edi,[a]
add edi,4
mov ecx,14
mov eax,0.0
rep stosd
mov eax,1.0
stosd
mov edi,[a]
stosd
add edi,16
stosd
add edi,16
stosd
ret
endp
align 4
proc gl_M4_IsId uses ebx ecx, a:dword
mov eax,[a]
xor ebx,ebx
xor ecx,ecx
.cycle_01:
fld dword[eax]
cmp ecx,ebx
je .once
ftst ;ñðàâíåíèå ñ 0.0
fstsw ax
sahf
je @f
jmp .not_1 ;åñëè äèàãîíàëüíûå ÷èñëà íå ðàâíû 0.0 ìàòðèöà íå åäèíè÷íàÿ
.once:
fld1
fcomp st1 ;ñðàâíåíèå ñ 1.0
fstsw ax
test ah,0x40
je .not_1 ;åñëè íå ðàâíî 1.0 ìàòðèöà íå åäèíè÷íàÿ
@@:
add eax,4
inc ebx
btr ebx,2
jnc .cycle_01
inc ecx
bt ecx,2 ;ïðîâåðÿåì ðàâåíñòâî ecx==4
jnc .cycle_01
mov eax,1
jmp @f
.not_1:
xor eax,eax
@@:
ret
endp
align 4
proc gl_M4_Mul, c:dword,a:dword,b:dword
pushad
mov edx,[c]
xor eax,eax
.cycle_0: ;i
xor ebx,ebx
.cycle_1: ;j
finit
fldz ;sum=0
xor ecx,ecx
M4_reg edi,[a],eax,0
.cycle_2: ;k
fld dword[edi]
add edi,4
M4_reg esi,[b],ecx,ebx
fmul dword[esi]
fadd st0,st1 ;sum += a[i][k] * b[k][j]
inc ecx
cmp ecx,4
jl .cycle_2
fstp dword[edx] ;c[i][j] = sum
add edx,4
inc ebx
cmp ebx,4
jl .cycle_1
inc eax
cmp eax,4
jl .cycle_0
finit
if DEBUG ;gl_M4_Mul
stdcall dbg_print,f_m4m,txt_nl
stdcall gl_print_matrix,[c],4
stdcall dbg_print,txt_sp,txt_nl
end if
popad
ret
endp
; c=c*a
align 4
proc gl_M4_MulLeft, c:dword,b:dword
locals
i dd ?
a M4
endl
pushad
mov ecx,16
mov esi,[c]
mov edi,ebp
sub edi,sizeof.M4
rep movsd ;êîïèðîâàíèå ìàòðèö [a]=[c]
mov edx,[c]
mov dword[i],0
.cycle_0: ;i
xor ebx,ebx
.cycle_1: ;j
finit
fldz ;sum=0
xor ecx,ecx
mov eax,ebp
sub eax,sizeof.M4
M4_reg edi,eax,dword[i],0
.cycle_2: ;k
fld dword[edi]
add edi,4
M4_reg esi,[b],ecx,ebx
fmul dword[esi]
fadd st0,st1 ;sum += a[i][k] * b[k][j]
inc ecx
add eax,4
cmp ecx,4
jl .cycle_2
fstp dword[edx] ;c[i][j] = sum
add edx,4
inc ebx
cmp ebx,4
jl .cycle_1
inc dword[i]
cmp dword[i],4
jl .cycle_0
finit
if DEBUG ;gl_M4_MulLeft
stdcall dbg_print,f_m4ml,txt_nl
stdcall gl_print_matrix,[c],4
stdcall dbg_print,txt_sp,txt_nl
end if
popad
ret
endp
align 4
proc gl_M4_Move uses ecx edi esi, a:dword,b:dword
mov edi,[a]
mov esi,[b]
mov ecx,sizeof.M4/4
rep movsd
ret
endp
align 4
proc gl_MoveV3 uses edi esi, a:dword,b:dword
mov edi,[a]
mov esi,[b]
movsd
movsd
movsd
ret
endp
;void gl_MulM4V3(V3 *a,M4 *b,V3 *c)
;{
; a->X=b->m[0][0]*c->X+b->m[0][1]*c->Y+b->m[0][2]*c->Z+b->m[0][3];
; a->Y=b->m[1][0]*c->X+b->m[1][1]*c->Y+b->m[1][2]*c->Z+b->m[1][3];
; a->Z=b->m[2][0]*c->X+b->m[2][1]*c->Y+b->m[2][2]*c->Z+b->m[2][3];
;}
;void gl_MulM3V3(V3 *a,M4 *b,V3 *c)
;{
; a->X=b->m[0][0]*c->X+b->m[0][1]*c->Y+b->m[0][2]*c->Z;
; a->Y=b->m[1][0]*c->X+b->m[1][1]*c->Y+b->m[1][2]*c->Z;
; a->Z=b->m[2][0]*c->X+b->m[2][1]*c->Y+b->m[2][2]*c->Z;
;}
;void gl_M4_MulV4(V4 *a,M4 *b,V4 *c)
;{
; a->X=b->m[0][0]*c->X+b->m[0][1]*c->Y+b->m[0][2]*c->Z+b->m[0][3]*c->W;
; a->Y=b->m[1][0]*c->X+b->m[1][1]*c->Y+b->m[1][2]*c->Z+b->m[1][3]*c->W;
; a->Z=b->m[2][0]*c->X+b->m[2][1]*c->Y+b->m[2][2]*c->Z+b->m[2][3]*c->W;
; a->W=b->m[3][0]*c->X+b->m[3][1]*c->Y+b->m[3][2]*c->Z+b->m[3][3]*c->W;
;}
; transposition of a 4x4 matrix
align 4
proc gl_M4_Transpose uses eax ecx edx, a:dword, b:dword
mov eax,[a]
mov ecx,[b]
mov edx,[ecx]
mov [eax],edx
mov edx,[ecx+0x10]
mov [eax+0x4],edx
mov edx,[ecx+0x20]
mov [eax+0x8],edx
mov edx,[ecx+0x30]
mov [eax+0x0c],edx
mov edx,[ecx+0x4]
mov [eax+0x10],edx
mov edx,[ecx+0x14]
mov [eax+0x14],edx
mov edx,[ecx+0x24]
mov [eax+0x18],edx
mov edx,[ecx+0x34]
mov [eax+0x1c],edx
mov edx,[ecx+0x8]
mov [eax+0x20],edx
mov edx,[ecx+0x18]
mov [eax+0x24],edx
mov edx,[ecx+0x28]
mov [eax+0x28],edx
mov edx,[ecx+0x38]
mov [eax+0x2c],edx
mov edx,[ecx+0x0c]
mov [eax+0x30],edx
mov edx,[ecx+0x1c]
mov [eax+0x34],edx
mov edx,[ecx+0x2c]
mov [eax+0x38],edx
mov edx,[ecx+0x3c]
mov [eax+0x3c],edx
ret
endp
;/* inversion of an orthogonal matrix of type Y=M.X+P */
;void gl_M4_InvOrtho(M4 *a,M4 b)
;{
; int i,j;
; float s;
; for(i=0;i<3;i++)
; for(j=0;j<3;j++) a->m[i][j]=b.m[j][i];
; a->m[3][0]=0.0; a->m[3][1]=0.0; a->m[3][2]=0.0; a->m[3][3]=1.0;
; for(i=0;i<3;i++) {
; s=0;
; for(j=0;j<3;j++) s-=b.m[j][i]*b.m[j][3];
; a->m[i][3]=s;
; }
;}
;/* Inversion of a general nxn matrix.
; Note : m is destroyed */
align 4
proc Matrix_Inv uses ecx, r:dword, m:dword, n:dword ;(float *r,float *m,int n)
; int i,j,k,l;
; float max,tmp,t;
; /* identitée dans r */
; for(i=0;i<n*n;i++) r[i]=0;
; for(i=0;i<n;i++) r[i*n+i]=1;
; for(j=0;j<n;j++) {
; /* recherche du nombre de plus grand module sur la colonne j */
; max=m[j*n+j];
; k=j;
; for(i=j+1;i<n;i++)
; if (fabs(m[i*n+j])>fabs(max)) {
; k=i;
; max=m[i*n+j];
; }
; /* non intersible matrix */
; if (max==0) return 1;
; /* permutation des lignes j et k */
; if (k!=j) {
; for(i=0;i<n;i++) {
; tmp=m[j*n+i];
; m[j*n+i]=m[k*n+i];
; m[k*n+i]=tmp;
;
; tmp=r[j*n+i];
; r[j*n+i]=r[k*n+i];
; r[k*n+i]=tmp;
; }
; }
; /* multiplication de la ligne j par 1/max */
; max=1/max;
; for(i=0;i<n;i++) {
; m[j*n+i]*=max;
; r[j*n+i]*=max;
; }
; for(l=0;l<n;l++) if (l!=j) {
; t=m[l*n+j];
; for(i=0;i<n;i++) {
; m[l*n+i]-=m[j*n+i]*t;
; r[l*n+i]-=r[j*n+i]*t;
; }
; }
; }
; return 0;
ret
endp
; inversion of a 4x4 matrix
align 4
proc gl_M4_Inv uses eax ecx edi esi, a:dword, b:dword
locals
tmp M4
endl
mov esi,[b]
mov edi,ebp
sub edi,sizeof.M4 ;edi = &tmp
mov ecx,16
rep movsd
sub edi,sizeof.M4 ;edi = &tmp
stdcall Matrix_Inv,[a],edi,4 ;ïîðòèò eax ïîòîìó â uses åñòü eax
ret
endp
align 4
proc gl_M4_Rotate uses eax ecx, a:dword,t:dword,u:dword
locals
s dd ? ;float
c dd ? ;float
v dd ? ;int
w dd ? ;int
endl
mov eax,[u]
inc eax
mov dword [v],eax
cmp dword [v],2
jle @f
mov dword [v],0
@@:
mov eax,[v]
inc eax
mov dword [w],eax
cmp dword [w],2
jle @f
mov dword [w],0
@@:
fld dword [t]
fsin
fstp dword [s]
fld dword [t]
fcos
fstp dword [c]
stdcall gl_M4_Id,[a]
M4_reg ecx,[a],[v],[v]
mov eax,[c]
mov [ecx],eax
M4_reg ecx,[a],[v],[w]
fld dword [s]
fchs
fstp dword [ecx]
M4_reg ecx,[a],[w],[v]
mov eax,[s]
mov [ecx],eax
M4_reg ecx,[a],[w],[w]
mov eax,[c]
mov [ecx],eax
ret
endp
; inverse of a 3x3 matrix
;void gl_M3_Inv(M3 *a,M3 *m)
;{
; float det;
; det = m->m[0][0]*m->m[1][1]*m->m[2][2]-m->m[0][0]*m->m[1][2]*m->m[2][1]-
; m->m[1][0]*m->m[0][1]*m->m[2][2]+m->m[1][0]*m->m[0][2]*m->m[2][1]+
; m->m[2][0]*m->m[0][1]*m->m[1][2]-m->m[2][0]*m->m[0][2]*m->m[1][1];
; a->m[0][0] = (m->m[1][1]*m->m[2][2]-m->m[1][2]*m->m[2][1])/det;
; a->m[0][1] = -(m->m[0][1]*m->m[2][2]-m->m[0][2]*m->m[2][1])/det;
; a->m[0][2] = -(-m->m[0][1]*m->m[1][2]+m->m[0][2]*m->m[1][1])/det;
; a->m[1][0] = -(m->m[1][0]*m->m[2][2]-m->m[1][2]*m->m[2][0])/det;
; a->m[1][1] = (m->m[0][0]*m->m[2][2]-m->m[0][2]*m->m[2][0])/det;
; a->m[1][2] = -(m->m[0][0]*m->m[1][2]-m->m[0][2]*m->m[1][0])/det;
; a->m[2][0] = (m->m[1][0]*m->m[2][1]-m->m[1][1]*m->m[2][0])/det;
; a->m[2][1] = -(m->m[0][0]*m->m[2][1]-m->m[0][1]*m->m[2][0])/det;
; a->m[2][2] = (m->m[0][0]*m->m[1][1]-m->m[0][1]*m->m[1][0])/det;
;}
; vector arithmetic
;int gl_V3_Norm(V3 *a)
;{
; float n;
; n=sqrt(a->X*a->X+a->Y*a->Y+a->Z*a->Z);
; if (n==0) return 1;
; a->X/=n;
; a->Y/=n;
; a->Z/=n;
; return 0;
;}
macro gl_V3_New p_mem, x, y, z
{
mov dword[p_mem],x
mov dword[p_mem+4],y
mov dword[p_mem+8],z
}
macro gl_V4_New p_mem, x, y, z, w
{
mov dword[p_mem],x
mov dword[p_mem+4],y
mov dword[p_mem+8],z
mov dword[p_mem+12],w
}

View File

@ -0,0 +1,42 @@
; Matrix & Vertex
align 4
an180f dd 180.0 ;константа для вычисления углов
struct M4
m rd 4*4 ;float[4][4]
ends
; макрос облегчающий доступ к элементам матрицы M4
; для доступа к элементам 1-й индекс множится на 16, 2-й на 4:
; m[i1*16][i2*4], потом все пишется в регистр reg:
; reg <-- m[i1][i2]
macro M4_reg reg,m,i1,i2
{
mov reg,i1 ;1-й индекс
if i2 eq 0
shl reg,4
else
shl reg,2
add reg,i2 ;2-й индекс
shl reg,2
end if
add reg,m ;указатель на начало матрицы
}
struct M3
m rd 3*3 ;float[3][3]
ends
struct M34
m rd 3*4 ;float[3][4]
ends
struct V3
v rd 3 ;float[3]
ends
struct V4
v rd 4 ;float[4]
ends

View File

@ -0,0 +1,344 @@
INTERP_Z equ 1
macro DRAW_INIT
{
if TGL_FEATURE_RENDER_BITS eq 24
mov ecx,[p2]
mov eax,[ecx+offs_zbup_r]
shr eax,8
mov [colorR],eax ;colorR=p2.r>>8
mov eax,[ecx+offs_zbup_g]
shr eax,8
mov [colorG],eax ;colorG=p2.g>>8
mov eax,[ecx+offs_zbup_b]
shr eax,8
mov [colorB],eax ;colorB=p2.b>>8
else
; color=RGB_TO_PIXEL(p2->r,p2->g,p2->b);
end if
}
macro PUT_PIXEL _a
{
; zz=z >> ZB_POINT_Z_FRAC_BITS;
; if (zz >= pz[_a]) {
if TGL_FEATURE_RENDER_BITS eq 24
; pp[3 * _a]=colorR;
; pp[3 * _a + 1]=colorG;
; pp[3 * _a + 2]=colorB;
; pz[_a]=zz;
else
; pp[_a]=color;
; pz[_a]=zz;
end if
; }
; z+=dzdx;
}
align 4
proc ZB_fillTriangleFlat, zb:dword, p0:dword, p1:dword, p2:dword
locals
if TGL_FEATURE_RENDER_BITS eq 24
colorR db ?
colorG db ?
colorB db ? ;unsigned char
else
color dd ? ;int
end if
include 'ztriangle.inc'
ret
endp
;
; Smooth filled triangle.
; The code below is very tricky :)
;
INTERP_Z equ 1
INTERP_RGB equ 1
macro DRAW_INIT
{
if TGL_FEATURE_RENDER_BITS eq 16
; _drgbdx=((drdx / (1<<6)) << 22) & 0xFFC00000;
; _drgbdx|=(dgdx / (1<<5)) & 0x000007FF;
; _drgbdx|=((dbdx / (1<<7)) << 12) & 0x001FF000;
end if
}
macro PUT_PIXEL _a
{
; zz=z >> ZB_POINT_Z_FRAC_BITS;
if TGL_FEATURE_RENDER_BITS eq 24
; if (zz >= pz[_a]) {
; pp[3 * _a]=or1 >> 8;
; pp[3 * _a + 1]=og1 >> 8;
; pp[3 * _a + 2]=ob1 >> 8;
; pz[_a]=zz;
; }
; z+=dzdx;
; og1+=dgdx;
; or1+=drdx;
; ob1+=dbdx;
elseif TGL_FEATURE_RENDER_BITS eq 16
; if (zz >= pz[_a]) {
; tmp=rgb & 0xF81F07E0;
; pp[_a]=tmp | (tmp >> 16);
; pz[_a]=zz;
; }
; z+=dzdx;
; rgb=(rgb+drgbdx) & ( ~ 0x00200800);
else
; if (zz >= pz[_a]) {
; pp[_a] = RGB_TO_PIXEL(or1, og1, ob1);
; pz[_a]=zz;
; }
; z+=dzdx;
; og1+=dgdx;
; or1+=drdx;
; ob1+=dbdx;
end if
}
macro DRAW_LINE
{
if TGL_FEATURE_RENDER_BITS eq 16
; register unsigned short *pz;
; register PIXEL *pp;
; register unsigned int tmp,z,zz,rgb,drgbdx;
; register int n;
; n=(x2 >> 16) - x1;
; pp=pp1+x1;
; pz=pz1+x1;
; z=z1;
; rgb=(r1 << 16) & 0xFFC00000;
; rgb|=(g1 >> 5) & 0x000007FF;
; rgb|=(b1 << 5) & 0x001FF000;
; drgbdx=_drgbdx;
; while (n>=3) {
; PUT_PIXEL(0);
; PUT_PIXEL(1);
; PUT_PIXEL(2);
; PUT_PIXEL(3);
; pz+=4;
; pp+=4;
; n-=4;
; }
; while (n>=0) {
; PUT_PIXEL(0);
; pz+=1;
; pp+=1;
; n-=1;
; }
end if
if TGL_FEATURE_RENDER_BITS eq 24
; register unsigned short *pz;
; register PIXEL *pp;
; register unsigned int s,t,z,zz;
; register int n,dsdx,dtdx;
; float sz,tz,fz,zinv;
; n=(x2>>16)-x1;
; fz=(float)z1;
; zinv=1.0 / fz;
; pp=(pp1 + x1 * PSZB);
; pz=pz1+x1;
; z=z1;
; sz=sz1;
; tz=tz1;
; while (n>=(NB_INTERP-1)) {
; {
; float ss,tt;
; ss=(sz * zinv);
; tt=(tz * zinv);
; s=(int) ss;
; t=(int) tt;
; dsdx= (int)( (dszdx - ss*fdzdx)*zinv );
; dtdx= (int)( (dtzdx - tt*fdzdx)*zinv );
; fz+=fndzdx;
; zinv=1.0 / fz;
; }
; PUT_PIXEL(0);
; PUT_PIXEL(1);
; PUT_PIXEL(2);
; PUT_PIXEL(3);
; PUT_PIXEL(4);
; PUT_PIXEL(5);
; PUT_PIXEL(6);
; PUT_PIXEL(7);
; pz+=NB_INTERP;
; pp=(pp + NB_INTERP * PSZB);
; n-=NB_INTERP;
; sz+=ndszdx;
; tz+=ndtzdx;
; }
; {
; float ss,tt;
; ss=(sz * zinv);
; tt=(tz * zinv);
; s=(int) ss;
; t=(int) tt;
; dsdx= (int)( (dszdx - ss*fdzdx)*zinv );
; dtdx= (int)( (dtzdx - tt*fdzdx)*zinv );
; }
; while (n>=0) {
; PUT_PIXEL(0);
; pz+=1;
; pp=(PIXEL *)((char *)pp + PSZB);
; n-=1;
; }
end if
}
align 4
proc ZB_fillTriangleSmooth, zb:dword, p0:dword, p1:dword, p2:dword
locals
if TGL_FEATURE_RENDER_BITS eq 16
_drgbdx dd ? ;int
end if
include 'ztriangle.inc'
ret
endp
align 4
proc ZB_setTexture uses eax ebx, zb:dword, texture:dword
mov eax,[zb]
mov ebx,[texture]
mov dword[eax+offs_zbuf_current_texture],ebx
ret
endp
INTERP_Z equ 1
INTERP_ST equ 1
macro DRAW_INIT
{
; texture=zb->current_texture;
}
macro PUT_PIXEL _a
{
; zz=z >> ZB_POINT_Z_FRAC_BITS;
if TGL_FEATURE_RENDER_BITS eq 24
; unsigned char *ptr;
; if (zz >= pz[_a]) {
; ptr = texture + (((t & 0x3FC00000) | s) >> 14) * 3;
; pp[3 * _a]= ptr[0];
; pp[3 * _a + 1]= ptr[1];
; pp[3 * _a + 2]= ptr[2];
; pz[_a]=zz;
; }
else
; if (zz >= pz[_a]) {
; pp[_a]=texture[((t & 0x3FC00000) | s) >> 14];
; pz[_a]=zz;
; }
end if
; z+=dzdx;
; s+=dsdx;
; t+=dtdx;
}
align 4
proc ZB_fillTriangleMapping, zb:dword, p0:dword, p1:dword, p2:dword
locals
texture dd ? ;PIXEL*
include 'ztriangle.inc'
ret
endp
;
; Texture mapping with perspective correction.
; We use the gradient method to make less divisions.
; TODO: pipeline the division
;
if 1
INTERP_Z equ 1
INTERP_STZ equ 1
NB_INTERP equ 8
macro DRAW_INIT
{
; texture=zb->current_texture;
; fdzdx=(float)dzdx;
; fndzdx=NB_INTERP * fdzdx;
; ndszdx=NB_INTERP * dszdx;
; ndtzdx=NB_INTERP * dtzdx;
}
macro PUT_PIXEL _a
{
; zz=z >> ZB_POINT_Z_FRAC_BITS;
if TGL_FEATURE_RENDER_BITS eq 24
; unsigned char *ptr;
; if (zz >= pz[_a]) {
; ptr = texture + (((t & 0x3FC00000) | (s & 0x003FC000)) >> 14) * 3;
; pp[3 * _a]= ptr[0];
; pp[3 * _a + 1]= ptr[1];
; pp[3 * _a + 2]= ptr[2];
; pz[_a]=zz;
; }
else
; if (zz >= pz[_a]) {
; pp[_a]=*(PIXEL *)((char *)texture+
; (((t & 0x3FC00000) | (s & 0x003FC000)) >> (17 - PSZSH)));
; pz[_a]=zz;
; }
end if
; z+=dzdx;
; s+=dsdx;
; t+=dtdx;
}
align 4
proc ZB_fillTriangleMappingPerspective, zb:dword, p0:dword, p1:dword, p2:dword
locals
; PIXEL *texture;
; float fdzdx,fndzdx,ndszdx,ndtzdx;
include 'ztriangle.inc'
ret
endp
end if
if 0
; slow but exact version (only there for reference, incorrect for 24
; bits)
INTERP_Z equ 1
INTERP_STZ equ 1
macro DRAW_INIT
{
; texture=zb->current_texture;
}
macro PUT_PIXEL _a
{
; float zinv;
; int s,t;
; zz=z >> ZB_POINT_Z_FRAC_BITS;
; if (zz >= pz[_a]) {
; zinv= 1.0 / (float) z;
; s= (int) (sz * zinv);
; t= (int) (tz * zinv);
; pp[_a]=texture[((t & 0x3FC00000) | s) >> 14];
; pz[_a]=zz;
; }
; z+=dzdx;
; sz+=dszdx;
; tz+=dtzdx;
}
align 4
proc ZB_fillTriangleMappingPerspective, zb:dword, p0:dword, p1:dword, p2:dword
locals
texture dd ? ;PIXEL*
include 'ztriangle.inc'
ret
endp
end if

View File

@ -0,0 +1,415 @@
;
; We draw a triangle with various interpolations
;
t dd ? ;ZBufferPoint*
pr1 dd ? ;ZBufferPoint*
pr2 dd ? ;ZBufferPoint*
l1 dd ? ;ZBufferPoint*
l2 dd ? ;ZBufferPoint*
fdx1 dd ?
fdx2 dd ?
fdy1 dd ?
fdy2 dd ?
fz dd ?
d1 dd ?
d2 dd ?
pz1 dd ? ;unsigned short*
pp1 dd ? ;PIXEL*
part dd ?
update_left dd ?
update_right dd ?
nb_lines dd ?
dx1 dd ?
dy1 dd ?
tmp dd ?
dx2 dd ?
dy2 dd ?
error dd ?
derror dd ?
x1 dd ?
dxdy_min dd ?
dxdy_max dd ?
; warning: x2 is multiplied by 2^16
x2 dd ?
dx2dy2 dd ?
if INTERP_Z eq 1
z1 dd ?
dzdx dd ?
dzdy dd ?
dzdl_min dd ?
dzdl_max dd ?
end if
if INTERP_RGB eq 1
r1 dd ? ;int
drdx dd ?
drdy dd ?
drdl_min dd ?
drdl_max dd ?
g1 dd ?
dgdx dd ?
dgdy dd ?
dgdl_min dd ?
dgdl_max dd ?
b1 dd ?
dbdx dd ?
dbdy dd ?
dbdl_min dd ?
dbdl_max dd ?
end if
if INTERP_ST eq 1
;s1 dd ?
dsdx dd ?
dsdy dd ?
dsdl_min dd ?
dsdl_max dd ?
t1 dd ?
dtdx dd ?
dtdy dd ?
dtdl_min dd ?
dtdl_max dd ?
end if
if INTERP_STZ eq 1
sz1 dd ?
dszdx dd ?
dszdy dd ?
dszdl_min dd ?
dszdl_max dd ?
tz1 dd ?
dtzdx dd ?
dtzdy dd ?
dtzdl_min dd ?
dtzdl_max dd ?
end if
endl
; /* we sort the vertex with increasing y */
; if (p1->y < p0->y) {
; t = p0;
; p0 = p1;
; p1 = t;
; }
; if (p2->y < p0->y) {
; t = p2;
; p2 = p1;
; p1 = p0;
; p0 = t;
; } else if (p2->y < p1->y) {
; t = p1;
; p1 = p2;
; p2 = t;
; }
; we compute dXdx and dXdy for all interpolated values
; fdx1 = p1->x - p0->x;
; fdy1 = p1->y - p0->y;
; fdx2 = p2->x - p0->x;
; fdy2 = p2->y - p0->y;
; fz = fdx1 * fdy2 - fdx2 * fdy1;
; if (fz == 0)
; return;
; fz = 1.0 / fz;
; fdx1 *= fz;
; fdy1 *= fz;
; fdx2 *= fz;
; fdy2 *= fz;
if INTERP_Z eq 1
; d1 = p1->z - p0->z;
; d2 = p2->z - p0->z;
; dzdx = (int) (fdy2 * d1 - fdy1 * d2);
; dzdy = (int) (fdx1 * d2 - fdx2 * d1);
end if
if INTERP_RGB eq 1
; d1 = p1->r - p0->r;
; d2 = p2->r - p0->r;
; drdx = (int) (fdy2 * d1 - fdy1 * d2);
; drdy = (int) (fdx1 * d2 - fdx2 * d1);
; d1 = p1->g - p0->g;
; d2 = p2->g - p0->g;
; dgdx = (int) (fdy2 * d1 - fdy1 * d2);
; dgdy = (int) (fdx1 * d2 - fdx2 * d1);
; d1 = p1->b - p0->b;
; d2 = p2->b - p0->b;
; dbdx = (int) (fdy2 * d1 - fdy1 * d2);
; dbdy = (int) (fdx1 * d2 - fdx2 * d1);
end if
if INTERP_ST eq 1
; d1 = p1->s - p0->s;
; d2 = p2->s - p0->s;
; dsdx = (int) (fdy2 * d1 - fdy1 * d2);
; dsdy = (int) (fdx1 * d2 - fdx2 * d1);
; d1 = p1->t - p0->t;
; d2 = p2->t - p0->t;
; dtdx = (int) (fdy2 * d1 - fdy1 * d2);
; dtdy = (int) (fdx1 * d2 - fdx2 * d1);
end if
if INTERP_STZ eq 1
; {
; float zz;
; zz=(float) p0->z;
; p0->sz= (float) p0->s * zz;
; p0->tz= (float) p0->t * zz;
; zz=(float) p1->z;
; p1->sz= (float) p1->s * zz;
; p1->tz= (float) p1->t * zz;
; zz=(float) p2->z;
; p2->sz= (float) p2->s * zz;
; p2->tz= (float) p2->t * zz;
; d1 = p1->sz - p0->sz;
; d2 = p2->sz - p0->sz;
; dszdx = (fdy2 * d1 - fdy1 * d2);
; dszdy = (fdx1 * d2 - fdx2 * d1);
; d1 = p1->tz - p0->tz;
; d2 = p2->tz - p0->tz;
; dtzdx = (fdy2 * d1 - fdy1 * d2);
; dtzdy = (fdx1 * d2 - fdx2 * d1);
; }
end if
; screen coordinates
; pp1 = (PIXEL *) ((char *) zb->pbuf + zb->linesize * p0->y);
; pz1 = zb->zbuf + p0->y * zb->xsize;
DRAW_INIT
; for(part=0;part<2;part++) {
; if (part == 0) {
; if (fz > 0) {
; update_left=1;
; update_right=1;
; l1=p0;
; l2=p2;
; pr1=p0;
; pr2=p1;
; } else {
; update_left=1;
; update_right=1;
; l1=p0;
; l2=p1;
; pr1=p0;
; pr2=p2;
; }
; nb_lines = p1->y - p0->y;
; } else {
; /* second part */
; if (fz > 0) {
; update_left=0;
; update_right=1;
; pr1=p1;
; pr2=p2;
; } else {
; update_left=1;
; update_right=0;
; l1=p1;
; l2=p2;
; }
; nb_lines = p2->y - p1->y + 1;
; }
; compute the values for the left edge
; if (update_left) {
; dy1 = l2->y - l1->y;
; dx1 = l2->x - l1->x;
; if (dy1 > 0)
; tmp = (dx1 << 16) / dy1;
; else
; tmp = 0;
; x1 = l1->x;
; error = 0;
; derror = tmp & 0x0000ffff;
; dxdy_min = tmp >> 16;
; dxdy_max = dxdy_min + 1;
if INTERP_Z eq 1
; z1=l1->z;
; dzdl_min=(dzdy + dzdx * dxdy_min);
; dzdl_max=dzdl_min + dzdx;
end if
if INTERP_RGB eq 1
; r1=l1->r;
; drdl_min=(drdy + drdx * dxdy_min);
; drdl_max=drdl_min + drdx;
; g1=l1->g;
; dgdl_min=(dgdy + dgdx * dxdy_min);
; dgdl_max=dgdl_min + dgdx;
; b1=l1->b;
; dbdl_min=(dbdy + dbdx * dxdy_min);
; dbdl_max=dbdl_min + dbdx;
end if
if INTERP_ST eq 1
; s1=l1->s;
; dsdl_min=(dsdy + dsdx * dxdy_min);
; dsdl_max=dsdl_min + dsdx;
; t1=l1->t;
; dtdl_min=(dtdy + dtdx * dxdy_min);
; dtdl_max=dtdl_min + dtdx;
end if
if INTERP_STZ eq 1
; sz1=l1->sz;
; dszdl_min=(dszdy + dszdx * dxdy_min);
; dszdl_max=dszdl_min + dszdx;
; tz1=l1->tz;
; dtzdl_min=(dtzdy + dtzdx * dxdy_min);
; dtzdl_max=dtzdl_min + dtzdx;
end if
; }
; /* compute values for the right edge */
; if (update_right) {
; dx2 = (pr2->x - pr1->x);
; dy2 = (pr2->y - pr1->y);
; if (dy2>0)
; dx2dy2 = ( dx2 << 16) / dy2;
; else
; dx2dy2 = 0;
; x2 = pr1->x << 16;
; }
; /* we draw all the scan line of the part */
; while (nb_lines>0) {
; nb_lines--;
;#ifndef DRAW_LINE
; /* generic draw line */
; {
; register PIXEL *pp;
; register int n;
if INTERP_Z eq 1
; register unsigned short *pz;
; register unsigned int z,zz;
end if
if INTERP_RGB eq 1
; register unsigned int or1,og1,ob1;
end if
if INTERP_ST eq 1
; register unsigned int s,t;
end if
if INTERP_STZ eq 1
; float sz,tz;
end if
; n=(x2 >> 16) - x1;
; pp=(PIXEL *)((char *)pp1 + x1 * PSZB);
if INTERP_Z eq 1
; pz=pz1+x1;
; z=z1;
end if
if INTERP_RGB eq 1
; or1 = r1;
; og1 = g1;
; ob1 = b1;
end if
if INTERP_ST eq 1
; s=s1;
; t=t1;
end if
if INTERP_STZ eq 1
; sz=sz1;
; tz=tz1;
end if
; while (n>=3) {
; PUT_PIXEL(0);
; PUT_PIXEL(1);
; PUT_PIXEL(2);
; PUT_PIXEL(3);
if INTERP_Z eq 1
; pz+=4;
end if
; pp=(PIXEL *)((char *)pp + 4 * PSZB);
; n-=4;
; }
; while (n>=0) {
; PUT_PIXEL(0);
if INTERP_Z eq 1
; pz+=1;
end if
; pp=(PIXEL *)((char *)pp + PSZB);
; n-=1;
; }
; }
;#else
; DRAW_LINE();
;#endif
;
; /* left edge */
; error+=derror;
; if (error > 0) {
; error-=0x10000;
; x1+=dxdy_max;
if INTERP_Z eq 1
; z1+=dzdl_max;
end if
if INTERP_RGB eq 1
; r1+=drdl_max;
; g1+=dgdl_max;
; b1+=dbdl_max;
end if
if INTERP_ST eq 1
; s1+=dsdl_max;
; t1+=dtdl_max;
end if
if INTERP_STZ eq 1
; sz1+=dszdl_max;
; tz1+=dtzdl_max;
end if
; } else {
; x1+=dxdy_min;
if INTERP_Z eq 1
; z1+=dzdl_min;
end if
if INTERP_RGB eq 1
; r1+=drdl_min;
; g1+=dgdl_min;
; b1+=dbdl_min;
end if
if INTERP_ST eq 1
; s1+=dsdl_min;
; t1+=dtdl_min;
end if
if INTERP_STZ eq 1
; sz1+=dszdl_min;
; tz1+=dtzdl_min;
end if
; }
;
; /* right edge */
; x2+=dx2dy2;
;
; /* screen coordinates */
; pp1=(PIXEL *)((char *)pp1 + zb->linesize);
; pz1+=zb->xsize;
; }
; }
;}
restore INTERP_Z
restore INTERP_RGB
restore INTERP_ST
restore INTERP_STZ
purge DRAW_INIT
purge DRAW_LINE
purge PUT_PIXEL