#include #include #include "speck.h" // This function is only used for the "x86" Speck compilation and as reference void FuncER16(u16 *x, u16 *y, u16 k) { u16 tmp_x = *x; u16 tmp_y = *y; *x = (((tmp_x)>>(7)) | ((tmp_x)<<(16-(7)))); *x += *y; *x = *x ^ k; *y = (((tmp_y)<<(2)) | (tmp_y>>(16-(2)))); *y = *y ^ *x; } #ifdef ARM // This function is used when running on the CW void FuncER16_ASM(u16 *x, u16 *y, u16 k) { asm volatile ( "nop\n\t" "push {r4, r5, lr}\n\t" "ldrh r5, [r0, #0]\n\t" "ldrh r4, [r1, #0]\n\t" "lsls r3, r5, #9\n\t" "orr.w r3, r3, r5, lsr #7\n\t" "uxth r3, r3\n\t" "strh r3, [r0, #0]\n\t" "ldrh r5, [r1, #0]\n\t" "add r3, r5\n\t" "eors r2, r3\n\t" "lsls r3, r4, #2\n\t" "orr.w r3, r3, r4, lsr #14\n\t" "uxth r3, r3\n\t" "strh r2, [r0, #0]\n\t" "strh r3, [r1, #0]\n\t" "ldrh r2, [r0, #0]\n\t" "eors r3, r2\n\t" "strh r3, [r1, #0]\n\t" "pop {r4, r5, pc}\n\t" ); } #endif void Words16ToBytes(u16 words[],u8 bytes[],int numwords) { int i,j=0; for(i=0;i>8); j+=2; } } void BytesToWords16(u8 bytes[],u16 words[],int numbytes) { int i,j=0; for(i=0;i=0;) DR16(Pt[1],Pt[0],rk[i--]); } void Speck3264_EncryptBlock(u8 pt[], u8 k[], u8 ct[]) { u16 Pt[2] = {0}; u16 K[4] = {0}; u16 rk[34] = {0}; u16 Ct[2] = {0}; BytesToWords16(pt,Pt,8); BytesToWords16(k,K,16); Speck3264KeySchedule(K,rk); #ifndef ARM // DEBUG Purposes for (int i=0; i < 16; i++) { printf("Key: 0x%x\n", rk[i]); } #endif Speck3264Encrypt(Pt,Ct,rk); Words16ToBytes(Ct,ct,2); } #ifndef ARM int main() { // test are from https://github.com/inmcm/Simon_Speck_Ciphers //u8 key[8] = {0x00, 0x01, 0x08, 0x09, 0x10, 0x11, 0x18, 0x19}; u8 pt[4] = {0x4c, 0x69, 0x74, 0x65}; u8 key[8] = {0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88}; u8 ct[4] = {0x0}; Speck3264_EncryptBlock(pt, key, ct); printf("[[ Speck 32/64 ]]\n"); printf("The output: \n"); for (int i = 0; i < 4; i++) { printf("- %08x\n", ct[i]); } return 0; } #endif