Search code examples
pythoncdjangoencryptionesp32

Encryption IV - C and Python equivalent


I have problems regarding initializing equivalent "initialization vectors" for the encryption of my message. I have an ESP32 (microcontroller) sending Data via JSON to a Django Server. On the ESP32 I use the Arduino IDE, so the code on the ESP32 is written in C/C++. Django of course is using Python.

My encryption works so far if I intialiaze the IV like this on both sides:

ESP32:

unsigned char iv[16] = {'0','0','0','0','0','0','0','0','0','0','0','0','0','0','0','0'};

Django:

iv = b'0000000000000000'

The library of the ESP32 has an encryption function which expects an unsigned char array. I have to pay attention that the array is not null-terminated ('\0' at the end) or i get different results. That are the background informations. you need. Now to my specific problem:

I want to use counter mode in my encryption. I want to copy an integer-counter to the last 4 bytes of the IV on both sides:

On the ESP32 I do:

int msg_counter = 15 //15 just as an example
memcpy(iv+12, &msg_counter, sizeof(msg_counter));

On Django I do:

counter = (int) 15;
iv = counter.to_bytes(16, byteorder = 'big')

If I print out the variable "iv" I get this on Django:

b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x0f'

The decryption fails. I dont get the original message from the ESP32 on the server.

If I dont initialize the IV's like above, I always get different results.

I am using PyCryptoDome for the encryption/decryption on Django. I am passing the IV to this line of code: obj = AES.new(enckey, AES.MODE_CFB, iv, segment_size = 128) The IV must be passed in a format like this b'0000000000000000'. So i dont have any other choices on the server-side.

If I do this on the ESP32:

memset(iv,0,16);

and

b'0000000000000000'

on Django I get different results. I dont know what to to.

Any ideas?


Solution

  • I kept trying and found it out myself.

    On the ESP32 you have to do:

    int msg_counter = 15;
    unsigned char iv[16];
    unsigned char bytes[4];
    bytes[0] = (msg_counter >> 24) & 0xFF;
    bytes[1] = (msg_counter >> 16) & 0xFF;
    bytes[2] = (msg_counter >> 8) & 0xFF;
    bytes[3] = msg_counter & 0xFF;
    memcpy(iv+12, bytes, sizeof(bytes));
    

    On Django:

    counter = 15;
    iv = counter.to_bytes(16, byteorder = 'big')