// nicked from output of PGC Rel 1.4 -opt 2 .text .align 8 .text #define trace_regs(label)\ adds -16, sp, sp; \ st.l r1, 4(sp); \ adds -256, sp, sp; \ st.l r17, 64(sp); \ orh ha%label, r0, r17; \ or l%label, r17, r17; \ call _reg_dump; \ adds 256, sp, sp; \ ld.l 4(sp), r1; \ adds 16, sp, sp // // aiming for - // // icoeff_p = vpx ( icoeff_ref, codeword, opcode0, conn, backwards, n_polys ); // // problem - edgizing quads, pents and hexes // #define chunk_next_offset 65532 //{{{ about this code // // // The triangle functions are C-callable, and simply chain together // calls to other functions in this module, which do not themselves // adhere to C calling conventions and register allocation // // These are the triangle functions - for each type of triangle // rendereable by the system, a different function exists. The currently // implemented set of triangles is // // _tri_zb_rgb // _tri_zb_rgb_t // _tri_zb_d_s // _tri_zb_d_s_t // _tri_zb_f // _tri_zb_f_t // _tri_zb_d // _tri_zb_d_t // // which are enough to cover PAZ 1 shading model, white light PAZ 2 // shading model, optimized lightscape / Eindhoven radiosity, skyfly // texturing, white light texturing //}}} #include "\projects\dbi0150\dbi0151\ucode\igc_opco.h" #include "\dpl3\vrender\pxpl5sup\pxplmacr.h" #include "\dpl3\vrender\pxpl5sup\divpxmap.h" #include "\dpl3\vrender\pxpl5sup\dmaengn.h" #include "\dpl3\vrender\pxpl5sup\register.h" //{{{ some load macros #define ld_from(reg, addr) \ orh ha%addr, r0, r31; \ ld.l l%addr(r31), reg #define fld_from(freg, addr) \ orh ha%addr, r0, r31; \ fld.l l%addr(r31), freg #define dfld_from(freg, addr) \ orh ha%addr, r0, r31; \ fld.d l%addr(r31), freg //}}} //{{{ declare offsets in VERTEX structure // // Note new placement of next field - ensures double-alignment of // position, normal and texcoords // // typedef struct s_rvert { // 0 dpl_POINT position; // 16 dpl_POINT normcol; // 32 float32 texcoords [3]; // 44 struct s_rvert *next; // 48 dpl_POINT xform_posn; // 64 float32 rendered_color[3]; // int32 touched; // 80 } dpl_REMOTE_VERTEX; #define VERT_position_offs 48 #define VERT_normal_offs 64 #define VERT_tex_offs 32 #define VERT_size 80 #define VERT_x_offs ((VERT_position_offs) + 0) #define VERT_y_offs ((VERT_position_offs) + 4) #define VERT_z_offs ((VERT_position_offs) + 8) #define VERT_w_offs ((VERT_position_offs) + 12) #define VERT_r_offs (VERT_normal_offs) #define VERT_g_offs ((VERT_normal_offs)+4) #define VERT_b_offs ((VERT_normal_offs)+8) #define VERT_tex_u_offs ((VERT_tex_offs)+0) #define VERT_tex_v_offs ((VERT_tex_offs)+4) #define VERT_a_offs ((VERT_tex_offs)+8) // typedef struct s_conn { // struct s_conn *next; /* 0 */ // int32 n_verts; /* 4 */ // dpl_REMOTE_VERTEX* indices[6]; /* 8 */ // dpl_POINT planeEqn; /* 32 */ // float32 rendered_color[3]; /* 48 */ // int32 touched; /* 60 */ // } dpl_REMOTE_CONNECTION; // #define FACET_next_offs 0 #define FACET_nverts_offs 4 #define FACET_vert0_offs 8 #define FACET_r_offs 48 #define FACET_g_offs (48+4) #define FACET_b_offs (48+8) #define FACET_touched_offs (60) //}}} // ///////////////////////////////// // triangle support code // preplane, planarize, binitize //{{{ triangle_entry #define triangle_entry(backwards_label) \ fst.d f2, -8(sp); \ fst.d f4, -16(sp); \ fst.d f6, -24(sp); \ st.l r1, -28(sp); \ st.l r3, -32(sp); \ st.l r4, -36(sp); \ st.l r5, -40(sp); \ st.l r6, -44(sp); \ st.l r7, -48(sp); \ st.l r8, -52(sp); \ st.l r9, -56(sp); \ st.l r10, -60(sp); \ st.l r11, -64(sp); \ st.l r12, -68(sp); \ st.l r13, -72(sp); \ st.l r14, -76(sp); \ st.l r15, -80(sp); \ adds -96, sp, sp; \ pxpl5op_0 (backwards, Ix_TREEltZERO_L3); \ bte 0x0, iparam4, backwards_label; \ pxpl5op_0 (backwards, Ix_TREEgeZERO_L3); \ backwards_label:: ;\ mov iparam1, rcoeff_pp; \ mov iparam2, opcode0; \ mov iparam3, rvertex; \ mov iparam5, n_polygons; \ fmov.ss fparam1, fmaterial; \ ld.l r0(rcoeff_pp), rcoeffsave; \ orh ha%_last_coeffchunk, r0, r31; \ ld.l l%_last_coeffchunk(r31), rcoeffmax; \ mov (chunk_next_offset-512), r31; \ adds r31, rcoeffmax, rcoeffmax //}}} //{{{ triangle_exit #define triangle_exit \ st.l rcoeffsave, 0(rcoeff_pp); \ adds 96, sp, sp; \ adds 4, rcoeffptr, iparam1; \ ld.l -80(sp), r15; \ ld.l -76(sp), r14; \ ld.l -72(sp), r13; \ ld.l -68(sp), r12; \ ld.l -64(sp), r11; \ ld.l -60(sp), r10; \ ld.l -56(sp), r9; \ ld.l -52(sp), r8; \ ld.l -48(sp), r7; \ ld.l -44(sp), r6; \ ld.l -40(sp), r5; \ ld.l -36(sp), r4; \ ld.l -32(sp), r3; \ ld.l -28(sp), r1; \ fld.d -24(sp), f6; \ fld.d -16(sp), f4; \ bri r1; \ fld.d -8(sp), f2 //}}} //{{{ edgize_fn // // NOTE WEIRDNESSS - in viewing matrix, y was INVERTED - thus, // the sign of all Ys in here is flipped. dont think about it, just // BELIEVE the expressions below and all will be well... // // // eqn[0]=p1[Y] - p2[Y]; // eqn[1]=p2[X] - p1[X]; // eqn[2]=(p2[Y]*p1[X]) - (p2[X]*p1[Y]); // // NB we already have // fx13 fx21 fx32 in registers // .align 8 edgize_fn:: d.pfsub.ss fy1, fy2, f0 btne 0x3, n_verts, edgize_poly_fn d.pfsub.ss fy2, fy3, f0 nop d.pfsub.ss fy3, fy1, f0 nop d.m12tpm.ss fx1, fy2, ftmp1 fst.l ftmp1, 8(rcoeffptr) // edge[0] eqn[0] d.m12tpm.ss fx2, fy3, ftmp2 fst.l ftmp2, 24(rcoeffptr) // edge[1] eqn [0] d.m12tpm.ss fx3, fy1, ftmp1 fst.l ftmp1, 40(rcoeffptr) // edge[2] eqn [0] d.pfmul.ss fy1, fx2, ftmp4 // fy2*fx1 fst.l fx21, 12(rcoeffptr) // edge[0] eqn [1] d.pfmul.ss fy2, fx3, ftmp5 // fy3*fx2 fst.l fx32, 28(rcoeffptr) // edge[1] eqn[1] d.pfmul.ss fy3, fx1, ftmp6 // fy1*fx3 fst.l fx13, 44(rcoeffptr) // edge[2] eqn[1] d.i2s1.ss ftmp4, f0, f0 // push y2*x1 - x2*y1 st.l backwards, 4(rcoeffptr) d.i2s1.ss ftmp5, f0, f0 st.l backwards, 20(rcoeffptr) d.i2s1.ss ftmp6, f0, f0 st.l backwards, 36(rcoeffptr) d.pfadd.ss f0, f0, ftmp1 fst.l ftmp1, 16(rcoeffptr) // edge[0] eqn[2] d.pfadd.ss f0, f0, ftmp2 fst.l ftmp2, 32(rcoeffptr) // edge[1] eqn[2] pfadd.ss f0, f0, ftmp3 bri r1 fnop fst.l ftmp3, 48(rcoeffptr)++ // edge[2] eqn[2] // edgize a polygon rather than a triangle... //}}} //{{{ edgize_poly_fn // NOTE WEIRDNESSS - in viewing matrix, y was INVERTED - thus, // the sign of all Ys in here is flipped. dont think about it, just // BELIEVE the expressions below and all will be well... // // eqn[0]=p1[Y] - p2[Y]; // eqn[1]=p2[X] - p1[X]; // eqn[2]=(p2[Y]*p1[X]) - (p2[X]*p1[Y]); // // NB we already have // fx13 fx21 fx32 in registers // .align 8 edgize_poly_fn_entry:: d.pfsub.ss fy1, fy2, f0 nop edgize_poly_fn:: // do 1st 2 edges in optimal manner, then wimp out for remainder d.pfsub.ss fy2, fy3, f0 st.l backwards, 4(rcoeffptr) // opcode edge 1 d.m12ttpa.ss fx1, fy2, f0 fst.l fx21, 12(rcoeffptr) // edge 1 B d.m12ttpa.ss fx2, fy1, ftmp1 fst.l ftmp1, 8(rcoeffptr) // edge 1 A d.m12ttpa.ss fx2, fy3, ftmp2 fst.l ftmp2, 24(rcoeffptr) // edge 2 A d.m12ttpa.ss fx3, fy2, f0 // x1y2 into t st.l backwards, 20(rcoeffptr) d.i2st.ss f0, f0, f0 // x1y2 - x2y1 adder 1 adds -2, n_verts, n_verts d.i2ap1.ss f0, f0, f0 // x2y3 into t 2 fst.l fx32, 28(rcoeffptr)++ // edge[1] eqn[1] d.i2st.ss f0, f0, f0 // x2y3-x3y2->a.1, x1y2-x2y1->a.3 xor 0x1, n_verts, r0 d.pfadd.ss f0, f0, ftmp1 // edge 1 C fst.l ftmp1, -12(rcoeffptr) d.pfadd.ss f0, f0, f0 bte 0x1, n_verts, edgize_last_poly_vert // // ok - what about rest of edges ? // // we have executed edges 1->2 and 2->3 // for all remaining edges BUT THE LAST, // copy 2->3, load new 3, re-execute 2->3 // // use x3 y3 and x2 y2 to construct edge // eqn[0]=y2-y3 // eqn[1]=x3-x2 // eqn[2]=y3*x2 - x3*y2 // // itmp1=vertex_index // itmp2=vertex_ptr // // set itmp1=2, ready for increment // and re-execute last instruction due to bc.t ! // d.fnop or (FACET_vert0_offs+12), r0, itmp1 // move x3y3 to x2y2, and load x3y3 carry_on_branching:: d.fmov.dd fx3, fx2 ld.l itmp1(rvertex), itmp2 d.pfadd.ss f0, f0, ftmp1 // edge 2 C fld.d VERT_position_offs(itmp2), fx3 d.pfsub.ss fy2, fy3, f0 fst.l ftmp1, 4(rcoeffptr)++ d.pfsub.ss fx3, fx2, f0 st.l backwards, 4(rcoeffptr) // opcode edge d.m12ttpa.ss fy3, fx2, f0 nop d.m12ttpa.ss fy2, fx3, ftmp1 // edge A fst.l ftmp1, 8(rcoeffptr)++ d.m12ttpa.ss f0, f0, ftmp2 fst.l ftmp2, 4(rcoeffptr)++ // edge B d.m12ttpa.ss f0, f0, f0 // y1x3->t adds 4, itmp1, itmp1 d.i2st.ss f0, f0, f0 // y3x1 - x3y1 into adder 1 adds -1, n_verts, n_verts d.pfadd.ss f0, f0, f0 // y3x1 - x3y1 into adder 2 ld.l itmp1(rvertex), itmp2 d.pfadd.ss f0, f0, f0 // y3x1 - x3y1 into adder 3 btne 0x1, n_verts, carry_on_branching edgize_last_poly_vert:: // use x3 y3 and x1 y1 to construct edge // eqn[0]=y3-y1 // eqn[1]=x1-x3 // eqn[2]=y1*x3 - x1*y3 // only x1y1 are known good, so re-load x2y2 and x3y3 d.pfadd.ss f0, f0, ftmp1 // y3x1 - x3y1 into ftmp1 fst.l ftmp1, 4(rcoeffptr)++ // edge C and exit d.pfsub.ss fy3, fy1, f0 st.l backwards, 4(rcoeffptr) // opcode edge d.pfsub.ss fx1, fx3, f0 nop d.m12ttpa.ss fy1, fx3, f0 nop d.m12ttpa.ss fy3, fx1, ftmp1 // edge A fst.l ftmp1, 8(rcoeffptr)++ d.m12ttpa.ss f0, f0, ftmp2 fst.l ftmp2, 4(rcoeffptr)++ // edge B d.m12ttpa.ss f0, f0, f0 // y1x3->t nop d.i2st.ss f0, f0, f0 // y3x1 - x3y1 into adder 1 fld.d VERT_position_offs(rv2), fx2 d.pfadd.ss f0, f0, f0 // y3x1 - x3y1 into adder 2 fld.d VERT_position_offs(rv3), fx3 pfadd.ss f0, f0, f0 // y3x1 - x3y1 into adder 3 bri r1 pfadd.ss f0, f0, ftmp1 // y3x1 - x3y1 into ftmp1 fst.l ftmp1, 4(rcoeffptr)++ // edge C and exit //}}} //{{{ preplanarize_fn_p // // // .globl _preplanarize_fn_p .align 8 // // preplanarize_fn ( float *coeffs, unused, v1, v2, v3, v4 ); // // preplanarize sets up all of the triangle code // // we need to cache all x,y into registers, // precompute x23, x31, x12 and C, and determine // minimax x, y for the triangle // // VICIOUS - returns TRIV_REJECT in r31 // // _preplanarize_fn_p:: #define max_screen_x fx4 #define max_screen_y fy4 adds FACET_vert0_offs, r0, itmp2 // index into vert[2] of connection fld_from(ftmp3,.C00037) ld.l itmp2(rvertex), rvert // rvert is vertex[0] fld_from(ftmp1,.C362436) fld.d VERT_position_offs(rvert), fminx fld.l VERT_z_offs(rvert), fminz dfld_from(max_screen_x,.Cmax_x) fmov.dd fminx, fmaxx fmov.ss fminz, ftexscale // rvert_p should be pointing at conn->verts[0] // nv should be a temp, ditto minus1 adds -2, n_verts, r31 // set up for bla - will loop twice on triangle adds -1, r0, itmp1 // auto-dec for bla adds 4, itmp2, itmp2 // bump vertex for minimax tests bla itmp1, r31, vertloop_db vertloop:: ld.l itmp2(rvertex), rvert vertloop_db:: fld.d VERT_position_offs(rvert), fx2 pfgt.ss fx2, fmaxx, f0 bnc xmax_ok br xmin_ok fmov.ss fx2, fmaxx xmax_ok:: pfgt.ss fminx, fx2, f0 bnc xmin_ok fmov.ss fx2, fminx xmin_ok:: ycheck:: pfgt.ss fy2, fmaxy, f0 bnc ymax_ok br ymin_ok fmov.ss fy2, fmaxy ymax_ok:: pfgt.ss fminy, fy2, f0 bnc ymin_ok fmov.ss fy2, fminy ymin_ok:: zcheck:: bte 0x0, needs_texture, zmin_ok fld.l VERT_z_offs(rvert), fv2 pfgt.ss fv2, ftexscale, f0 bnc texscale_ok br zmin_ok fmov.ss fv2, ftexscale texscale_ok:: pfgt.ss fminz, fv2, f0 bnc zmin_ok fmov.ss fv2, fminz zmin_ok:: bla itmp1, r31, vertloop adds 4, itmp2, itmp2 // re-load x any y registers we have trashed fld.d VERT_position_offs(rv1), fx1 fld.d VERT_position_offs(rv2), fx2 fld.d VERT_position_offs(rv3), fx3 // now pipe up repeated expressions pfsub.ss fy1, fy2, f0 pfsub.ss fy3, fy1, f0 pfsub.ss fy2, fy3, f0 pfsub.ss f0, f0, fy12 pfsub.ss f0, f0, fy31 pfsub.ss f0, f0, fy23 // repeated expressions fx32, fx13, fx21, fC // // The definitive planarization algorithm // // invC=1.0f / (fx1 * (fy2 - fy3)) + // (fx2 * (fy3 - fy1)) + // (fx3 * (fy1 - fy2)); // // eqn[0]= invC*(fy1 * (fv3 - fv2)) + // (fy2 * (fv1 - fv3)) + // (fy3 * (fv2 - fv1)); // // eqn[1]= invC*(fv1 * (fx3 - fx2)) + // (fv2 * (fx1 - fx3)) + // (fv3 * (fx2 - fx1)); // // eqn[2]= invC*(fx1*((fy2*fv3) - (fy3*fv2))) + // (fx2*((fy3*fv1) - (fy1*fv3))) + // (fx3*((fy1*fv2) - (fy2*fv1))); // // 11 ticks all told pfmul.ss fx1, fy23, f0 pfmul.ss fx2, fy31, f0 pfmul.ss fx3, fy12, f0 // use T-reg as staging post... rat1s2.ss fx1, fx3, f0 i2pt.ss f0, f0, f0 rat1s2.ss fx2, fx1, f0 pfsub.ss fx3, fx2, fx13 i2apt.ss f0, f0, f0 pfadd.ss f0, f0, fx21 pfadd.ss f0, f0, fx32 pfadd.ss f0, f0, fC // ****************************************** // clamp minimax against screen max coordinates // now get real minimax xy for binning // // firstly check triv rejection, max < 0 etc. // pfgt.ss ftmp1, fmaxx, f0 bc .triv_reject pfgt.ss ftmp1, fmaxy, f0 bc .triv_reject pfgt.ss fminx, max_screen_x, f0 bc .triv_reject pfgt.ss fminy, max_screen_y, f0 bc .triv_reject // now check binning // get real minx pfgt.ss fminx, f0, f0 bc .no_clamp_fminx fmov.ss f0, fminx .no_clamp_fminx:: // get real miny pfgt.ss fminy, f0, f0 bc .no_clamp_fminy fmov.ss f0, fminy .no_clamp_fminy:: // get real maxx pfgt.ss max_screen_x, fmaxx, f0 bc .no_clamp_fmaxx fmov.ss max_screen_x, fmaxx .no_clamp_fmaxx:: // get real maxy pfgt.ss max_screen_y, fmaxy, f0 bc .no_clamp_fmaxy fmov.ss max_screen_y, fmaxy .no_clamp_fmaxy:: // if entire patch is on-screen, we can just come here // ok, lets think about the minimum area test // we have in registers x13 x21 x32 // and y31 y12 y23 // // // we need to check that (x21*y21) + (x32*y32) + (x13*y13) < min // SO we compute (x21*y12 + x32*y23 + x13*y31) > min // // around 18 tick overhead, reduce to 12 ish by pfs // // fmul.ss fx21, fy12, ftmp1 // 3 // fmul.ss fx32, fy23, ftmp2 // 6 // fmul.ss fx13, fy31, ftmp3 // 9 // fadd.ss ftmp1, ftmp2, ftmp2 // 12 // fadd.ss ftmp3, ftmp2, ftmp2 // 15 // pfgt.ss ftmp2, ftmp1, f0 // 17 pfmul.ss fx21, fy12, f0 // 1 pfmul.ss fx32, fy23, f0 // 2 pfmul.ss fx13, fy31, f0 // 3 i2ap1.ss f0, f0, f0 // 4 last-stage mul into T i2pt.ss f0, f0, f0 // 5 add last-stage mul and T i2ap1.ss f0, f0, f0 // 6 last-stage mul into T again pfadd.ss f0, f0, f0 // 7 adder stage3 now x21*y12 i2apt.ss f0, f0, f0 // 8 add adder 3 and T pfadd.ss f0, f0, f0 // 9 adder stage2 now result pfadd.ss f0, f0, f0 // 10 adder stage3 now result pfadd.ss f0, f0, ftmp2 // 11 pfgt.ss ftmp2, ftmp1, f0 // 12 bnc .triv_reject // // straight out of the i860 prog ref man // // to iterate towards 1/V; // // G_new=G_old*(2.0f-(G_old*V)) // // 20 ticks !? pretty poor frcp.ss fC, ftmp1 // start 1.0 / fC - 2^-8 fmul.ss fC, ftmp1, ftmp2 // guess * divisor // fld.l 16(r31), ftexscale fsub.ss ftmp3, ftmp2, ftmp2 // 2 - (guess * divisor) fld.l iparam2(rv1), fv1 fmul.ss ftmp1, ftmp2, ftmp1 // 2^-15 fld.l iparam2(rv2), fv2 fmul.ss fC, ftmp1, ftmp2 // guess * divisor fsub.ss ftmp3, ftmp2, ftmp2 // 2 - (guess * divisor) fld.l iparam2(rv3), fv3 fmul.ss ftmp1, ftmp2, fC // 2^-23 - run with it bri r1 or 0x0, r0, r31 .triv_reject:: bri r1 or 0x1, r0, r31 //}}} //{{{ _planarize_fn_p pipelined // // Hey Ho Lets Go! // // The definitive planarization algorithm // // invC=1.0f / (fx1 * (fy2 - fy3)) + // (fx2 * (fy3 - fy1)) + // (fx3 * (fy1 - fy2)); // // eqn[0]= invC*(fy1 * (fv3 - fv2)) + // (fy2 * (fv1 - fv3)) + // (fy3 * (fv2 - fv1)); // // a = fv3 - fv2 // b = fv1 - fv3 // c = fv2 - fv1 // d = fy1 * a // e = fy2 * b // f = fy3 * c // g = d + e // h = g + f // eqn[0] = fC * h // // eqn[1]= invC*(fv1 * (fx3 - fx2)) + // (fv2 * (fx1 - fx3)) + // (fv3 * (fx2 - fx1)); // // i = fv1 * fx32 // j = fv2 * fx13 // k = fv3 * fx21 // l = i + j // m = k + l // eqn[1] = fC * m // // eqn[2]= invC*(fx1*((fy2*fv3) - (fy3*fv2))) + // (fx2*((fy3*fv1) - (fy1*fv3))) + // (fx3*((fy1*fv2) - (fy2*fv1))); // // n = fy2 * fv3 // o = fy3 * fv2 // p = fy3 * fv1 // q = fy1 * fv3 // r = fy1 * fv2 // s = fy2 * fv1 // t = n - o // u = p - q // v = r - s // w = fx1 * t // x = fx2 * u // y = fx3 * v // z = w + x // aa= y + z // eqn[2] = invC * aa // #define ft1 ftmp1 #define ft2 ftmp2 #define ft3 ftmp3 .globl _planarize_fn_p .align 8 _planarize_fn_p:: // m1 m2 m3 | T | a1 a2 a3 | KR | t1 t2 t3 pfmul.ss fy2, fv3, f0 // n ? ? | ? | ? ? ? | ? | ? ? ? pfmul.ss fy3, fv2, f0 // o n ? | ? | ? ? ? | ? | ? ? ? pfmul.ss fy3, fv1, f0 // p o n | ? | ? ? ? | ? | ? ? ? mm12ttpm.ss fy1, fv3, f0 // q p o | n | ? ? ? | ? | ? ? ? m12tsm.ss fy1, fv2, f0 // r q p | ? | t ? ? | ? | ? ? ? mm12ttpm.ss fy2, fv1, f0 // s r q | p | ? t ? | ? | ? ? ? m12tsm.ss fv1, fx32, f0 // i s r | ? | u ? t | ? | ? ? ? pfsub.ss fv3, fv2, ft1 // i s r | ? | a u ? | ? | t ? ? mm12ttpm.ss fv2, fx13, f0 // j i s | r | ? a u | ? | t ? ? m12tsm.ss fv3, fx21, ft2 // k j i | ? | v ? a | ? | t u ? pfmul.ss fx1, ft1, ft3 // w k j | ? | v ? a | ? | ? u i pfmul.ss fx2, ft2, ft1 // x w k | ? | v ? a | ? | j ? i pfadd.ss ft1, ft3, ft2 // x w k | ? | l v ? | ? | ? a ? mm12mpm.ss fy1, ft2, ft3 // d x w | ? | ? l v | ? | ? ? k d.pfsub.ss fv1, fv3, ft1 // d x w | ? | b ? l | ? | v ? k nop d.pfsub.ss fv2, fv1, ft2 // d x w | ? | c b ? | ? | v l k fld.l iparam2(rv3), fv3 d.rat1p2.ss ft2, ft3, f0 // ? d x | w | m c b | ? | v ? ? nop d.m12tpm.ss fx3, ft1, ft2 // y ? d | ? | z m c | ? | ? b ? nop d.m12ttpa.ss fy2, ft2, ft1 // e y ? | d | ? z m | ? | c ? ? fld.l iparam2(rv2), fv2 d.m12apm.ss fy3, ft1, ft2 // f e y | d | ? ? z | ? | ? m ? nop d.pfmul.ss fC, ft2, ft1 // e1 f e | d | ? ? z | ? | y ? ? nop d.r2pt.ss fC, f0, ft2 // ? e1 f | ? | g ? ? | ? | y z ? fld.l iparam2(rv1), fv1 d.mrm1p2.ss ft1, ft2, ft3 // ? ? e1| ? | aa g ? | ? | ? ? f nop d.mm12mpm.ss f0, f0, ft2 // ? ? ? | ? | ? aa g | ? | ? e1 f st.l iparam1, 4(rcoeffptr) d.r2ap1.ss ft3, f0, f0 // ? ? ? | ? | h ? aa | ? | ? e1 ? nop d.ra1p2.ss f0, f0, f0 // e2 ? ? | ? | ? h ? | ? | ? e1 ? nop d.i2p1.ss f0, f0, f0 // ? e2 ? | ? | ? ? h | ? | ? e1 ? fst.l ft2, 12(rcoeffptr) d.rat1p2.ss f0, f0, f0 nop d.mi2p1.ss f0, f0, ft1 nop d.mi2p1.ss ft3, f0, f0 fst.l ft1, 16(rcoeffptr)++ mi2p1.ss f0, f0, ft3 bri r1 fnop fst.l ft3, -8(rcoeffptr) #undef ft1 #undef ft2 #undef ft3 //}}} //{{{ _texture_rescale .globl _texture_rescale .align 8 _texture_rescale:: #define eight ftmp3 #define max_by_eight ftmp2 // // ENSURE YOU CALL THIS STRAIGHT AFTER PLANARIZING texu, v and z !!! // // note that at the nearest point on a triangle, the texz value is // forced to 'turn_tex_to_z'. premultiply the far z by 8. then // // while (far_z < turn_tex_to_z) { // enable_pixels_if_lt_turn_tex_to_z_by_8; // far_z *= 8.0f; // } // // i.e repeatedly execute MEMltTREE_C1 ( turn_z_to_tex / 8); // // rcoeffptr points at the next free word // // i just wrote // tree a b c // tree a b c // tree a b c // ==> tree_lt_mem c // tree 8a 8b 8c // tree 8a 8b 8c // tree 8a 8b 8c // // so the first tree is at rcoeffptr-(12*4) fld_from(max_by_eight, _.Cturn_z_to_tex_by_4 ) fld_from(eight, .four_point_0 ) // precompute this opcode in parallel with multiply pxpl5op_1 ( iparam2,Ix_MEMintoENAB, dvpx_enblpush ) // adds 1, r0, extra_stuff // this 1 deals with push / pop opcodes fmul.ss eight, fminz, fminz // minz*=8 adds 4, rcoeffptr, rcoeffptr // so now rcoeffptr is next free opcode // precompute the selective disable opcode // N.B - STAY ENABLED if my texz < (tex_to_z / 8) pxpl5op_2 ( iparam1, Ix_MEMltTREE_C1, dvpx_texz, dvpx_texzbits ) // the delayed branch op fld.l -(12*4)(rcoeffptr), ftmp6 .loop_8x: pfgt.ss fminz, ftexscale, f0 bc .done_8x // do texu - note delayed branch opcode is missing fld.l -(11*4)(rcoeffptr), ftmp7 fld.l -(10*4)(rcoeffptr), ftmp8 fld.l -(9*4)(rcoeffptr), ftmp9 pfmul.ss eight, ftmp7, f0 pfmul.ss eight, ftmp8, f0 pfmul.ss eight, ftmp9, f0 pfmul.ss f0, f0, ftmp7 pfmul.ss f0, f0, ftmp8 pfmul.ss f0, f0, ftmp9 // do the disable pixels thing st.l iparam1, 0(rcoeffptr) fst.l max_by_eight, 4(rcoeffptr) fst.l ftmp6, 8(rcoeffptr) fst.l ftmp7, 12(rcoeffptr) fst.l ftmp8, 16(rcoeffptr) fst.l ftmp9, 20(rcoeffptr) // do texu fld.l -(8*4)(rcoeffptr), ftmp6 fld.l -(7*4)(rcoeffptr), ftmp7 fld.l -(6*4)(rcoeffptr), ftmp8 fld.l -(5*4)(rcoeffptr), ftmp9 pfmul.ss eight, ftmp7, f0 pfmul.ss eight, ftmp8, f0 pfmul.ss eight, ftmp9, f0 pfmul.ss f0, f0, ftmp7 pfmul.ss f0, f0, ftmp8 pfmul.ss f0, f0, ftmp9 fst.l ftmp6, 24(rcoeffptr) fst.l ftmp7, 28(rcoeffptr) fst.l ftmp8, 32(rcoeffptr) fst.l ftmp9, 36(rcoeffptr) // do texv fld.l -(4*4)(rcoeffptr), ftmp6 fld.l -(3*4)(rcoeffptr), ftmp7 fld.l -(2*4)(rcoeffptr), ftmp8 fld.l -(1*4)(rcoeffptr), ftmp9 pfmul.ss eight, ftmp7, f0 pfmul.ss eight, ftmp8, f0 pfmul.ss eight, ftmp9, f0 pfmul.ss f0, f0, ftmp7 pfmul.ss f0, f0, ftmp8 pfmul.ss f0, f0, ftmp9 fst.l ftmp6, 40(rcoeffptr) fst.l ftmp7, 44(rcoeffptr) fst.l ftmp8, 48(rcoeffptr) fst.l ftmp9, 52(rcoeffptr) fmul.ss eight, fminz, fminz adds 7, extra_stuff, extra_stuff adds 56, rcoeffptr, rcoeffptr bte 22, extra_stuff, .done_8x // clamp at a maximum of 3 rescans, roughly 1.5x time br .loop_8x // do something in delayed branch!! fld.l -(12*4)(rcoeffptr), ftmp6 .done_8x: bri r1 st.l iparam2, 0(rcoeffptr) #undef eight #undef max_by_eight //}}} //{{{ locals defines for this fn #define divpl5_xshift 6 #define divpl5_yshift 7 #define bin_size 8 // head, tail #define binchunk_size 2048 // DMA_opcodes[512] // int usage // *next #define BIN_FULL 2032 // byte count of 254*2 #define usage_offs 2040 #define nextbin_offs 2044 #define head_offs 0 #define tail_offs 4 #define x_bins_shift 4 #define x_bins_bytes 128 // 16 bins in 1024 //}}} //{{{ the incredibly expensive 'bin is full branch' // dont panic - // this branch is infrequent - happens every 256 triangles // note that it can result in a call to malloc! // // if (bin->usage == BIN_FULL) { // binchunk *nextbin=next_binchunk (); // // bin->DMA_opcodes[usage++]=(int) nextbin; // bin->DMA_opcodes[usage++]=DMA_GOTO; // bin=nextbin; // xbin->tail=bin; // usage=0; // } // // damn, we enter C land here - push all registers onto stack // note that floating-point registers are no longer needed // .align 8 bin_was_full:: st.l r16, -4(sp) st.l r17, -8(sp) st.l r18, -12(sp) st.l r19, -16(sp) st.l r20, -20(sp) st.l r21, -24(sp) st.l r22, -28(sp) st.l r23, -32(sp) st.l r24, -36(sp) st.l r25, -40(sp) st.l r26, -44(sp) st.l r27, -48(sp) st.l r28, -52(sp) st.l r29, -56(sp) st.l r30, -60(sp) st.l r1, -64(sp) call _next_binchunk adds -80, sp, sp // lets restore registers adds 80, sp, sp ld.l -8(sp), r17 ld.l -12(sp), r18 ld.l -16(sp), r19 ld.l -20(sp), r20 ld.l -24(sp), r21 ld.l -28(sp), r22 ld.l -32(sp), r23 ld.l -36(sp), r24 ld.l -40(sp), r25 ld.l -44(sp), r26 ld.l -48(sp), r27 ld.l -52(sp), r28 ld.l -56(sp), r29 ld.l -60(sp), r30 ld.l -64(sp), r1 // now iparam1 holds nextbin adds usage, bin, r31 // construct pointer to coeff store st.l iparam1, nextbin_offs(bin) // do linked list thing mov iparam1, bin // return val from next_binchunk st.l iparam1, 0(r31) // save it away adds DMA_GOTO, r0, iparam1 // chain in new bin st.l iparam1, 4(r31) // and save this opcode away // restore iparam1 ld.l -4(sp), r16 // so now to patch up the new bin - simply fall thru // into the bin not full branch mov r0, usage bri r1 st.l bin, tail_offs(xbin) //}}} //{{{ safe_binitize_fn pipelined intro // void safe_binitize ( int macro_lo, int macro_hi, // float fminx, float fminy, // float fmaxx, float fmaxy, // int screen_bins_x ) // // binitize a triangle known to be on-screen, i.e minimax x y // are within screen-space // .globl _safe_binitize_fn .align 8 // binitize a primitive .align 8 _safe_binitize_fn:: // // NB fxfr MUST have NOP as companion, or you are shafted // // minx=(int) fminx; // miny=(int) fminy; // maxx=(int) fmaxx; // maxy=(int) fmaxy; // minx >>= divpl5_xshift; // miny >>= divpl5_yshift; // maxx >>= divpl5_xshift; // maxy >>= divpl5_yshift; // { // screenbin *lbin=&screenbins[(miny< go mango // rcoeffptr holds last place we wrote // rcoeffsave is base of data // so, (rcoeffptr+7 - rcoeffbase) >> 3 gives n_words ixfr rcoeffsave, f24 // fv1 adds 7, rcoeffptr, r31 subs r31, rcoeffsave, rcoeffsave shr 0x3, rcoeffsave, r31 orh (DMA_SEND_VAL>>16)&0xffff, r31, iparam2 adds 35, rcoeffptr, rcoeffptr d.pftrunc.sd fminx, f0 andnot 31, rcoeffptr, rcoeffsave d.pftrunc.sd fminy, f0 orh ha%_screenbins, r0, r31 d.pftrunc.sd fmaxx, f0 ld.l l%_screenbins(r31), r31 d.pftrunc.sd fmaxy, ftmp1 ixfr iparam2, f25 // fv2 d.fxfr ftmp1, itmp1 nop d.pfadd.sd f0, f0, ftmp3 shr divpl5_xshift, itmp1, iminx d.fxfr ftmp3, itmp2 nop d.pfadd.sd f0, f0, ftmp1 shr divpl5_yshift, itmp2, iminy d.fxfr ftmp1, itmp1 nop pfadd.sd f0, f0, ftmp3 shr divpl5_xshift, itmp1, imaxx fxfr ftmp3, itmp2 nop shl x_bins_shift, iminy, lbin adds iminx, lbin, lbin shr divpl5_yshift, itmp2, imaxy // each bin is head/tail pointer, so 8 bytes per bin entry shl 3, lbin, lbin adds r31, lbin, lbin subs imaxy, iminy, ycnt // while (ycnt) _y_loop:: mov lbin, xbin _y_loopdb:: subs imaxx, iminx, xcnt // while (xcnt) _x_loop:: ld.l tail_offs(xbin), bin _x_loopdb:: ld.l usage_offs(bin), usage xor BIN_FULL, usage, r0 bnc.t _bin_not_full fst.d f24, usage(bin) _bin_full:: st.l r1, -4(sp) call bin_was_full adds -8, sp, sp adds 8, sp, sp ld.l -4(sp), r1 fst.d f24, usage(bin) _bin_not_full:: // bin->DMA_opcodes[usage++]=macro_lo; // bin->DMA_opcodes[usage++]=macro_hi; // bin->usage=usage; // xbin++; adds 8, usage, usage adds bin_size, xbin, xbin st.l usage, usage_offs(bin) _bump_x:: // lbin+=screen_bins_x; bte r0, xcnt, _bump_y ld.l tail_offs(xbin), bin br _x_loopdb adds -1, xcnt, xcnt _bump_y:: bte r0, ycnt, _exit_binitize adds x_bins_bytes, lbin, lbin adds -1, ycnt, ycnt br _y_loopdb mov lbin, xbin _exit_binitize: bri r1 nop //}}} //{{{ chunk_fn .align 8 chunk_fn:: subs rcoeffmax, rcoeffsave, r0 bnc .dont_grab_chunk // do we need to malloc, or shall we just chain the list // find last_coeffchunk from rcoeffmax // well - rcoeffmax=lastcoeffchunk+65532-512, so // add 512 to rcoeffmax, and we have the next pointer // hmm trace regs here ? ld.l 512(rcoeffmax), rcoeffsave // rcoeffsave=lcc->next btne 0x0, rcoeffsave, .dont_malloc st.l r16, -4(sp) st.l r17, -8(sp) st.l r18, -12(sp) st.l r19, -16(sp) st.l r20, -20(sp) st.l r21, -24(sp) st.l r22, -28(sp) st.l r23, -32(sp) st.l r24, -36(sp) st.l r25, -40(sp) st.l r26, -44(sp) st.l r27, -48(sp) st.l r28, -52(sp) st.l r29, -56(sp) st.l r30, -60(sp) st.l r1, -64(sp) mov 65536, r16 call _newBytes adds -80, sp, sp // lets restore registers adds 80, sp, sp ld.l -8(sp), r17 ld.l -12(sp), r18 ld.l -16(sp), r19 ld.l -20(sp), r20 ld.l -24(sp), r21 ld.l -28(sp), r22 ld.l -32(sp), r23 ld.l -36(sp), r24 ld.l -40(sp), r25 ld.l -44(sp), r26 ld.l -48(sp), r27 ld.l -52(sp), r28 ld.l -56(sp), r29 ld.l -60(sp), r30 ld.l -64(sp), r1 mov r16, rcoeffsave // rcoeffsave=malloc(64k) st.l r16, 512(rcoeffmax) // lcc->next = rcoeffsave mov chunk_next_offset, r31 fst.l f0, r31(rcoeffsave) // rcoeffsave->next = NULL .dont_malloc:: // last_coeffchunk=next, // rcoeffptr=next, // rcoeffmax=next+65020, orh ha%_last_coeffchunk, r0, r31 st.l rcoeffsave, l%_last_coeffchunk(r31) mov (chunk_next_offset-512), r31 adds r31, rcoeffsave, rcoeffmax .dont_grab_chunk:: bri r1 nop //}}} //{{{ opacity_intro(label1, label2) #define opacity_intro(label1,label2) \ label1::;\ ld.l FACET_touched_offs(rvertex), r31;\ ld.l FACET_nverts_offs(rvertex), n_verts; \ bte 0x0, r31, label2; \ call chunk_fn; \ ld.l (FACET_vert0_offs+0)(rvertex), rv1; \ adds 12, rcoeffsave, rcoeffptr; \ ld.l (FACET_vert0_offs+4)(rvertex), rv2; \ or Ix_SETENABS(), r0, iparam2; \ ld.l (FACET_vert0_offs+8)(rvertex), rv3; \ st.l iparam2, 0(rcoeffsave); \ pxpl5op_2(iparam2,Ix_MEMgeSCA_S1, dvpx_opacity, dvpx_opacitybits); \ st.l iparam2, 4(rcoeffsave); \ or P_MEMgeSCA(dvpx_opacity, dvpx_opacitybits), r0, iparam2; \ st.l iparam2, 8(rcoeffsave); \ st.l opcode0, 12(rcoeffsave) //}}} //{{{ ignore_opacity_intro(label1,label2) #define ignore_opacity_intro(label1,label2) \ label1::;\ ld.l FACET_touched_offs(rvertex), r31;\ ld.l FACET_nverts_offs(rvertex), n_verts; \ bte 0x0, r31, label2; \ call chunk_fn; \ ld.l (FACET_vert0_offs+0)(rvertex), rv1; \ adds 0, rcoeffsave, rcoeffptr; \ ld.l (FACET_vert0_offs+4)(rvertex), rv2; \ or Ix_SETENABS(), r0, iparam2; \ ld.l (FACET_vert0_offs+8)(rvertex), rv3; \ st.l iparam2, 0(rcoeffptr) //}}} //{{{ next_poly(label) #define next_poly(label1,label2) \ label2::;\ adds -1, n_polygons, n_polygons; \ xor 0x0000, n_polygons, r0; \ bnc.t label1; \ ld.l 0(rvertex), rvertex //}}} // ///////////////////////////// // the currently implemented functions // _tri_zb_rgb // _tri_zb_rgb_t // _tri_zb_f // _tri_zb_f_t // // NOTE the texturing triangle functions now need to compute // zscale based on smallest z in triangle, and multiply up // z, u and v by this number // // use register backwards to hold edge opcode, so intro needs to go, // if backwards, opcode=tree_ge_zero, else opcode=tree_lt_zero // // // triangle, z-buffered, flat // //{{{ _tri_zb_f .globl _tri_zb_f .align 8 _tri_zb_f:: triangle_entry(back_000) adds 0, r0, needs_texture // 4 4 // // new opacity code // opacity_intro(label000, label001) call _preplanarize_fn_p adds VERT_z_offs, r0, iparam2 // should we just exit ? xor 0x0, r31, r0 bnc label001 pxpl5op_2_l(iparam1,Ix_MEMltTREE_L3,dvpx_zbuf,dvpx_zbufbits) call edgize_fn pxpl5op_2_h(iparam1,Ix_MEMltTREE_L3,dvpx_zbuf,dvpx_zbufbits) call _planarize_fn_p or VERT_z_offs, r0, iparam2 fld.l FACET_r_offs(rvertex), fv2 // store 'do zbuffer, no arguments' into coeff store pxpl5op_2(iparam1,Ix_TREEintoMEM_L0, dvpx_zbuf, dvpx_zbufbits) st.l iparam1, 4(rcoeffptr) adds 4, rcoeffptr, rcoeffptr pxpl5op_2(iparam2,Ix_TREEclmpintoMEM_C1, dvpx_r24, 8 ) st.l iparam2, 4(rcoeffptr) pxpl5op_2(iparam1,P_TREEclmpintoMEM, dvpx_r24, 8 ) st.l iparam1, 8(rcoeffptr) fst.l fv2, 12(rcoeffptr)++ fld.l FACET_g_offs(rvertex), fv2 pxpl5op_2(iparam2,Ix_TREEclmpintoMEM_C1, dvpx_g24, 8 ) st.l iparam2, 4(rcoeffptr) pxpl5op_2(iparam1,P_TREEclmpintoMEM, dvpx_g24, 8 ) st.l iparam1, 8(rcoeffptr) fst.l fv2, 12(rcoeffptr)++ fld.l FACET_b_offs(rvertex), fv2 pxpl5op_2(iparam2,Ix_TREEclmpintoMEM_C1, dvpx_b24, 8 ) st.l iparam2, 4(rcoeffptr) pxpl5op_2(iparam1,P_TREEclmpintoMEM, dvpx_b24, 8 ) st.l iparam1, 8(rcoeffptr) fst.l fv2, 12(rcoeffptr)++ pxpl5op_2(iparam1,Ix_SCAintoMEM_S1, dvpx_scalar, dvpx_scalarbits) st.l iparam1, 4(rcoeffptr) fst.l fmaterial, 8(rcoeffptr)++ call _safe_binitize_fn fst.l f0, 4(rcoeffptr)++ // addu 10, r0, iparam3 next_poly(label000,label001) .bomb_tri_zb_f:: triangle_exit //}}} // triangle, z-buffered, rgb // //{{{ _tri_zb_rgb .globl _tri_zb_rgb .align 8 _tri_zb_rgb:: triangle_entry(back_001) adds 0, r0, needs_texture // 4 4 // // new opacity code // opacity_intro(label002,label003) call _preplanarize_fn_p adds VERT_z_offs, r0, iparam2 // should we just exit ? xor 0x0, r31, r0 bnc label003 pxpl5op_2_l(iparam1,Ix_MEMltTREE_L3,dvpx_zbuf,dvpx_zbufbits) call edgize_fn pxpl5op_2_h(iparam1,Ix_MEMltTREE_L3,dvpx_zbuf,dvpx_zbufbits) call _planarize_fn_p or VERT_r_offs, r0, iparam2 // store 'do zbuffer, no arguments' into coeff store pxpl5op_2(iparam1,Ix_TREEintoMEM_L0, dvpx_zbuf, dvpx_zbufbits) st.l iparam1, 4(rcoeffptr) // 2 23 pxpl5op_2(iparam2,Ix_SCAintoMEM_S1, dvpx_scalar, dvpx_scalarbits) st.l iparam2, 8(rcoeffptr) fst.l fmaterial, 12(rcoeffptr)++ // 15 38 pxpl5op_2(iparam2,Ix_TREEclmpintoMEM_L3, dvpx_r24, 8 ) st.l iparam2, 4(rcoeffptr) adds 4, rcoeffptr, rcoeffptr pxpl5op_2(iparam1,P_TREEclmpintoMEM, dvpx_r24, 8 ) call _planarize_fn_p or VERT_g_offs, r0, iparam2 pxpl5op_2(iparam2,Ix_TREEclmpintoMEM_L3, dvpx_g24, 8 ) st.l iparam2, 4(rcoeffptr) adds 4, rcoeffptr, rcoeffptr pxpl5op_2(iparam1,P_TREEclmpintoMEM, dvpx_g24, 8 ) call _planarize_fn_p or VERT_b_offs, r0, iparam2 pxpl5op_2(iparam2,Ix_TREEclmpintoMEM_L3, dvpx_b24, 8 ) st.l iparam2, 4(rcoeffptr) adds 4, rcoeffptr, rcoeffptr pxpl5op_2(iparam1,P_TREEclmpintoMEM, dvpx_b24, 8 ) call _planarize_fn_p or VERT_b_offs, r0, iparam2 // DMAop_1 (iparam2,DMA_SEND, 19 ) // // fix_rcoeffptr(19) // // mov rcoeffsave, iparam1 call _safe_binitize_fn fst.l f0, 4(rcoeffptr)++ // addu 10, r0, iparam3 next_poly(label002,label003) .bomb_tri_zb_rgb:: triangle_exit //}}} // // Now the textured triangles // NB if you need 1 bit of pushed storage during triangle processing, // use texz LSB, it is dropped before perspective divide... // // // all these functions need the texture rescale // // // triangle, z-buffered, flat, textured // //{{{ _tri_zb_f_t .globl _tri_zb_f_t .align 8 _tri_zb_f_t:: triangle_entry(back_002) adds 1, r0, needs_texture opacity_intro(label004,label005) call _preplanarize_fn_p adds VERT_z_offs, r0, iparam2 // should we just exit ? xor 0x0, r31, r0 bnc label005 pxpl5op_2_l(iparam1,Ix_MEMltTREE_L3,dvpx_zbuf,dvpx_zbufbits) call edgize_fn pxpl5op_2_h(iparam1,Ix_MEMltTREE_L3,dvpx_zbuf,dvpx_zbufbits) // TEXTURIZE TO FIND ZSCALE fld_from ( ftmp2, _.Cturn_z_to_tex ) frcp.ss ftexscale, ftmp1 fmul.ss ftmp1, ftmp2, ftmp1 // store 'do zbuffer, no arguments' into coeff store pxpl5op_2(iparam1,Ix_TREEintoMEM_L0, dvpx_zbuf, dvpx_zbufbits) fmul.ss fv1, ftmp1, ftmp7 st.l iparam1, 20(rcoeffptr) fmul.ss fv2, ftmp1, ftmp8 fmul.ss fv3, ftmp1, ftmp9 fmul.ss fminz, ftmp1, fminz pxpl5op_2(iparam1,Ix_MEMltTREE_L3,dvpx_zbuf,dvpx_zbufbits) call _planarize_fn_p or VERT_tex_u_offs, r0, iparam2 fmov.ss ftmp7, fv1 fmov.ss ftmp8, fv2 fmov.ss ftmp9, fv3 // push enable flag for texture support pxpl5op_1 ( iparam1,Ix_ENABintoMEM, dvpx_enblpush ); st.l iparam1, 8(rcoeffptr) adds 8, rcoeffptr, rcoeffptr // 4 25 tex z-coordinate pxpl5op_2(iparam1,Ix_TREEintoMEM_L3, dvpx_texz, dvpx_texzbits) call _planarize_fn_p or VERT_tex_u_offs, r0, iparam2 // fix u-coordinate fld_from ( ftmp2, _Cdelta_u ) pfadd.ss ftmp2, fv1, f0 pfadd.ss ftmp2, fv2, f0 pfadd.ss ftmp2, fv3, f0 pfadd.ss f0, f0, fv1 m12apm.ss ftmp7, fv1, fv2 m12apm.ss ftmp8, fv2, fv3 pfmul.ss ftmp9, fv3, f0 pfmul.ss f0, f0, fv1 pfmul.ss f0, f0, fv2 pfmul.ss f0, f0, fv3 // 4 29 tex v-coordinate pxpl5op_2(iparam1,Ix_TREEintoMEM_L3, dvpx_texu, dvpx_texubits) call _planarize_fn_p or VERT_tex_v_offs, r0, iparam2 // fix v-coordinate fld_from ( ftmp2, _Cdelta_v ) pfadd.ss ftmp2, fv1, f0 pfadd.ss ftmp2, fv2, f0 pfadd.ss ftmp2, fv3, f0 pfadd.ss f0, f0, fv1 m12apm.ss ftmp7, fv1, fv2 m12apm.ss ftmp8, fv2, fv3 pfmul.ss ftmp9, fv3, f0 pfmul.ss f0, f0, fv1 pfmul.ss f0, f0, fv2 pfmul.ss f0, f0, fv3 // 4 33 tex u-coordinate pxpl5op_2(iparam1,Ix_TREEintoMEM_L3, dvpx_texv, dvpx_texvbits) call _planarize_fn_p or VERT_z_offs, r0, iparam2 // do texture dynamic range frig call _texture_rescale adds 1, r0, extra_stuff // 9 42 fld.l FACET_r_offs(rvertex), fv2 pxpl5op_2(iparam2,Ix_TREEclmpintoMEM_C1, dvpx_r24, 8 ) st.l iparam2, 4(rcoeffptr) pxpl5op_2(iparam1,P_TREEclmpintoMEM, dvpx_r24, 8 ) st.l iparam1, 8(rcoeffptr) fst.l fv2, 12(rcoeffptr)++ fld.l FACET_g_offs(rvertex), fv2 pxpl5op_2(iparam2,Ix_TREEclmpintoMEM_C1, dvpx_g24, 8) st.l iparam2, 4(rcoeffptr) pxpl5op_2(iparam1,P_TREEclmpintoMEM, dvpx_g24, 8 ) st.l iparam1, 8(rcoeffptr) fst.l fv2, 12(rcoeffptr)++ fld.l FACET_b_offs(rvertex), fv2 pxpl5op_2(iparam2,Ix_TREEclmpintoMEM_C1, dvpx_b24, 8) st.l iparam2, 4(rcoeffptr) pxpl5op_2(iparam1,P_TREEclmpintoMEM, dvpx_b24, 8 ) st.l iparam1, 8(rcoeffptr) fst.l fv2, 12(rcoeffptr)++ // 2 44 pxpl5op_2(iparam1,Ix_SCAintoMEM_S1, dvpx_scalar, dvpx_scalarbits) st.l iparam1, 4(rcoeffptr) fst.l fmaterial, 8(rcoeffptr)++ // adds 22, extra_stuff, iparam2 // orh (DMA_SEND_VAL>>16)&0xffff, iparam2, iparam2 // adds 35, rcoeffptr, rcoeffptr // andnot 31, rcoeffptr, rcoeffptr // adds -4, rcoeffptr, rcoeffptr // mov rcoeffsave, iparam1 call _safe_binitize_fn fst.l f0, 4(rcoeffptr)++ // addu 10, r0, iparam3 next_poly(label004,label005) .bomb_tri_zb_f_t:: triangle_exit //}}} // triangle, z-buffered, rgb, textured // 24 64-bit words // //{{{ _tri_zb_rgb_t .globl _tri_zb_rgb_t .align 8 _tri_zb_rgb_t:: triangle_entry(back_003) adds 1, r0, needs_texture // 4 4 // // new opacity code // opacity_intro(label006,label007) call _preplanarize_fn_p adds VERT_z_offs, r0, iparam2 // should we just exit ? xor 0x0, r31, r0 bnc label007 pxpl5op_2_l(iparam1,Ix_MEMltTREE_L3,dvpx_zbuf,dvpx_zbufbits) call edgize_fn pxpl5op_2_h(iparam1,Ix_MEMltTREE_L3,dvpx_zbuf,dvpx_zbufbits) // TEXTURIZE TO FIND ZSCALE fld_from ( ftmp2, _.Cturn_z_to_tex ) frcp.ss ftexscale, ftmp1 fmul.ss ftmp1, ftmp2, ftmp1 pfmul.ss fv1, ftmp1, f0 pfmul.ss fv2, ftmp1, f0 pfmul.ss fv3, ftmp1, f0 pfmul.ss f0, f0, ftmp7 pfmul.ss f0, f0, ftmp8 pfmul.ss f0, f0, ftmp9 call _planarize_fn_p or VERT_tex_u_offs, r0, iparam2 // push enable flag for texture support pxpl5op_1 ( iparam1,Ix_ENABintoMEM, dvpx_enblpush ); st.l iparam1, 4(rcoeffptr) pxpl5op_2(iparam1,Ix_TREEintoMEM_L0, dvpx_zbuf, dvpx_zbufbits) st.l iparam1, 8(rcoeffptr) fmov.ss ftmp7, fv1 adds 8, rcoeffptr, rcoeffptr // cater for tree_l0 and enable push fmov.ss ftmp8, fv2 pxpl5op_2(iparam1,Ix_TREEintoMEM_L3, dvpx_texz, dvpx_texzbits) fmov.ss ftmp9, fv3 // 4 25 tex z-coordinate call _planarize_fn_p or VERT_tex_u_offs, r0, iparam2 // fix u-coordinate // fix v-coordinate fld_from ( ftmp2, _Cdelta_u ) pfadd.ss ftmp2, fv1, f0 pfadd.ss ftmp2, fv2, f0 pfadd.ss ftmp2, fv3, f0 pfadd.ss f0, f0, fv1 m12apm.ss ftmp7, fv1, fv2 m12apm.ss ftmp8, fv2, fv3 pfmul.ss ftmp9, fv3, f0 pfmul.ss f0, f0, fv1 pfmul.ss f0, f0, fv2 pfmul.ss f0, f0, fv3 // 4 29 tex v-coordinate pxpl5op_2(iparam1,Ix_TREEintoMEM_L3, dvpx_texu, dvpx_texubits) call _planarize_fn_p or VERT_tex_v_offs, r0, iparam2 // fix v-coordinate // fix v-coordinate fld_from ( ftmp2, _Cdelta_v ) pfadd.ss ftmp2, fv1, f0 pfadd.ss ftmp2, fv2, f0 pfadd.ss ftmp2, fv3, f0 pfadd.ss f0, f0, fv1 m12apm.ss ftmp7, fv1, fv2 m12apm.ss ftmp8, fv2, fv3 pfmul.ss ftmp9, fv3, f0 pfmul.ss f0, f0, fv1 pfmul.ss f0, f0, fv2 pfmul.ss f0, f0, fv3 // 4 33 tex u-coordinate pxpl5op_2(iparam1,Ix_TREEintoMEM_L3, dvpx_texv, dvpx_texvbits) call _planarize_fn_p or VERT_r_offs, r0, iparam2 // do texture dynamic range frig call _texture_rescale adds 1, r0, extra_stuff // 2 35 pxpl5op_2(iparam1,Ix_SCAintoMEM_S1, dvpx_scalar, dvpx_scalarbits ) st.l iparam1, 4(rcoeffptr) fst.l fmaterial, 8(rcoeffptr)++ // 15 50 pxpl5op_2(iparam2,Ix_TREEclmpintoMEM_L3, dvpx_r24, 8 ) st.l iparam2, 4(rcoeffptr) adds 4, rcoeffptr, rcoeffptr pxpl5op_2(iparam1,P_TREEclmpintoMEM, dvpx_r24, 8 ) call _planarize_fn_p or VERT_g_offs, r0, iparam2 pxpl5op_2(iparam2,Ix_TREEclmpintoMEM_L3, dvpx_g24, 8 ) st.l iparam2, 4(rcoeffptr) adds 4, rcoeffptr, rcoeffptr pxpl5op_2(iparam1,P_TREEclmpintoMEM, dvpx_g24, 8 ) call _planarize_fn_p or VERT_b_offs, r0, iparam2 pxpl5op_2(iparam2,Ix_TREEclmpintoMEM_L3, dvpx_b24, 8 ) st.l iparam2, 4(rcoeffptr) adds 4, rcoeffptr, rcoeffptr pxpl5op_2(iparam1,P_TREEclmpintoMEM, dvpx_b24, 8 ) call _planarize_fn_p or VERT_b_offs, r0, iparam2 // adds 25, extra_stuff, iparam2 // orh (DMA_SEND_VAL>>16)&0xffff, iparam2, iparam2 // adds 35, rcoeffptr, rcoeffptr // andnot 31, rcoeffptr, rcoeffptr // adds -4, rcoeffptr, rcoeffptr // mov rcoeffsave, iparam1 call _safe_binitize_fn fst.l f0, 4(rcoeffptr)++ // addu 10, r0, iparam3 next_poly(label006,label007) .bomb_tri_zb_rgb_t:: triangle_exit //}}} // triangle, z-buffered, rgb, textured, opacity-per-vertex // 24 64-bit words // //{{{ _tri_zb_rgb_o_t .globl _tri_zb_rgb_o_t .align 8 _tri_zb_rgb_o_t:: triangle_entry(back_004) adds 1, r0, needs_texture // 1 1 // // new opacity code // // destination for per-triangle loop - what registers are still in shape? ignore_opacity_intro(label008,label009) call _preplanarize_fn_p adds VERT_a_offs, r0, iparam2 // should we just exit ? xor 0x0, r31, r0 bnc label009 pxpl5op_2_l(iparam1,Ix_MEMgeTREE_L3, dvpx_opacity, dvpx_opacitybits ) call edgize_fn pxpl5op_2_h(iparam1,Ix_MEMgeTREE_L3, dvpx_opacity, dvpx_opacitybits ) call _planarize_fn_p or VERT_z_offs, r0, iparam2 pxpl5op_2(iparam1,Ix_MEMltTREE_L3, dvpx_zbuf,dvpx_zbufbits) // 5 22 // TEXTURIZE TO FIND ZSCALE fld_from ( ftmp2, _.Cturn_z_to_tex ) frcp.ss ftexscale, ftmp1 fmul.ss ftmp1, ftmp2, ftmp1 pfmul.ss fv1, ftmp1, f0 pfmul.ss fv2, ftmp1, f0 pfmul.ss fv3, ftmp1, f0 pfmul.ss f0, f0, ftmp7 pfmul.ss f0, f0, ftmp8 pfmul.ss f0, f0, ftmp9 call _planarize_fn_p or VERT_tex_u_offs, r0, iparam2 // push enable flag for texture support pxpl5op_1 ( iparam1,Ix_ENABintoMEM, dvpx_enblpush ); st.l iparam1, 4(rcoeffptr) pxpl5op_2(iparam1,Ix_TREEintoMEM_L0, dvpx_zbuf, dvpx_zbufbits) st.l iparam1, 8(rcoeffptr) fmov.ss ftmp7, fv1 adds 8, rcoeffptr, rcoeffptr // cater for tree_l0 and enable push fmov.ss ftmp8, fv2 pxpl5op_2(iparam1,Ix_TREEintoMEM_L3, dvpx_texz, dvpx_texzbits) fmov.ss ftmp9, fv3 // 4 26 tex z-coordinate call _planarize_fn_p or VERT_tex_u_offs, r0, iparam2 // fix u-coordinate // fix v-coordinate fld_from ( ftmp2, _Cdelta_u ) pfadd.ss ftmp2, fv1, f0 pfadd.ss ftmp2, fv2, f0 pfadd.ss ftmp2, fv3, f0 pfadd.ss f0, f0, fv1 m12apm.ss ftmp7, fv1, fv2 m12apm.ss ftmp8, fv2, fv3 pfmul.ss ftmp9, fv3, f0 pfmul.ss f0, f0, fv1 pfmul.ss f0, f0, fv2 pfmul.ss f0, f0, fv3 // 4 30 tex v-coordinate pxpl5op_2(iparam1,Ix_TREEintoMEM_L3, dvpx_texu, dvpx_texubits) call _planarize_fn_p or VERT_tex_v_offs, r0, iparam2 // fix v-coordinate // fix v-coordinate fld_from ( ftmp2, _Cdelta_v ) pfadd.ss ftmp2, fv1, f0 pfadd.ss ftmp2, fv2, f0 pfadd.ss ftmp2, fv3, f0 pfadd.ss f0, f0, fv1 m12apm.ss ftmp7, fv1, fv2 m12apm.ss ftmp8, fv2, fv3 pfmul.ss ftmp9, fv3, f0 pfmul.ss f0, f0, fv1 pfmul.ss f0, f0, fv2 pfmul.ss f0, f0, fv3 // 4 34 tex u-coordinate pxpl5op_2(iparam1,Ix_TREEintoMEM_L3, dvpx_texv, dvpx_texvbits) call _planarize_fn_p or VERT_r_offs, r0, iparam2 // do texture dynamic range frig call _texture_rescale adds 1, r0, extra_stuff // 2 36 pxpl5op_2(iparam1,Ix_SCAintoMEM_S1, dvpx_scalar, dvpx_scalarbits ) st.l iparam1, 4(rcoeffptr) fst.l fmaterial, 8(rcoeffptr)++ // 15 51 pxpl5op_2(iparam2,Ix_TREEclmpintoMEM_L3, dvpx_r24, 8 ) st.l iparam2, 4(rcoeffptr) adds 4, rcoeffptr, rcoeffptr pxpl5op_2(iparam1,P_TREEclmpintoMEM, dvpx_r24, 8 ) call _planarize_fn_p or VERT_g_offs, r0, iparam2 pxpl5op_2(iparam2,Ix_TREEclmpintoMEM_L3, dvpx_g24, 8 ) st.l iparam2, 4(rcoeffptr) adds 4, rcoeffptr, rcoeffptr pxpl5op_2(iparam1,P_TREEclmpintoMEM, dvpx_g24, 8 ) call _planarize_fn_p or VERT_b_offs, r0, iparam2 pxpl5op_2(iparam2,Ix_TREEclmpintoMEM_L3, dvpx_b24, 8 ) st.l iparam2, 4(rcoeffptr) adds 4, rcoeffptr, rcoeffptr pxpl5op_2(iparam1,P_TREEclmpintoMEM, dvpx_b24, 8 ) call _planarize_fn_p or VERT_b_offs, r0, iparam2 // fst.l f0, 4(rcoeffptr)++ // adds 26, extra_stuff, iparam2 // orh (DMA_SEND_VAL>>16)&0xffff, iparam2, iparam2 // adds 35, rcoeffptr, rcoeffptr // andnot 31, rcoeffptr, rcoeffptr // adds -4, rcoeffptr, rcoeffptr // mov rcoeffsave, iparam1 call _safe_binitize_fn fst.l f0, 4(rcoeffptr)++ // addu 10, r0, iparam3 next_poly(label008,label009) .bomb_tri_zb_rgb_o_t:: triangle_exit //}}} #if 0 //{{{ pxpl5op_2_l(iparam1,Ix_MEMltTREE_L3,dvpx_zbuf,dvpx_zbufbits) call edgize_fn pxpl5op_2_h(iparam1,Ix_MEMltTREE_L3,dvpx_zbuf,dvpx_zbufbits) //}}} //{{{ spheres // // s p h e r e s // //{{{ presphereize // // VICIOUS - returns TRIV_REJECT in r31 // .align 8 _prespherize:: fld.d (0+VERT_position_offs)(rv1), fxc // load x and y fld.d (8+VERT_position_offs)(rv1), fzc // load z and radius fld_from ( ftmp1, .C362436 ) dfld_from ( max_screen_x, .Cmax_x ) pfadd.ss fxc, frad, f0 pfadd.ss fyc, frad, f0 pfsub.ss fxc, frad, f0 pfsub.ss fyc, frad, fmaxx // cool pipelining here - dig the pfgt! // ****************************************** // clamp minimax against screen max coordinates // now get real minimax xy for binning // // firstly check triv rejection, max < 0 etc. // pfgt.ss ftmp1, fmaxx, fmaxy bc .sph_triv_reject pfgt.ss ftmp1, fmaxy, fminx bc .sph_triv_reject pfgt.ss fminx, max_screen_x, fminy bc .sph_triv_reject pfgt.ss fminy, max_screen_y, f0 bc .sph_triv_reject pfgt.ss fminy, fmaxy, f0 bc .sph_triv_reject pfgt.ss fminx, fmaxx, f0 bc .sph_triv_reject // now check binning // get real minx pfgt.ss fminx, f0, f0 bc .no_clamp_sfminx fmov.ss f0, fminx .no_clamp_sfminx:: // get real miny pfgt.ss fminy, f0, f0 bc .no_clamp_sfminy fmov.ss f0, fminy .no_clamp_sfminy:: // get real maxx pfgt.ss max_screen_x, fmaxx, f0 bc .no_clamp_sfmaxx fmov.ss max_screen_x, fmaxx .no_clamp_sfmaxx:: // get real maxy pfgt.ss max_screen_y, fmaxy, f0 bc .no_clamp_sfmaxy fmov.ss max_screen_y, fmaxy .no_clamp_sfmaxy:: fmul.ss fxc, fxc, ftmp1 fld_from(ftwo,.C00037) fld.d (16+VERT_position_offs)(rv2), flx fmul.ss fyc, fyc, ftmp2 fld.l (24+VERT_position_offs)(rv2), flz fmul.ss frad, frad, fr2 fld_from ( fminus1, .fminus_one ) fadd.ss ftmp1, ftmp2, fx2y2 // do 1.0f / r2 frcp.ss fr2, ftmp1 // error 2^-7 fmul.ss fr2, ftmp1, ftmp2 // guess * divisor fld.l (28+VERT_position_offs)(rv1), frz fsub.ss ftwo, ftmp2, ftmp2 // 2 - (guess * divisor) pxpl5op_1 ( iparam1, Ix_FBITS, 22 ) fmul.ss ftmp1, ftmp2, fr12 // accurate to 2^-15 pxpl5op_1 ( iparam2, P_FBITS, 22 ) bri r1 or 0x0, r0, r31 .sph_triv_reject:: bri r1 or 0x1, r0, r31 //}}} // sphere, z-buffered, rgb lit // 17 64-bit words // //{{{ _sph_zb_rgb .globl _sphere_zb_rgb .align 8 _sphere_zb_rgb:: triangle_entry(sphere_zb_rgb_mesh, back_005) sphere_zb_rgb_mesh:: // 1 1 // call _prespherize st.l iparam2, 4(rcoeffptr) // should we just exit ? xor 0x0, r31, r0 bnc .bomb_sphere_zb_rgb // r2-=x2y2; // // fA=x*two; // fB=y*two; // fC=r2; // fD=-1.0f; // 10 11 fbits, p_fbits, noop, TREE a b c d e f fsub.ss fr2, fx2y2, fr2 // r^2 now r^2-(x^2+y^2) st.l iparam1, 8(rcoeffptr) // store I_FBITS pxpl5op_0 ( iparam1, Ix_TREEgeZERO_Q6 ) fadd.ss fxc, fxc, fxtwo st.l iparam2, 12(rcoeffptr) // and P_FBITS fst.l f0, 16(rcoeffptr) // quick NOOP fadd.ss fyc, fyc, fytwo st.l iparam1, 20(rcoeffptr) // opcode fst.l fminus1, 24(rcoeffptr) // done D fst.l f0, 28(rcoeffptr) // done E fmul.ss frz, fr12, fK // precompute K fst.l fminus1, 32(rcoeffptr) // done F fst.l fxtwo, 36(rcoeffptr) // done A fmul.ss fxtwo, fK, ftmp1 // do A = twox*K fst.l fytwo, 40(rcoeffptr) // done B fst.l fr2, 44(rcoeffptr)++ // done C // K =rz*r12; // fA*=K; // fB*=K; // fC=(z+rz)-(x2y2*K); // fD=-K; // // opcode = 4 A=20, B=24, C=28, D=8, E=12, F=16 // // 9 20 zbuf compare / replace // fmul.ss fytwo, fK, ftmp2 // do B = twoy*K pxpl5op_2 ( iparam1, Ix_MEMltTREE_Q6, dvpx_zbuf, dvpx_zbufbits ) st.l iparam1, 4(rcoeffptr) // save MEMltTREE fsub.ss f0, fK, ftmp3 // do D = -K fst.l ftmp1, 20(rcoeffptr) // save A fst.l ftmp2, 24(rcoeffptr) // save B fmul.ss fx2y2, fK, ftmp1 // do x2y2*K fst.l ftmp3, 8(rcoeffptr) // save D fst.l f0, 12(rcoeffptr) // save E 0.0f fadd.ss fzc, frz, ftmp2 // do z+rz fst.l ftmp3, 16(rcoeffptr) // save F fsub.ss ftmp2, ftmp1, ftmp1 // do C = (z+rz) - (x2y2*K) fst.l ftmp1, 28(rcoeffptr) // save C pxpl5op_2 ( iparam1, Ix_TREEclmpintoMEM_Q0, dvpx_zbuf, dvpx_zbufbits ) st.l iparam1, 32(rcoeffptr) // save TREEclmp pxpl5op_2 ( iparam2,P_TREEclmpintoMEM, dvpx_zbuf, dvpx_zbufbits ) st.l iparam2, 36(rcoeffptr) // save P_TREEclmp // 3 23 SCAintoMEM, material, CLEAR ( r, g, b ) // r_invlz=r/lz; frcp.ss flz, ftmp1 // start 1.0 / fC - 2^-8 fmul.ss flz, ftmp1, ftmp2 // guess * divisor pxpl5op_2(iparam2, Ix_CLEAR, dvpx_r24, 24 ) st.l iparam2, 40(rcoeffptr) // store IGC_CLEAR fsub.ss ftwo, ftmp2, ftmp2 // 2 - (guess * divisor) pxpl5op_2(iparam1, Ix_SCAintoMEM_S1, dvpx_scalar, dvpx_scalarbits) st.l iparam1, 44(rcoeffptr) // store SCAintoMEM fmul.ss ftmp1, ftmp2, frinvlz // accurate to 2^-15 fst.l fmaterial, 48(rcoeffptr)++ // store SCALAR // 8 31 pxpl5op_2(iparam1,Ix_TREEclmpintoMEM_Q6, dvpx_r24, 8 ) fmul.ss frinvlz, frad, frinvlz st.l iparam1, 4(rcoeffptr) // store TREEclmp pxpl5op_2(iparam2,P_TREEclmpintoMEM, dvpx_r24, 8 ) st.l iparam2, 8(rcoeffptr) // store P_TREEclmp // K=-255.99f*lz*r12; // lx*=r_invlz; // ly*=r_invlz; // // fA= K*((x*two) - lx); // fB= K*((y*two) - ly); // fC= K*(r2 + (lx*x + ly*y)); // fD=-K; fmul.ss flz, fr12, ftmp1 fld_from ( ftmp2, .fminus_256 ) fmul.ss flx, frinvlz, flx pxpl5op_1 ( iparam1,Ix_FBITS, 15 ) st.l iparam1, 36(rcoeffptr) fmul.ss ftmp2, ftmp1, fK // got K pxpl5op_1 ( iparam1,P_FBITS, 15 ) st.l iparam1, 40(rcoeffptr) fsub.ss f0, fK, ftmp3 // tmp3 = -K fmul.ss fly, frinvlz, fly fst.l ftmp3, 12(rcoeffptr) // save D fst.l f0, 16(rcoeffptr) // save E fsub.ss fxtwo, flx, ftmp1 fst.l ftmp3, 20(rcoeffptr) // save F fsub.ss fytwo, fly, ftmp2 fmul.ss fK, ftmp1, ftmp1 // A fmul.ss fK, ftmp2, ftmp2 // B fst.l ftmp1, 24(rcoeffptr) // save A fst.l ftmp2, 28(rcoeffptr) // save B fmul.ss flx, fxc, ftmp1 DMAop_1 (iparam2, DMA_SEND, 17 ) fmul.ss fly, fyc, ftmp2 mov rcoeffsave, iparam1 fadd.ss ftmp1, ftmp2, ftmp2 // lx.x + ly.y fadd.ss fr2, ftmp2, ftmp1 // r2 + lx.x + ly.y fmul.ss fK, ftmp1, ftmp2 // tmp2 = C fst.l ftmp2, 32(rcoeffptr) // save C // 3 34 fst.l f0, 44(rcoeffptr)++ fix_rcoeffptr(17) call _safe_binitize_fn addu 10, r0, iparam3 .bomb_sphere_zb_rgb:: triangle_exit //}}} //{{{ _circ_z_rgb // // z-buffered disk, full colour // .globl _circ_zb_rgb .align 8 _circ_zb_rgb:: triangle_entry(circ_zb_rgb_mesh) circ_zb_rgb_mesh:: // 1 1 // call _prespherize st.l iparam2, 4(rcoeffptr) // should we just exit ? xor 0x0, r31, r0 bnc .bomb_circ_zb_rgb // r2-=x2y2; // // fA=x*two; // fB=y*two; // fC=r2; // fD=-1.0f; // 10 11 fbits, p_fbits, noop, TREE a b c d e f fsub.ss fr2, fx2y2, fr2 // r^2 now r^2-(x^2+y^2) st.l iparam1, 8(rcoeffptr) // store I_FBITS pxpl5op_0 ( iparam1, Ix_TREEgeZERO_Q6 ) fadd.ss fxc, fxc, fxtwo st.l iparam2, 12(rcoeffptr) // and P_FBITS fst.l f0, 16(rcoeffptr) // quick NOOP fadd.ss fyc, fyc, fytwo st.l iparam1, 20(rcoeffptr) // opcode fst.l fminus1, 24(rcoeffptr) // done D fst.l f0, 28(rcoeffptr) // done E fst.l fminus1, 32(rcoeffptr) // done F fst.l fxtwo, 36(rcoeffptr) // done A fst.l fytwo, 40(rcoeffptr) // done B fst.l fr2, 44(rcoeffptr)++ // done C // 5 16 MEMltTREE, C, TREEintoMEM, SCAintoMEM, S pxpl5op_2 ( iparam1, Ix_MEMltTREE_C1, dvpx_zbuf, dvpx_zbufbits ) st.l iparam1, 4(rcoeffptr) fst.l zc, 8(rcoeffptr)++ pxpl5op_2 ( iparam1, Ix_TREEintoMEM_C0, dvpx_zbuf, dvpx_zbufbits ) st.l iparam1, 4(rcoeffptr) pxpl5op_2(iparam2,Ix_SCAintoMEM_S1, dvpx_scalar, (dvpx_intrinsic-dvpx_scalar)) st.l iparam2, 8(rcoeffptr) fst.l fmaterial, 12(rcoeffptr)++ // now put r g b into memory // 5 16 MEMltTREE, C, TREEintoMEM, SCAintoMEM, S pxpl5op_2(iparam2,Ix_TREEintoMEM_L3, dvpx_r24, 24 ) st.l iparam2, 4(rcoeffptr) fst.l f0, 8(rcoeffptr) pxpl5op_1 ( iparam1,Ix_FBITS, 15 ) pxpl5op_1 ( iparam2,P_FBITS, 15 ) st.l iparam1, 40(rcoeffptr) st.l iparam2, 40(rcoeffptr) fst.l f0, 44(rcoeffptr)++ DMAop_1 (iparam2, DMA_SEND, 17 ) fix_rcoeffptr(17) call _safe_binitize_fn addu 10, r0, iparam3 .bomb_circ_zb_rgb:: triangle_exit //}}} //}}} #endif //{{{ _reg_dump .globl _reg_dump .align 8 _reg_dump:: //{{{ proc entry - save r1 r2 r3 addu -256, sp, sp st.l r1,0(sp) adds 256,sp,r1 // save r2 **before** call into stack frame st.l r1,4(sp) st.l fp,8(sp) //}}} //{{{ save r4..r31, f2..f31 st.l r4, 12(sp) st.l r5, 16(sp) st.l r6, 20(sp) st.l r7, 24(sp) st.l r8, 28(sp) st.l r9, 32(sp) st.l r10, 36(sp) st.l r11, 40(sp) st.l r12, 44(sp) st.l r13, 48(sp) st.l r14, 52(sp) st.l r15, 56(sp) st.l r16, 60(sp) //st.l r17, 64(sp) st.l r18, 68(sp) st.l r19, 72(sp) st.l r20, 76(sp) st.l r21, 80(sp) st.l r22, 84(sp) st.l r23, 88(sp) st.l r24, 92(sp) st.l r25, 96(sp) st.l r26, 100(sp) st.l r27, 104(sp) st.l r28, 108(sp) st.l r29, 112(sp) st.l r30, 116(sp) st.l r31, 120(sp) adds 120, sp, sp fst.l f2, 4(sp)++ fst.l f3, 4(sp)++ fst.l f4, 4(sp)++ fst.l f5, 4(sp)++ fst.l f6, 4(sp)++ fst.l f7, 4(sp)++ fst.l f8, 4(sp)++ fst.l f9, 4(sp)++ fst.l f10, 4(sp)++ fst.l f11, 4(sp)++ fst.l f12, 4(sp)++ fst.l f13, 4(sp)++ fst.l f14, 4(sp)++ fst.l f15, 4(sp)++ fst.l f16, 4(sp)++ fst.l f17, 4(sp)++ fst.l f18, 4(sp)++ fst.l f19, 4(sp)++ fst.l f20, 4(sp)++ fst.l f21, 4(sp)++ fst.l f22, 4(sp)++ fst.l f23, 4(sp)++ fst.l f24, 4(sp)++ fst.l f25, 4(sp)++ fst.l f26, 4(sp)++ fst.l f27, 4(sp)++ fst.l f28, 4(sp)++ fst.l f29, 4(sp)++ fst.l f30, 4(sp)++ fst.l f31, 4(sp)++ adds -240, sp, sp //}}} call _trace_regs mov sp, r16 //{{{ restore all ld.l 12(sp) , r4 ld.l 16(sp) , r5 ld.l 20(sp) , r6 ld.l 24(sp) , r7 ld.l 28(sp) , r8 ld.l 32(sp) , r9 ld.l 36(sp) , r10 ld.l 40(sp) , r11 ld.l 44(sp) , r12 ld.l 48(sp) , r13 ld.l 52(sp) , r14 ld.l 56(sp) , r15 ld.l 60(sp) , r16 ld.l 64(sp) , r17 ld.l 68(sp) , r18 ld.l 72(sp) , r19 ld.l 76(sp) , r20 ld.l 80(sp) , r21 ld.l 84(sp) , r22 ld.l 88(sp) , r23 ld.l 92(sp) , r24 ld.l 96(sp) , r25 ld.l 100(sp) , r26 ld.l 104(sp) , r27 ld.l 108(sp) , r28 ld.l 112(sp) , r29 ld.l 116(sp) , r30 ld.l 120(sp) , r31 adds 120, sp, sp fld.l 4(sp)++, f2 fld.l 4(sp)++, f3 fld.l 4(sp)++, f4 fld.l 4(sp)++, f5 fld.l 4(sp)++, f6 fld.l 4(sp)++, f7 fld.l 4(sp)++, f8 fld.l 4(sp)++, f9 fld.l 4(sp)++, f10 fld.l 4(sp)++, f11 fld.l 4(sp)++, f12 fld.l 4(sp)++, f13 fld.l 4(sp)++, f14 fld.l 4(sp)++, f15 fld.l 4(sp)++, f16 fld.l 4(sp)++, f17 fld.l 4(sp)++, f18 fld.l 4(sp)++, f19 fld.l 4(sp)++, f20 fld.l 4(sp)++, f21 fld.l 4(sp)++, f22 fld.l 4(sp)++, f23 fld.l 4(sp)++, f24 fld.l 4(sp)++, f25 fld.l 4(sp)++, f26 fld.l 4(sp)++, f27 fld.l 4(sp)++, f28 fld.l 4(sp)++, f29 fld.l 4(sp)++, f30 fld.l 4(sp)++, f31 adds -240, sp, sp //}}} //{{{ proc exit ld.l 0(sp),r1 ld.l 8(sp),fp bri r1 addu 256, sp, sp //}}} //}}} // constant for 1/x code .data .align 8 .globl _Cmax_x .globl _Cmax_y .globl _Cdelta_u .globl _Cdelta_v _Cdelta_u: .long 0x0 _Cdelta_v: .long 0x0 _Cmax_x: // (0) .Cmax_x: // (0) .C640: .long 0x442fbf5c // 7.02989990E+02 _Cmax_y: // (0) .Cmax_y: // (0) .C480: .long 0x43ff7eb8 // 5.10989990E+02 .fminus_one: .long 0xbf800000 // -1.00000000E+00 .fminus_256: .long 0xc37ffd71 // -2.55990005E+02 .C00037: // (0) .two_point_0: // (0) .long 0x40000000 // 2.00000000E+00 .eight_point_0: // (0) .long 0x41000000 // 8.00000000E+00 .four_point_0: // (0) .long 0x40800000 // 4.00000000E+00 .C362436: // (0) .long 0x3ecccccd // 4.00000006E-01 //.Czscale1024: // (0) // .long 0x49800000 // 1.04857600E+06 .Czscale: // (0) .long 0x497fffff // 1.04857588E+06 .Ctexscale: // (0) .long 0x477fffff // 6.55359883E+04 _.Cturn_z_to_tex: // (0) // .long 0x4879999a // 2.55590406E+05 .long 0x48f99980 // 5.11180000E+05 // NB this is now by 4 !!!!! _.Cturn_z_to_tex_by_4: // (0) .long 0x47f99980 // 1.27795000E+05 _.Cturn_z_to_tex_by_8: // (0) .long 0x4779999a // 6.38976016E+04 .r5r6r7opcodes: .string "r5 r6 r7 have opcodes?" .byte 0x0 .done_opacity_intro: .string "done opacity intro" .byte 0x0 .have_binitized: .string "have binitized, about to go next_triangle" .byte 0x0 .run_out_of_coeffs: .string "run out of coeffstore" .byte 0x0 .bini_pipe_minimax: .string "computed minimax piped" .byte 0x0