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);