0

I tried different methods but eventually got errors. Please give a solution and a brief explanation of the concept.

uint8_t **subBytes()
{
    int i,j;
    uint8_t r,c;
    uint8_t t[4][4];

    for(i=0;i<4;i++)
    {
        for (j=0;j<4;j++)
        {
            r = pt[p1][j] & 0xf0;
            r = r >> 4;
            c = pt[p1][j] & 0x0f;
            t[i][j] = (uint8_t *) malloc(sizeof(uint8_t));
            t[i][j] = sBox[r][c];
        }
        p1++;
    }
    return t;
}

int main()
{
    uint8_t **temp;
    temp = subBytes();
    for(i=0;i<4;i++)
    {
        for(j=0;j<4;j++)
        {
            printf("%x  ", temp[i][j]);
        }
        printf("\n");
    }
}

This is my original code. Here, I used malloc, but then too it is not working.

ikh
  • 10,119
  • 1
  • 31
  • 70
Melvin
  • 301
  • 1
  • 3
  • 7

3 Answers3

0

m is LOCAL VARIABLES. When add returns, m is DESTROYED!

You SHOULD NOT return the pointer or reference of local variables. Look the following code:

int foo() { return 1; }
int *bar() { int i = 1; return &i; }

When I call foo(), it returns 1.

When I call bar(), it try to return the local variables, i's address. But when bar() returns, the i variable is DESTROYED! So the return pointer become trash pointer. (Sorry, I don't know how to say that term in English;)

You should use like that:

void bar(int *ret) { *ret = 1; }

int i;
bar(&i); /* now i is 1 */

or

int *bar()
{
    int *p = (int *)malloc(sizeof(int));
    *p = 1;
    return p;
}

int *pi = bar();
/* now *pi is 1 */

...

free(pi); /* You MUST free pi. If not, memory lack is coming~ */

(I recommend first one. the second one require free and it can be mistaken.)

ikh
  • 10,119
  • 1
  • 31
  • 70
  • int add() {int p=9; return p;}. here "p" is also a local variable but i could use the return value in main()? how it is? and my purpose is to return a matrix , can you show me in my code,how do we do that? – Melvin Jan 20 '14 at 05:44
0

When a variable is declared (statically allocated) within a function, it is placed on what is called the stack, which is only local to that function. When the program leaves that function's scope, the variable is no longer guaranteed to be preserved, and so the pointer you return to it is essentially useless.

You have three options to fix your error:

  1. Don't do it

    Simply declare the array in the same function as you use it, don't bother with trying to return a pointer from another function.

  2. Pass a pointer to a variable local to main

    A pointer to a variable local to main will be valid until main returns, so you could do this:

    void subBytes(uint8_t t[4][4]){
        //perform initialization of matrix on passed variable
    }
    
    int main(){
        uint8_t temp[4][4];
        subBytes(&temp);
        //...
    }    
    
  3. Dynamic Allocation

    This will probably give you more errors than it will solve in this case, but if you are heartset on returning a pointer to a matrix, you could malloc() the memory for the array and then return it, but you would have to free() it afterwards.

    In C, there are several ways to dynamically allocate a 2D array. The first is to create it as a single array, and operate on the indices to treat it as 2D.

    //...
    int *arr = (int *)malloc(rows*cols*sizeof(int));
    for (int i = 0; i<rows; i++){
        for (int j = 0; j<height; j++){
            arr[i*height + j] = i*j; //whatever
        }
    }
    
    return arr; // type  is int *
    //...
    

    Note that in this method, you cannot use array[i][j] syntax, because the compiler doesn't know the width and height.

    The second way is to treat it as an array of arrays, so store an array of pointers to other arrays.

    //...
    int **arr = (int **)malloc(rows*sizeof(int *));
    for (int i = 0; i<rows; i++){
        arr[i] = (int *)malloc(cols*sizeof(int));
    }
    
    arr[i][j] = 86; //whatever
    
    return arr; //type is int **
    //...
    

For further information, see: Pointer to Local Variable

Community
  • 1
  • 1
andars
  • 1,384
  • 7
  • 12
  • int add() {int p=9; return p;}. here "p" is also a local variable but i could use the return value in main()? how it is? and my purpose is to return a matrix , can you show me in my code,how do we do that? – Melvin Jan 20 '14 at 05:44
  • given below my original code, uint8_t **subBytes() { int i,j; uint8_t r,c; uint8_t t[4][4]; for(i=0;i<4;i++) { for(j=0;j<4;j++) { r = pt[p1][j] & 0xf0; r = r >> 4 ; c = pt[p1][j] & 0x0f; t[i][j] = (uint8_t *) malloc(sizeof(uint8_t)); t[i][j] = sBox[r][c]; } p1++; } return t[0]; } void AddRoundKey(uint8_t t[4][4]) {int i,j; for(i=0;i<4;i++) { p++; for(j=0;j<4;j++) { pt[p][j] = t[i][j] ^ k.m[p-4][j]; } } } – Melvin Jan 20 '14 at 06:00
  • Please don't post that much code in a comment. I'll edit and try to answer your questions. – andars Jan 20 '14 at 15:57
0

the memory space alloced for your matrix is a LOCAL VARIABLE. The scope of a LOCAL VARIABLE is only within that function.

When you returned it is discarded.

In your code it is uint8_t t[4][4].

t is discarded right after return t.

So you return nothing and may cause undefined behavior.

You should use malloc to alloc memory for your matrix not just declare it locally.

in code

uint8_t **t.

t = malloc(sizeof(uint8_t) * 16 )  //size of a  4x4 matrix

then use t as a two dimension array and return t.like

t[0][0] = 1;

don't forgot to free it after use it out side of the function.

free(t);
oyss
  • 662
  • 1
  • 8
  • 20