void CData::CryptBlock(Byte *buf, bool encrypt) { Byte inBuf[16]; UInt32 A, B, C, D, T, TA, TB; A = GetUInt32FromMemLE(buf + 0) ^ Keys[0]; B = GetUInt32FromMemLE(buf + 4) ^ Keys[1]; C = GetUInt32FromMemLE(buf + 8) ^ Keys[2]; D = GetUInt32FromMemLE(buf + 12) ^ Keys[3]; if (!encrypt) memcpy(inBuf, buf, sizeof(inBuf)); for(int i = 0; i < kNumRounds; i++) { UInt32 key = Keys[(encrypt ? i : (kNumRounds - 1 - i)) & 3]; T = ((C + rol(D, 11)) ^ key); TA = A ^ SubstLong(T); T = ((D ^ rol(C, 17)) + key); TB = B ^ SubstLong(T); A = C; B = D; C = TA; D = TB; } WriteUInt32ToMemLE(C ^ Keys[0], buf + 0); WriteUInt32ToMemLE(D ^ Keys[1], buf + 4); WriteUInt32ToMemLE(A ^ Keys[2], buf + 8); WriteUInt32ToMemLE(B ^ Keys[3], buf + 12); UpdateKeys(encrypt ? buf : inBuf); }
void MapleEncryption::mapleEncrypt(unsigned char *buf, int32_t size) { int32_t j; uint8_t a, c; for (uint8_t i = 0; i < 3; i++) { a = 0; for (j = size; j > 0; j--) { c = buf[size - j]; c = rol(c, 3); c = (uint8_t)(c + j); // Guess this is supposed to be right? c = c ^ a; a = c; c = ror(a, j); c = c ^ 0xFF; c = c + 0x48; buf[size - j] = c; } a = 0; for (j = size; j > 0; j--) { c = buf[j - 1]; c = rol(c, 4); c = (uint8_t)(c + j); // Guess this is supposed to be right? c = c ^ a; a = c; c = c ^ 0x13; c = ror(c, 3); buf[j - 1] = c; } } }
static uint32_t hars_petruska_f54_1_random (void) { #define rol(x,k) ((x << k) | (x >> (32-k))) return state = (state ^ rol (state, 5) ^ rol (state, 24)) + 0x37798849; #undef rol }
static inline void f(uint32_t *a, uint32_t *b) { switch (state) { case 1: a[i % 5] += ((a[(3 + i) % 5] & (a[(2 + i) % 5] ^ a[(1 + i) % 5])) ^ a[(1 + i) % 5]) + b[i] + 0x5a827999 + rol(a[(4 + i) % 5], 5); a[(3 + i) % 5] = rol(a[(3 + i) % 5], 30); break; case 2: b[i] = blk(b, i); a[(1 + i) % 5] += ((a[(4 + i) % 5] & (a[(3 + i) % 5] ^ a[(2 + i) % 5])) ^ a[(2 + i) % 5]) + b[i] + 0x5a827999 + rol(a[(5 + i) % 5], 5); a[(4 + i) % 5] = rol(a[(4 + i) % 5], 30); break; case 3: b[(i + 4) % 16] = blk(b, (i + 4) % 16); a[i % 5] += (a[(3 + i) % 5] ^ a[(2 + i) % 5] ^ a[(1 + i) % 5]) + b[(i + 4) % 16] + 0x6ed9eba1 + rol(a[(4 + i) % 5], 5); a[(3 + i) % 5] = rol(a[(3 + i) % 5], 30); break; case 4: b[(i + 8) % 16] = blk(b, (i + 8) % 16); a[i % 5] += (((a[(3 + i) % 5] | a[(2 + i) % 5]) & a[(1 + i) % 5]) | (a[(3 + i) % 5] & a[(2 + i) % 5])) + b[(i + 8) % 16] + 0x8f1bbcdc + rol(a[(4 + i) % 5], 5); a[(3 + i) % 5] = rol(a[(3 + i) % 5], 30); break; case 5: b[(i + 12) % 16] = blk(b, (i + 12) % 16); a[i % 5] += (a[(3 + i) % 5] ^ a[(2 + i) % 5] ^ a[(1 + i) % 5]) + b[(i + 12) % 16] + 0xca62c1d6 + rol(a[(4 + i) % 5], 5); a[(3 + i) % 5] = rol(a[(3 + i) % 5], 30); break; case 6: b[i] += a[4 - i]; } }
static void MD5Update(struct MD5Context *ctx, unsigned char *HashBlock, int len) { /* ctx was built (CPU endian-independent) as unsigned longs */ /* HashBlock was built (CPU endian-independent) as unsigned chars */ UBS_UINT32 a, b, c, d; int block, i; /* Process as many blocks as possible */ for (block = 0; len >= 64; len -= 64, ++block) { UBS_UINT32 m[16], A, B, C, D; RTL_Memcpy(m, HashBlock + 64*block, 64); /* Get one block of data */ /* At this point m[] is built as a char array. However, m[] will be operated on from here on out as an array of unsigned longs. This algorithm's definition assumes a little endian CPU, so we'll endian-adjust the byte array if we have a big endian CPU */ #if (UBS_CPU_ATTRIBUTE == UBS_BIG_ENDIAN) for( i = 0; i < 16; ++i ) m[i] = BYTESWAPLONG( m[i] ); /* View data as big endian */ #endif a = ctx->buf[0]; b = ctx->buf[1]; c = ctx->buf[2]; d = ctx->buf[3]; /* Now for the hyper-compact SHA-style formulation of MD5 */ A = b; B = c; C = d; D = a; Dbg_Print(DBG_MD5,("pre round 0: 0x%x 0x%x 0x%x 0x%x\n", A, B, C, D)); for (i = 0; i < 64; ++i) { UBS_UINT32 temp, fn = 0, rolt, prerolt; switch (i / 16) { case 0: fn = F(A,B,C); break; case 1: fn = G(A,B,C); break; case 2: fn = H(A,B,C); break; case 3: fn = I(A,B,C); break; default: ; } prerolt = D + fn + m[MD5_P[i]] + MD5_T[i]; rolt = rol(D + fn + m[MD5_P[i]] + MD5_T[i], MD5_S[i]); temp = A + rol(D + fn + m[MD5_P[i]] + MD5_T[i], MD5_S[i]); D = C; C = B; B = A; A = temp; Dbg_Print(DBG_MD5,("post round %d: 0x%x 0x%x 0x%x 0x%x\n", i, A, B, C, D)); Dbg_Print(DBG_MD5,("fn=0x%x, before rol=0x%x, rol()=0x%x\n", fn, prerolt, rolt)); Dbg_Print(DBG_MD5,("\tcte=0x%x, data=0x%x, shift amt=%d\n\n", MD5_T[i], m[MD5_P[i]], MD5_S[i])); } b = A; c = B; d = C; a = D; ctx->buf[0] += a; ctx->buf[1] += b; ctx->buf[2] += c; ctx->buf[3] += d; } }
void CryptData::DecryptBlock20(unsigned char *Buf) { unsigned char InBuf[16]; unsigned int A,B,C,D,T,TA,TB; #if defined(BIG_ENDIAN) || !defined(PRESENT_INT32) || !defined(ALLOW_NOT_ALIGNED_INT) A=((unsigned int)Buf[0]|((unsigned int)Buf[1]<<8)|((unsigned int)Buf[2]<<16)|((unsigned int)Buf[3]<<24))^Key[0]; B=((unsigned int)Buf[4]|((unsigned int)Buf[5]<<8)|((unsigned int)Buf[6]<<16)|((unsigned int)Buf[7]<<24))^Key[1]; C=((unsigned int)Buf[8]|((unsigned int)Buf[9]<<8)|((unsigned int)Buf[10]<<16)|((unsigned int)Buf[11]<<24))^Key[2]; D=((unsigned int)Buf[12]|((unsigned int)Buf[13]<<8)|((unsigned int)Buf[14]<<16)|((unsigned int)Buf[15]<<24))^Key[3]; #else uint32 *BufPtr=(uint32 *)Buf; A=BufPtr[0]^Key[0]; B=BufPtr[1]^Key[1]; C=BufPtr[2]^Key[2]; D=BufPtr[3]^Key[3]; #endif memcpy(InBuf,Buf,sizeof(InBuf)); for(int I=NROUNDS-1;I>=0;I--) { T=((C+rol(D,11,32))^Key[I&3]); TA=A^substLong(T); T=((D^rol(C,17,32))+Key[I&3]); TB=B^substLong(T); A=C; B=D; C=TA; D=TB; } #if defined(BIG_ENDIAN) || !defined(PRESENT_INT32) || !defined(ALLOW_NOT_ALIGNED_INT) C^=Key[0]; Buf[0]=(unsigned char)C; Buf[1]=(unsigned char)(C>>8); Buf[2]=(unsigned char)(C>>16); Buf[3]=(unsigned char)(C>>24); D^=Key[1]; Buf[4]=(unsigned char)D; Buf[5]=(unsigned char)(D>>8); Buf[6]=(unsigned char)(D>>16); Buf[7]=(unsigned char)(D>>24); A^=Key[2]; Buf[8]=(unsigned char)A; Buf[9]=(unsigned char)(A>>8); Buf[10]=(unsigned char)(A>>16); Buf[11]=(unsigned char)(A>>24); B^=Key[3]; Buf[12]=(unsigned char)B; Buf[13]=(unsigned char)(B>>8); Buf[14]=(unsigned char)(B>>16); Buf[15]=(unsigned char)(B>>24); #else BufPtr[0]=C^Key[0]; BufPtr[1]=D^Key[1]; BufPtr[2]=A^Key[2]; BufPtr[3]=B^Key[3]; #endif UpdKeys(InBuf); }
inline void R4(std::uint32_t block[BLOCK_INTS], std::uint32_t v, std::uint32_t &w, std::uint32_t x, std::uint32_t y, std::uint32_t &z, std::size_t i) { block[i] = blk(block, i); z += (w^x^y) + block[i] + 0xca62c1d6 + rol(v, 5); w = rol(w, 30); }
inline void R3(std::uint32_t block[BLOCK_INTS], std::uint32_t v, std::uint32_t &w, std::uint32_t x, std::uint32_t y, std::uint32_t &z, std::size_t i) { block[i] = blk(block, i); z += (((w|x)&y)|(w&x)) + block[i] + 0x8f1bbcdc + rol(v, 5); w = rol(w, 30); }
void CryptData::EncryptBlock20(byte *Buf) { uint A,B,C,D,T,TA,TB; #if defined(BIG_ENDIAN) || !defined(PRESENT_INT32) || !defined(ALLOW_NOT_ALIGNED_INT) A=((uint)Buf[0]|((uint)Buf[1]<<8)|((uint)Buf[2]<<16)|((uint)Buf[3]<<24))^Key[0]; B=((uint)Buf[4]|((uint)Buf[5]<<8)|((uint)Buf[6]<<16)|((uint)Buf[7]<<24))^Key[1]; C=((uint)Buf[8]|((uint)Buf[9]<<8)|((uint)Buf[10]<<16)|((uint)Buf[11]<<24))^Key[2]; D=((uint)Buf[12]|((uint)Buf[13]<<8)|((uint)Buf[14]<<16)|((uint)Buf[15]<<24))^Key[3]; #else uint32 *BufPtr=(uint32 *)Buf; A=BufPtr[0]^Key[0]; B=BufPtr[1]^Key[1]; C=BufPtr[2]^Key[2]; D=BufPtr[3]^Key[3]; #endif for(int I=0;I<NROUNDS;I++) { T=((C+rol(D,11,32))^Key[I&3]); TA=A^substLong(T); T=((D^rol(C,17,32))+Key[I&3]); TB=B^substLong(T); A=C; B=D; C=TA; D=TB; } #if defined(BIG_ENDIAN) || !defined(PRESENT_INT32) || !defined(ALLOW_NOT_ALIGNED_INT) C^=Key[0]; Buf[0]=(byte)C; Buf[1]=(byte)(C>>8); Buf[2]=(byte)(C>>16); Buf[3]=(byte)(C>>24); D^=Key[1]; Buf[4]=(byte)D; Buf[5]=(byte)(D>>8); Buf[6]=(byte)(D>>16); Buf[7]=(byte)(D>>24); A^=Key[2]; Buf[8]=(byte)A; Buf[9]=(byte)(A>>8); Buf[10]=(byte)(A>>16); Buf[11]=(byte)(A>>24); B^=Key[3]; Buf[12]=(byte)B; Buf[13]=(byte)(B>>8); Buf[14]=(byte)(B>>16); Buf[15]=(byte)(B>>24); #else BufPtr[0]=C^Key[0]; BufPtr[1]=D^Key[1]; BufPtr[2]=A^Key[2]; BufPtr[3]=B^Key[3]; #endif UpdKeys(Buf); }
uint8_t F0(uint8_t x) { uint8_t temp1, temp2, temp3; temp1 = rol(x); temp2 = rol(temp1); temp3 = ror(x); return temp1 ^ temp2 ^ temp3; }
static char * ROL2() { CPU *c = getCPU(); setRegByte(c, ACCUM, 0xA1); OP_CODE_INFO *o1 = getOP_CODE_INFO(getRegByte(c,ACCUM) & 0xFF, 0, modeAccumulator); rol(c,o1); OP_CODE_INFO *o2 = getOP_CODE_INFO(getRegByte(c,ACCUM) & 0xFF, 0, modeAccumulator); rol(c,o2); mu_assert("ROL2 err, ACCUM != 0x85", (0xFF & getRegByte(c,ACCUM)) == 0x85); mu_assert("ROL2 err, CARRY != 0", getFlag(c,C) == 0); freeOP_CODE_INFO(o1); freeOP_CODE_INFO(o2); free(c); return 0; }
static void transform(uint32_t state[5], uint8_t buffer[64]){ uint32_t block[80]; unsigned int i, a, b, c, d, e; a = state[0]; b = state[1]; c = state[2]; d = state[3]; e = state[4]; #ifdef CONFIG_SMALL for(i=0; i<80; i++){ int t; if(i<16) t= be2me_32(((uint32_t*)buffer)[i]); else t= rol(block[i-3]^block[i-8]^block[i-14]^block[i-16],1); block[i]= t; t+= e+rol(a,5); if(i<40){ if(i<20) t+= ((b&(c^d))^d) +0x5A827999; else t+= ( b^c ^d) +0x6ED9EBA1; }else{ if(i<60) t+= (((b|c)&d)|(b&c))+0x8F1BBCDC; else t+= ( b^c ^d) +0xCA62C1D6; } e= d; d= c; c= rol(b,30); b= a; a= t; } #else for(i=0; i<15; i+=5){ R0(a,b,c,d,e,0+i); R0(e,a,b,c,d,1+i); R0(d,e,a,b,c,2+i); R0(c,d,e,a,b,3+i); R0(b,c,d,e,a,4+i); } R0(a,b,c,d,e,15); R1(e,a,b,c,d,16); R1(d,e,a,b,c,17); R1(c,d,e,a,b,18); R1(b,c,d,e,a,19); for(i=20; i<40; i+=5){ R2(a,b,c,d,e,0+i); R2(e,a,b,c,d,1+i); R2(d,e,a,b,c,2+i); R2(c,d,e,a,b,3+i); R2(b,c,d,e,a,4+i); } for(; i<60; i+=5){ R3(a,b,c,d,e,0+i); R3(e,a,b,c,d,1+i); R3(d,e,a,b,c,2+i); R3(c,d,e,a,b,3+i); R3(b,c,d,e,a,4+i); } for(; i<80; i+=5){ R4(a,b,c,d,e,0+i); R4(e,a,b,c,d,1+i); R4(d,e,a,b,c,2+i); R4(c,d,e,a,b,3+i); R4(b,c,d,e,a,4+i); } #endif state[0] += a; state[1] += b; state[2] += c; state[3] += d; state[4] += e; }
static void SHA1_transform(SHA_CTX *ctx) { uint32_t W[80]; uint32_t A, B, C, D, E; uint8_t *p = ctx->buf; int t; for(t = 0; t < 16; ++t) { uint32_t tmp = *p++ << 24; tmp |= *p++ << 16; tmp |= *p++ << 8; tmp |= *p++; W[t] = tmp; } for(; t < 80; t++) { W[t] = rol(1,W[t-3] ^ W[t-8] ^ W[t-14] ^ W[t-16]); } A = ctx->state[0]; B = ctx->state[1]; C = ctx->state[2]; D = ctx->state[3]; E = ctx->state[4]; for(t = 0; t < 80; t++) { uint32_t tmp = rol(5,A) + E + W[t]; if (t < 20) tmp += (D^(B&(C^D))) + 0x5A827999; else if ( t < 40) tmp += (B^C^D) + 0x6ED9EBA1; else if ( t < 60) tmp += ((B&C)|(D&(B|C))) + 0x8F1BBCDC; else tmp += (B^C^D) + 0xCA62C1D6; E = D; D = C; C = rol(30,B); B = A; A = tmp; } ctx->state[0] += A; ctx->state[1] += B; ctx->state[2] += C; ctx->state[3] += D; ctx->state[4] += E; }
static void doblock(md5sig state, const unsigned char *data) { md5uint a, b, c, d, t, x[16]; const md5uint msk = 0xffffffffUL; int i; /* encode input bytes into md5uint */ for (i = 0; i < 16; ++i) { const unsigned char *p = data + 4 * i; x[i] = p[0] | (p[1] << 8) | (p[2] << 16) | (p[3] << 24); } a = state[0]; b = state[1]; c = state[2]; d = state[3]; for (i = 0; i < 64; ++i) { const struct roundtab *p = roundtab + i; int round = i / 16; switch (round) { case 0: a += (b & c) | (~b & d); break; case 1: a += (b & d) | (c & ~d); break; case 2: a += b ^ c ^ d; break; case 3: a += c ^ (b | ~d); break; } a += sintab[i]; a += x[(int)(p->k)]; a &= msk; t = b + rol(a, p->s); a = d; d = c; c = b; b = t; } state[0] = (state[0] + a) & msk; state[1] = (state[1] + b) & msk; state[2] = (state[2] + c) & msk; state[3] = (state[3] + d) & msk; }
main() { int a=0xf00f; rol(a,31); printf("%x\n",a); }
/** * @brief ROL mem */ void Cpu::rol_mem(uint16_t addr, uint8_t cycles) { uint8_t v = load_byte(addr); /* see ASL doc */ mem_->write_byte(addr,v); mem_->write_byte(addr,rol(v)); tick(cycles); }
/* Derive the 33 subkeys from KEY and store them in SUBKEYS. */ static void serpent_subkeys_generate (serpent_key_t key, serpent_subkeys_t subkeys) { u32 w_real[140]; /* The `prekey'. */ u32 k[132]; u32 *w = &w_real[8]; int i, j; /* Initialize with key values. */ for (i = 0; i < 8; i++) w[i - 8] = key[i]; /* Expand to intermediate key using the affine recurrence. */ for (i = 0; i < 132; i++) w[i] = rol (w[i - 8] ^ w[i - 5] ^ w[i - 3] ^ w[i - 1] ^ PHI ^ i, 11); /* Calculate subkeys via S-Boxes, in bitslice mode. */ SBOX (3, w, k, 0); SBOX (2, w, k, 4); SBOX (1, w, k, 8); SBOX (0, w, k, 12); SBOX (7, w, k, 16); SBOX (6, w, k, 20); SBOX (5, w, k, 24); SBOX (4, w, k, 28); SBOX (3, w, k, 32); SBOX (2, w, k, 36); SBOX (1, w, k, 40); SBOX (0, w, k, 44); SBOX (7, w, k, 48); SBOX (6, w, k, 52); SBOX (5, w, k, 56); SBOX (4, w, k, 60); SBOX (3, w, k, 64); SBOX (2, w, k, 68); SBOX (1, w, k, 72); SBOX (0, w, k, 76); SBOX (7, w, k, 80); SBOX (6, w, k, 84); SBOX (5, w, k, 88); SBOX (4, w, k, 92); SBOX (3, w, k, 96); SBOX (2, w, k, 100); SBOX (1, w, k, 104); SBOX (0, w, k, 108); SBOX (7, w, k, 112); SBOX (6, w, k, 116); SBOX (5, w, k, 120); SBOX (4, w, k, 124); SBOX (3, w, k, 128); /* Renumber subkeys. */ for (i = 0; i < ROUNDS + 1; i++) for (j = 0; j < 4; j++) subkeys[i][j] = k[4 * i + j]; }
static char * ROL1() { CPU *c = getCPU(); setRegByte(c, ACCUM, 0xA1); OP_CODE_INFO *o = getOP_CODE_INFO(0xA1, 0, modeAccumulator); rol(c,o); mu_assert("ROL1 err, ACCUM != 0x42", (0xFF & getRegByte(c,ACCUM)) == 0x42); mu_assert("ROL1 err, CARRY != 1", getFlag(c,C) == 1); freeOP_CODE_INFO(o); free(c); return 0; }
int main() { unsigned long val; int ii; val = 0x80000000; for ( ii = 0; ii < 64; ++ii ) { val = rol(val); printf("%3d : 0x%08x\n", ii, val); } }
static int redspark_probe(AVProbeData *p) { uint32_t key, data; uint8_t header[8]; /* Decrypt first 8 bytes of the header */ data = AV_RB32(p->buf); key = data ^ 0x52656453; data ^= key; AV_WB32(header, data); key = rol(key, 11); key += rol(key, 3); data = AV_RB32(p->buf + 4) ^ key; AV_WB32(header + 4, data); if (AV_RB64(header) == AV_RB64("RedSpark")) return AVPROBE_SCORE_MAX; return 0; }
node* insert(node* root, int new_val) { if (!root) { root = new node(); root->val = new_val; root->left = NULL; root->right = NULL; root->ht = 1; return root; } else { if (new_val < root->val) { root->left = insert(root->left, new_val); } else /* (new_val > root->val) */ { root->right = insert(root->right, new_val); } // Update height of acestor node as we come out of recursion root->ht = (max(height(root->left), height(root->right))) + 1; // Check the balance factor of the node to see if we need to rebalance int balance = getBalance(root); // Check the 4 cases of imbalance if (balance < -1 && new_val < root->left->val) return ror(root); if (balance < -1 && new_val > root->right->val) return rol(root); if (balance > 1 && new_val > root->left->val) { root->left = rol(root->left); return ror(root); } if (balance < -1 && new_val < root->right->val) { root->right = ror(root->right); return rol(root); } return root; } }
// Returns the next random number based on seeds // and updates the seeds accordingly. dodBYTE RNG::RANDOM() { int x, y; dodBYTE a, b; carry = 0; for (x = 8; x != 0; --x) { b = 0; a = (SEED[2] & 0xE1); for (y = 8; y != 0; --y) { a = lsl(a); if (carry != 0) ++b; } b = lsr(b); SEED[0] = rol(SEED[0]); SEED[1] = rol(SEED[1]); SEED[2] = rol(SEED[2]); } return SEED[0]; }
/*** Keccak-f[1600] ***/ static inline void keccakf(void* state) { uint64_t* a = (uint64_t*)state; uint64_t b[5] = {0}; uint64_t t = 0; uint8_t x, y; for (int i = 0; i < 24; i++) { // Theta FOR5(x, 1, b[x] = 0; FOR5(y, 5, b[x] ^= a[x + y]; )) FOR5(x, 1, FOR5(y, 5, a[y + x] ^= b[(x + 4) % 5] ^ rol(b[(x + 1) % 5], 1); ))
/* * key schedule * inputKey: the original keys * keys: round keys */ void encryptKeySchedule(const u8 * inputKey, u8 * keys ) { u32 *rk = (u32*)keys; const u32 *ik = (const u32*)inputKey; u32 l[SPECK_ROUNDS+SPECK_KEY_WORDS-2]; rk[0] = ik[0]; l[0] = ik[1]; l[1] = ik[2]; #if defined(SPECK_KEY_WORDS) && (SPECK_KEY_WORDS==4) l[2] = ik[3]; #endif int i; for ( i = 0; i < SPECK_ROUNDS-1; i++ ) { l[i+SPECK_KEY_WORDS-1] = (rk[i] + ror(l[i], SPECK_A)) ^ (u32)i; rk[i+1] = rol(rk[i], SPECK_B) ^ l[i+SPECK_KEY_WORDS-1]; } }
void MifareDES_Auth1(uint8_t mode, uint8_t algo, uint8_t keyno, uint8_t *datain){ int len = 0; //uint8_t PICC_MASTER_KEY8[8] = { 0x40,0x41,0x42,0x43,0x44,0x45,0x46,0x47}; uint8_t PICC_MASTER_KEY16[16] = { 0x40,0x41,0x42,0x43,0x44,0x45,0x46,0x47,0x48,0x49,0x4a,0x4b,0x4c,0x4d,0x4e,0x4f }; uint8_t null_key_data8[8] = {0x00}; //uint8_t null_key_data16[16] = {0x00}; //uint8_t new_key_data8[8] = { 0x00,0x11,0x22,0x33,0x44,0x55,0x66,0x77}; //uint8_t new_key_data16[16] = { 0x00,0x11,0x22,0x33,0x44,0x55,0x66,0x77,0x88,0x99,0xAA,0xBB,0xCC,0xDD,0xEE,0xFF}; uint8_t resp[256] = {0x00}; uint8_t IV[16] = {0x00}; size_t datalen = datain[0]; uint8_t cmd[40] = {0x00}; uint8_t encRndB[16] = {0x00}; uint8_t decRndB[16] = {0x00}; uint8_t nonce[16] = {0x00}; uint8_t both[32] = {0x00}; uint8_t encBoth[32] = {0x00}; InitDesfireCard(); LED_A_ON(); LED_B_OFF(); LED_C_OFF(); // 3 olika sätt att authenticera. AUTH (CRC16) , AUTH_ISO (CRC32) , AUTH_AES (CRC32) // 4 olika crypto algo DES, 3DES, 3K3DES, AES // 3 olika kommunikations sätt, PLAIN,MAC,CRYPTO // des, nyckel 0, switch (mode){ case 1:{ uint8_t keybytes[16]; uint8_t RndA[8] = {0x00}; uint8_t RndB[8] = {0x00}; if (algo == 2) { if (datain[1] == 0xff){ memcpy(keybytes,PICC_MASTER_KEY16,16); } else { memcpy(keybytes, datain+1, datalen); } } else { if (algo == 1) { if (datain[1] == 0xff){ memcpy(keybytes,null_key_data8,8); } else{ memcpy(keybytes, datain+1, datalen); } } } struct desfire_key defaultkey = {0}; desfirekey_t key = &defaultkey; if (algo == 2) Desfire_3des_key_new_with_version(keybytes, key); else if (algo ==1) Desfire_des_key_new(keybytes, key); cmd[0] = AUTHENTICATE; cmd[1] = keyno; //keynumber len = DesfireAPDU(cmd, 2, resp); if ( !len ) { if (MF_DBGLEVEL >= MF_DBG_ERROR) { DbpString("Authentication failed. Card timeout."); } OnError(3); return; } if ( resp[2] == 0xaf ){ } else { DbpString("Authetication failed. Invalid key number."); OnError(3); return; } memcpy( encRndB, resp+3, 8); if (algo == 2) tdes_dec(&decRndB, &encRndB, key->data); else if (algo == 1) des_dec(&decRndB, &encRndB, key->data); memcpy(RndB, decRndB, 8); rol(decRndB,8); // This should be random uint8_t decRndA[8] = {0x00}; memcpy(RndA, decRndA, 8); uint8_t encRndA[8] = {0x00}; if (algo == 2) tdes_dec(&encRndA, &decRndA, key->data); else if (algo == 1) des_dec(&encRndA, &decRndA, key->data); memcpy(both, encRndA, 8); for (int x = 0; x < 8; x++) { decRndB[x] = decRndB[x] ^ encRndA[x]; } if (algo == 2) tdes_dec(&encRndB, &decRndB, key->data); else if (algo == 1) des_dec(&encRndB, &decRndB, key->data); memcpy(both + 8, encRndB, 8); cmd[0] = ADDITIONAL_FRAME; memcpy(cmd+1, both, 16 ); len = DesfireAPDU(cmd, 17, resp); if ( !len ) { if (MF_DBGLEVEL >= MF_DBG_ERROR) { DbpString("Authentication failed. Card timeout."); } OnError(3); return; } if ( resp[2] == 0x00 ){ struct desfire_key sessionKey = {0}; desfirekey_t skey = &sessionKey; Desfire_session_key_new( RndA, RndB , key, skey ); //print_result("SESSION : ", skey->data, 8); memcpy(encRndA, resp+3, 8); if (algo == 2) tdes_dec(&encRndA, &encRndA, key->data); else if (algo == 1) des_dec(&encRndA, &encRndA, key->data); rol(decRndA,8); for (int x = 0; x < 8; x++) { if (decRndA[x] != encRndA[x]) { DbpString("Authetication failed. Cannot varify PICC."); OnError(4); return; } } //Change the selected key to a new value. /* // Current key is a 3DES key, change it to a DES key if (algo == 2) { cmd[0] = CHANGE_KEY; cmd[1] = keyno; uint8_t newKey[16] = {0x00,0x11,0x22,0x33,0x44,0x55,0x66,0x77,0x00,0x11,0x22,0x33,0x44,0x55,0x66,0x77}; uint8_t first, second; uint8_t buff1[8] = {0x00}; uint8_t buff2[8] = {0x00}; uint8_t buff3[8] = {0x00}; memcpy(buff1,newKey, 8); memcpy(buff2,newKey + 8, 8); ComputeCrc14443(CRC_14443_A, newKey, 16, &first, &second); memcpy(buff3, &first, 1); memcpy(buff3 + 1, &second, 1); tdes_dec(&buff1, &buff1, skey->data); memcpy(cmd+2,buff1,8); for (int x = 0; x < 8; x++) { buff2[x] = buff2[x] ^ buff1[x]; } tdes_dec(&buff2, &buff2, skey->data); memcpy(cmd+10,buff2,8); for (int x = 0; x < 8; x++) { buff3[x] = buff3[x] ^ buff2[x]; } tdes_dec(&buff3, &buff3, skey->data); memcpy(cmd+18,buff3,8); // The command always times out on the first attempt, this will retry until a response // is recieved. len = 0; while(!len) { len = DesfireAPDU(cmd,26,resp); } } else { // Current key is a DES key, change it to a 3DES key if (algo == 1) { cmd[0] = CHANGE_KEY; cmd[1] = keyno; uint8_t newKey[16] = {0x40,0x41,0x42,0x43,0x44,0x45,0x46,0x47,0x48,0x49,0x4a,0x4b,0x4c,0x4d,0x4e,0x4f}; uint8_t first, second; uint8_t buff1[8] = {0x00}; uint8_t buff2[8] = {0x00}; uint8_t buff3[8] = {0x00}; memcpy(buff1,newKey, 8); memcpy(buff2,newKey + 8, 8); ComputeCrc14443(CRC_14443_A, newKey, 16, &first, &second); memcpy(buff3, &first, 1); memcpy(buff3 + 1, &second, 1); des_dec(&buff1, &buff1, skey->data); memcpy(cmd+2,buff1,8); for (int x = 0; x < 8; x++) { buff2[x] = buff2[x] ^ buff1[x]; } des_dec(&buff2, &buff2, skey->data); memcpy(cmd+10,buff2,8); for (int x = 0; x < 8; x++) { buff3[x] = buff3[x] ^ buff2[x]; } des_dec(&buff3, &buff3, skey->data); memcpy(cmd+18,buff3,8); // The command always times out on the first attempt, this will retry until a response // is recieved. len = 0; while(!len) { len = DesfireAPDU(cmd,26,resp); } } } */ OnSuccess(); if (algo == 2) cmd_send(CMD_ACK,1,0,0,skey->data,16); else if (algo == 1) cmd_send(CMD_ACK,1,0,0,skey->data,8); } else { DbpString("Authetication failed."); OnError(6); return; } } break; case 2: //SendDesfireCommand(AUTHENTICATE_ISO, &keyno, resp); break; case 3:{ //defaultkey uint8_t keybytes[16] = {0x00}; if (datain[1] == 0xff){ memcpy(keybytes,PICC_MASTER_KEY16,16); } else{ memcpy(keybytes, datain+1, datalen); } struct desfire_key defaultkey = {0x00}; desfirekey_t key = &defaultkey; Desfire_aes_key_new( keybytes, key); AesCtx ctx; if ( AesCtxIni(&ctx, IV, key->data, KEY128, CBC) < 0 ){ if( MF_DBGLEVEL >= 4) { Dbprintf("AES context failed to init"); } OnError(7); return; } cmd[0] = AUTHENTICATE_AES; cmd[1] = 0x00; //keynumber len = DesfireAPDU(cmd, 2, resp); if ( !len ) { if (MF_DBGLEVEL >= MF_DBG_ERROR) { DbpString("Authentication failed. Card timeout."); } OnError(3); return; } memcpy( encRndB, resp+3, 16); // dekryptera tagnonce. AesDecrypt(&ctx, encRndB, decRndB, 16); rol(decRndB,16); memcpy(both, nonce,16); memcpy(both+16, decRndB ,16 ); AesEncrypt(&ctx, both, encBoth, 32 ); cmd[0] = ADDITIONAL_FRAME; memcpy(cmd+1, encBoth, 32 ); len = DesfireAPDU(cmd, 33, resp); // 1 + 32 == 33 if ( !len ) { if (MF_DBGLEVEL >= MF_DBG_ERROR) { DbpString("Authentication failed. Card timeout."); } OnError(3); return; } if ( resp[2] == 0x00 ){ // Create AES Session key struct desfire_key sessionKey = {0}; desfirekey_t skey = &sessionKey; Desfire_session_key_new( nonce, decRndB , key, skey ); print_result("SESSION : ", skey->data, 16); } else { DbpString("Authetication failed."); OnError(7); return; } break; } } OnSuccess(); cmd_send(CMD_ACK,1,len,0,resp,len); }
int CmdHF14AMfDESAuth(const char *Cmd){ uint8_t blockNo = 0; //keyNo=0; uint32_t cuid=0; uint8_t reply[16]; //DES_cblock r1_b1; uint8_t b1[8]={ 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}; uint8_t b2[8]={ 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}; DES_cblock nr, b0, r1, r0; uint8_t key[8]={ 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}; //DES_cblock iv={0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}; DES_key_schedule ks1; DES_cblock key1; if (strlen(Cmd)<1) { PrintAndLog("Usage: hf desfire des-auth k <key number>"); PrintAndLog(" sample: hf desfire des-auth k 0"); return 0; } //Change key to user defined one memcpy(key1,key,8); //memcpy(key2,key+8,8); DES_set_key((DES_cblock *)key1,&ks1); //DES_set_key((DES_cblock *)key2,&ks2); //Auth1 UsbCommand c = {CMD_MIFARE_DES_AUTH1, {blockNo}}; SendCommand(&c); UsbCommand resp; if (WaitForResponseTimeout(CMD_ACK,&resp,1500)) { uint8_t isOK = resp.arg[0] & 0xff; cuid = resp.arg[1]; uint8_t * data= resp.d.asBytes; if (isOK){ PrintAndLog("enc(nc)/b0:%s", sprint_hex(data+2,8)); memcpy(b0,data+2,8); } } else { PrintAndLog("Command execute timeout"); } //Do crypto magic DES_random_key(&nr); //b1=dec(nr) //r0=dec(b0) DES_ecb_encrypt(&nr,&b1,&ks1,0); DES_ecb_encrypt(&b0,&r0,&ks1,0); //PrintAndLog("b1:%s",sprint_hex(b1, 8)); PrintAndLog("r0:%s",sprint_hex(r0, 8)); //r1=rol(r0) memcpy(r1,r0,8); rol(r1,8); PrintAndLog("r1:%s",sprint_hex(r1, 8)); for(int i=0;i<8;i++){ b2[i]=(r1[i] ^ b1[i]); } DES_ecb_encrypt(&b2,&b2,&ks1,0); //PrintAndLog("b1:%s",sprint_hex(b1, 8)); PrintAndLog("b2:%s",sprint_hex(b2, 8)); //Auth2 UsbCommand d = {CMD_MIFARE_DES_AUTH2, {cuid}}; memcpy(reply,b1,8); memcpy(reply+8,b2,8); memcpy(d.d.asBytes,reply, 16); SendCommand(&d); UsbCommand respb; if (WaitForResponseTimeout(CMD_ACK,&respb,1500)) { uint8_t isOK = respb.arg[0] & 0xff; uint8_t * data2= respb.d.asBytes; if (isOK){ PrintAndLog("b3:%s", sprint_hex(data2+2, 8)); } } else { PrintAndLog("Command execute timeout"); } return 1; }
//EV1 // Reader 2 Card : 02AA, key (1 byte), CRC1 CRC2 ; auth // Card 2 Reader : 02AF, 16 Bytes(b0), CRC1 CRC2 // Reader 2 Card : 03AF, 16 Bytes(b1),16Bytes(b2) CRC1 CRC2 // Card 2 Reader : 0300, 16 bytes(b3), CRC1 CRC2 ; success int CmdHF14AMfAESAuth(const char *Cmd){ uint8_t blockNo = 0; //keyNo=0; uint32_t cuid=0; uint8_t reply[32]; //DES_cblock r1_b1; //unsigned char * b1, b2, nr, b0, r0, r1; uint8_t b1[16]={ 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}; uint8_t b2[16]={ 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}; uint8_t nr[16]={ 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}; uint8_t b0[16]={ 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}; uint8_t r0[16]={ 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}; uint8_t r1[16]={ 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}; // uint8_t key[16]={ 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}; uint8_t iv[16]={ 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}; AES_KEY key_e; AES_KEY key_d; if (strlen(Cmd)<1) { PrintAndLog("Usage: hf desfire aes-auth k <key number>"); PrintAndLog(" sample: hf desfire aes-auth k 0"); return 0; } //Change key to user defined one // // int private_AES_set_encrypt_key(const unsigned char *userKey, const int bits,AES_KEY *key); //int private_AES_set_decrypt_key(const unsigned char *userKey, const int bits,AES_KEY *key); // //memcpy(key1,key,16); //memcpy(key2,key+8,8); AES_set_encrypt_key(key,128,&key_e); AES_set_decrypt_key(key,128,&key_d); //Auth1 UsbCommand c = {CMD_MIFARE_DES_AUTH1, {blockNo}}; SendCommand(&c); UsbCommand resp; if (WaitForResponseTimeout(CMD_ACK,&resp,1500)) { uint8_t isOK = resp.arg[0] & 0xff; cuid = resp.arg[1]; uint8_t * data= resp.d.asBytes; if (isOK){ PrintAndLog("enc(nc)/b0:%s", sprint_hex(data+2,16)); memcpy(b0,data+2,16); } } else { PrintAndLog("Command execute timeout"); } // // void AES_cbc_encrypt(const unsigned char *in, unsigned char *out, //size_t length, const AES_KEY *key, //unsigned char *ivec, const int enc); //Do crypto magic //DES_random_key(&nr); //b1=dec(nr) //r0=dec(b0) //AES_cbc_encrypt(&nr,&b1,16,&key,0); AES_cbc_encrypt(&b0,&r0,16,&key_d,iv,0); //PrintAndLog("b1:%s",sprint_hex(b1, 8)); PrintAndLog("r0:%s",sprint_hex(r0, 16)); //r1=rol(r0) memcpy(r1,r0,16); rol(r1,8); PrintAndLog("r1:%s",sprint_hex(r1, 16)); for(int i=0;i<16;i++){ b1[i]=(nr[i] ^ b0[i]); b2[i]=(r1[i] ^ b1[i]); } PrintAndLog("nr:%s",sprint_hex(nr, 16)); AES_cbc_encrypt(&b1,&b1,16,&key_e,iv,1); AES_cbc_encrypt(&b2,&b2,16,&key_e,iv,1); PrintAndLog("b1:%s",sprint_hex(b1, 16)); PrintAndLog("b2:%s",sprint_hex(b2, 16)); //Auth2 UsbCommand d = {CMD_MIFARE_DES_AUTH2, {cuid}}; memcpy(reply,b1,16); memcpy(reply+16,b2,16); memcpy(d.d.asBytes,reply, 32); SendCommand(&d); UsbCommand respb; if (WaitForResponseTimeout(CMD_ACK,&respb,1500)) { uint8_t isOK = respb.arg[0] & 0xff; uint8_t * data2= respb.d.asBytes; if (isOK){ PrintAndLog("b3:%s", sprint_hex(data2+2, 16)); } } else { PrintAndLog("Command execute timeout"); } return 1; }
/* * Authenticate to the provided MIFARE tag. */ int mifare_ultralightc_authenticate (MifareTag tag, const MifareDESFireKey key) { ASSERT_ACTIVE (tag); ASSERT_MIFARE_ULTRALIGHT_C (tag); BUFFER_INIT (cmd1, 2); BUFFER_INIT (res, 9); BUFFER_APPEND (cmd1, 0x1A); BUFFER_APPEND (cmd1, 0x00); ULTRALIGHT_TRANSCEIVE_RAW(tag, cmd1, res); uint8_t PICC_E_RndB[8]; memcpy (PICC_E_RndB, res+1, 8); uint8_t PICC_RndB[8]; memcpy (PICC_RndB, PICC_E_RndB, 8); uint8_t ivect[8]; memset (ivect, '\0', sizeof (ivect)); mifare_cypher_single_block (key, PICC_RndB, ivect, MCD_RECEIVE, MCO_DECYPHER, 8); uint8_t PCD_RndA[8]; DES_random_key ((DES_cblock*)&PCD_RndA); uint8_t PCD_r_RndB[8]; memcpy (PCD_r_RndB, PICC_RndB, 8); rol (PCD_r_RndB, 8); uint8_t token[16]; memcpy (token, PCD_RndA, 8); memcpy (token+8, PCD_r_RndB, 8); size_t offset = 0; while (offset < 16) { mifare_cypher_single_block (key, token + offset, ivect, MCD_SEND, MCO_ENCYPHER, 8); offset += 8; } BUFFER_INIT (cmd2, 17); BUFFER_APPEND (cmd2, 0xAF); BUFFER_APPEND_BYTES (cmd2, token, 16); ULTRALIGHT_TRANSCEIVE_RAW(tag, cmd2, res); uint8_t PICC_E_RndA_s[8]; memcpy (PICC_E_RndA_s, res+1, 8); uint8_t PICC_RndA_s[8]; memcpy (PICC_RndA_s, PICC_E_RndA_s, 8); mifare_cypher_single_block (key, PICC_RndA_s, ivect, MCD_RECEIVE, MCO_DECYPHER, 8); uint8_t PCD_RndA_s[8]; memcpy (PCD_RndA_s, PCD_RndA, 8); rol (PCD_RndA_s, 8); if (0 != memcmp (PCD_RndA_s, PICC_RndA_s, 8)) { return -1; } // XXX Should we store the state "authenticated" in the tag struct?? return 0; }
static void SHAUpdate(SHA_CTX *ctx, unsigned char *HashBlock, int len) { UBS_UINT32 a, b, c, d, e; int block, i; /* Process as many blocks as possible */ for (block = 0; len >= 64; len -= 64, ++block) { UBS_UINT32 m[16]; /* A 16-byte buffer is sufficient -- we build needed words beyond the first 16 on the fly */ RTL_Memcpy(m, HashBlock + 64*block, 64); /* Get one block of data */ /* At this point m[] is built as a char array. However, m[] will be operated on from here on out as an array of unsigned longs. This algorithm assumes m[] is arranged in big-endian byte order, so we'll endian-adjust the byte array if we have a little endian CPU */ #if (UBS_CPU_ATTRIBUTE == UBS_LITTLE_ENDIAN) for (i = 0; i < 16; ++i) m[i] = BYTESWAPLONG(m[i]); /* View data as big endian */ #endif a = ctx->buffer[0]; b = ctx->buffer[1]; c = ctx->buffer[2]; d = ctx->buffer[3]; e = ctx->buffer[4]; Dbg_Print(DBG_SHA1,("pre round 0: 0x%x 0x%x 0x%x 0x%x 0x%x\n", a, b, c, d, e)); /* Four sets of 20 rounds each */ for (i = 0; i < 80; ++i) { unsigned long fn = 0, temp, K = 0; switch (i / 20) { case 0: K = SHA1_K[0]; fn = F(b,c,d); break; case 1: K = SHA1_K[1]; fn = G(b,c,d); break; case 2: K = SHA1_K[2]; fn = H(b,c,d); break; case 3: K = SHA1_K[3]; fn = G(b,c,d); break; default: ; } /* Build needed words beyond original 16 on the fly */ if (i >= 16) m[i % 16] = rol(m[(i-3) % 16] ^ m[(i-8) % 16] ^ m[(i-14) % 16] ^ m[(i-16) % 16], 1); temp = rol(a, 5) + fn + e + m[i%16] + K; e = d; d = c; c = rol(b, 30); b = a; a = temp; Dbg_Print(DBG_SHA1,("post round %d: 0x%x 0x%x 0x%x 0x%x 0x%x\n", i, a, b, c, d, e)); } ctx->buffer[0] += a; ctx->buffer[1] += b; ctx->buffer[2] += c; ctx->buffer[3] += d; ctx->buffer[4] += e; } }
unsigned *md5( const char *msg, int mlen) { static Digest h0 = { 0x67452301, 0xEFCDAB89, 0x98BADCFE, 0x10325476 }; // static Digest h0 = { 0x01234567, 0x89ABCDEF, 0xFEDCBA98, 0x76543210 }; static DgstFctn ff[] = { &f0, &f1, &f2, &f3 }; static short M[] = { 1, 5, 3, 7 }; static short O[] = { 0, 1, 5, 0 }; static short rot0[] = { 7,12,17,22}; static short rot1[] = { 5, 9,14,20}; static short rot2[] = { 4,11,16,23}; static short rot3[] = { 6,10,15,21}; static short *rots[] = {rot0, rot1, rot2, rot3 }; static unsigned kspace[64]; static unsigned *k; static Digest h; Digest abcd; DgstFctn fctn; short m, o, g; unsigned f; short *rotn; union { unsigned w[16]; char b[64]; }mm; int os = 0; int grp, grps, q, p; unsigned char *msg2; if (k==NULL) k= calcKs(kspace); for (q=0; q<4; q++) h[q] = h0[q]; // initialize { grps = 1 + (mlen+8)/64; msg2 = (unsigned char *)malloc(64*grps); memcpy( msg2, msg, mlen); msg2[mlen] = (unsigned char)0x80; q = mlen + 1; while (q < 64*grps){ msg2[q] = 0; q++ ; } { // unsigned char t; WBunion u; u.w = 8*mlen; // t = u.b[0]; u.b[0] = u.b[3]; u.b[3] = t; // t = u.b[1]; u.b[1] = u.b[2]; u.b[2] = t; q -= 8; memcpy(msg2+q, &u.w, 4 ); } } for (grp=0; grp<grps; grp++) { memcpy( mm.b, msg2+os, 64); for(q=0;q<4;q++) abcd[q] = h[q]; for (p = 0; p<4; p++) { fctn = ff[p]; rotn = rots[p]; m = M[p]; o= O[p]; for (q=0; q<16; q++) { g = (m*q + o) % 16; f = abcd[1] + rol( abcd[0]+ fctn(abcd) + k[q+16*p] + mm.w[g], rotn[q%4]); abcd[0] = abcd[3]; abcd[3] = abcd[2]; abcd[2] = abcd[1]; abcd[1] = f; } } for (p=0; p<4; p++) h[p] += abcd[p]; os += 64; } return h; }