0

I'm learning esp8266 using arduino IDE. I'm still a beginner in development board programming. What I've been trying to do is use a crypto library. I am trying out AES in arduino and I chose that library because it seemed complete, and was one of the only library that used ECB. My problem is whilst calling the encrypt function, I get confused with the output.

This is what I've done so far.

#include <Crypto.h>
#include <AES.h>
#include <string.h>

AESSmall128 aes128;


void setup()
{
    Serial.begin(9600);


  uint8_t key = (uint8_t)1234567654321234;

    aes128.setKey(&key, 16);

    uint8_t output = 0;

    Serial.println("before");
    Serial.print(output);

      uint8_t input = (uint8_t)9164567654321234;


    aes128.encryptBlock(&output, &input);
    Serial.println("after");
    Serial.print(output);

}

void loop()
{
}

When I print output it returns 252. What is 252? Why only 252? It seems really short looking at it. Why doesn't it output strings?

  • Have you seen the example? github.com/rweather/arduinolibs/blob/master/libraries/Crypto/… – Jot Dec 13 '18 at 19:51
  • Hey. I've tried the examples. They don't output any results from the encryption/ decryption. The test examples are for "performance checks". I've got this question done, look at Jose's answer. Thank you. – Adis Dec 13 '18 at 19:52
3

uint8_t is an Unsigned 8-bit Integer, and so the range of values it can represent are 0 to 255.

When you typecast your long/large values to uint8_t, you basically only show the least-significant 8-bits.

However, the decryptBlock() and encryptBlock() functions expect an array of bytes, not a single byte.

The library you link to notes, right in the linked position, that the output and input parameters must be at least blockSize() bytes in length. Referencing blockSize(), it notes that this function always returns 16. So you need to pass an array of uint8_ts of at least 16 length.

When you define your variables for the key, plaintext, and ciphertext, you need to not define then as a single byte type, but as an array of bytes:

uint8_t[16] key =    {1,2,3,4,5,6,7,6,5,4,3,2,1,2,3,4};  // This is not a good key, btw
uint8_t[16] output = {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0};
uint8_t[16] input =  {9,1,6,4,5,6,7,6,5,4,3,2,1,2,3,4};

(When passing an array, you don't need to dereference the variable, so call aes128.setKey(key, 16);, etc. Omit the &)

Each of the 16 bytes can have a value in the range 0 to 255. They do not have to be limited to single-digit numbers; I just copied/translated what you wrote to demonstrate the example. You could set your key in this way:

uint8_t[16] key =    {66,127,164,72,68,158,148,255,23,36,226,192,198,248,251,221};

You can also refer to bytes with a 2-digit hexadecimal representation:

uint8_t[16] key =    {0xa6,0x09,0x81,0xc5,0xb8,0xf6,0x9a,0x33,0x75,0x24,0xff,0x79,0xd3,0x48,0x4f,0x1d);

UPDATE to address strings

A C-style string is a sequence of bytes, with type char to indicate ASCII data, though any byte-wide type could work in theory. The sequence of bytes ends with a value of 0 (i.e., 0x00, not the ASCII character '0'), so you must remember that the termination byte takes up a byte of memory.

To initialize your key with a string:

const unsigned char[17] key = "helloareyouarehi"; // 16 characters, and 1 byte termination means 17 total bytes reserved in memory.

I have not investigated how the crypto library you are using handles C-style strings, so let's assume it does not acknowledge them at all, and we will have to null-terminate our strings ourselves.

char[17] output = {0}; // Initialized to all zeros
char[17] input = "iwanttoencryptme";

aes128.encryptBlock(output, input);
output[16] = 0x00; // Just to be safe, put the null terminator in the last slot.

Serial.print(output);

If the encryptBlock() function only changes 16 bytes in the output array, then the 17th (zero) could remain from the initialization, but not knowing whether the function preserves strings, it is better to be safe than sorry.

  • Hello @jose, thanks so much for replying. Before I continue, yes I do know it's not a good key, I'm just trying out the library for fun. I have a better understanding now after you explained that it represent values between 0-255. Now my question would be, do those numbers represent ASCII values? – Adis Dec 13 '18 at 17:08
  • ASCII values are bytes, but they typically range only from 0 to 128, and even smaller for printable ASCII. If you want to start working with strings instead of arrays of numbers, you have to take extra care when reading and writing the string data. – jose can u c Dec 13 '18 at 17:10
  • Okay, lets say I wanted my key to be "helloareyouarehi", how would that be represented as array of uint8_t? And to output the array of uint8_t? – Adis Dec 13 '18 at 17:13
  • Oh yea, isn't it meant to be uint8_t key [] = {1,2,3,4,5,6,7,6,5,4,3,2,1,2,3,4}; syntax wise? – Adis Dec 13 '18 at 17:13
  • Array initialization can have explicit or implicit sizing. It's my preference to explicitly define the array size. – jose can u c Dec 13 '18 at 17:26
1

The uint8_t is exactly 8bits wide, so it can hold values from 0 to 255. Your number however is about 54bits wide.

I think you should use the array.

Also numeric literals are usually int type, so even if you do have enough space for it, it gets wrong value. Something like uint64_t value = UINT64_C(1234567654321234); must be used

Your Answer

By clicking "Post Your Answer", you acknowledge that you have read our updated terms of service, privacy policy and cookie policy, and that your continued use of the website is subject to these policies.

Not the answer you're looking for? Browse other questions tagged or ask your own question.