[英]Why am I getting E_OUTOFMEMORY?
由於某些原因,下面的代碼將給我一個內存不足的錯誤。 我想念什么?
for(int n = 0; n < 512; ++n)
{
D3D11_TEXTURE2D_DESC texture_desc = {};
texture_desc.Width = 1920;
texture_desc.Height = 1080;
texture_desc.MipLevels = 1;
texture_desc.ArraySize = 1;
texture_desc.Format = DXGI_FORMAT_R8G8B8A8_UNORM;
texture_desc.SampleDesc.Count = 1;
texture_desc.Usage = D3D11_USAGE_DEFAULT;
texture_desc.BindFlags = D3D11_BIND_RENDER_TARGET | D3D11_BIND_SHADER_RESOURCE;
ID3D11Texture2D* target_d3d_ptr;
HRESULT hr = this->device_ptr->CreateTexture2D(&texture_desc, nullptr, &target_d3d_ptr);
if(FAILED(hr))
throw runtime_error(_com_error(hr).ErrorMessage());
target_d3d_ptr->Release();
}
只是一個想法,但您是否考慮過這一點:1920 * 1080 * 32位= 8294400字節現在,8294400字節x 485紋理= 3.836 G的內存。 這是對32位計算機的限制。 我不知道您是在編碼32位還是64位程序,但是如果它是32位,則您可以處理的最大虛擬內存在4GB以下,而512個紋理會使您超出此限制。 考慮到Release不會立即釋放此內存,並且如果您實際上是在以32位進行編碼,則應該清楚為什么耗盡內存。
也許不是您的情況,但是,例如,Microsoft的COM方法CComObject::CreateInstance
可以返回E_OUTOFMEMORY
(至少在我可以在我的環境中找到的實現中,即Visual Studio 2012),並且我認為這可能會引起誤解。
COM方法類似於以下內容(在atlcom.h
)
ATLPREFAST_SUPPRESS(6387)
template <class Base>
_Success_(return == S_OK) HRESULT WINAPI CComObject<Base>::CreateInstance(
_Deref_out_ CComObject<Base>** pp) throw()
{
// code omitted
HRESULT hRes = E_OUTOFMEMORY;
CComObject<Base>* p = NULL;
ATLTRY(p = new CComObject<Base>())
if (p != NULL)
{
// code omitted
}
*pp = p;
return hRes;
}
ATLPREFAST_UNSUPPRESS()
在我看來,即使您仍有大量可用內存,上述代碼也可以返回E_OUTOFMEMORY
:宏ATLTRY
只是將對new
的調用包裝在try-catch(...)塊中,因此,如果Base
的構造函數未能引發異常,即使與內存問題無關的任何異常,則p
將為NULL
且該函數將返回E_OUTOFMEMORY
。
事實證明,catflier在評論中提供了此問題的答案:
release不會立即發布,並且由於在代碼上沒有調用,因此它永遠也不會執行。 調用devicecontext
Flush
方法或存在的某些swapchain(將刷新設備)將導致資源刪除
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.