Casi he implementado el algoritmo DES con lenguaje C y quiero optimizar mi código. Entonces usé gprof . He aquí parte del informe:
Each sample counts as 0.01 seconds. % cumulative self self total time seconds seconds calls us/call us/call name 51.78 9.32 9.32 8000000 1.17 1.17 sboxes 34.71 15.57 6.25 8000000 0.78 0.78 extendRight 9.90 17.35 1.78 500000 3.56 35.96 operation 2.39 17.78 0.43 8000000 0.05 0.05 xorRightAndKey gprof muestra que la función sboxes ocupó el 51,78% del tiempo.
En sboxes(uchar aucData[6], ...) , me dieron 48 bits, los dividí en 8 ranuras, cada ranura de 6 bits.
para cada ranura:
combine el primer bit con el último bit para obtener X ;
obtener el bit medio 4 para obtener Y ;
hacer algo con (X, Y) ;
Por ejemplo, 011110 es una ranura, por lo que X = 00 e Y = 1111 .
Para implementar esto, escribí MACRO en el bit GET/SET en la memoria, aquí hay un código relativo:
#define LOCATE(ptr, index) (((char *)(ptr))[(index) >> 3]) #define GET_BIT(ptr, index) (LOCATE((ptr), (index)) & (((uchar)0x80) >> ((index) % 8))) Y aquí está el código para obtener (X, Y)
uchar basePos = 0x00; for (int i = 0; i < 8; ++i) { x = 0; y = 0; basePos = i * 6; // to locate the slot // combine first bit with last bit if (0 != GET_BIT(aucData, basePos)) { x |= 0x02; } if (0 != GET_BIT(aucData, basePos + 5)) { x |= 0x01; } // get continuous 4 bits for (int j = 1; j <= 4; ++j) { if (0 != GET_BIT(aucData, basePos + j)) { y |= (0x01 << (4 - j)); } } // do something with (x, y) }Entonces mi pregunta es, me dieron 48 bits, ¿cómo obtener los 4 bits del medio lo más rápido posible?
Sin tabla de búsqueda:
typedef unsigned long long u64; void sboxes(uchar aucData[6]) { u64 v = aucData[0] + (((u64)aucData[1]) << 8) + (((u64)aucData[2]) << 16) + (((u64)aucData[3]) << 24) + (((u64)aucData[4]) << 32) + (((u64)aucData[5]) << 40); for(int i = 0; i < 8; i++) { uchar x = ((v & 1) << 1) | ((v >> 5) & 1); uchar y = ((v >> 1) & 0xF); // do something with x, y printf("x: %hhu, y: %hhu\n", x, y); v >>= 6; } }Descargo de responsabilidad completo: no hice un benchmark. Pero debe ser rápido. Es posible que pueda hacer el empaquetado en u64 más rápido, si todavía es demasiado lento.