gbadev.org forum archive

This is a read-only mirror of the content originally found on forum.gbadev.org (now offline), salvaged from Wayback machine copies. A new forum can be found here.

DS development > Hardware: Vertex * Matrix.

#157496 - DensitY - Mon May 26, 2008 12:58 am

Greetings all :)

I've been doing some playing around on the DS, specifically software 3d rendering, and I'm currently looking at ways to improve a rather expensive routine.

now I know its possible to-do matrix * matrix using the DS's geometry hardware, and I'm wondering if there is a proper way of performing a vertex * matrix operation using the hardware since my C code is a tad too slow for my liking. I've had a look here and I've found nothing that fits that natively at least. I figure atm I could just fill my vertex into a dummy matrix (filling the rest with zeros) and do a matrix*matrix hardware multiply but I am seeking for a less annoying fix up.

Thoughts :)

#157498 - DiscoStew - Mon May 26, 2008 1:14 am

Quote:
40005C4h - Cmd 71h - POS_TEST - Set Position Coordinates for Test (W)

Parameter 1, Bit 0-15 X-Coordinate
Parameter 1, Bit 16-31 Y-Coordinate
Parameter 2, Bit 0-15 Z-Coordinate
Parameter 2, Bit 16-31 Not used
All values are 1bit sign, 3bit integer, 12bit fractional part.

Multiplies the specified line-vector (x,y,z,1) by the clip coordinate matrix.
After sending the command, wait until GXSTAT.Bit0 indicates Ready, then read the result from POS_RESULT registers. POS_TEST can be issued anywhere, except within polygon strips.

000620h..62Fh - POS_RESULT - Position Test Results (R)
This 16-byte region (4 words) contains the resulting clip coordinates (x,y,z,w) from the POS_TEST command. Each value is 1bit sign, 19bit integer, 12bit fractional part.


That should help ya. I's what I currently use for my vertex manipulations. Just plug in your matrix, then plug in the vertex vector into POS_TEST, and retrieve the result from POS_RESULT. One cool thing about this is that it doesn't affect the matrix, so you can ignore that while plugging in and retrieving values.
_________________
DS - It's all about DiscoStew

#157499 - DensitY - Mon May 26, 2008 1:23 am

Thats pretty darn clever , thank you DiscoStew. I'll surely give it a try, I'm rather embarrassed I didn't deduce that ;)

Cheers,

#157502 - TwentySeven - Mon May 26, 2008 1:45 am

Oooh! Yum. Any benchmarks on that stu? Vector transforms per second? :D

#157517 - DensitY - Mon May 26, 2008 7:54 am

right all working, for those that are interested

Code:

// 1. there is actually no need to specify the matrix, as the DS will automatically
//    multiply against position*projection matrix it is feed. not doing this will return
//    odd results
// 2. an identity matrix must be set before using this function else we get odd results.
// 3. our vertex is in 20.12 format, however we can only feed on 1.3.12 formated vertices
//    so masking down to a 16bit variable (FFFF) is required unless shifting up.
// 4. you have to wait for both Geometry engine and Pos Test values to be set free. (bit 27
//    and bit 0 in GFX_STATUS.
void MultiplyVertexByMatrixHard(vec3_t &result, vec3_t const &vector)
{   
   // configure test position
   GFX_POS_TEST = ((vector[0] & 0xFFFF)) | ((vector[1]) << 16);
   GFX_POS_TEST = ((vector[2] & 0xFFFF));   

   while((GFX_STATUS & ((1<<27) & 0))); // wait for result

   // read back results
   result[0] = GFX_POS_RESULT[0];
   result[1] = GFX_POS_RESULT[1];
   result[2] = GFX_POS_RESULT[2];
}