Segfault when I loop through the array of a dynamically allocated structure

Here’s the problem, I’m trying to allocate a struct containing an array of pixels but it gives me a segfault and I can’t find the error, here’s how I originally tried to do it:

#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>

typedef struct {
    int len;
    uint16_t tex_w;
    uint16_t tex_h;
    uint32_t** tex;
} Tex_Array;

int main(void)
{
    const uint8_t tex_num = 8;
    const uint16_t tex_w = 64;
    const uint16_t tex_h = 64;

    Tex_Array* wall_tex = malloc(sizeof(Tex_Array) + (tex_w * tex_h) * tex_num * sizeof(uint32_t));

    /* Texture generation */

    for(int x = 0; x < tex_w; x++) {
        for(int y = 0; y < tex_h; y++)
        {
            int xorcolor = (x * 256 / tex_w) ^ (y * 256 / tex_h);
            int ycolor = y * 256 / tex_h;
            int xycolor = y * 128 / tex_h + x * 128 / tex_w;
            wall_tex->tex[0][tex_w * y + x] = 65536 * 254 * (x != y && x != tex_w - y);
            wall_tex->tex[1][tex_w * y + x] = xycolor + 256 * xycolor + 65536 * xycolor;
            wall_tex->tex[2][tex_w * y + x] = 256 * xycolor + 65536 * xycolor;
            wall_tex->tex[3][tex_w * y + x] = xorcolor + 256 * xorcolor + 65536 * xorcolor;
            wall_tex->tex[4][tex_w * y + x] = 256 * xorcolor;
            wall_tex->tex[5][tex_w * y + x] = 65536 * 192 * (x % 16 && y % 16);
            wall_tex->tex[6][tex_w * y + x] = 65536 * ycolor;
            wall_tex->tex[7][tex_w * y + x] = 128 + 256 * 128 + 65536 * 128;
        }
    }

    /* Test if the program arrives here */

    printf("Generation is finished !\n");

    /* rest of initialization just for example */

    wall_tex->len = tex_num;
    wall_tex->tex_w = tex_w;
    wall_tex->tex_h = tex_h;

    return 0;

}

What I understand even less is that I tried to do it even more "literally" as below, with memcpy(), but it gives me exactly the same result (segfault) at copy time :

#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <string.h>

typedef struct {
    int len;
    uint16_t tex_w;
    uint16_t tex_h;
    uint32_t** tex;
} Tex_Array;

int main(void)
{
    const uint8_t tex_num = 8;
    const uint16_t tex_w = 64;
    const uint16_t tex_h = 64;

    uint32_t tex[8][tex_w * tex_h];

    /* Texture generation */

    for(int x = 0; x < tex_w; x++) {
        for(int y = 0; y < tex_h; y++)
        {
            int xorcolor = (x * 256 / tex_w) ^ (y * 256 / tex_h);
            int ycolor = y * 256 / tex_h;
            int xycolor = y * 128 / tex_h + x * 128 / tex_w;
            tex[0][tex_w * y + x] = 65536 * 254 * (x != y && x != tex_w - y);
            tex[1][tex_w * y + x] = xycolor + 256 * xycolor + 65536 * xycolor;
            tex[2][tex_w * y + x] = 256 * xycolor + 65536 * xycolor;
            tex[3][tex_w * y + x] = xorcolor + 256 * xorcolor + 65536 * xorcolor;
            tex[4][tex_w * y + x] = 256 * xorcolor;
            tex[5][tex_w * y + x] = 65536 * 192 * (x % 16 && y % 16);
            tex[6][tex_w * y + x] = 65536 * ycolor;
            tex[7][tex_w * y + x] = 128 + 256 * 128 + 65536 * 128;
        }
    }

    printf("Generation is finished !\n"); // It's okay'

    /* rest of initialization */

    Tex_Array* wall_tex = malloc(sizeof(Tex_Array) + sizeof(tex));

    wall_tex->len = tex_num;
    wall_tex->tex_w = tex_w;
    wall_tex->tex_h = tex_h;

    memcpy(wall_tex->tex, tex, sizeof(tex)); // Segfault here

    /* Test if the program arrives here */

    printf("Struct alloc is finished !\n");

    return 0;

}

Where am I going wrong with using malloc()?

I want to clarify that these are just shortened examples and I need to be able to allocate this structure in the real project.

>Solution :

Like I said in my comment, your allocation is only for the wall_tex pointer. Which you don’t really need to be a pointer or do to dynamic allocation:

Tex_Array wall_tex;  // Create one single Tex_Array structure object

Then you need to allocate the actual array for tex itself:

wall_tex.tex = malloc(sizeof *wall_tex.tex * tex_num);

And lastly create the sub-arrays:

for (unsigned i = 0; i < tex_num; ++i)
{
    wall_tex.tex[i] = malloc(sizeof *wall_tex.tex[0] * tex_w * tex_h);
}

If you need to dynamically allocate the Tex_Array structure object itself, then allocate only it:

Tex_Array *wall_tex = malloc(sizeof *wall_tex);

Leave a Reply