user5410082
user5410082

Reputation:

Error in storing variable values with size 8bits (uint8) in Matlab

I'm implementing a 128-bit AES encryption algorithm in Matlab, I'm implementing this code based on a functional code in C, the big problem is that in the C code all variables are defined as unsigned char making it easier to manipulate , In MatLab I declared all variables as uint8 (unsingned integer 8 bits), a part of encryption is almost ready, however I came across a problem, I was running the code and realized that some values ​​were sent wrong from the vector S- Box, debugging the Codes I found the problem, there is a moment without code that a letter below returns me the value 255:

 for i = 1 : 16
        stateU(i)= sboxU(bitxor(stateU(i),keyU(i))+1);
 end

This function is responsible for changing the values ​​of the naked data by the corresponding value of S-box, in C the same function is used to make this change, but the vector in C starts in the index 0 going to 255, in matlab the vectors start in Index 1 and go up to 256, and that's where the problem is, when my function returns 255 as the index value is always added +1 due to this difference of indicies in relation from C to MatLab, but how all variables are defined With 8-bit size, it is not possible to store the value of 256 in the variable, so the code stores 255, resulting in a wrong value in the variable.

The expected output should be (this is the correct output of the code in C, after the second iteration of the for loop ranging from 1-16):

State[0] before shift: 207
State[1] before shift: 0
State[2] before shift: 152
State[3] before shift: 115
State[4] before shift: 237
State[5] before shift: 77
State[6] before shift: 148
State[7] before shift: 123
State[8] before shift: 22
State[9] before shift: 182
State[10] before shift: 122
State[11] before shift: 190
State[12] before shift: 130
State[13] before shift: 198
State[14] before shift: 29
State[15] before shift: 155

Notice that position [8] is 22, this value is obtained through a bit-a-bit XOR of the state variable with the variable key, as spoken at the beginning of this post, in C the variables are defined as unsigned char, so , There are no problems with the size of the values. In Matlab I have the following output:

State[0] before shift: 207
State[1] before shift: 0
State[2] before shift: 152
State[3] before shift: 115
State[4] before shift: 237
State[5] before shift: 77
State[6] before shift: 148
State[7] before shift: 123
State[8] before shift: 187
State[9] before shift: 182
State[10] before shift: 122
State[11] before shift: 190
State[12] before shift: 130
State[13] before shift: 198
State[14] before shift: 29
State[15] before shift: 155

Note that the position [8] of the vector in MatLab has a different value, since the type of the variable is defined as uint8 in MatLab, it can only store values ​​up to 255, theoretically it should take the value of position 256 of S -box, but as the type is uint8 it takes the value of a position at least (255 - 1111 1111), which maximum 8 bits can store.

Below are the two codes for analysis.

Galois_mul2 function:

function galois_value = galois_mul2( value )
    value = uint8(value);
    temp = typecast(value, 'int8');
    temp = bitshift(temp,-7); 
    hex = int8(hex2dec('1B')); 
    temp = bitand(temp,hex); 
    temp2 = typecast(bitshift(value,1),'int8');
    galois_value =  typecast(bitxor(temp2,temp),'uint8'); 
end

Main code:

%Key
key = {'00','01','02','03','04','05','06','07','08','09','0a','0b','0c','0d','0e','0f'};
for n = 1 : 16
   keyU(n)=uint8(hex2dec(key(n)));
end
%State
state = {'00','11','22','33','44','55','66','77','88','99','aa','bb','cc','dd','ee','ff'};
for n = 1 : 16
   stateU(n)=uint8(hex2dec(state(n)));
end
%Sbox
sbox = {'63','7c','77','7b','f2','6b','6f','c5','30','01','67','2b','fe','d7','ab','76','ca','82','c9','7d','fa','59','47','f0','ad','d4','a2','af','9c','a4','72','c0','b7','fd','93','26','36','3f','f7','cc','34','a5','e5','f1','71','d8','31','15','04','c7','23','c3','18','96','05','9a','07','12','80','e2','eb','27','b2','75','09','83','2c','1a','1b','6e','5a','a0','52','3b','d6','b3','29','e3','2f','84','53','d1','00','ed','20','fc','b1','5b','6a','cb','be','39','4a','4c','58','cf','d0','ef','aa','fb','43','4d','33','85','45','f9','02','7f','50','3c','9f','a8','51','a3','40','8f','92','9d','38','f5','bc','b6','da','21','10','ff','f3','d2','cd','0c','13','ec','5f','97','44','17','c4','a7','7e','3d','64','5d','19','73','60','81','4f','dc','22','2a','90','88','46','ee','b8','14','de','5e','0b','db','e0','32','3a','0a','49','06','24','5c','c2','d3','ac','62','91','95','e4','79','e7','c8','37','6d','8d','d5','4e','a9','6c','56','f4','ea','65','7a','ae','08','ba','78','25','2e','1c','a6','b4','c6','e8','dd','74','1f','4b','bd','8b','8a','70','3e','b5','66','48','03','f6','0e','61','35','57','b9','86','c1','1d','9e','e1','f8','98','11','69','d9','8e','94','9b','1e','87','e9','ce','55','28','df','8c','a1','89','0d','bf','e6','42','68','41','99','2d','0f','b0','54','bb','16'}; 
for n = 1 : 256
   sboxU(n)=uint8(hex2dec(sbox(n)));
end
%Rcon
rcon = {'01','02','04','08','10','20','40','80','1b','36'};
for n = 1 : 10
   rconU(n)=uint8(hex2dec(rcon(n)));
end
%Main AES Data Loop
for round = 1 : 10
%Add key + sbox 
    for i = 1 : 16
        stateU(i)= sboxU(bitxor(stateU(i),keyU(i))+1);
    end
%Shift Rows
    buf1 = stateU(2);
    stateU(2) = stateU(6);
    stateU(6) = stateU(10);
    stateU(10) = stateU(14);
    stateU(14) = buf1;

      buf1 = stateU(3);
      buf2 = stateU(7);
      stateU(3) = stateU(11);
      stateU(7) = stateU(15);
      stateU(11) = buf1;
      stateU(15) = buf2;

      buf1 = stateU(16);
      stateU(16) = stateU(12);
      stateU(12) = stateU(8);
      stateU(8) = stateU(4);
      stateU(4) = buf1;
  %Process mixcolumn for all rounds but the last one
      if round < 10
          for j = 0 : 3
  %Compute the current index
              buf4 = (bitshift(j,2));
              %buf1
              aux1 = bitxor(stateU(buf4+1),stateU(buf4+2));
              aux2 = bitxor(stateU(buf4+3),stateU(buf4+4));
              buf1 = bitxor(aux1,aux2);
              %buf2
              buf2 = stateU(buf4+1);
              %buf3
              buf3 = bitxor(stateU(buf4+1),stateU(buf4+2));
              buf3 = galois_mul2(buf3);
              %%%%%%%%%%%%%%%%%%%
              aux = bitxor(stateU(buf4+1),buf3);
              stateU(buf4+1) = bitxor (aux,buf1); 
          end
      end
  end

It is noteworthy that when I found the error I stopped debugging in the second iteration of the for loop, that is, the correct output that is shown up there is the output after the second iteration of the for loop that goes from 0-16 that was posted there in Top too. In the first iteration it works because the bit-a-bit XOR function returns no value greater than 255 (1111 1111).

I already tried to change all the variables to uint16 however the code does not work, it says that the types must be scalar or multiples of 2.

Upvotes: 1

Views: 167

Answers (1)

Yvon
Yvon

Reputation: 2993

The problem is when you add 1 to 255 of the type uint8 an overflow will happen.

 for i = 1 : 16
        stateU(i)= sboxU(bitxor(stateU(i),keyU(i))+1);
 end

Since you are only adding 1 to generate the index, which does not relate to your data type, you can convert the vector index to a more suitable data type before adding 1. In this way overflow is avoided, and your data is non-touched, still of uint8.

 for i = 1 : 16
        stateU(i)= sboxU(double(bitxor(stateU(i),keyU(i)))+1);
 end

Some consideration about data type: Although a type conversion to double (or any type that can hold 256) is used, that does not mean you are storing any data in other type than uint8. It's just the indexing convention of Matlab; in fact in C you can totally rely on uint8 since vector indices in C start at 0, so the last index would be 255.

Upvotes: 3

Related Questions