#include <objgfx40/objgfx40.h> #include <objgfx40/ogPixCon.h> // ogPixCon constructor ogPixCon::ogPixCon(ogPixelFmt srcPixFmt, ogPixelFmt dstPixFmt) { uInt8 channelIdx[4]; uInt8 srcFieldSize[4]; uInt8 srcFieldPos[4]; uInt8 dstShifters[4]; uInt8 tmpb; int32 i, j; channelIdx[0] = 0; channelIdx[1] = 1; channelIdx[2] = 2; channelIdx[3] = 3; srcFieldSize[0] = srcPixFmt.alphaMaskSize; srcFieldSize[1] = srcPixFmt.redMaskSize; srcFieldSize[2] = srcPixFmt.greenMaskSize; srcFieldSize[3] = srcPixFmt.blueMaskSize; srcFieldPos[0] = srcPixFmt.alphaFieldPosition; srcFieldPos[1] = srcPixFmt.redFieldPosition; srcFieldPos[2] = srcPixFmt.greenFieldPosition; srcFieldPos[3] = srcPixFmt.blueFieldPosition; /* * The dest shifters are 32-(fieldPosition+fieldSize). For things like * 24bpp where there is no alpha, the field position will be 0, and the * field size will be 0. 32-(0+0) is 32.. and when the shift takes place * the 32 will turn into a 0 and the shift will do nothing */ dstShifters[0] = 32-(dstPixFmt.alphaFieldPosition+dstPixFmt.alphaMaskSize); dstShifters[1] = 32-(dstPixFmt.redFieldPosition+dstPixFmt.redMaskSize); dstShifters[2] = 32-(dstPixFmt.greenFieldPosition+dstPixFmt.greenMaskSize); dstShifters[3] = 32-(dstPixFmt.blueFieldPosition+dstPixFmt.blueMaskSize); i = srcPixFmt.redMaskSize - dstPixFmt.redMaskSize; if (i>0) srcMasker = OG_MASKS[dstPixFmt.redMaskSize] << (srcPixFmt.redFieldPosition+i); else srcMasker = OG_MASKS[srcPixFmt.redMaskSize] << srcPixFmt.redFieldPosition; i = srcPixFmt.greenMaskSize - dstPixFmt.greenMaskSize; if (i>0) srcMasker+= OG_MASKS[dstPixFmt.greenMaskSize] << (srcPixFmt.greenFieldPosition+i); else srcMasker+= OG_MASKS[srcPixFmt.greenMaskSize] << srcPixFmt.greenFieldPosition; i = srcPixFmt.blueMaskSize - dstPixFmt.blueMaskSize; if (i>0) srcMasker+= OG_MASKS[dstPixFmt.blueMaskSize] << (srcPixFmt.blueFieldPosition+i); else srcMasker+= OG_MASKS[srcPixFmt.blueMaskSize] << srcPixFmt.blueFieldPosition; i = srcPixFmt.alphaMaskSize - dstPixFmt.alphaMaskSize; if (i>0) srcMasker+= OG_MASKS[dstPixFmt.alphaMaskSize] << (srcPixFmt.alphaFieldPosition+i); else srcMasker+= OG_MASKS[srcPixFmt.alphaMaskSize] << srcPixFmt.alphaFieldPosition; /* * sort in descending order based on srcFieldPos (oth field will hold * highest position value) */ for (i = 1; i < 4; i++ ) for (j = 0; j < i; j++) { if (srcFieldPos[j] < srcFieldPos[i]) { tmpb = srcFieldPos[j]; srcFieldPos[j] = srcFieldPos[i]; srcFieldPos[i] = tmpb; tmpb = srcFieldSize[j]; srcFieldSize[j] = srcFieldSize[i]; srcFieldSize[i] = tmpb; tmpb = channelIdx[j]; channelIdx[j] = channelIdx[i]; channelIdx[i] = tmpb; } // if } // for j srcShifter = ((srcFieldSize[0] << 24) | (srcFieldSize[1] << 16) | (srcFieldSize[2] << 8) | (srcFieldSize[3])); dstShifter = ((dstShifters[channelIdx[0]] << 24) | (dstShifters[channelIdx[1]] << 16) | (dstShifters[channelIdx[2]] << 8) | (dstShifters[channelIdx[3]])); return; } // ogPixCon::ogPixCon uInt32 ogPixCon::ConvPix(uInt32 pixel) { __asm__ __volatile__( " xor %%ebx, %%ebx \n" // xor ebx, ebx " xor %%edi, %%edi \n" // xor edi, edi " \n" " push %%eax \n" // push eax " \n" " and %%edx, %%esi \n" // and esi, edx " xor %%eax, %%eax \n" // xor eax, eax " xor %%edx, %%edx \n" // xor edx, edx " \n" " shrdl %%cl, %%esi, %%eax \n" // shrd eax, esi, cl " shr %%cl, %%esi \n" // shr esi, cl " mov %%ch, %%cl \n" // mov cl, ch " shrdl %%cl, %%esi, %%ebx \n" // shrd ebx, esi, cl " shr %%cl, %%esi \n" // shr esi, cl " shr $16, %%ecx \n" // shr ecx, 16 " shrdl %%cl, %%esi, %%edx \n" // shrd edx, esi, cl " shr %%cl, %%esi \n" // shr esi, cl " mov %%ch, %%cl \n" // mov cl, ch " shrdl %%cl, %%esi, %%edi \n" // shrd edi, esi, cl " \n" " pop %%ecx \n" // pop ecx " \n" " shr %%cl, %%eax \n" // shr eax, cl " shr $8, %%ecx \n" // shr ecx, 8 " shr %%cl, %%ebx \n" // shr ebx, cl " shr $8, %%ecx \n" // shr ecx, 8 " shr %%cl, %%edx \n" // shr edx, cl " shr $8, %%ecx \n" // shr ecx, 8 " shr %%cl, %%edi \n" // shr edi, cl " \n" " or %%ebx, %%eax \n" // or eax, ebx " or %%edi, %%edx \n" // or edx, edi " nop \n" // nop " or %%edx, %%eax \n" // or eax, edx : "=a" (pixel) // %0 : "S" (pixel), "d" (srcMasker), // %1, %2 "c" (srcShifter), "a" (dstShifter) // %3, %4 // "ecx" (srcShifter), "eax" (dstShifter) // %2, %3 ); return pixel; }; // ogPixCon::ConvPix