En un seguimiento a algunas de las preguntas anteriores sobre la conversión de RGB a RGBA, y ARGB a BGR, me gustaría acelerar un RGB a BGRA de conversión con SSE. Supongamos una máquina de 32 bits y nos gustaría usar intrinsics. Tengo dificultades para alinear los almacenamientos intermedios de origen y destino para trabajar con registros de 128 bits y buscar otras soluciones de vectorización inteligentes.rápida conversión de RGB a vectorizado BGRA
La rutina para ser vectorizado es el siguiente ...
void RGB8ToBGRX8(int w, const void *in, void *out)
{
int i;
int width = w;
const unsigned char *src= (const unsigned char*) in;
unsigned int *dst= (unsigned int*) out;
unsigned int invalue, outvalue;
for (i=0; i<width; i++, src+=3, dst++)
{
invalue = src[0];
outvalue = (invalue<<16);
invalue = src[1];
outvalue |= (invalue<<8);
invalue = src[2];
outvalue |= (invalue);
*dst = outvalue | 0xff000000;
}
}
Esta rutina se utiliza primariamente para grandes texturas (512KB), así que si puedo paralelizar algunas de las operaciones, puede ser beneficioso para el proceso más píxeles en un intento. Por supuesto, necesitaré un perfil. :)
Editar:
Mis argumentos de compilación ...
gcc -O2 main.c
¿Está utilizando el indicador de optimización para su compilador (¿cuál?)? El compilador a menudo hará un mejor trabajo al optimizar el código, _sin introducir lo incorrecto. ¿Qué datos de referencia ha recopilado? –
No es una respuesta SSE, pero ¿ha intentado desenrollar su circuito 4 veces para que la entrada siempre comience en una dirección alineada? Luego puede leer la entrada de una palabra de máquina a la vez en lugar de hacerlo de manera manual, con desplazamiento y enmascaramiento especializado para cada posición relativa del píxel fuente. Como Dana menciona, vale la pena ver qué tan bien funciona el compilador en altos niveles de optimización (inspeccionar el código ensamblador generado, además de la evaluación comparativa), pero dudo que sea lo suficientemente agresivo para desenrollar el bucle _y_ divida el punto de entrada de acuerdo con el alineación de 'en' todo por sí mismo. –
Grandes preguntas. Es simplemente "O2" (NO O3) con GCC4.6. Mi caso de referencia es una corrida de iteración de 10K con 512 como el lapso de "ancho". Gracias por las excelentes respuestas! – Rev316