OcttBitsOfFun/BouncyCubePs1.asm/LIB/3D.INC

5533 lines
170 KiB
Plaintext

.macro LoadXYZ,X,Y,Z ; Load X,Y,Z: X,Y,Z
lw t0,0(a2) ; T0 = X
lw t1,4(a2) ; T1 = Y
lw t2,8(a2) ; T2 = Z
addiu a2,12 ; A2 += 12
Calc3D t0,t1,t2,X,Y,Z
.endmacro
.macro Calc3D,X,Y,Z,XCALC,YCALC,ZCALC ; Calculate X,Y,Z 3D: X,Y,Z,XCalc,YCalc,ZCalc
la a1,Matrix3D ; Load Matrix3D Address
lw t3,0(a1) ; XCalc = (Matrix3D[0] * X) + (Matrix3D[1] * Y) + (Matrix3D[2] * Z) + Matrix3D[3]
lw t4,4(a1)
lw t5,8(a1)
lw t6,12(a1)
mult t3,x
mflo XCALC
mult t4,y
mflo t3
add XCALC,t3
mult t5,z
mflo t3
add XCALC,t3
sll t6,8
add XCALC,t6
lw t3,16(a1) ; YCalc = (Matrix3D[4] * X) + (Matrix3D[5] * Y) + (Matrix3D[6] * Z) + Matrix3D[7]
lw t4,20(a1)
lw t5,24(a1)
lw t6,28(a1)
mult t3,x
mflo YCALC
mult t4,y
mflo t3
add YCALC,t3
mult t5,z
mflo t3
add YCALC,t3
sll t6,8
add YCALC,t6
lw t3,32(a1) ; ZCalc = (Matrix3D[8] * X) + (Matrix3D[9] * Y) + (Matrix3D[10] * Z) + Matrix3D[11]
lw t4,36(a1)
lw t5,40(a1)
lw t6,44(a1)
mult t3,x
mflo ZCALC
mult t4,y
mflo t3
add ZCALC,t3
mult t5,z
mflo t3
add ZCALC,t3
sll t6,8
add ZCALC,t6
Calc2D XCALC,YCALC,ZCALC
.endmacro
.macro Calc2D,X,Y,Z ; Calculate X,Y 2D: X,Y,Z
beqz Z,Skip ; IF (Z <= 0) Skip
sra Z,8 ; Z /= 256 (Delay Slot)
div X,Z ; X = X / Z + (ScreenX / 2)
mflo X
addi X,320/2
div Y,Z ; Y = Y / Z + (ScreenY / 2)
mflo Y
addi Y,240/2
Skip:
.endmacro
.macro CullFace,X1,Y1,X2,Y2,X3,Y3 ; Cull Face Calculation: X1,Y1,X2,Y2,X3,Y3
sub t0,X3,X1 ; T0 = HDX (X3 - X1)
sub t1,Y2,Y1 ; T1 = MDY (Y2 - Y1)
mult t0,t1 ; T0 = HDX * MDY
mflo t0
sub t1,Y3,Y1 ; T1 = HDY (Y3 - Y1)
sub t2,X2,X1 ; T2 = MDX (X2 - X1)
mult t1,t2 ; T1 = HDY * MDX
mflo t1
sub t0,t1 ; T0 = R (HDX * MDY) - (HDY * MDX) Compare To Zero
.endmacro
.macro AverageZTri,Z1,Z2,Z3 ; Average Z Triangle: Z1,Z2,Z3
add t0,Z1,Z2 ; T0 = Z1+Z2
add t0,Z3 ; T0 = Z1+Z2+Z3
.endmacro
.macro AverageZQuad,Z1,Z2,Z3,Z4 ; Average Z Quad: Z1,Z2,Z3,Z4
add t0,Z1,Z2 ; T0 = Z1+Z2
add t0,Z3 ; T0 = Z1+Z2+Z3
add t0,Z4 ; T0 = Z1+Z2+Z3+Z4
.endmacro
.macro Point,START,END ; Point: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X, S1 = 2D Y
sll s1,16 ; Y <<= 16
andi s0,0xFFFF ; X &= 0xFFFF
or s0,s1 ; X |= Y
lw s1,0(a2) ; S1 = Color+Command
addiu a2,4 ; A2 += 4
sw s1,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex)
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro PointZSort,START,END,SORT ; Point Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X, S1 = 2D Y, S2 = 3D Z
sll s1,16 ; Y <<= 16
andi s0,0xFFFF ; X &= 0xFFFF
or s0,s1 ; X |= Y
sw s2,0(v0) ; Store Z To Sort Address
addiu v0,4 ; V0 += 4
lw s1,0(a2) ; S1 = Color+Command
addiu a2,4 ; A2 += 4
sw s1,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s0,0(v0) ; Store Vertex To Sort Address
addiu v0,4 ; V0 += 4
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,12 ; A3 += 12
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,12 ; A2 += 12 (Delay Slot)
subiu a2,12 ; A2 -= 12
li t0,(12/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(8/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
.endmacro
.macro Line,START,END ; Line: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
lw s2,0(a2) ; S2 = Color+Command
addiu a2,4 ; A2 += 4
sw s2,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro LineZSort,START,END,SORT ; Line Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1, S2 = 3D Z1
LoadXYZ s3,s4,s5 ; S3 = 2D X2, S4 = 2D Y2, S5 = 3D Z2
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s4,16 ; Y2 <<= 16
andi s3,0xFFFF ; X2 &= 0xFFFF
or s1,s3,s4 ; X2 |= Y2
add s2,s5 ; Z1 += Z2
sw s2,0(v0) ; Store Z1+Z2 To Sort Address
addiu v0,4 ; V0 += 4
lw s2,0(a2) ; S2 = Color+Command
addiu a2,4 ; A2 += 4
sw s2,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s0,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,16 ; A3 += 16
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,16 ; A2 += 16 (Delay Slot)
subiu a2,16 ; A2 -= 16
li t0,(16/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(12/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
.endmacro
.macro WireTriCullNone,START,END ; Wire Triangle Face Cull None: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
lw s3,0(a2) ; S3 = Color+Command
addiu a2,4 ; A2 += 4
sw s3,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex4)
WRIOW GP0,0x55555555 ; Write GP0 Packet Word (Termination Code)
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro WireTriCullBack,START,END ; Wire Triangle Back Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,4 ; A2 += 4 (Delay Slot)
subiu a2,4 ; A2 -= 4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
lw s3,0(a2) ; S3 = Color+Command
addiu a2,4 ; A2 += 4
sw s3,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex4)
WRIOW GP0,0x55555555 ; Write GP0 Packet Word (Termination Code)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro WireTriCullFront,START,END ; Wire Triangle Front Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,4 ; A2 += 4 (Delay Slot)
subiu a2,4 ; A2 -= 4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
lw s3,0(a2) ; S3 = Color+Command
addiu a2,4 ; A2 += 4
sw s3,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex4)
WRIOW GP0,0x55555555 ; Write GP0 Packet Word (Termination Code)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro WireTriCullNoneZSort,START,END,SORT ; Wire Triangle Face Cull None Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
AverageZTri s0,s1,s2 ; Average Z Triangle: Z1,Z2,Z3
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
li t0,0x55555555 ; T0 = Termination Code
sw t0,0(v0) ; Store Termination Code To Sort Address
addiu v0,4 ; V0 += 4
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,28 ; A3 += 28
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,28 ; A2 += 28 (Delay Slot)
subiu a2,28 ; A2 -= 28
li t0,(28/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(24/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
.endmacro
.macro WireTriCullBackZSort,START,END,SORT ; Wire Triangle Back Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,4 ; A2 += 4 (Delay Slot)
subiu a2,4 ; A2 -= 4
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
AverageZTri s0,s1,s2 ; Average Z Triangle: Z1,Z2,Z3
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
li t0,0x55555555 ; T0 = Termination Code
sw t0,0(v0) ; Store Termination Code To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,28 ; A3 += 28
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,28 ; A2 += 28 (Delay Slot)
subiu a2,28 ; A2 -= 28
li t0,(28/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(24/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro WireTriCullFrontZSort,START,END,SORT ; Wire Triangle Front Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,4 ; A2 += 4 (Delay Slot)
subiu a2,4 ; A2 -= 4
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
AverageZTri s0,s1,s2 ; Average Z Triangle: Z1,Z2,Z3
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
li t0,0x55555555 ; T0 = Termination Code
sw t0,0(v0) ; Store Termination Code To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,28 ; A3 += 28
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,28 ; A2 += 28 (Delay Slot)
subiu a2,28 ; A2 -= 28
li t0,(28/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(24/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro FillTriCullNone,START,END ; Fill Triangle Face Cull None: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
lw s3,0(a2) ; S3 = Color+Command
addiu a2,4 ; A2 += 4
sw s3,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro FillTriCullBack,START,END ; Fill Triangle Back Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,4 ; A2 += 4 (Delay Slot)
subiu a2,4 ; A2 -= 4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
lw s3,0(a2) ; S3 = Color+Command
addiu a2,4 ; A2 += 4
sw s3,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro FillTriCullFront,START,END ; Fill Triangle Front Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,4 ; A2 += 4 (Delay Slot)
subiu a2,4 ; A2 -= 4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
lw s3,0(a2) ; S3 = Color+Command
addiu a2,4 ; A2 += 4
sw s3,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro FillTriCullNoneZSort,START,END,SORT ; Fill Triangle Face Cull None Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
AverageZTri s0,s1,s2 ; Average Z Triangle: Z1,Z2,Z3
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,20 ; A3 += 20
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,20 ; A2 += 20 (Delay Slot)
subiu a2,20 ; A2 -= 20
li t0,(20/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(16/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
.endmacro
.macro FillTriCullBackZSort,START,END,SORT ; Fill Triangle Back Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,4 ; A2 += 4 (Delay Slot)
subiu a2,4 ; A2 -= 4
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
AverageZTri s0,s1,s2 ; Average Z Triangle: Z1,Z2,Z3
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,20 ; A3 += 20
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,20 ; A2 += 20 (Delay Slot)
subiu a2,20 ; A2 -= 20
li t0,(20/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(16/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro FillTriCullFrontZSort,START,END,SORT ; Fill Triangle Front Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,4 ; A2 += 4 (Delay Slot)
subiu a2,4 ; A2 -= 4
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
AverageZTri s0,s1,s2 ; Average Z Triangle: Z1,Z2,Z3
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,20 ; A3 += 20
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,20 ; A2 += 20 (Delay Slot)
subiu a2,20 ; A2 -= 20
li t0,(20/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(16/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro ShadeTriCullNone,START,END ; Shaded Triangle Face Cull None: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
lw s3,0(a2) ; S3 = Color1+Command
addiu a2,4 ; A2 += 4
lw s4,0(a2) ; S4 = Color2
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Color3
addiu a2,4 ; A2 += 4
sw s3,GP0(a0) ; Write GP0 Command Word (Color1+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s4,GP0(a0) ; Write GP0 Packet Word (Color2)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s5,GP0(a0) ; Write GP0 Packet Word (Color3)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro ShadeTriCullBack,START,END ; Shaded Triangle Back Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,12 ; A2 += 12 (Delay Slot)
subiu a2,12 ; A2 -= 12
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
lw s3,0(a2) ; S3 = Color1+Command
addiu a2,4 ; A2 += 4
lw s4,0(a2) ; S4 = Color2
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Color3
addiu a2,4 ; A2 += 4
sw s3,GP0(a0) ; Write GP0 Command Word (Color1+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s4,GP0(a0) ; Write GP0 Packet Word (Color2)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s5,GP0(a0) ; Write GP0 Packet Word (Color3)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro ShadeTriCullFront,START,END ; Shaded Triangle Front Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,12 ; A2 += 12 (Delay Slot)
subiu a2,12 ; A2 -= 12
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
lw s3,0(a2) ; S3 = Color1+Command
addiu a2,4 ; A2 += 4
lw s4,0(a2) ; S4 = Color2
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Color3
addiu a2,4 ; A2 += 4
sw s3,GP0(a0) ; Write GP0 Command Word (Color1+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s4,GP0(a0) ; Write GP0 Packet Word (Color2)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s5,GP0(a0) ; Write GP0 Packet Word (Color3)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro ShadeTriCullNoneZSort,START,END,SORT ; Shaded Triangle Face Cull None Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
AverageZTri s0,s1,s2 ; Average Z Triangle: Z1,Z2,Z3
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
lw s0,0(a2) ; S0 = Color1+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Color2
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Color3
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color1+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Color2 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Color3 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,28 ; A3 += 28
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,28 ; A2 += 28 (Delay Slot)
subiu a2,28 ; A2 -= 28
li t0,(28/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(24/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
.endmacro
.macro ShadeTriCullBackZSort,START,END,SORT ; Shaded Triangle Back Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,12 ; A2 += 12 (Delay Slot)
subiu a2,12 ; A2 -= 12
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
AverageZTri s0,s1,s2 ; Average Z Triangle: Z1,Z2,Z3
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
lw s0,0(a2) ; S0 = Color1+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Color2
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Color3
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color1+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Color2 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Color3 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,28 ; A3 += 28
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,28 ; A2 += 28 (Delay Slot)
subiu a2,28 ; A2 -= 28
li t0,(28/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(24/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro ShadeTriCullFrontZSort,START,END,SORT ; Shaded Triangle Front Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,12 ; A2 += 12 (Delay Slot)
subiu a2,12 ; A2 -= 12
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
AverageZTri s0,s1,s2 ; Average Z Triangle: Z1,Z2,Z3
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
lw s0,0(a2) ; S0 = Color1+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Color2
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Color3
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color1+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Color2 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Color3 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,28 ; A3 += 28
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,28 ; A2 += 28 (Delay Slot)
subiu a2,28 ; A2 -= 28
li t0,(28/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(24/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro TexTriCullNone,START,END ; Texture Triangle Face Cull None: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
lw s3,0(a2) ; S3 = Color+Command
addiu a2,4 ; A2 += 4
lw s4,0(a2) ; S4 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord3
addiu a2,4 ; A2 += 4
sw s3,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s4,GP0(a0) ; Write GP0 Packet Word (Texcoord1+Palette)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s5,GP0(a0) ; Write GP0 Packet Word (Texcoord2+Texpage)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s6,GP0(a0) ; Write GP0 Packet Word (Texcoord3)
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro TexTriCullBack,START,END ; Texture Triangle Back Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,16 ; A2 += 16 (Delay Slot)
subiu a2,16 ; A2 -= 16
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
lw s3,0(a2) ; S3 = Color+Command
addiu a2,4 ; A2 += 4
lw s4,0(a2) ; S4 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord3
addiu a2,4 ; A2 += 4
sw s3,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s4,GP0(a0) ; Write GP0 Packet Word (Texcoord1+Palette)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s5,GP0(a0) ; Write GP0 Packet Word (Texcoord2+Texpage)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s6,GP0(a0) ; Write GP0 Packet Word (Texcoord3)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro TexTriCullFront,START,END ; Texture Triangle Front Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,16 ; A2 += 16 (Delay Slot)
subiu a2,16 ; A2 -= 16
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
lw s3,0(a2) ; S3 = Color+Command
addiu a2,4 ; A2 += 4
lw s4,0(a2) ; S4 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord3
addiu a2,4 ; A2 += 4
sw s3,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s4,GP0(a0) ; Write GP0 Packet Word (Texcoord1+Palette)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s5,GP0(a0) ; Write GP0 Packet Word (Texcoord2+Texpage)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s6,GP0(a0) ; Write GP0 Packet Word (Texcoord3)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro TexTriCullNoneZSort,START,END,SORT ; Texture Triangle Face Cull None Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
AverageZTri s0,s1,s2 ; Average Z Triangle: Z1,Z2,Z3
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord3
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Texcoord1+Palette To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Texcoord2+TexPage To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s6,0(v0) ; Store Texcoord3 To Sort Address
addiu v0,4 ; V0 += 4
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,32 ; A3 += 32
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,32 ; A2 += 32 (Delay Slot)
subiu a2,32 ; A2 -= 32
li t0,(32/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(28/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
.endmacro
.macro TexTriCullBackZSort,START,END,SORT ; Texture Triangle Back Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,16 ; A2 += 16 (Delay Slot)
subiu a2,16 ; A2 -= 16
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
AverageZTri s0,s1,s2 ; Average Z Triangle: Z1,Z2,Z3
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord3
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Texcoord1+Palette To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Texcoord2+TexPage To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s6,0(v0) ; Store Texcoord3 To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,32 ; A3 += 32
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,32 ; A2 += 32 (Delay Slot)
subiu a2,32 ; A2 -= 32
li t0,(32/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(28/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro TexTriCullFrontZSort,START,END,SORT ; Texture Triangle Front Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,16 ; A2 += 16 (Delay Slot)
subiu a2,16 ; A2 -= 16
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
AverageZTri s0,s1,s2 ; Average Z Triangle: Z1,Z2,Z3
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord3
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Texcoord1+Palette To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Texcoord2+TexPage To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s6,0(v0) ; Store Texcoord3 To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,32 ; A3 += 32
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,32 ; A2 += 32 (Delay Slot)
subiu a2,32 ; A2 -= 32
li t0,(32/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(28/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro ShadeTexTriCullNone,START,END ; Shaded Texture Triangle Face Cull None: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
lw s3,0(a2) ; S3 = Color1+Command
addiu a2,4 ; A2 += 4
lw s4,0(a2) ; S4 = Color2
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Color3
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s7,0(a2) ; S7 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord3
addiu a2,4 ; A2 += 4
sw s3,GP0(a0) ; Write GP0 Command Word (Color1+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s6,GP0(a0) ; Write GP0 Packet Word (Texcoord1+Palette)
sw s4,GP0(a0) ; Write GP0 Packet Word (Color2)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s7,GP0(a0) ; Write GP0 Packet Word (Texcoord2+Texpage)
sw s5,GP0(a0) ; Write GP0 Packet Word (Color3)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s8,GP0(a0) ; Write GP0 Packet Word (Texcoord3)
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro ShadeTexTriCullBack,START,END ; Shaded Texture Triangle Back Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,24 ; A2 += 24 (Delay Slot)
subiu a2,24 ; A2 -= 24
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
lw s3,0(a2) ; S3 = Color1+Command
addiu a2,4 ; A2 += 4
lw s4,0(a2) ; S4 = Color2
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Color3
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s7,0(a2) ; S7 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord3
addiu a2,4 ; A2 += 4
sw s3,GP0(a0) ; Write GP0 Command Word (Color1+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s6,GP0(a0) ; Write GP0 Packet Word (Texcoord1+Palette)
sw s4,GP0(a0) ; Write GP0 Packet Word (Color2)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s7,GP0(a0) ; Write GP0 Packet Word (Texcoord2+Texpage)
sw s5,GP0(a0) ; Write GP0 Packet Word (Color3)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s8,GP0(a0) ; Write GP0 Packet Word (Texcoord3)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro ShadeTexTriCullFront,START,END ; Shaded Texture Triangle Front Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,24 ; A2 += 24 (Delay Slot)
subiu a2,24 ; A2 -= 24
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
lw s3,0(a2) ; S3 = Color1+Command
addiu a2,4 ; A2 += 4
lw s4,0(a2) ; S4 = Color2
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Color3
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s7,0(a2) ; S7 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord3
addiu a2,4 ; A2 += 4
sw s3,GP0(a0) ; Write GP0 Command Word (Color1+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s6,GP0(a0) ; Write GP0 Packet Word (Texcoord1+Palette)
sw s4,GP0(a0) ; Write GP0 Packet Word (Color2)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s7,GP0(a0) ; Write GP0 Packet Word (Texcoord2+Texpage)
sw s5,GP0(a0) ; Write GP0 Packet Word (Color3)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s8,GP0(a0) ; Write GP0 Packet Word (Texcoord3)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro ShadeTexTriCullNoneZSort,START,END,SORT ; Shaded Texture Triangle Face Cull None Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
AverageZTri s0,s1,s2 ; Average Z Triangle: Z1,Z2,Z3
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
lw s0,0(a2) ; S0 = Color1+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Color2
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Color3
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s7,0(a2) ; S7 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord3
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color1+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s6,0(v0) ; Store Texcoord1+Palette To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Color2 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Texcoord2+TexPage To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Color3 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s8,0(v0) ; Store Texcoord3 To Sort Address
addiu v0,4 ; V0 += 4
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,40 ; A3 += 40
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,40 ; A2 += 40 (Delay Slot)
subiu a2,40 ; A2 -= 40
li t0,(40/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(36/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
.endmacro
.macro ShadeTexTriCullBackZSort,START,END,SORT ; Shaded Texture Triangle Back Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,24 ; A2 += 24 (Delay Slot)
subiu a2,24 ; A2 -= 24
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
AverageZTri s0,s1,s2 ; Average Z Triangle: Z1,Z2,Z3
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
lw s0,0(a2) ; S0 = Color1+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Color2
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Color3
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s7,0(a2) ; S7 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord3
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color1+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s6,0(v0) ; Store Texcoord1+Palette To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Color2 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Texcoord2+TexPage To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Color3 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s8,0(v0) ; Store Texcoord3 To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,40 ; A3 += 40
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,40 ; A2 += 40 (Delay Slot)
subiu a2,40 ; A2 -= 40
li t0,(40/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(36/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro ShadeTexTriCullFrontZSort,START,END,SORT ; Shaded Texture Triangle Front Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,24 ; A2 += 24 (Delay Slot)
subiu a2,24 ; A2 -= 24
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
AverageZTri s0,s1,s2 ; Average Z Triangle: Z1,Z2,Z3
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
lw s0,0(a2) ; S0 = Color1+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Color2
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Color3
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s7,0(a2) ; S7 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord3
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color1+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s6,0(v0) ; Store Texcoord1+Palette To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Color2 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Texcoord2+TexPage To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Color3 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s8,0(v0) ; Store Texcoord3 To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,40 ; A3 += 40
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,40 ; A2 += 40 (Delay Slot)
subiu a2,40 ; A2 -= 40
li t0,(40/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(36/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro WireQuadCullNone,START,END ; Wire Quad Face Cull None: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
LoadXYZ s6,s7,s8 ; S6 = 2D X4, S7 = 2D Y4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
sll s7,16 ; Y4 <<= 16
andi s6,0xFFFF ; X4 &= 0xFFFF
or s3,s6,s7 ; X4 |= Y4
lw s4,0(a2) ; S4 = Color+Command
addiu a2,4 ; A2 += 4
sw s4,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s3,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex4)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex5)
WRIOW GP0,0x55555555 ; Write GP0 Packet Word (Termination Code)
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro WireQuadCullBack,START,END ; Wire Quad Back Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,16 ; A2 += 16 (Delay Slot)
subiu a2,16 ; A2 -= 16
LoadXYZ s6,s7,s8 ; S6 = 2D X4, S7 = 2D Y4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
sll s7,16 ; Y4 <<= 16
andi s6,0xFFFF ; X4 &= 0xFFFF
or s3,s6,s7 ; X4 |= Y4
lw s4,0(a2) ; S4 = Color+Command
addiu a2,4 ; A2 += 4
sw s4,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s3,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex4)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex5)
WRIOW GP0,0x55555555 ; Write GP0 Packet Word (Termination Code)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro WireQuadCullFront,START,END ; Wire Quad Front Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,16 ; A2 += 16 (Delay Slot)
subiu a2,16 ; A2 -= 16
LoadXYZ s6,s7,s8 ; S6 = 2D X4, S7 = 2D Y4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
sll s7,16 ; Y4 <<= 16
andi s6,0xFFFF ; X4 &= 0xFFFF
or s3,s6,s7 ; X4 |= Y4
lw s4,0(a2) ; S4 = Color+Command
addiu a2,4 ; A2 += 4
sw s4,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s3,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex4)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex5)
WRIOW GP0,0x55555555 ; Write GP0 Packet Word (Termination Code)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro WireQuadCullNoneZSort,START,END,SORT ; Wire Quad Face Cull None Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
LoadXYZ s7,s8,s6 ; S7 = 2D X4, S8 = 2D Y4, S6 = 3D Z4
AverageZQuad s0,s1,s2,s6 ; Average Z Quad: Z1,Z2,Z3,Z4
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
sll s8,16 ; Y4 <<= 16
andi s7,0xFFFF ; X4 &= 0xFFFF
or s7,s8 ; X4 |= Y4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex5 To Sort Address
addiu v0,4 ; V0 += 4
li t0,0x55555555 ; T0 = Termination Code
sw t0,0(v0) ; Store Termination Code To Sort Address
addiu v0,4 ; V0 += 4
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,32 ; A3 += 32
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,32 ; A2 += 32 (Delay Slot)
subiu a2,32 ; A2 -= 32
li t0,(32/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(28/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
.endmacro
.macro WireQuadCullBackZSort,START,END,SORT ; Wire Quad Back Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,16 ; A2 += 16 (Delay Slot)
subiu a2,16 ; A2 -= 16
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
LoadXYZ s7,s8,s6 ; S7 = 2D X4, S8 = 2D Y4, S6 = 3D Z4
AverageZQuad s0,s1,s2,s6 ; Average Z Quad: Z1,Z2,Z3,Z4
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
sll s8,16 ; Y4 <<= 16
andi s7,0xFFFF ; X4 &= 0xFFFF
or s7,s8 ; X4 |= Y4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex5 To Sort Address
addiu v0,4 ; V0 += 4
li t0,0x55555555 ; T0 = Termination Code
sw t0,0(v0) ; Store Termination Code To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,32 ; A3 += 32
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,32 ; A2 += 32 (Delay Slot)
subiu a2,32 ; A2 -= 32
li t0,(32/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(28/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro WireQuadCullFrontZSort,START,END,SORT ; Wire Quad Front Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,16 ; A2 += 16 (Delay Slot)
subiu a2,16 ; A2 -= 16
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
LoadXYZ s7,s8,s6 ; S7 = 2D X4, S8 = 2D Y4, S6 = 3D Z4
AverageZQuad s0,s1,s2,s6 ; Average Z Quad: Z1,Z2,Z3,Z4
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
sll s8,16 ; Y4 <<= 16
andi s7,0xFFFF ; X4 &= 0xFFFF
or s7,s8 ; X4 |= Y4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex5 To Sort Address
addiu v0,4 ; V0 += 4
li t0,0x55555555 ; T0 = Termination Code
sw t0,0(v0) ; Store Termination Code To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,32 ; A3 += 32
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,32 ; A2 += 32 (Delay Slot)
subiu a2,32 ; A2 -= 32
li t0,(32/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(28/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro FillQuadCullNone,START,END ; Fill Quad Face Cull None: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
LoadXYZ s6,s7,s8 ; S6 = 2D X4, S7 = 2D Y4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
sll s7,16 ; Y4 <<= 16
andi s6,0xFFFF ; X4 &= 0xFFFF
or s3,s6,s7 ; X4 |= Y4
lw s4,0(a2) ; S4 = Color+Command
addiu a2,4 ; A2 += 4
sw s4,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s3,GP0(a0) ; Write GP0 Packet Word (Vertex4)
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro FillQuadCullBack,START,END ; Fill Quad Back Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,16 ; A2 += 16 (Delay Slot)
subiu a2,16 ; A2 -= 16
LoadXYZ s6,s7,s8 ; S6 = 2D X4, S7 = 2D Y4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
sll s7,16 ; Y4 <<= 16
andi s6,0xFFFF ; X4 &= 0xFFFF
or s3,s6,s7 ; X4 |= Y4
lw s4,0(a2) ; S4 = Color+Command
addiu a2,4 ; A2 += 4
sw s4,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s3,GP0(a0) ; Write GP0 Packet Word (Vertex4)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro FillQuadCullFront,START,END ; Fill Quad Front Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,16 ; A2 += 16 (Delay Slot)
subiu a2,16 ; A2 -= 16
LoadXYZ s6,s7,s8 ; S6 = 2D X4, S7 = 2D Y4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
sll s7,16 ; Y4 <<= 16
andi s6,0xFFFF ; X4 &= 0xFFFF
or s3,s6,s7 ; X4 |= Y4
lw s4,0(a2) ; S4 = Color+Command
addiu a2,4 ; A2 += 4
sw s4,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s3,GP0(a0) ; Write GP0 Packet Word (Vertex4)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro FillQuadCullNoneZSort,START,END,SORT ; Fill Quad Face Cull None Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
LoadXYZ s7,s8,s6 ; S7 = 2D X4, S8 = 2D Y4, S6 = 3D Z4
AverageZQuad s0,s1,s2,s6 ; Average Z Quad: Z1,Z2,Z3,Z4
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
sll s8,16 ; Y4 <<= 16
andi s7,0xFFFF ; X4 &= 0xFFFF
or s7,s8 ; X4 |= Y4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,24 ; A3 += 24
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,24 ; A2 += 24 (Delay Slot)
subiu a2,24 ; A2 -= 24
li t0,(24/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(20/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
.endmacro
.macro FillQuadCullBackZSort,START,END,SORT ; Fill Quad Back Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,16 ; A2 += 16 (Delay Slot)
subiu a2,16 ; A2 -= 16
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
LoadXYZ s7,s8,s6 ; S7 = 2D X4, S8 = 2D Y4, S6 = 3D Z4
AverageZQuad s0,s1,s2,s6 ; Average Z Quad: Z1,Z2,Z3,Z4
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
sll s8,16 ; Y4 <<= 16
andi s7,0xFFFF ; X4 &= 0xFFFF
or s7,s8 ; X4 |= Y4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,24 ; A3 += 24
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,24 ; A2 += 24 (Delay Slot)
subiu a2,24 ; A2 -= 24
li t0,(24/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(20/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro FillQuadCullFrontZSort,START,END,SORT ; Fill Quad Front Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,16 ; A2 += 16 (Delay Slot)
subiu a2,16 ; A2 -= 16
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
LoadXYZ s7,s8,s6 ; S7 = 2D X4, S8 = 2D Y4, S6 = 3D Z4
AverageZQuad s0,s1,s2,s6 ; Average Z Quad: Z1,Z2,Z3,Z4
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
sll s8,16 ; Y4 <<= 16
andi s7,0xFFFF ; X4 &= 0xFFFF
or s7,s8 ; X4 |= Y4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,24 ; A3 += 24
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,24 ; A2 += 24 (Delay Slot)
subiu a2,24 ; A2 -= 24
li t0,(24/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(20/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro ShadeQuadCullNone,START,END ; Shaded Quad Face Cull None: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
LoadXYZ s6,s7,s8 ; S6 = 2D X4, S7 = 2D Y4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
sll s7,16 ; Y4 <<= 16
andi s6,0xFFFF ; X4 &= 0xFFFF
or s3,s6,s7 ; X4 |= Y4
lw s4,0(a2) ; S4 = Color1+Command
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Color2
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Color3
addiu a2,4 ; A2 += 4
lw s7,0(a2) ; S7 = Color4
addiu a2,4 ; A2 += 4
sw s4,GP0(a0) ; Write GP0 Command Word (Color1+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s5,GP0(a0) ; Write GP0 Packet Word (Color2)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s6,GP0(a0) ; Write GP0 Packet Word (Color3)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s7,GP0(a0) ; Write GP0 Packet Word (Color4)
sw s3,GP0(a0) ; Write GP0 Packet Word (Vertex4)
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro ShadeQuadCullBack,START,END ; Shaded Quad Back Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,28 ; A2 += 28 (Delay Slot)
subiu a2,28 ; A2 -= 28
LoadXYZ s6,s7,s8 ; S6 = 2D X4, S7 = 2D Y4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
sll s7,16 ; Y4 <<= 16
andi s6,0xFFFF ; X4 &= 0xFFFF
or s3,s6,s7 ; X4 |= Y4
lw s4,0(a2) ; S4 = Color1+Command
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Color2
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Color3
addiu a2,4 ; A2 += 4
lw s7,0(a2) ; S7 = Color4
addiu a2,4 ; A2 += 4
sw s4,GP0(a0) ; Write GP0 Command Word (Color1+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s5,GP0(a0) ; Write GP0 Packet Word (Color2)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s6,GP0(a0) ; Write GP0 Packet Word (Color3)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s7,GP0(a0) ; Write GP0 Packet Word (Color4)
sw s3,GP0(a0) ; Write GP0 Packet Word (Vertex4)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro ShadeQuadCullFront,START,END ; Shaded Quad Front Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,28 ; A2 += 28 (Delay Slot)
subiu a2,28 ; A2 -= 28
LoadXYZ s6,s7,s8 ; S6 = 2D X4, S7 = 2D Y4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
sll s7,16 ; Y4 <<= 16
andi s6,0xFFFF ; X4 &= 0xFFFF
or s3,s6,s7 ; X4 |= Y4
lw s4,0(a2) ; S4 = Color1+Command
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Color2
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Color3
addiu a2,4 ; A2 += 4
lw s7,0(a2) ; S7 = Color4
addiu a2,4 ; A2 += 4
sw s4,GP0(a0) ; Write GP0 Command Word (Color1+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s5,GP0(a0) ; Write GP0 Packet Word (Color2)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s6,GP0(a0) ; Write GP0 Packet Word (Color3)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s7,GP0(a0) ; Write GP0 Packet Word (Color4)
sw s3,GP0(a0) ; Write GP0 Packet Word (Vertex4)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro ShadeQuadCullNoneZSort,START,END,SORT ; Shaded Quad Face Cull None Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
LoadXYZ s7,s8,s6 ; S7 = 2D X4, S8 = 2D Y4, S6 = 3D Z4
AverageZQuad s0,s1,s2,s6 ; Average Z Quad: Z1,Z2,Z3,Z4
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
sll s8,16 ; Y4 <<= 16
andi s7,0xFFFF ; X4 &= 0xFFFF
or s7,s8 ; X4 |= Y4
lw s0,0(a2) ; S0 = Color1+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Color2
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Color3
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Color4
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color1+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Color2 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Color3 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s6,0(v0) ; Store Color4 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,36 ; A3 += 36
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,36 ; A2 += 36 (Delay Slot)
subiu a2,36 ; A2 -= 36
li t0,(36/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(32/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
.endmacro
.macro ShadeQuadCullBackZSort,START,END,SORT ; Shaded Quad Back Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,28 ; A2 += 28 (Delay Slot)
subiu a2,28 ; A2 -= 28
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
LoadXYZ s7,s8,s6 ; S7 = 2D X4, S8 = 2D Y4, S6 = 3D Z4
AverageZQuad s0,s1,s2,s6 ; Average Z Quad: Z1,Z2,Z3,Z4
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
sll s8,16 ; Y4 <<= 16
andi s7,0xFFFF ; X4 &= 0xFFFF
or s7,s8 ; X4 |= Y4
lw s0,0(a2) ; S0 = Color1+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Color2
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Color3
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Color4
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color1+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Color2 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Color3 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s6,0(v0) ; Store Color4 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,36 ; A3 += 36
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,36 ; A2 += 36 (Delay Slot)
subiu a2,36 ; A2 -= 36
li t0,(36/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(32/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro ShadeQuadCullFrontZSort,START,END,SORT ; Shaded Quad Front Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,28 ; A2 += 28 (Delay Slot)
subiu a2,28 ; A2 -= 28
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
LoadXYZ s7,s8,s6 ; S7 = 2D X4, S8 = 2D Y4, S6 = 3D Z4
AverageZQuad s0,s1,s2,s6 ; Average Z Quad: Z1,Z2,Z3,Z4
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
sll s8,16 ; Y4 <<= 16
andi s7,0xFFFF ; X4 &= 0xFFFF
or s7,s8 ; X4 |= Y4
lw s0,0(a2) ; S0 = Color1+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Color2
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Color3
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Color4
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color1+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Color2 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Color3 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s6,0(v0) ; Store Color4 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,36 ; A3 += 36
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,36 ; A2 += 36 (Delay Slot)
subiu a2,36 ; A2 -= 36
li t0,(36/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(32/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro TexQuadCullNone,START,END ; Texture Quad Face Cull None: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
LoadXYZ s6,s7,s8 ; S6 = 2D X4, S7 = 2D Y4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
sll s7,16 ; Y4 <<= 16
andi s6,0xFFFF ; X4 &= 0xFFFF
or s3,s6,s7 ; X4 |= Y4
lw s4,0(a2) ; S4 = Color+Command
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s7,0(a2) ; S7 = Texcoord3
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord4
addiu a2,4 ; A2 += 4
sw s4,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s5,GP0(a0) ; Write GP0 Packet Word (Texcoord1+Palette)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s6,GP0(a0) ; Write GP0 Packet Word (Texcoord2+Texpage)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s7,GP0(a0) ; Write GP0 Packet Word (Texcoord3)
sw s3,GP0(a0) ; Write GP0 Packet Word (Vertex4)
sw s8,GP0(a0) ; Write GP0 Packet Word (Texcoord4)
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro TexQuadCullBack,START,END ; Texture Quad Back Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,32 ; A2 += 32 (Delay Slot)
subiu a2,32 ; A2 -= 32
LoadXYZ s6,s7,s8 ; S6 = 2D X4, S7 = 2D Y4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
sll s7,16 ; Y4 <<= 16
andi s6,0xFFFF ; X4 &= 0xFFFF
or s3,s6,s7 ; X4 |= Y4
lw s4,0(a2) ; S4 = Color+Command
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s7,0(a2) ; S7 = Texcoord3
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord4
addiu a2,4 ; A2 += 4
sw s4,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s5,GP0(a0) ; Write GP0 Packet Word (Texcoord1+Palette)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s6,GP0(a0) ; Write GP0 Packet Word (Texcoord2+Texpage)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s7,GP0(a0) ; Write GP0 Packet Word (Texcoord3)
sw s3,GP0(a0) ; Write GP0 Packet Word (Vertex4)
sw s8,GP0(a0) ; Write GP0 Packet Word (Texcoord4)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro TexQuadCullFront,START,END ; Texture Quad Front Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,32 ; A2 += 32 (Delay Slot)
subiu a2,32 ; A2 -= 32
LoadXYZ s6,s7,s8 ; S6 = 2D X4, S7 = 2D Y4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
sll s7,16 ; Y4 <<= 16
andi s6,0xFFFF ; X4 &= 0xFFFF
or s3,s6,s7 ; X4 |= Y4
lw s4,0(a2) ; S4 = Color+Command
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s7,0(a2) ; S7 = Texcoord3
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord4
addiu a2,4 ; A2 += 4
sw s4,GP0(a0) ; Write GP0 Command Word (Color+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s5,GP0(a0) ; Write GP0 Packet Word (Texcoord1+Palette)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw s6,GP0(a0) ; Write GP0 Packet Word (Texcoord2+Texpage)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw s7,GP0(a0) ; Write GP0 Packet Word (Texcoord3)
sw s3,GP0(a0) ; Write GP0 Packet Word (Vertex4)
sw s8,GP0(a0) ; Write GP0 Packet Word (Texcoord4)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro TexQuadCullNoneZSort,START,END,SORT ; Texture Quad Face Cull None Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
LoadXYZ s7,s8,s6 ; S7 = 2D X4, S8 = 2D Y4, S6 = 3D Z4
AverageZQuad s0,s1,s2,s6 ; Average Z Quad: Z1,Z2,Z3,Z4
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
sll s8,16 ; Y4 <<= 16
andi s7,0xFFFF ; X4 &= 0xFFFF
or s7,s8 ; X4 |= Y4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord3
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord4
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Texcoord1+Palette To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Texcoord2+TexPage To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s6,0(v0) ; Store Texcoord3 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
sw s8,0(v0) ; Store Texcoord4 To Sort Address
addiu v0,4 ; V0 += 4
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,40 ; A3 += 40
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,40 ; A2 += 40 (Delay Slot)
subiu a2,40 ; A2 -= 40
li t0,(40/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(36/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
.endmacro
.macro TexQuadCullBackZSort,START,END,SORT ; Texture Quad Back Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,32 ; A2 += 32 (Delay Slot)
subiu a2,32 ; A2 -= 32
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
LoadXYZ s7,s8,s6 ; S7 = 2D X4, S8 = 2D Y4, S6 = 3D Z4
AverageZQuad s0,s1,s2,s6 ; Average Z Quad: Z1,Z2,Z3,Z4
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
sll s8,16 ; Y4 <<= 16
andi s7,0xFFFF ; X4 &= 0xFFFF
or s7,s8 ; X4 |= Y4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord3
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord4
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Texcoord1+Palette To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Texcoord2+TexPage To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s6,0(v0) ; Store Texcoord3 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
sw s8,0(v0) ; Store Texcoord4 To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,40 ; A3 += 40
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,40 ; A2 += 40 (Delay Slot)
subiu a2,40 ; A2 -= 40
li t0,(40/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(36/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro TexQuadCullFrontZSort,START,END,SORT ; Texture Quad Front Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,32 ; A2 += 32 (Delay Slot)
subiu a2,32 ; A2 -= 32
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
LoadXYZ s7,s8,s6 ; S7 = 2D X4, S8 = 2D Y4, S6 = 3D Z4
AverageZQuad s0,s1,s2,s6 ; Average Z Quad: Z1,Z2,Z3,Z4
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
sll s8,16 ; Y4 <<= 16
andi s7,0xFFFF ; X4 &= 0xFFFF
or s7,s8 ; X4 |= Y4
lw s0,0(a2) ; S0 = Color+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Texcoord3
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord4
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Texcoord1+Palette To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Texcoord2+TexPage To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw s6,0(v0) ; Store Texcoord3 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
sw s8,0(v0) ; Store Texcoord4 To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,40 ; A3 += 40
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,40 ; A2 += 40 (Delay Slot)
subiu a2,40 ; A2 -= 40
li t0,(40/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(36/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro ShadeTexQuadCullNone,START,END ; Shaded Texture Quad Face Cull None: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
LoadXYZ s6,s7,s8 ; S6 = 2D X4, S7 = 2D Y4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
sll s7,16 ; Y4 <<= 16
andi s6,0xFFFF ; X4 &= 0xFFFF
or s3,s6,s7 ; X4 |= Y4
lw s4,0(a2) ; S4 = Color1+Command
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Color2
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Color3
addiu a2,4 ; A2 += 4
lw s7,0(a2) ; S7 = Color4
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw t0,0(a2) ; T0 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw t1,0(a2) ; T1 = Texcoord3
addiu a2,4 ; A2 += 4
lw t2,0(a2) ; T2 = Texcoord4
addiu a2,4 ; A2 += 4
sw s4,GP0(a0) ; Write GP0 Command Word (Color1+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s8,GP0(a0) ; Write GP0 Packet Word (Texcoord1+Palette)
sw s5,GP0(a0) ; Write GP0 Packet Word (Color2)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw t0,GP0(a0) ; Write GP0 Packet Word (Texcoord2+Texpage)
sw s6,GP0(a0) ; Write GP0 Packet Word (Color3)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw t1,GP0(a0) ; Write GP0 Packet Word (Texcoord3)
sw s7,GP0(a0) ; Write GP0 Packet Word (Color4)
sw s3,GP0(a0) ; Write GP0 Packet Word (Vertex4)
sw t2,GP0(a0) ; Write GP0 Packet Word (Texcoord4)
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro ShadeTexQuadCullBack,START,END ; Shaded Texture Quad Back Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,44 ; A2 += 44 (Delay Slot)
subiu a2,44 ; A2 -= 44
LoadXYZ s6,s7,s8 ; S6 = 2D X4, S7 = 2D Y4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
sll s7,16 ; Y4 <<= 16
andi s6,0xFFFF ; X4 &= 0xFFFF
or s3,s6,s7 ; X4 |= Y4
lw s4,0(a2) ; S4 = Color1+Command
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Color2
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Color3
addiu a2,4 ; A2 += 4
lw s7,0(a2) ; S7 = Color4
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw t0,0(a2) ; T0 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw t1,0(a2) ; T1 = Texcoord3
addiu a2,4 ; A2 += 4
lw t2,0(a2) ; T2 = Texcoord4
addiu a2,4 ; A2 += 4
sw s4,GP0(a0) ; Write GP0 Command Word (Color1+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s8,GP0(a0) ; Write GP0 Packet Word (Texcoord1+Palette)
sw s5,GP0(a0) ; Write GP0 Packet Word (Color2)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw t0,GP0(a0) ; Write GP0 Packet Word (Texcoord2+Texpage)
sw s6,GP0(a0) ; Write GP0 Packet Word (Color3)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw t1,GP0(a0) ; Write GP0 Packet Word (Texcoord3)
sw s7,GP0(a0) ; Write GP0 Packet Word (Color4)
sw s3,GP0(a0) ; Write GP0 Packet Word (Vertex4)
sw t2,GP0(a0) ; Write GP0 Packet Word (Texcoord4)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro ShadeTexQuadCullFront,START,END ; Shaded Texture Quad Front Face Cull: Object Start Address, Object End Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
Loop:
LoadXYZ s0,s1,s2 ; S0 = 2D X1, S1 = 2D Y1
LoadXYZ s2,s3,s4 ; S2 = 2D X2, S3 = 2D Y2
LoadXYZ s4,s5,s6 ; S4 = 2D X3, S5 = 2D Y3
CullFace s0,s1,s2,s3,s4,s5 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,44 ; A2 += 44 (Delay Slot)
subiu a2,44 ; A2 -= 44
LoadXYZ s6,s7,s8 ; S6 = 2D X4, S7 = 2D Y4
sll s1,16 ; Y1 <<= 16
andi s0,0xFFFF ; X1 &= 0xFFFF
or s0,s1 ; X1 |= Y1
sll s3,16 ; Y2 <<= 16
andi s2,0xFFFF ; X2 &= 0xFFFF
or s1,s2,s3 ; X2 |= Y2
sll s5,16 ; Y3 <<= 16
andi s4,0xFFFF ; X3 &= 0xFFFF
or s2,s4,s5 ; X3 |= Y3
sll s7,16 ; Y4 <<= 16
andi s6,0xFFFF ; X4 &= 0xFFFF
or s3,s6,s7 ; X4 |= Y4
lw s4,0(a2) ; S4 = Color1+Command
addiu a2,4 ; A2 += 4
lw s5,0(a2) ; S5 = Color2
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Color3
addiu a2,4 ; A2 += 4
lw s7,0(a2) ; S7 = Color4
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw t0,0(a2) ; T0 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw t1,0(a2) ; T1 = Texcoord3
addiu a2,4 ; A2 += 4
lw t2,0(a2) ; T2 = Texcoord4
addiu a2,4 ; A2 += 4
sw s4,GP0(a0) ; Write GP0 Command Word (Color1+Command)
sw s0,GP0(a0) ; Write GP0 Packet Word (Vertex1)
sw s8,GP0(a0) ; Write GP0 Packet Word (Texcoord1+Palette)
sw s5,GP0(a0) ; Write GP0 Packet Word (Color2)
sw s1,GP0(a0) ; Write GP0 Packet Word (Vertex2)
sw t0,GP0(a0) ; Write GP0 Packet Word (Texcoord2+Texpage)
sw s6,GP0(a0) ; Write GP0 Packet Word (Color3)
sw s2,GP0(a0) ; Write GP0 Packet Word (Vertex3)
sw t1,GP0(a0) ; Write GP0 Packet Word (Texcoord3)
sw s7,GP0(a0) ; Write GP0 Packet Word (Color4)
sw s3,GP0(a0) ; Write GP0 Packet Word (Vertex4)
sw t2,GP0(a0) ; Write GP0 Packet Word (Texcoord4)
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
.endmacro
.macro ShadeTexQuadCullNoneZSort,START,END,SORT ; Shaded Texture Quad Face Cull None Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
LoadXYZ s7,s8,s6 ; S7 = 2D X4, S8 = 2D Y4, S6 = 3D Z4
AverageZQuad s0,s1,s2,s6 ; Average Z Quad: Z1,Z2,Z3,Z4
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
sll s8,16 ; Y4 <<= 16
andi s7,0xFFFF ; X4 &= 0xFFFF
or s7,s8 ; X4 |= Y4
lw s0,0(a2) ; S0 = Color1+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Color2
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Color3
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Color4
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw t0,0(a2) ; T0 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw t1,0(a2) ; T1 = Texcoord3
addiu a2,4 ; A2 += 4
lw t2,0(a2) ; T2 = Texcoord4
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color1+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s8,0(v0) ; Store Texcoord1+Palette To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Color2 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw t0,0(v0) ; Store Texcoord2+TexPage To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Color3 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw t1,0(v0) ; Store Texcoord3 To Sort Address
addiu v0,4 ; V0 += 4
sw s6,0(v0) ; Store Color4 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
sw t2,0(v0) ; Store Texcoord4 To Sort Address
addiu v0,4 ; V0 += 4
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,52 ; A3 += 52
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,52 ; A2 += 52 (Delay Slot)
subiu a2,52 ; A2 -= 52
li t0,(52/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(48/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
.endmacro
.macro ShadeTexQuadCullBackZSort,START,END,SORT ; Shaded Texture Quad Back Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Back Face Cull: X1,Y1,X2,Y2,X3,Y3
bgez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) >= 0 Skip
addiu a2,44 ; A2 += 44 (Delay Slot)
subiu a2,44 ; A2 -= 44
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
LoadXYZ s7,s8,s6 ; S7 = 2D X4, S8 = 2D Y4, S6 = 3D Z4
AverageZQuad s0,s1,s2,s6 ; Average Z Quad: Z1,Z2,Z3,Z4
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
sll s8,16 ; Y4 <<= 16
andi s7,0xFFFF ; X4 &= 0xFFFF
or s7,s8 ; X4 |= Y4
lw s0,0(a2) ; S0 = Color1+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Color2
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Color3
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Color4
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw t0,0(a2) ; T0 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw t1,0(a2) ; T1 = Texcoord3
addiu a2,4 ; A2 += 4
lw t2,0(a2) ; T2 = Texcoord4
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color1+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s8,0(v0) ; Store Texcoord1+Palette To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Color2 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw t0,0(v0) ; Store Texcoord2+TexPage To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Color3 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw t1,0(v0) ; Store Texcoord3 To Sort Address
addiu v0,4 ; V0 += 4
sw s6,0(v0) ; Store Color4 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
sw t2,0(v0) ; Store Texcoord4 To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,52 ; A3 += 52
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,52 ; A2 += 52 (Delay Slot)
subiu a2,52 ; A2 -= 52
li t0,(52/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(48/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro ShadeTexQuadCullFrontZSort,START,END,SORT ; Shaded Texture Quad Front Face Cull Z Sort: Object Start Address, Object End Address, Sort Address
la a2,START ; A2 = Object Start Address
la a3,END ; A3 = Object End Address
la v0,SORT ; V0 = Sort Address
Loop:
LoadXYZ s3,s4,s0 ; S3 = 2D X1, S4 = 2D Y1, S0 = 3D Z1
LoadXYZ s5,s6,s1 ; S5 = 2D X2, S6 = 2D Y2, S1 = 3D Z2
LoadXYZ s7,s8,s2 ; S6 = 2D X3, S8 = 2D Y3, S2 = 3D Z3
CullFace s3,s4,s5,s6,s7,s8 ; Front Face Cull: X1,Y1,X2,Y2,X3,Y3
blez t0,Skip ; IF ((X3-X1 * Y2-Y1) - (Y3-Y1 * X2-X1)) <= 0 Skip
addiu a2,44 ; A2 += 44 (Delay Slot)
subiu a2,44 ; A2 -= 44
sll s4,16 ; Y1 <<= 16
andi s3,0xFFFF ; X1 &= 0xFFFF
or s3,s4 ; X1 |= Y1
sll s6,16 ; Y2 <<= 16
andi s5,0xFFFF ; X2 &= 0xFFFF
or s4,s5,s6 ; X2 |= Y2
sll s8,16 ; Y3 <<= 16
andi s7,0xFFFF ; X3 &= 0xFFFF
or s5,s7,s8 ; X3 |= Y3
LoadXYZ s7,s8,s6 ; S7 = 2D X4, S8 = 2D Y4, S6 = 3D Z4
AverageZQuad s0,s1,s2,s6 ; Average Z Quad: Z1,Z2,Z3,Z4
sw t0,0(v0) ; Store Average Z To Sort Address
addiu v0,4 ; V0 += 4
sll s8,16 ; Y4 <<= 16
andi s7,0xFFFF ; X4 &= 0xFFFF
or s7,s8 ; X4 |= Y4
lw s0,0(a2) ; S0 = Color1+Command
addiu a2,4 ; A2 += 4
lw s1,0(a2) ; S1 = Color2
addiu a2,4 ; A2 += 4
lw s2,0(a2) ; S2 = Color3
addiu a2,4 ; A2 += 4
lw s6,0(a2) ; S6 = Color4
addiu a2,4 ; A2 += 4
lw s8,0(a2) ; S8 = Texcoord1+Palette
addiu a2,4 ; A2 += 4
lw t0,0(a2) ; T0 = Texcoord2+Texpage
addiu a2,4 ; A2 += 4
lw t1,0(a2) ; T1 = Texcoord3
addiu a2,4 ; A2 += 4
lw t2,0(a2) ; T2 = Texcoord4
addiu a2,4 ; A2 += 4
sw s0,0(v0) ; Store Color1+Command To Sort Address
addiu v0,4 ; V0 += 4
sw s3,0(v0) ; Store Vertex1 To Sort Address
addiu v0,4 ; V0 += 4
sw s8,0(v0) ; Store Texcoord1+Palette To Sort Address
addiu v0,4 ; V0 += 4
sw s1,0(v0) ; Store Color2 To Sort Address
addiu v0,4 ; V0 += 4
sw s4,0(v0) ; Store Vertex2 To Sort Address
addiu v0,4 ; V0 += 4
sw t0,0(v0) ; Store Texcoord2+TexPage To Sort Address
addiu v0,4 ; V0 += 4
sw s2,0(v0) ; Store Color3 To Sort Address
addiu v0,4 ; V0 += 4
sw s5,0(v0) ; Store Vertex3 To Sort Address
addiu v0,4 ; V0 += 4
sw t1,0(v0) ; Store Texcoord3 To Sort Address
addiu v0,4 ; V0 += 4
sw s6,0(v0) ; Store Color4 To Sort Address
addiu v0,4 ; V0 += 4
sw s7,0(v0) ; Store Vertex4 To Sort Address
addiu v0,4 ; V0 += 4
sw t2,0(v0) ; Store Texcoord4 To Sort Address
addiu v0,4 ; V0 += 4
Skip:
bne a2,a3,Loop ; IF (Object Start Offset != Object End Offset) Loop
nop ; Delay Slot
; Sort List (Selection Sort)
la a2,SORT ; A2 = Sort Start Address
beq a2,v0,SkipObject ; IF (Sort Start Offset == Sort End Offset) Skip Object
nop ; Delay Slot
SelectionSort:
or a3,a2,r0 ; A3 = Sort Current Address
li t0,0 ; T0 = MaxZ
SortLoop:
lw t1,0(a3) ; T1 = Average Z Value
nop ; Delay Slot
blt t1,t0,ZLT ; IF (Average Z Value < MaxZ) Z Less Than
nop ; Delay Slot
or t0,t1,r0 ; ELSE (MaxZ = Average Z Value)
or v1,a3,r0 ; V1 = MaxZ Address
ZLT:
addiu a3,52 ; A3 += 52
bne a3,v0,SortLoop ; IF (Sort Current Offset != Sort End Offset) Sort Loop
nop ; Delay Slot
beq v1,a2,NoSwap ; IF (MaxZ Address == Sort Start Address) No Swap
addiu a2,52 ; A2 += 52 (Delay Slot)
subiu a2,52 ; A2 -= 52
li t0,(52/4)-1 ; T0 = Swap Count
Swap:
lw t1,0(a2)
lw t2,0(v1)
sw t1,0(v1)
sw t2,0(a2)
addiu a2,4 ; A2 += 4
addiu v1,4 ; V1 += 4
bnez t0,Swap ; IF (Swap Count != 0) Swap
subiu t0,1 ; T0-- (Delay Slot)
NoSwap:
bne a2,v0,SelectionSort ; IF (Sort Start Offset != Sort End Offset) Selection Sort
nop ; Delay Slot
; Render Sort List
la a1,SORT ; A1 = Sort Start Address
RenderLoop:
addiu a1,4 ; A1 += 4 (Skip Average Z)
li t0,(48/4)-1 ; T0 = Render Count
Render:
lw t1,0(a1) ; T1 = Command/Packet Word
addiu a1,4 ; A1 += 4
sw t1,GP0(a0) ; Write GP0 Command/Packet Word
bnez t0,Render ; IF (Render Count != 0) Render
subiu t0,1 ; T0-- (Delay Slot)
bne a1,v0,RenderLoop ; IF (Sort Start Offset != Sort End Offset) Render Loop
nop ; Delay Slot
SkipObject:
.endmacro
.macro XPos,X ; Object X Translation: X
la a1,X ; Load X Translation Value Address
lw t0,0(a1) ; Load X Translation Value
la a1,Matrix3D ; Load Matrix3D Address
sw t0,12(a1) ; Matrix3D[3] = (Translation X)
.endmacro
.macro YPos,Y ; Object Y Translation: Y
la a1,Y ; Load Y Translation Value Address
lw t0,0(a1) ; Load Y Translation Value
la a1,Matrix3D ; Load Matrix3D Address
sw t1,28(a1) ; Matrix3D[7] = (Translation Y)
.endmacro
.macro ZPos,Z ; Object Z Translation: Z
la a1,Z ; Load Z Translation Value Address
lw t0,0(a1) ; Load Z Translation Value
la a1,Matrix3D ; Load Matrix3D Address
sw t2,44(a1) ; Matrix3D[11] = (Translation Z)
.endmacro
.macro XYZPos,X,Y,Z ; Object X,Y,Z Translation: X,Y,Z
la a1,X ; Load X Translation Value Address
lw t0,0(a1) ; Load X Translation Value
la a1,Y ; Load Y Translation Value Address
lw t1,0(a1) ; Load Y Translation Value
la a1,Z ; Load Z Translation Value Address
lw t2,0(a1) ; Load Z Translation Value
la a1,Matrix3D ; Load Matrix3D Address
sw t0,12(a1) ; Matrix3D[3] = (Translation X)
sw t1,28(a1) ; Matrix3D[7] = (Translation Y)
sw t2,44(a1) ; Matrix3D[11] = (Translation Z)
.endmacro
.macro XRotCalc,XROT,PRECALC ; X Rotation Calculation: X Rotation, Matrix Sin & Cos Pre-Calculated Table
la a1,XROT ; Load X Rotation Address
lw t0,0(a1) ; T0 = X Rotation
la a1,PRECALC ; Load Matrix Sin & Cos Pre-Calculated Table Address
sll t0,4 ; T0 *= 16
addu a1,t0 ; Add X Rotation * 16 To X Rotate Matrix Offset
lw t0,0(a1) ; Load XC
lw t1,4(a1) ; Load -XS
lw t2,8(a1) ; Load XS
la a1,Matrix3D ; Load Matrix3D Address
sw t0,20(a1) ; Store T0 (XC) To Matrix3D 6th Word
sw t1,24(a1) ; Store T1 (-XS) To Matrix3D 7th Word
sw t2,36(a1) ; Store T2 (XS) To Matrix3D 10th Word
sw t0,40(a1) ; Store T0 (XC) To Matrix3D 11th Word
.endmacro
.macro YRotCalc,YROT,PRECALC ; Y Rotation Calculation: Y Rotation, Matrix Sin & Cos Pre-Calculated Table
la a1,YROT ; Load Y Rotation Address
lw t0,0(a1) ; T0 = Y Rotation
la a1,PRECALC ; Load Matrix Sin & Cos Pre-Calculated Table Address
sll t0,4 ; T0 *= 16
addu a1,t0 ; Add Y Rotation * 16 To Y Rotate Matrix Offset
lw t0,0(a1) ; Load YC
lw t1,4(a1) ; Load -YS
lw t2,8(a1) ; Load YS
la a1,Matrix3D ; Load Matrix3D Address
sw t0,0(a1) ; Store T0 (YC) To Matrix3D 1st Word
sw t2,8(a1) ; Store T1 (YS) To Matrix3D 3rd Word
sw t1,32(a1) ; Store T2 (-YS) To Matrix3D 9th Word
sw t0,40(a1) ; Store T0 (YC) To Matrix3D 11th Word
.endmacro
.macro ZRotCalc,ZROT,PRECALC ; Z Rotation Calculation: Z Rotation, Matrix Sin & Cos Pre-Calculated Table
la a1,ZROT ; Load Z Rotation Address
lw t0,0(a1) ; T0 = Z Rotation
la a1,PRECALC ; Load Matrix Sin & Cos Pre-Calculated Table Address
sll t0,4 ; T0 *= 16
addu a1,t0 ; Add Z Rotation * 16 To Z Rotate Matrix Offset
lw t0,0(a1) ; Load ZC
lw t1,4(a1) ; Load -ZS
lw t2,8(a1) ; Load ZS
la a1,Matrix3D ; Load Matrix3D Address
sw t0,0(a1) ; Store T0 (ZC) To Matrix3D 1st Word
sw t1,4(a1) ; Store T1 (-ZS) To Matrix3D 2nd Word
sw t2,16(a1) ; Store T2 (ZS) To Matrix3D 5th Word
sw t0,20(a1) ; Store T0 (ZC) To Matrix3D 6th Word
.endmacro
.macro XYRotCalc,XROT,YROT,PRECALC ; XY Rotation Calculation: X Rotation, Y Rotation, Matrix Sin & Cos Pre-Calculated Table
la a1,XROT ; Load X Rotation Address
lw t0,0(a1) ; T0 = X Rotation
la a1,PRECALC ; Load Matrix Sin & Cos Pre-Calculated Table Address
sll t0,4 ; T0 *= 16
addu a1,t0 ; Add X Rotation * 16 To X Rotate Matrix Offset
lw t0,0(a1) ; Load XC
lw t1,4(a1) ; Load -XS
lw t2,8(a1) ; Load XS
lw t3,12(a1) ; Load -XC
la a1,YROT ; Load Y Rotation Address
lw t4,0(a1) ; T4 = Y Rotation
la a1,PRECALC ; Load Matrix Sin & Cos Pre-Calculated Table Address
sll t4,4 ; T4 *= 16
addu a1,t4 ; Add Y Rotation * 16 To Y Rotate Matrix Offset
lw t4,0(a1) ; Load YC
lw t5,4(a1) ; Load -YS
lw t6,8(a1) ; Load YS
la a1,Matrix3D ; Load Matrix3D Address
sw t4,0(a1) ; Store T4 (YC) To Matrix3D 1st Word
mult t2,t6 ; Load (XS * YS) To T7
mflo t7
sra t7,8 ; Divide T7 By 256
sw t7,4(a1) ; Store T7 (XS * YS) To Matrix3D 2nd Word
mult t3,t6 ; Load (-XC * YS) To T7
mflo t7
sra t7,8 ; Divide T7 By 256
sw t7,8(a1) ; Store T7 (-XC * YS) To Matrix3D 3rd Word
sw t0,20(a1) ; Store T0 (XC) To Matrix3D 6th Word
sw t2,24(a1) ; Store T2 (XS) To Matrix3D 7th Word
sw t6,32(a1) ; Store T6 (YS) To Matrix3D 9th Word
mult t1,t4 ; Load (-XS * YC) To T7
mflo t7
sra t7,8 ; Divide T7 By 256
sw t7,36(a1) ; Store T7 (-XS * YC) To Matrix3D 10th Word
mult t0,t4 ; Load (XC * YC) To T7
mflo t7
sra t7,8 ; Divide T7 By 256
sw t7,40(a1) ; Store T7 (XC * YC) To Matrix3D 11th Word
.endmacro
.macro XZRotCalc,XROT,ZROT,PRECALC ; XZ Rotation Calculation: X Rotation, Z Rotation, Matrix Sin & Cos Pre-Calculated Table
la a1,XROT ; Load X Rotation Address
lw t0,0(a1) ; T0 = X Rotation
la a1,PRECALC ; Load Matrix Sin & Cos Pre-Calculated Table Address
sll t0,4 ; T0 *= 16
addu a1,t0 ; Add X Rotation * 16 To X Rotate Matrix Offset
lw t0,0(a1) ; Load XC
lw t1,4(a1) ; Load -XS
lw t2,8(a1) ; Load XS
la a1,ZROT ; Load Z Rotation Address
lw t3,0(a1) ; T3 = Z Rotation
la a1,PRECALC ; Load Matrix Sin & Cos Pre-Calculated Table Address
sll t3,4 ; T3 *= 16
addu a1,t3 ; Add Z Rotation * 16 To Z Rotate Matrix Offset
lw t3,0(a1) ; Load ZC
lw t4,4(a1) ; Load -ZS
lw t5,8(a1) ; Load ZS
lw t6,12(a1) ; Load -ZC
la a1,Matrix3D ; Load Matrix3D Address
sw t3,0(a1) ; Store T3 (ZC) To Matrix3D 1st Word
sw t5,4(a1) ; Store T5 (ZS) To Matrix3D 2nd Word
mult t0,t4 ; Load (XC * -ZS) To T7
mflo t7
sra t7,8 ; Divide T7 By 256
sw t7,16(a1) ; Store T7 (XC * -ZS) To Matrix3D 5th Word
mult t0,t3 ; Load (XC * ZC) To T7
mflo t7
sra t7,8 ; Divide T7 By 256
sw t7,20(a1) ; Store T7 (XC * ZC) To Matrix3D 6th Word
sw t2,24(a1) ; store T2 (XS) To Matrix3D 7th Word
mult t2,t5 ; Load (XS * ZS) To T7
mflo t7
sra t7,8 ; Divide T7 By 256
sw t7,32(a1) ; Store T7 (XS * ZS) To Matrix3D 9th Word
mult t2,t6 ; Load (XS * -ZC) To T7
mflo t7
sra t7,8 ; Divide T7 By 256
sw t7,36(a1) ; Store T7 (XS * -ZC) To Matrix3D 10th Word
sw t0,40(a1) ; Store T0 (XC) To Matrix3D 11th Word
.endmacro
.macro YZRotCalc,YROT,ZROT,PRECALC ; YZ Rotation Calculation: Y Rotation, Z Rotation, Matrix Sin & Cos Pre-Calculated Table
la a1,YROT ; Load Y Rotation Address
lw t0,0(a1) ; T0 = Y Rotation
la a1,PRECALC ; Load Matrix Sin & Cos Pre-Calculated Table Address
sll t0,4 ; T0 *= 16
addu a1,t0 ; Add Y Rotation * 16 To Y Rotate Matrix Offset
lw t0,0(a1) ; Load YC
lw t1,4(a1) ; Load -YS
lw t2,8(a1) ; Load YS
la a1,ZROT ; Load Z Rotation Address
lw t3,0(a1) ; T3 = Z Rotation
la a1,PRECALC ; Load Matrix Sin & Cos Pre-Calculated Table Address
sll t3,4 ; T3 *= 16
addu a1,t3 ; Add Z Rotation * 16 To Z Rotate Matrix Offset
lw t3,0(a1) ; Load ZC
lw t4,4(a1) ; Load -ZS
lw t5,8(a1) ; Load ZS
lw t6,12(a1) ; Load -ZC
la a1,Matrix3D ; Load Matrix3D Address
mult t0,t3 ; Load (YC * ZC) To T7
mflo t7
sra t7,8 ; Divide T7 By 256
sw t7,0(a1) ; Store T7 (YC * ZC) To Matrix3D 1st Word
sw t5,4(a1) ; Store T5 (ZS) To Matrix3D 2nd Word
mult t2,t6 ; Load (YS * -ZC) To T7
mflo t7
sra t7,8 ; Divide T7 By 256
sw t7,8(a1) ; Store T7 (YS * -ZC) To Matrix3D 3rd Word
mult t0,t4 ; Load (YC * -ZS) To T7
mflo t7
sra t7,8 ; Divide T7 By 256
sw t7,16(a1) ; Store T7 (YC * -ZS) To Matrix3D 5th Word
sw t3,20(a1) ; Store T3 (ZC) To Matrix3D 6th Word
mult t2,t5 ; Load (YS * ZS) To T7
mflo t7
sra t7,8 ; Divide T7 By 256
sw t7,24(a1) ; Store T7 (YS * ZS) To Matrix3D 7th Word
sw t2,32(a1) ; Store T2 (YS) To Matrix3D 9th Word
sw t0,40(a1) ; Store T0 (YC) To Matrix3D 11th Word
.endmacro
.macro XYZRotCalc,XROT,YROT,ZROT,PRECALC ; XYZ Rotation Calculation: X Rotation, Y Rotation, Z Rotation, Matrix Sin & Cos Pre-Calculated Table
la a1,XROT ; Load X Rotation Address
lw t0,0(a1) ; T0 = X Rotation
la a1,PRECALC ; Load Matrix Sin & Cos Pre-Calculated Table Address
sll t0,4 ; T0 *= 16
addu a1,t0 ; Add X Rotation * 16 To X Rotate Matrix Offset
lw t0,0(a1) ; Load XC
lw t1,4(a1) ; Load -XS
lw t2,8(a1) ; Load XS
lw t3,12(a1) ; Load -XC
la a1,YROT ; Load Y Rotation Address
lw t4,0(a1) ; T4 = Y Rotation
la a1,PRECALC ; Load Matrix Sin & Cos Pre-Calculated Table Address
sll t4,4 ; T4 *= 16
addu a1,t4 ; Add Y Rotation * 16 To Y Rotate Matrix Offset
lw t4,0(a1) ; Load YC
lw t5,4(a1) ; Load -YS
lw t6,8(a1) ; Load YS
la a1,ZROT ; Load Z Rotation Address
lw t7,0(a1) ; T7 = Z Rotation
la a1,PRECALC ; Load Matrix Sin & Cos Pre-Calculated Table Address
sll t7,4 ; T7 *= 16
addu a1,t7 ; Add Z Rotation * 16 To Z Rotate Matrix Offset
lw t7,0(a1) ; Load ZC
lw t8,4(a1) ; Load -ZS
lw t9,8(a1) ; Load ZS
la a1,Matrix3D ; Load Matrix3D Address
mult t0,t4 ; Load (XC * YC) To S0
mflo s0
sra s0,8 ; Divide S0 By 256
mult s0,t7 ; Load (XC * YC * ZC) To S0
mflo s0
sra s0,8 ; Divide S0 By 256
mult t2,t9 ; Load (XS * ZS) To S1
mflo s1
sra s1,8 ; Divide S1 By 256
sub s0,s1
sw s0,0(a1) ; Store S0 (XC * YC * ZC) - (XS * ZS) To Matrix3D 1st Word
mult t0,t4 ; Load (XC * YC) To S0
mflo s0
sra s0,8 ; Divide S0 By 256
mult s0,t9 ; Load (XC * YC * ZS) To S0
mflo s0
sra s0,8 ; Divide S0 By 256
mult t2,t7 ; Load (XS * ZC) To S1
mflo s1
sra s1,8 ; Divide S1 By 256
add s0,s1
sw s0,4(a1) ; Store S0 (XC * YC * ZS) + (XS * ZC) To Matrix3D 2nd Word
mult t3,t6 ; Load (-XC * YS) To S0
mflo s0
sra s0,8 ; Divide S0 By 256
sw s0,8(a1) ; Store S0 (-XC * YS) To Matrix3D 3rd Word
mult t1,t4 ; Load (-XS * YC) To S0
mflo s0
sra s0,8 ; Divide S0 By 256
mult s0,t7 ; Load (-XS * YC * ZC) To S0
mflo s0
sra s0,8 ; Divide S0 By 256
mult t0,t9 ; Load (XC * ZS) To S1
mflo s1
sra s1,8 ; Divide S1 By 256
sub s0,s1
sw s0,16(a1) ; Store S0 (-XS * YC * ZC) - (XC * ZS) To Matrix3D 5th Word
mult t1,t4 ; Load (-XS * YC) To S0
mflo s0
sra s0,8 ; Divide S0 By 256
mult s0,t9 ; Load (-XS * YC * ZS) To S0
mflo s0
sra s0,8 ; Divide S0 By 256
mult t0,t7 ; Load (XC * ZC) To S1
mflo s1
sra s1,8 ; Divide S1 By 256
add s0,s1
sw s0,20(a1) ; Stores S0 (-XS * YC * ZS) + (XC * ZC) To Matrix3D 6th Word
mult t2,t6 ; Load (XS * YS) To S0
mflo s0
sra s0,8 ; Divide S0 By 256
sw s0,24(a1) ; Store S0 (XS * YS) To Matrix3D 7th Word
mult t6,t7 ; Load (YS * ZC) To S0
mflo s0
sra s0,8 ; Divide S0 By 256
sw s0,32(a1) ; Store S0 (YS * ZC) To Matrix3D 9th Word
mult t6,t9 ; Load (YS * ZS) To S0
mflo s0
sra s0,8 ; Divide S0 By 256
sw s0,36(a1) ; Store S0 (YS * ZS) To Matrix3D 10th Word
sw t4,40(a1) ; Store T4 (YC) To Matrix3D 11th Word
.endmacro