#include <stdio.h>

unsigned char Password[16] = { 0x00 , 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88, 0x99, 0xAA, 0xBB, 0xCC, 0xDD, 0xEE,0xFF };
//unsigned char Password[16] = { 0 };

unsigned char Plaintext[16] = { 0 };

const unsigned char IV[16] = { 0x35, 0xF8, 0x2D, 0xEA, 0x31, 0x13, 0xD2, 0xEC, 0xF3, 0xED, 0x35, 0x54, 0xC4, 0xA1, 0x99, 0xF6 };
const unsigned char Data[16] = { 0x36, 0x36, 0x4C, 0x47, 0xF9, 0xD6, 0x48, 0x39, 0x84, 0xD7, 0xD2, 0x53, 0xDB, 0x47, 0xB2, 0x21, };

void DecryptBlock(unsigned char Password[16]) {
	//Just a guess
	//Just a guess	
	int *s0 = (int *)Data;
	int s3 = 0;
	int s5 = 0;
	int s1 = 0; //*(unsigned int *)(&Data[4]); //get ptr to round


	int a3 = *(unsigned int *)(&Password[4]);  //a3 = b[13]
	int t5 = *(unsigned int *)(&Password[12]); //t5 = b[30]

	int a5 = -337237 * 0x1000;
	int t0 = 337237 * 0x1000;
	int s2 = a5 - 1622;
	t0 = t0 + 1621;
	int a4 = s1 + 23;
	int a2 = t5 & s2;
	a5 = a3 & t0;
	a4 = a4 & 31; //fishy
	a5 = a5 | a2;
	a2 = 0 - a4;
	a4 = ((unsigned int)a5) >> a4;
	a5 = a5 << a2;
	a4 = a4 | a5;
	int t1 = ((unsigned int)a4) >> 24;
	t1 = t1 + 65;
	a5 = ((unsigned int)a4) >> 16;
	a2 = t1 & 255;
	a5 = a5 & 255;
	a2 = a2 + a5;

	int t4 = *(unsigned int *)(&Password[0]);
	int t2 = *(unsigned int *)(&Password[8]);

	a2 = a2 + 72;
	int a0 = ((unsigned int)a4) >> 8;
	int a1 = a2 & 255;
	a0 = a0 & 255;
	a5 = s1 + 19; //wrong
	a1 = a1 + a0;
	int a6 = t4 & t0;
	a0 = t2 & s2;
	a5 = a5 & 31;
	a1 = a1 + 79;
	a6 = a6 | a0;
	int a7 = 0 - a5;
	a0 = a1 & 255;
	a4 = a4 & 255;
	a5 = ((unsigned int)a6) >> a5;
	a4 = a0 + a4;
	a6 = a6 << a7;
	a5 = a5 | a6;
	a0 = a4 + 86;
	a6 = a0 & 255;
	a4 = ((unsigned int)a5) >> 24;
	a6 = a6 + a4;
	a6 = a6 + 93;
	a4 = ((unsigned int)a5) >> 16;
	a7 = a6 & 255;
	a4 = a4 & 255;
	a7 = a7 + a4;
	a7 = a7 + 100;
	int t6 = ((unsigned int)a5) >> 8;
	int t3 = a7 & 0xFF;
	t6 = t6 & 0xFF;
	a4 = s1 + 0x11;
	t3 = t3 + t6;
	t5 = t5 & t0;
	a4 = a4 & 0x1F;
	t3 = t3 + 0x6B;
	a3 = a3 & s2;
	a3 = a3 | t5;
	t6 = 0 - a4;
	t5 = t3 & 0xFF;
	a5 = a5 & 0xFF;
	a5 = t5 + a5;
	a4 = ((unsigned int)a3) >> a4;
	a3 = a3 << t6;
	a4 = a4 | a3;
	a3 = a5 + 0x72;
	t5 = a3 & 0xFF;
	a5 = ((unsigned int)a4) >> 0x18;
	t5 = t5 + a5;
	t5 = t5 + 0x79;
	a5 = ((unsigned int)a4) >> 0x10;
	t6 = t5 & 0xFF;
	a5 = a5 & 0xFF;
	t6 = t6 + a5;
	t6 = t6 + 0x80;
	a5 = ((unsigned int)a4) >> 8;
	int s4 = t6 & 0xFF;
	a5 = a5 & 0xFF;
	s4 = s4 + a5;
	s1 = s1 + 0xD;
	a5 = t4 & s2;
	t0 = t2 & t0;
	s1 = s1 & 0x1F;
	s4 = s4 + 0x87;
	a5 = a5 | t0;
	t4 = 0 - s1;
	t0 = s4 & 0xFF;
	a4 = a4 & 0xFF;
	s1 = ((unsigned int)a5) >> s1;
	a4 = t0 + a4;
	a5 = a5 << t4;
	a5 = s1 | a5;
	t0 = a4 + 0x8E;
	t2 = t0 & 0xFF;
	a4 = ((unsigned int)a5) >> 0x18;
	t2 = t2 + a4;
	t2 = t2 + 0x95;
	a4 = ((unsigned int)a5) >> 0x10;
	s1 = t2 & 0xFF;
	a4 = a4 & 0xFF;
	s1 = s1 + a4;
	s1 = s1 + 0x9C;
	a4 = ((unsigned int)a5) >> 8;
	s2 = s1 & 0xFF;
	a4 = a4 & 0xFF;
	s2 = s2 + a4;
	s2 = s2 + 0xA3;
	a4 = s2 & 0xFF;
	a5 = a5 & 0xFF;
	a5 = a5 + a4;
	//int *s6 = s0 + 8; //ptr to encrypted data
	a4 = s3 + 8;
	t4 = s3 + 0xC;
	//s5 = s0 + 0xC;
	a5 = a5 + 0xAA;
	//sltu           t4 = s6, t4
	//((unsigned) t6 < (unsigned) t4) ? (t4 = 1) : (t4 = 0);
	//sltu           s5 = a4, s5
	//((unsigned) a4 < (unsigned) s5) ? (s5 = 1) : (s5 = 0);
	int s7 = a3 & 0xFF;
	t1 = t1 & 0xFF;
	a2 = a2 & 0xFF;
	a1 = a1 & 0xFF;
	a0 = a0 & 0xFF;
	a6 = a6 & 0xFF;
	a7 = a7 & 0xFF;
	t3 = t3 & 0xFF;
	t5 = t5 & 0xFF;
	t6 = t6 & 0xFF;
	s4 = s4 & 0xFF;
	t0 = t0 & 0xFF;
	t2 = t2 & 0xFF;
	s1 = s1 & 0xFF;
	s2 = s2 & 0xFF;
	a5 = a5 & 0xFF;
	//t4 = t4 ^ 1;
	//a3 = s5 ^ 1;

	//Store
	Plaintext[15] = t1 ^ Data[15] ^ IV[0];
	Plaintext[14] = a2 ^ Data[14] ^ IV[1];
	Plaintext[13] = a1 ^ Data[13] ^ IV[2];
	Plaintext[12] = a0 ^ Data[12] ^ IV[3];
	Plaintext[11] = a6 ^ Data[11] ^ IV[4];
	Plaintext[10] = a7 ^ Data[10] ^ IV[5];
	Plaintext[9] = t3 ^ Data[9] ^ IV[6];
	Plaintext[8] = s7 ^ Data[8] ^ IV[7];
	Plaintext[7] = t5 ^ Data[7] ^ IV[8];
	Plaintext[6] = t6 ^ Data[6] ^ IV[9];
	Plaintext[5] = s4 ^ Data[5] ^ IV[10];
	Plaintext[4] = t0 ^ Data[4] ^ IV[11];
	Plaintext[3] = t2 ^ Data[3] ^ IV[12];
	Plaintext[2] = s1 ^ Data[2] ^ IV[13];
	Plaintext[1] = s2 ^ Data[1] ^ IV[14];
	Plaintext[0] = a5 ^ Data[0] ^ IV[15];
}


//char Plaintext[] = { 0x5d ,0x00 ,0x00 ,0x80 ,0x00 ,0xff ,0xff ,0xff ,0xff ,0xff ,0xff ,0xff ,0xff ,0x00 ,0x23 ,0x93 };

int main(int argc, char **argv) {
	DecryptBlock((unsigned char *) argv[1]);
	printf("'");
	for (int i = 0; i < 16; i++) {
		printf("%02X", Plaintext[i]);
	}
	printf("'\n");

	return 0;
}