aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGeoff Lang <geofflang@chromium.org>2014-09-22 15:21:39 -0400
committerGeoff Lang <geofflang@chromium.org>2014-10-24 16:56:18 +0000
commit553c6bee81fa41e2c36512023f06c049fba98979 (patch)
tree3688019d642f451e947379dfc925a06a76aa4f97
parent5ca41055d838a0bb16a698076a7b7df6730fefde (diff)
downloadangle-553c6bee81fa41e2c36512023f06c049fba98979.tar.gz
Defer the creation of textures in TextureStorage11.
BUG=angle:520 Change-Id: If1c1f7519a84900f594701b6298b64ebf8798073 Reviewed-on: https://chromium-review.googlesource.com/219333 Reviewed-by: Shannon Woods <shannonwoods@chromium.org> Tested-by: Geoff Lang <geofflang@chromium.org>
-rw-r--r--src/libGLESv2/renderer/d3d/d3d11/Image11.cpp11
-rw-r--r--src/libGLESv2/renderer/d3d/d3d11/TextureStorage11.cpp493
-rw-r--r--src/libGLESv2/renderer/d3d/d3d11/TextureStorage11.h10
3 files changed, 296 insertions, 218 deletions
diff --git a/src/libGLESv2/renderer/d3d/d3d11/Image11.cpp b/src/libGLESv2/renderer/d3d/d3d11/Image11.cpp
index c9f538b4..a8196f64 100644
--- a/src/libGLESv2/renderer/d3d/d3d11/Image11.cpp
+++ b/src/libGLESv2/renderer/d3d/d3d11/Image11.cpp
@@ -331,14 +331,21 @@ gl::Error Image11::copy(GLint xoffset, GLint yoffset, GLint zoffset, const gl::R
TextureStorage11 *sourceStorage11 = TextureStorage11::makeTextureStorage11(source);
UINT subresourceIndex = sourceStorage11->getSubresourceIndex(sourceIndex);
- ID3D11Texture2D *sourceTexture2D = d3d11::DynamicCastComObject<ID3D11Texture2D>(sourceStorage11->getResource());
+ ID3D11Resource *resource = NULL;
+ gl::Error error = sourceStorage11->getResource(&resource);
+ if (error.isError())
+ {
+ return error;
+ }
+
+ ID3D11Texture2D *sourceTexture2D = d3d11::DynamicCastComObject<ID3D11Texture2D>(resource);
if (!sourceTexture2D)
{
return gl::Error(GL_OUT_OF_MEMORY, "Failed to retrieve the ID3D11Texture2D from the source TextureStorage.");
}
- gl::Error error = copy(xoffset, yoffset, zoffset, sourceArea, sourceTexture2D, subresourceIndex);
+ error = copy(xoffset, yoffset, zoffset, sourceArea, sourceTexture2D, subresourceIndex);
SafeRelease(sourceTexture2D);
diff --git a/src/libGLESv2/renderer/d3d/d3d11/TextureStorage11.cpp b/src/libGLESv2/renderer/d3d/d3d11/TextureStorage11.cpp
index e5a5dfed..07bd7dd8 100644
--- a/src/libGLESv2/renderer/d3d/d3d11/TextureStorage11.cpp
+++ b/src/libGLESv2/renderer/d3d/d3d11/TextureStorage11.cpp
@@ -161,14 +161,10 @@ int TextureStorage11::getLevelDepth(int mipLevel) const
UINT TextureStorage11::getSubresourceIndex(const gl::ImageIndex &index) const
{
- UINT subresource = 0;
- if (getResource())
- {
- UINT mipSlice = static_cast<UINT>(index.mipIndex + mTopLevel);
- UINT arraySlice = static_cast<UINT>(index.hasLayer() ? index.layerIndex : 0);
- subresource = D3D11CalcSubresource(mipSlice, arraySlice, mMipLevels);
- ASSERT(subresource != std::numeric_limits<UINT>::max());
- }
+ UINT mipSlice = static_cast<UINT>(index.mipIndex + mTopLevel);
+ UINT arraySlice = static_cast<UINT>(index.hasLayer() ? index.layerIndex : 0);
+ UINT subresource = D3D11CalcSubresource(mipSlice, arraySlice, mMipLevels);
+ ASSERT(subresource != std::numeric_limits<UINT>::max());
return subresource;
}
@@ -205,7 +201,11 @@ gl::Error TextureStorage11::getSRV(const gl::SamplerState &samplerState, ID3D11S
}
else
{
- texture = getResource();
+ gl::Error error = getResource(&texture);
+ if (error.isError())
+ {
+ return error;
+ }
}
ID3D11ShaderResourceView *srv = NULL;
@@ -229,7 +229,14 @@ gl::Error TextureStorage11::getSRVLevel(int mipLevel, ID3D11ShaderResourceView *
if (!mLevelSRVs[mipLevel])
{
- gl::Error error = createSRV(mipLevel, 1, mShaderResourceFormat, getResource(), &mLevelSRVs[mipLevel]);
+ ID3D11Resource *resource = NULL;
+ gl::Error error = getResource(&resource);
+ if (error.isError())
+ {
+ return error;
+ }
+
+ error = createSRV(mipLevel, 1, mShaderResourceFormat, resource, &mLevelSRVs[mipLevel]);
if (error.isError())
{
return error;
@@ -317,7 +324,13 @@ gl::Error TextureStorage11::updateSubresourceLevel(ID3D11Resource *srcTexture, u
copyArea.height == texSize.height &&
copyArea.depth == texSize.depth;
- ID3D11Resource *dstTexture = getResource();
+ ID3D11Resource *dstTexture = NULL;
+ gl::Error error = getResource(&dstTexture);
+ if (error.isError())
+ {
+ return error;
+ }
+
unsigned int dstSubresource = getSubresourceIndex(index);
ASSERT(dstTexture);
@@ -357,7 +370,13 @@ gl::Error TextureStorage11::copySubresourceLevel(ID3D11Resource* dstTexture, uns
{
ASSERT(dstTexture);
- ID3D11Resource *srcTexture = getResource();
+ ID3D11Resource *srcTexture = NULL;
+ gl::Error error = getResource(&srcTexture);
+ if (error.isError())
+ {
+ return error;
+ }
+
ASSERT(srcTexture);
unsigned int srcSubresource = getSubresourceIndex(index);
@@ -416,10 +435,23 @@ gl::Error TextureStorage11::copyToStorage(TextureStorage *destStorage)
{
ASSERT(destStorage);
+ ID3D11Resource *sourceResouce = NULL;
+ gl::Error error = getResource(&sourceResouce);
+ if (error.isError())
+ {
+ return error;
+ }
+
TextureStorage11 *dest11 = TextureStorage11::makeTextureStorage11(destStorage);
+ ID3D11Resource *destResource = NULL;
+ error = dest11->getResource(&destResource);
+ if (error.isError())
+ {
+ return error;
+ }
ID3D11DeviceContext *immediateContext = mRenderer->getDeviceContext();
- immediateContext->CopyResource(dest11->getResource(), getResource());
+ immediateContext->CopyResource(destResource, sourceResouce);
dest11->invalidateSwizzleCache();
@@ -429,7 +461,12 @@ gl::Error TextureStorage11::copyToStorage(TextureStorage *destStorage)
gl::Error TextureStorage11::setData(const gl::ImageIndex &index, Image *image, const gl::Box *destBox, GLenum type,
const gl::PixelUnpackState &unpack, const uint8_t *pixelData)
{
- ID3D11Resource *resource = getResource();
+ ID3D11Resource *resource = NULL;
+ gl::Error error = getResource(&resource);
+ if (error.isError())
+ {
+ return error;
+ }
ASSERT(resource);
UINT destSubresource = getSubresourceIndex(index);
@@ -563,51 +600,11 @@ TextureStorage11_2D::TextureStorage11_2D(Renderer *renderer, GLenum internalform
mSwizzleShaderResourceFormat = formatInfo.swizzleSRVFormat;
mSwizzleRenderTargetFormat = formatInfo.swizzleRTVFormat;
- // if the width or height is not positive this should be treated as an incomplete texture
- // we handle that here by skipping the d3d texture creation
- if (width > 0 && height > 0)
- {
- // adjust size if needed for compressed textures
- d3d11::MakeValidSize(false, mTextureFormat, &width, &height, &mTopLevel);
-
- ID3D11Device *device = mRenderer->getDevice();
-
- D3D11_TEXTURE2D_DESC desc;
- desc.Width = width; // Compressed texture size constraints?
- desc.Height = height;
- desc.MipLevels = ((levels > 0) ? (mTopLevel + levels) : 0);
- desc.ArraySize = 1;
- desc.Format = mTextureFormat;
- desc.SampleDesc.Count = 1;
- desc.SampleDesc.Quality = 0;
- desc.Usage = D3D11_USAGE_DEFAULT;
- desc.BindFlags = getBindFlags();
- desc.CPUAccessFlags = 0;
- desc.MiscFlags = 0;
-
- HRESULT result = device->CreateTexture2D(&desc, NULL, &mTexture);
-
- // this can happen from windows TDR
- if (d3d11::isDeviceLostError(result))
- {
- mRenderer->notifyDeviceLost();
- gl::error(GL_OUT_OF_MEMORY);
- }
- else if (FAILED(result))
- {
- ASSERT(result == E_OUTOFMEMORY);
- ERR("Creating image failed.");
- gl::error(GL_OUT_OF_MEMORY);
- }
- else
- {
- mTexture->GetDesc(&desc);
- mMipLevels = desc.MipLevels;
- mTextureWidth = desc.Width;
- mTextureHeight = desc.Height;
- mTextureDepth = 1;
- }
- }
+ d3d11::MakeValidSize(false, mTextureFormat, &width, &height, &mTopLevel);
+ mMipLevels = mTopLevel + levels;
+ mTextureWidth = width;
+ mTextureHeight = height;
+ mTextureDepth = 1;
initializeSerials(getLevelCount(), 1);
}
@@ -726,9 +723,46 @@ gl::Error TextureStorage11_2D::releaseAssociatedImage(const gl::ImageIndex &inde
return gl::Error(GL_NO_ERROR);
}
-ID3D11Resource *TextureStorage11_2D::getResource() const
+gl::Error TextureStorage11_2D::getResource(ID3D11Resource **outResource)
{
- return mTexture;
+ // if the width or height is not positive this should be treated as an incomplete texture
+ // we handle that here by skipping the d3d texture creation
+ if (mTexture == NULL && mTextureWidth > 0 && mTextureHeight > 0)
+ {
+ ASSERT(mMipLevels > 0);
+
+ ID3D11Device *device = mRenderer->getDevice();
+
+ D3D11_TEXTURE2D_DESC desc;
+ desc.Width = mTextureWidth; // Compressed texture size constraints?
+ desc.Height = mTextureHeight;
+ desc.MipLevels = mMipLevels;
+ desc.ArraySize = 1;
+ desc.Format = mTextureFormat;
+ desc.SampleDesc.Count = 1;
+ desc.SampleDesc.Quality = 0;
+ desc.Usage = D3D11_USAGE_DEFAULT;
+ desc.BindFlags = getBindFlags();
+ desc.CPUAccessFlags = 0;
+ desc.MiscFlags = 0;
+
+ HRESULT result = device->CreateTexture2D(&desc, NULL, &mTexture);
+
+ // this can happen from windows TDR
+ if (d3d11::isDeviceLostError(result))
+ {
+ mRenderer->notifyDeviceLost();
+ return gl::Error(GL_OUT_OF_MEMORY, "Failed to create 2D texture storage, result: 0x%X.", result);
+ }
+ else if (FAILED(result))
+ {
+ ASSERT(result == E_OUTOFMEMORY);
+ return gl::Error(GL_OUT_OF_MEMORY, "Failed to create 2D texture storage, result: 0x%X.", result);
+ }
+ }
+
+ *outResource = mTexture;
+ return gl::Error(GL_NO_ERROR);
}
gl::Error TextureStorage11_2D::getRenderTarget(const gl::ImageIndex &index, RenderTarget **outRT)
@@ -740,8 +774,15 @@ gl::Error TextureStorage11_2D::getRenderTarget(const gl::ImageIndex &index, Rend
if (!mRenderTarget[level])
{
+ ID3D11Resource *texture = NULL;
+ gl::Error error = getResource(&texture);
+ if (error.isError())
+ {
+ return error;
+ }
+
ID3D11ShaderResourceView *srv = NULL;
- gl::Error error = getSRVLevel(level, &srv);
+ error = getSRVLevel(level, &srv);
if (error.isError())
{
return error;
@@ -757,7 +798,7 @@ gl::Error TextureStorage11_2D::getRenderTarget(const gl::ImageIndex &index, Rend
rtvDesc.Texture2D.MipSlice = mTopLevel + level;
ID3D11RenderTargetView *rtv;
- HRESULT result = device->CreateRenderTargetView(mTexture, &rtvDesc, &rtv);
+ HRESULT result = device->CreateRenderTargetView(texture, &rtvDesc, &rtv);
ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
if (FAILED(result))
@@ -765,7 +806,7 @@ gl::Error TextureStorage11_2D::getRenderTarget(const gl::ImageIndex &index, Rend
return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal render target view for texture storage, result: 0x%X.", result);
}
- mRenderTarget[level] = new RenderTarget11(mRenderer, rtv, mTexture, srv, getLevelWidth(level), getLevelHeight(level), 1);
+ mRenderTarget[level] = new RenderTarget11(mRenderer, rtv, texture, srv, getLevelWidth(level), getLevelHeight(level), 1);
// RenderTarget will take ownership of these resources
SafeRelease(rtv);
@@ -781,7 +822,7 @@ gl::Error TextureStorage11_2D::getRenderTarget(const gl::ImageIndex &index, Rend
dsvDesc.Flags = 0;
ID3D11DepthStencilView *dsv;
- HRESULT result = device->CreateDepthStencilView(mTexture, &dsvDesc, &dsv);
+ HRESULT result = device->CreateDepthStencilView(texture, &dsvDesc, &dsv);
ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
if (FAILED(result))
@@ -789,7 +830,7 @@ gl::Error TextureStorage11_2D::getRenderTarget(const gl::ImageIndex &index, Rend
return gl::Error(GL_OUT_OF_MEMORY,"Failed to create internal depth stencil view for texture storage, result: 0x%X.", result);
}
- mRenderTarget[level] = new RenderTarget11(mRenderer, dsv, mTexture, srv, getLevelWidth(level), getLevelHeight(level), 1);
+ mRenderTarget[level] = new RenderTarget11(mRenderer, dsv, texture, srv, getLevelWidth(level), getLevelHeight(level), 1);
// RenderTarget will take ownership of these resources
SafeRelease(dsv);
@@ -921,51 +962,18 @@ TextureStorage11_Cube::TextureStorage11_Cube(Renderer *renderer, GLenum internal
mSwizzleShaderResourceFormat = formatInfo.swizzleSRVFormat;
mSwizzleRenderTargetFormat = formatInfo.swizzleRTVFormat;
- // if the size is not positive this should be treated as an incomplete texture
- // we handle that here by skipping the d3d texture creation
- if (size > 0)
- {
- // adjust size if needed for compressed textures
- int height = size;
- d3d11::MakeValidSize(false, mTextureFormat, &size, &height, &mTopLevel);
-
- ID3D11Device *device = mRenderer->getDevice();
-
- D3D11_TEXTURE2D_DESC desc;
- desc.Width = size;
- desc.Height = size;
- desc.MipLevels = ((levels > 0) ? (mTopLevel + levels) : 0);
- desc.ArraySize = CUBE_FACE_COUNT;
- desc.Format = mTextureFormat;
- desc.SampleDesc.Count = 1;
- desc.SampleDesc.Quality = 0;
- desc.Usage = D3D11_USAGE_DEFAULT;
- desc.BindFlags = getBindFlags();
- desc.CPUAccessFlags = 0;
- desc.MiscFlags = D3D11_RESOURCE_MISC_TEXTURECUBE;
+ // adjust size if needed for compressed textures
+ int height = size;
+ d3d11::MakeValidSize(false, mTextureFormat, &size, &height, &mTopLevel);
- HRESULT result = device->CreateTexture2D(&desc, NULL, &mTexture);
-
- if (FAILED(result))
- {
- ASSERT(result == E_OUTOFMEMORY);
- ERR("Creating image failed.");
- gl::error(GL_OUT_OF_MEMORY);
- }
- else
- {
- mTexture->GetDesc(&desc);
- mMipLevels = desc.MipLevels;
- mTextureWidth = desc.Width;
- mTextureHeight = desc.Height;
- mTextureDepth = 1;
- }
- }
+ mMipLevels = mTopLevel + levels;
+ mTextureWidth = size;
+ mTextureHeight = size;
+ mTextureDepth = 1;
initializeSerials(getLevelCount() * CUBE_FACE_COUNT, CUBE_FACE_COUNT);
}
-
TextureStorage11_Cube::~TextureStorage11_Cube()
{
for (unsigned int level = 0; level < gl::IMPLEMENTATION_MAX_TEXTURE_LEVELS; level++)
@@ -1101,9 +1109,46 @@ gl::Error TextureStorage11_Cube::releaseAssociatedImage(const gl::ImageIndex &in
return gl::Error(GL_NO_ERROR);
}
-ID3D11Resource *TextureStorage11_Cube::getResource() const
+gl::Error TextureStorage11_Cube::getResource(ID3D11Resource **outResource)
{
- return mTexture;
+ // if the size is not positive this should be treated as an incomplete texture
+ // we handle that here by skipping the d3d texture creation
+ if (mTexture == NULL && mTextureWidth > 0 && mTextureHeight > 0)
+ {
+ ASSERT(mMipLevels > 0);
+
+ ID3D11Device *device = mRenderer->getDevice();
+
+ D3D11_TEXTURE2D_DESC desc;
+ desc.Width = mTextureWidth;
+ desc.Height = mTextureHeight;
+ desc.MipLevels = mMipLevels;
+ desc.ArraySize = CUBE_FACE_COUNT;
+ desc.Format = mTextureFormat;
+ desc.SampleDesc.Count = 1;
+ desc.SampleDesc.Quality = 0;
+ desc.Usage = D3D11_USAGE_DEFAULT;
+ desc.BindFlags = getBindFlags();
+ desc.CPUAccessFlags = 0;
+ desc.MiscFlags = D3D11_RESOURCE_MISC_TEXTURECUBE;
+
+ HRESULT result = device->CreateTexture2D(&desc, NULL, &mTexture);
+
+ // this can happen from windows TDR
+ if (d3d11::isDeviceLostError(result))
+ {
+ mRenderer->notifyDeviceLost();
+ return gl::Error(GL_OUT_OF_MEMORY, "Failed to create cube texture storage, result: 0x%X.", result);
+ }
+ else if (FAILED(result))
+ {
+ ASSERT(result == E_OUTOFMEMORY);
+ return gl::Error(GL_OUT_OF_MEMORY, "Failed to create cube texture storage, result: 0x%X.", result);
+ }
+ }
+
+ *outResource = mTexture;
+ return gl::Error(GL_NO_ERROR);
}
gl::Error TextureStorage11_Cube::getRenderTarget(const gl::ImageIndex &index, RenderTarget **outRT)
@@ -1119,6 +1164,13 @@ gl::Error TextureStorage11_Cube::getRenderTarget(const gl::ImageIndex &index, Re
ID3D11Device *device = mRenderer->getDevice();
HRESULT result;
+ ID3D11Resource *texture = NULL;
+ gl::Error error = getResource(&texture);
+ if (error.isError())
+ {
+ return error;
+ }
+
D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc;
srvDesc.Format = mShaderResourceFormat;
srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DARRAY; // Will be used with Texture2D sampler, not TextureCube
@@ -1128,7 +1180,7 @@ gl::Error TextureStorage11_Cube::getRenderTarget(const gl::ImageIndex &index, Re
srvDesc.Texture2DArray.ArraySize = 1;
ID3D11ShaderResourceView *srv;
- result = device->CreateShaderResourceView(mTexture, &srvDesc, &srv);
+ result = device->CreateShaderResourceView(texture, &srvDesc, &srv);
ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
if (FAILED(result))
@@ -1146,7 +1198,7 @@ gl::Error TextureStorage11_Cube::getRenderTarget(const gl::ImageIndex &index, Re
rtvDesc.Texture2DArray.ArraySize = 1;
ID3D11RenderTargetView *rtv;
- result = device->CreateRenderTargetView(mTexture, &rtvDesc, &rtv);
+ result = device->CreateRenderTargetView(texture, &rtvDesc, &rtv);
ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
if (FAILED(result))
@@ -1155,7 +1207,7 @@ gl::Error TextureStorage11_Cube::getRenderTarget(const gl::ImageIndex &index, Re
return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal render target view for texture storage, result: 0x%X.", result);
}
- mRenderTarget[faceIndex][level] = new RenderTarget11(mRenderer, rtv, mTexture, srv, getLevelWidth(level), getLevelHeight(level), 1);
+ mRenderTarget[faceIndex][level] = new RenderTarget11(mRenderer, rtv, texture, srv, getLevelWidth(level), getLevelHeight(level), 1);
// RenderTarget will take ownership of these resources
SafeRelease(rtv);
@@ -1172,7 +1224,7 @@ gl::Error TextureStorage11_Cube::getRenderTarget(const gl::ImageIndex &index, Re
dsvDesc.Texture2DArray.ArraySize = 1;
ID3D11DepthStencilView *dsv;
- result = device->CreateDepthStencilView(mTexture, &dsvDesc, &dsv);
+ result = device->CreateDepthStencilView(texture, &dsvDesc, &dsv);
ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
if (FAILED(result))
@@ -1181,7 +1233,7 @@ gl::Error TextureStorage11_Cube::getRenderTarget(const gl::ImageIndex &index, Re
return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal depth stencil view for texture storage, result: 0x%X.", result);
}
- mRenderTarget[faceIndex][level] = new RenderTarget11(mRenderer, dsv, mTexture, srv, getLevelWidth(level), getLevelHeight(level), 1);
+ mRenderTarget[faceIndex][level] = new RenderTarget11(mRenderer, dsv, texture, srv, getLevelWidth(level), getLevelHeight(level), 1);
// RenderTarget will take ownership of these resources
SafeRelease(dsv);
@@ -1328,49 +1380,13 @@ TextureStorage11_3D::TextureStorage11_3D(Renderer *renderer, GLenum internalform
mSwizzleShaderResourceFormat = formatInfo.swizzleSRVFormat;
mSwizzleRenderTargetFormat = formatInfo.swizzleRTVFormat;
- // If the width, height or depth are not positive this should be treated as an incomplete texture
- // we handle that here by skipping the d3d texture creation
- if (width > 0 && height > 0 && depth > 0)
- {
- // adjust size if needed for compressed textures
- d3d11::MakeValidSize(false, mTextureFormat, &width, &height, &mTopLevel);
-
- ID3D11Device *device = mRenderer->getDevice();
-
- D3D11_TEXTURE3D_DESC desc;
- desc.Width = width;
- desc.Height = height;
- desc.Depth = depth;
- desc.MipLevels = ((levels > 0) ? (mTopLevel + levels) : 0);
- desc.Format = mTextureFormat;
- desc.Usage = D3D11_USAGE_DEFAULT;
- desc.BindFlags = getBindFlags();
- desc.CPUAccessFlags = 0;
- desc.MiscFlags = 0;
+ // adjust size if needed for compressed textures
+ d3d11::MakeValidSize(false, mTextureFormat, &width, &height, &mTopLevel);
- HRESULT result = device->CreateTexture3D(&desc, NULL, &mTexture);
-
- // this can happen from windows TDR
- if (d3d11::isDeviceLostError(result))
- {
- mRenderer->notifyDeviceLost();
- gl::error(GL_OUT_OF_MEMORY);
- }
- else if (FAILED(result))
- {
- ASSERT(result == E_OUTOFMEMORY);
- ERR("Creating image failed.");
- gl::error(GL_OUT_OF_MEMORY);
- }
- else
- {
- mTexture->GetDesc(&desc);
- mMipLevels = desc.MipLevels;
- mTextureWidth = desc.Width;
- mTextureHeight = desc.Height;
- mTextureDepth = desc.Depth;
- }
- }
+ mMipLevels = mTopLevel + levels;
+ mTextureWidth = width;
+ mTextureHeight = height;
+ mTextureDepth = depth;
initializeSerials(getLevelCount() * depth, depth);
}
@@ -1491,9 +1507,44 @@ gl::Error TextureStorage11_3D::releaseAssociatedImage(const gl::ImageIndex &inde
return gl::Error(GL_NO_ERROR);
}
-ID3D11Resource *TextureStorage11_3D::getResource() const
+gl::Error TextureStorage11_3D::getResource(ID3D11Resource **outResource)
{
- return mTexture;
+ // If the width, height or depth are not positive this should be treated as an incomplete texture
+ // we handle that here by skipping the d3d texture creation
+ if (mTexture == NULL && mTextureWidth > 0 && mTextureHeight > 0 && mTextureDepth > 0)
+ {
+ ASSERT(mMipLevels > 0);
+
+ ID3D11Device *device = mRenderer->getDevice();
+
+ D3D11_TEXTURE3D_DESC desc;
+ desc.Width = mTextureWidth;
+ desc.Height = mTextureHeight;
+ desc.Depth = mTextureDepth;
+ desc.MipLevels = mMipLevels;
+ desc.Format = mTextureFormat;
+ desc.Usage = D3D11_USAGE_DEFAULT;
+ desc.BindFlags = getBindFlags();
+ desc.CPUAccessFlags = 0;
+ desc.MiscFlags = 0;
+
+ HRESULT result = device->CreateTexture3D(&desc, NULL, &mTexture);
+
+ // this can happen from windows TDR
+ if (d3d11::isDeviceLostError(result))
+ {
+ mRenderer->notifyDeviceLost();
+ return gl::Error(GL_OUT_OF_MEMORY, "Failed to create 3D texture storage, result: 0x%X.", result);
+ }
+ else if (FAILED(result))
+ {
+ ASSERT(result == E_OUTOFMEMORY);
+ return gl::Error(GL_OUT_OF_MEMORY, "Failed to create 3D texture storage, result: 0x%X.", result);
+ }
+ }
+
+ *outResource = mTexture;
+ return gl::Error(GL_NO_ERROR);
}
gl::Error TextureStorage11_3D::createSRV(int baseLevel, int mipLevels, DXGI_FORMAT format, ID3D11Resource *texture,
@@ -1530,8 +1581,15 @@ gl::Error TextureStorage11_3D::getRenderTarget(const gl::ImageIndex &index, Rend
{
if (!mLevelRenderTargets[mipLevel])
{
+ ID3D11Resource *texture = NULL;
+ gl::Error error = getResource(&texture);
+ if (error.isError())
+ {
+ return error;
+ }
+
ID3D11ShaderResourceView *srv = NULL;
- gl::Error error = getSRVLevel(mipLevel, &srv);
+ error = getSRVLevel(mipLevel, &srv);
if (error.isError())
{
return error;
@@ -1547,7 +1605,7 @@ gl::Error TextureStorage11_3D::getRenderTarget(const gl::ImageIndex &index, Rend
rtvDesc.Texture3D.WSize = -1;
ID3D11RenderTargetView *rtv;
- HRESULT result = device->CreateRenderTargetView(mTexture, &rtvDesc, &rtv);
+ HRESULT result = device->CreateRenderTargetView(texture, &rtvDesc, &rtv);
ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
if (FAILED(result))
@@ -1556,7 +1614,7 @@ gl::Error TextureStorage11_3D::getRenderTarget(const gl::ImageIndex &index, Rend
return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal render target view for texture storage, result: 0x%X.", result);
}
- mLevelRenderTargets[mipLevel] = new RenderTarget11(mRenderer, rtv, mTexture, srv, getLevelWidth(mipLevel), getLevelHeight(mipLevel), getLevelDepth(mipLevel));
+ mLevelRenderTargets[mipLevel] = new RenderTarget11(mRenderer, rtv, texture, srv, getLevelWidth(mipLevel), getLevelHeight(mipLevel), getLevelDepth(mipLevel));
// RenderTarget will take ownership of these resources
SafeRelease(rtv);
@@ -1576,6 +1634,13 @@ gl::Error TextureStorage11_3D::getRenderTarget(const gl::ImageIndex &index, Rend
ID3D11Device *device = mRenderer->getDevice();
HRESULT result;
+ ID3D11Resource *texture = NULL;
+ gl::Error error = getResource(&texture);
+ if (error.isError())
+ {
+ return error;
+ }
+
// TODO, what kind of SRV is expected here?
ID3D11ShaderResourceView *srv = NULL;
@@ -1587,7 +1652,7 @@ gl::Error TextureStorage11_3D::getRenderTarget(const gl::ImageIndex &index, Rend
rtvDesc.Texture3D.WSize = 1;
ID3D11RenderTargetView *rtv;
- result = device->CreateRenderTargetView(mTexture, &rtvDesc, &rtv);
+ result = device->CreateRenderTargetView(texture, &rtvDesc, &rtv);
ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
if (FAILED(result))
@@ -1596,7 +1661,7 @@ gl::Error TextureStorage11_3D::getRenderTarget(const gl::ImageIndex &index, Rend
}
ASSERT(SUCCEEDED(result));
- mLevelLayerRenderTargets[key] = new RenderTarget11(mRenderer, rtv, mTexture, srv, getLevelWidth(mipLevel), getLevelHeight(mipLevel), 1);
+ mLevelLayerRenderTargets[key] = new RenderTarget11(mRenderer, rtv, texture, srv, getLevelWidth(mipLevel), getLevelHeight(mipLevel), 1);
// RenderTarget will take ownership of these resources
SafeRelease(rtv);
@@ -1697,51 +1762,13 @@ TextureStorage11_2DArray::TextureStorage11_2DArray(Renderer *renderer, GLenum in
mSwizzleShaderResourceFormat = formatInfo.swizzleSRVFormat;
mSwizzleRenderTargetFormat = formatInfo.swizzleRTVFormat;
- // if the width, height or depth is not positive this should be treated as an incomplete texture
- // we handle that here by skipping the d3d texture creation
- if (width > 0 && height > 0 && depth > 0)
- {
- // adjust size if needed for compressed textures
- d3d11::MakeValidSize(false, mTextureFormat, &width, &height, &mTopLevel);
-
- ID3D11Device *device = mRenderer->getDevice();
-
- D3D11_TEXTURE2D_DESC desc;
- desc.Width = width;
- desc.Height = height;
- desc.MipLevels = ((levels > 0) ? (mTopLevel + levels) : 0);
- desc.ArraySize = depth;
- desc.Format = mTextureFormat;
- desc.SampleDesc.Count = 1;
- desc.SampleDesc.Quality = 0;
- desc.Usage = D3D11_USAGE_DEFAULT;
- desc.BindFlags = getBindFlags();
- desc.CPUAccessFlags = 0;
- desc.MiscFlags = 0;
-
- HRESULT result = device->CreateTexture2D(&desc, NULL, &mTexture);
+ // adjust size if needed for compressed textures
+ d3d11::MakeValidSize(false, mTextureFormat, &width, &height, &mTopLevel);
- // this can happen from windows TDR
- if (d3d11::isDeviceLostError(result))
- {
- mRenderer->notifyDeviceLost();
- gl::error(GL_OUT_OF_MEMORY);
- }
- else if (FAILED(result))
- {
- ASSERT(result == E_OUTOFMEMORY);
- ERR("Creating image failed.");
- gl::error(GL_OUT_OF_MEMORY);
- }
- else
- {
- mTexture->GetDesc(&desc);
- mMipLevels = desc.MipLevels;
- mTextureWidth = desc.Width;
- mTextureHeight = desc.Height;
- mTextureDepth = desc.ArraySize;
- }
- }
+ mMipLevels = mTopLevel + levels;
+ mTextureWidth = width;
+ mTextureHeight = height;
+ mTextureDepth = depth;
initializeSerials(getLevelCount() * depth, depth);
}
@@ -1860,9 +1887,46 @@ gl::Error TextureStorage11_2DArray::releaseAssociatedImage(const gl::ImageIndex
return gl::Error(GL_NO_ERROR);
}
-ID3D11Resource *TextureStorage11_2DArray::getResource() const
+gl::Error TextureStorage11_2DArray::getResource(ID3D11Resource **outResource)
{
- return mTexture;
+ // if the width, height or depth is not positive this should be treated as an incomplete texture
+ // we handle that here by skipping the d3d texture creation
+ if (mTexture == NULL && mTextureWidth > 0 && mTextureHeight > 0 && mTextureDepth > 0)
+ {
+ ASSERT(mMipLevels > 0);
+
+ ID3D11Device *device = mRenderer->getDevice();
+
+ D3D11_TEXTURE2D_DESC desc;
+ desc.Width = mTextureWidth;
+ desc.Height = mTextureHeight;
+ desc.MipLevels = mMipLevels;
+ desc.ArraySize = mTextureDepth;
+ desc.Format = mTextureFormat;
+ desc.SampleDesc.Count = 1;
+ desc.SampleDesc.Quality = 0;
+ desc.Usage = D3D11_USAGE_DEFAULT;
+ desc.BindFlags = getBindFlags();
+ desc.CPUAccessFlags = 0;
+ desc.MiscFlags = 0;
+
+ HRESULT result = device->CreateTexture2D(&desc, NULL, &mTexture);
+
+ // this can happen from windows TDR
+ if (d3d11::isDeviceLostError(result))
+ {
+ mRenderer->notifyDeviceLost();
+ return gl::Error(GL_OUT_OF_MEMORY, "Failed to create 2D array texture storage, result: 0x%X.", result);
+ }
+ else if (FAILED(result))
+ {
+ ASSERT(result == E_OUTOFMEMORY);
+ return gl::Error(GL_OUT_OF_MEMORY, "Failed to create 2D array texture storage, result: 0x%X.", result);
+ }
+ }
+
+ *outResource = mTexture;
+ return gl::Error(GL_NO_ERROR);
}
gl::Error TextureStorage11_2DArray::createSRV(int baseLevel, int mipLevels, DXGI_FORMAT format, ID3D11Resource *texture,
@@ -1903,6 +1967,13 @@ gl::Error TextureStorage11_2DArray::getRenderTarget(const gl::ImageIndex &index,
ID3D11Device *device = mRenderer->getDevice();
HRESULT result;
+ ID3D11Resource *texture = NULL;
+ gl::Error error = getResource(&texture);
+ if (error.isError())
+ {
+ return error;
+ }
+
D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc;
srvDesc.Format = mShaderResourceFormat;
srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DARRAY;
@@ -1912,7 +1983,7 @@ gl::Error TextureStorage11_2DArray::getRenderTarget(const gl::ImageIndex &index,
srvDesc.Texture2DArray.ArraySize = 1;
ID3D11ShaderResourceView *srv;
- result = device->CreateShaderResourceView(mTexture, &srvDesc, &srv);
+ result = device->CreateShaderResourceView(texture, &srvDesc, &srv);
ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
if (FAILED(result))
@@ -1930,7 +2001,7 @@ gl::Error TextureStorage11_2DArray::getRenderTarget(const gl::ImageIndex &index,
rtvDesc.Texture2DArray.ArraySize = 1;
ID3D11RenderTargetView *rtv;
- result = device->CreateRenderTargetView(mTexture, &rtvDesc, &rtv);
+ result = device->CreateRenderTargetView(texture, &rtvDesc, &rtv);
ASSERT(result == E_OUTOFMEMORY || SUCCEEDED(result));
if (FAILED(result))
@@ -1939,7 +2010,7 @@ gl::Error TextureStorage11_2DArray::getRenderTarget(const gl::ImageIndex &index,
return gl::Error(GL_OUT_OF_MEMORY, "Failed to create internal render target view for texture storage, result: 0x%X.", result);
}
- mRenderTargets[key] = new RenderTarget11(mRenderer, rtv, mTexture, srv, getLevelWidth(mipLevel), getLevelHeight(mipLevel), 1);
+ mRenderTargets[key] = new RenderTarget11(mRenderer, rtv, texture, srv, getLevelWidth(mipLevel), getLevelHeight(mipLevel), 1);
// RenderTarget will take ownership of these resources
SafeRelease(rtv);
diff --git a/src/libGLESv2/renderer/d3d/d3d11/TextureStorage11.h b/src/libGLESv2/renderer/d3d/d3d11/TextureStorage11.h
index 0355536b..3ec2be67 100644
--- a/src/libGLESv2/renderer/d3d/d3d11/TextureStorage11.h
+++ b/src/libGLESv2/renderer/d3d/d3d11/TextureStorage11.h
@@ -41,7 +41,7 @@ class TextureStorage11 : public TextureStorage
UINT getBindFlags() const;
- virtual ID3D11Resource *getResource() const = 0;
+ virtual gl::Error getResource(ID3D11Resource **outResource) = 0;
virtual gl::Error getSRV(const gl::SamplerState &samplerState, ID3D11ShaderResourceView **outSRV);
virtual gl::Error getRenderTarget(const gl::ImageIndex &index, RenderTarget **outRT) = 0;
@@ -147,7 +147,7 @@ class TextureStorage11_2D : public TextureStorage11
static TextureStorage11_2D *makeTextureStorage11_2D(TextureStorage *storage);
- virtual ID3D11Resource *getResource() const;
+ virtual gl::Error getResource(ID3D11Resource **outResource);
virtual gl::Error getRenderTarget(const gl::ImageIndex &index, RenderTarget **outRT);
virtual void associateImage(Image11* image, const gl::ImageIndex &index);
@@ -182,7 +182,7 @@ class TextureStorage11_Cube : public TextureStorage11
static TextureStorage11_Cube *makeTextureStorage11_Cube(TextureStorage *storage);
- virtual ID3D11Resource *getResource() const;
+ virtual gl::Error getResource(ID3D11Resource **outResource);
virtual gl::Error getRenderTarget(const gl::ImageIndex &index, RenderTarget **outRT);
virtual void associateImage(Image11* image, const gl::ImageIndex &index);
@@ -220,7 +220,7 @@ class TextureStorage11_3D : public TextureStorage11
static TextureStorage11_3D *makeTextureStorage11_3D(TextureStorage *storage);
- virtual ID3D11Resource *getResource() const;
+ virtual gl::Error getResource(ID3D11Resource **outResource);
// Handles both layer and non-layer RTs
virtual gl::Error getRenderTarget(const gl::ImageIndex &index, RenderTarget **outRT);
@@ -262,7 +262,7 @@ class TextureStorage11_2DArray : public TextureStorage11
static TextureStorage11_2DArray *makeTextureStorage11_2DArray(TextureStorage *storage);
- virtual ID3D11Resource *getResource() const;
+ virtual gl::Error getResource(ID3D11Resource **outResource);
virtual gl::Error getRenderTarget(const gl::ImageIndex &index, RenderTarget **outRT);
virtual void associateImage(Image11* image, const gl::ImageIndex &index);