This same piece of code that checks the pointers for neighboring blocks of another block, seems to be working fine in my debian build with gcc C11 but it is throwing a read access violation exception on visual studio c11.
#include <stdio.h>
#include <stdlib.h>
#define CHUNK_WIDTH 16
#define CHUNK_HEIGHT 64
#define CHUNK_DEPTH 16
struct Block
{
// data
struct
{
struct Block* above;
struct Block* below;
struct Block* left;
struct Block* right;
struct Block* front;
struct Block* behind;
} neighbors;
};
struct Chunk
{
struct Block blocks[CHUNK_HEIGHT][CHUNK_DEPTH][CHUNK_WIDTH];
};
void SetNeighboringBlocks(struct Chunk* chunk, int blockIndexX, int blockIndexY, int blockIndexZ)
{
struct Block* curBlock = &chunk->blocks[blockIndexY][blockIndexZ][blockIndexX];
curBlock->neighbors.left = (blockIndexX != 0) ? &chunk->blocks[blockIndexY][blockIndexZ][blockIndexX - 1] : NULL;
curBlock->neighbors.right = (blockIndexX != CHUNK_WIDTH - 1) ? &chunk->blocks[blockIndexY][blockIndexZ][blockIndexX + 1] : NULL;
curBlock->neighbors.above = (blockIndexY != CHUNK_HEIGHT - 1) ? &chunk->blocks[blockIndexY + 1][blockIndexZ][blockIndexX] : NULL;
curBlock->neighbors.below = (blockIndexY != 0) ? &chunk->blocks[blockIndexY - 1][blockIndexZ][blockIndexX] : NULL;
curBlock->neighbors.front = (blockIndexZ != 0) ? &chunk->blocks[blockIndexY][blockIndexZ - 1][blockIndexX] : NULL;
curBlock->neighbors.behind = (blockIndexZ != CHUNK_DEPTH - 1) ? &chunk->blocks[blockIndexY][blockIndexZ + 1][blockIndexX] : NULL;
}
struct Chunk* CreateChunk(int x, int z)
{
struct Chunk* ret = (struct Chunk*)malloc(sizeof(struct Chunk));
for (int z = 0; z < CHUNK_DEPTH; ++z)
for (int y = 0; y < CHUNK_HEIGHT; ++y)
for (int x = 0; x < CHUNK_WIDTH; ++x)
{
SetNeighboringBlocks(ret, x, y, z);
}
return ret;
}
int main(void)
{
struct Chunk* chunk = CreateChunk(0, 0);
for (int z = 0; z < CHUNK_DEPTH; ++z)
for (int y = 0; y < CHUNK_HEIGHT; ++y)
for (int x = 0; x < CHUNK_WIDTH; ++x)
{
// If it has neighbors in all direction, then it is inside
struct Block* cur = &chunk->blocks[y][z][x];
if (
cur->neighbors.above &&
cur->neighbors.below &&
cur->neighbors.left &&
cur->neighbors.right &&
cur->neighbors.front &&
cur->neighbors.behind
)
// Do something
}
return 0;
}
I’ve been trying to solve this but i still have no idea why it’s causing an exception.
2
Answers
If you’re getting access violations from that code, it’s almost certainly due to
cur
,chunk
, or the index ofblocks[]
.Therefore it would be a good idea to find out what those values are before you use them, either with a stepping debugger, or printing them out in the code (flushing output to ensure you see them before the crash happens).
In other words, print out:
chunk
before thez
loop starts;CHUNK_INDEX(x,y,z)
as the first thing inside thex
loop; andcur
immediately after it is set;Debugging needs data, without that, you’re just doing static analysis which is much harder.
return &ret;
is wrong. It returns the address of a local variable, whose lifetime ends when the function returns. It should bereturn ret;
.Enable warnings in your compiler and elevate warnings to errors. With Clang, start with
-Wmost -Werror
. With GCC, start with-Wall -Werror
. With MSVC, start with/W3 /WX
.