gpt4 book ai didi

C++ 3D 数组到 1D 导致堆缓冲区溢出

转载 作者:太空宇宙 更新时间:2023-11-04 13:04:19 24 4
gpt4 key购买 nike

我想举一个最小的例子。如果提供的代码还不够,请告诉我您还需要什么。这不是什么 super secret ;)

考虑以下两个实现:

使用 3d 数组:

.h

class Grid
{
public:
Grid();

uint8_t get(int x, int y, int z);
void set(int x, int y, int z, uint8_t value);

private:
uint8_t blocks[Chunk::width][Chunk::height][Chunk::depth];
};

.cpp

Grid::Grid()
{
memset(blocks, 0, sizeof(blocks));
}

uint8_t Grid::get(int x, int y, int z)
{
return blocks[x][y][z];
}

void Grid::set(int x, int y, int z, uint8_t value)
{
blocks[x][y][z] = value;
}

现在是一维数组:

.h

class Grid
{
public:
Grid();

uint8_t get(int x, int y, int z);
void set(int x, int y, int z, uint8_t value);

private:
uint8_t blocks[Chunk::width * Chunk::height * Chunk::depth];
int to1D(int x, int y, int z) { return x + (y * Chunk::width) + (z * Chunk::width * Chunk::height); }
};

.cpp

Grid::Grid()
{
memset(blocks, 0, sizeof(blocks));
}

uint8_t Grid::get(int x, int y, int z)
{
return this->blocks[x + (y * Chunk::width) + (z * Chunk::width * Chunk::height)];
}

void Grid::set(int x, int y, int z, uint8_t value)
{
this->blocks[x + (y * Chunk::width) + (z * Chunk::width * Chunk::height)] = value;
}

现在有了 3D 版本,一切都像魅力一样,而对于相同的整体尺寸我得到了

SUMMARY: AddressSanitizer: heap-buffer-overflow src/Grid.cpp:16 in Grid::get(int, int, int)

我真的很想知道为什么会这样。两种实现都包含 uint8_t...我似乎看不到/无法理解的 3d 数组版本中正在进行什么优化?

(是的,这是我的世界体素引擎实验;))

最佳答案

如果您正在为游戏构建环境,我猜您会遇到内存分配问题。假设您正在运行的游戏需要 50 MB 内存。从任何地方获取 50 MB 都不是什么大问题。但是试图获得 50 MB 的连续内存是 waaaaaayyy 更困难。现在大多数操作系统都使用分页系统来跟踪已分配和未分配的内存。这里有更多信息:https://en.wikipedia.org/wiki/Paging

3D 数组基本上是指向指针数组的指针,其中每个指针都指向另一个指针数组。这些指针中的每一个都包含一个有限的内存块来与之交互。所以在这种情况下,操作系统可以给你 5,000 个 50 KB 的内存块,指针可以将所有这些内存保存在不同的地方。

关于C++ 3D 数组到 1D 导致堆缓冲区溢出,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43056536/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com