使用new的C ++ / CLI内存分配会引发异常

时间:2014-04-27 15:47:56

标签: exception memory-management c++-cli new-operator

我(我相信)使用" new"进行内存分配是一个非常经典的问题。 这是我使用的代码片段:

float * _normals = NULL;
try{

    _normals = new float[_x*_y*_z*3];
}catch(System::Exception ^ e){

    Windows::Forms::MessageBox::Show("Normals:\n" + e->Message);

    if(e->InnerException != nullptr && e->InnerException->Message != nullptr)
        Windows::Forms::MessageBox::Show("Details:\n" + e->InnerException->Message);

    _file->Close();

return 0;
}

我不知道你是否可以从这段代码中分辨出来,但这是一个混合的托管和非托管代码程序。我不知道这是否重要。

现在,当我运行此代码并尝试分配,例如,256 * 256 * 128 * 3浮点数时,它会正常运行。当我使用492 * 492 * 442浮点数时,它会抛出一个"外部组件抛出异常"例外。这大约是1.2GB,对吧。我的系统有6GB的RAM和3GB左右的免费。你能从这些信息中说出问题吗?我能处理吗?我读过有关程序存储空间的地方。也许程序记忆不够?(我对这件事情一无所知,如果你可以开导我的话)

请询问您是否需要更多信息。

提前谢谢

1 个答案:

答案 0 :(得分:2)

在64位操作系统上运行的32位Windows程序(C ++ - CLI隐含的Windows)的地址空间

  • 默认为2 GB
  • 如果与/LARGEADDRESSAWARE关联,则为4 GB。此标志也可以稍后由editbin添加。

您的问题是地址空间碎片。仅仅因为您只分配了100MB,并不意味着您可以在2GB地址空间中分配另一个1.9GB的块。您的新分配需要连续地址。

例如,如果您的非LAA进程使用的DLL在0x40000000处有一个加载地址,那么您可以在它下面分配一个1GB的块,或者在它上面的差不多1GB的块,但是你永远不会分配大于1GB的单个块。

最简单的解决方案是编译为64位。即使地址空间仍然是碎片化的,分配之间的开放空间也会大得多,并且不会给你带来问题。