|
1 #include "precompiled.h" |
|
2 // |
|
3 // Copyright (c) 2012 The ANGLE Project Authors. All rights reserved. |
|
4 // Use of this source code is governed by a BSD-style license that can be |
|
5 // found in the LICENSE file. |
|
6 // |
|
7 |
|
8 // IndexBuffer11.cpp: Defines the D3D11 IndexBuffer implementation. |
|
9 |
|
10 #include "libGLESv2/renderer/IndexBuffer11.h" |
|
11 #include "libGLESv2/renderer/Renderer11.h" |
|
12 |
|
13 namespace rx |
|
14 { |
|
15 |
|
16 IndexBuffer11::IndexBuffer11(Renderer11 *const renderer) : mRenderer(renderer) |
|
17 { |
|
18 mBuffer = NULL; |
|
19 mBufferSize = 0; |
|
20 mDynamicUsage = false; |
|
21 } |
|
22 |
|
23 IndexBuffer11::~IndexBuffer11() |
|
24 { |
|
25 if (mBuffer) |
|
26 { |
|
27 mBuffer->Release(); |
|
28 mBuffer = NULL; |
|
29 } |
|
30 } |
|
31 |
|
32 bool IndexBuffer11::initialize(unsigned int bufferSize, GLenum indexType, bool dynamic) |
|
33 { |
|
34 if (mBuffer) |
|
35 { |
|
36 mBuffer->Release(); |
|
37 mBuffer = NULL; |
|
38 } |
|
39 |
|
40 updateSerial(); |
|
41 |
|
42 if (bufferSize > 0) |
|
43 { |
|
44 ID3D11Device* dxDevice = mRenderer->getDevice(); |
|
45 |
|
46 D3D11_BUFFER_DESC bufferDesc; |
|
47 bufferDesc.ByteWidth = bufferSize; |
|
48 bufferDesc.Usage = D3D11_USAGE_DYNAMIC; |
|
49 bufferDesc.BindFlags = D3D11_BIND_INDEX_BUFFER; |
|
50 bufferDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE; |
|
51 bufferDesc.MiscFlags = 0; |
|
52 bufferDesc.StructureByteStride = 0; |
|
53 |
|
54 HRESULT result = dxDevice->CreateBuffer(&bufferDesc, NULL, &mBuffer); |
|
55 if (FAILED(result)) |
|
56 { |
|
57 return false; |
|
58 } |
|
59 } |
|
60 |
|
61 mBufferSize = bufferSize; |
|
62 mIndexType = indexType; |
|
63 mDynamicUsage = dynamic; |
|
64 |
|
65 return true; |
|
66 } |
|
67 |
|
68 IndexBuffer11 *IndexBuffer11::makeIndexBuffer11(IndexBuffer *indexBuffer) |
|
69 { |
|
70 ASSERT(HAS_DYNAMIC_TYPE(IndexBuffer11*, indexBuffer)); |
|
71 return static_cast<IndexBuffer11*>(indexBuffer); |
|
72 } |
|
73 |
|
74 bool IndexBuffer11::mapBuffer(unsigned int offset, unsigned int size, void** outMappedMemory) |
|
75 { |
|
76 if (mBuffer) |
|
77 { |
|
78 // Check for integer overflows and out-out-bounds map requests |
|
79 if (offset + size < offset || offset + size > mBufferSize) |
|
80 { |
|
81 ERR("Index buffer map range is not inside the buffer."); |
|
82 return false; |
|
83 } |
|
84 |
|
85 ID3D11DeviceContext *dxContext = mRenderer->getDeviceContext(); |
|
86 |
|
87 D3D11_MAPPED_SUBRESOURCE mappedResource; |
|
88 HRESULT result = dxContext->Map(mBuffer, 0, D3D11_MAP_WRITE_NO_OVERWRITE, 0, &mappedResource); |
|
89 if (FAILED(result)) |
|
90 { |
|
91 ERR("Index buffer map failed with error 0x%08x", result); |
|
92 return false; |
|
93 } |
|
94 |
|
95 *outMappedMemory = reinterpret_cast<char*>(mappedResource.pData) + offset; |
|
96 return true; |
|
97 } |
|
98 else |
|
99 { |
|
100 ERR("Index buffer not initialized."); |
|
101 return false; |
|
102 } |
|
103 } |
|
104 |
|
105 bool IndexBuffer11::unmapBuffer() |
|
106 { |
|
107 if (mBuffer) |
|
108 { |
|
109 ID3D11DeviceContext *dxContext = mRenderer->getDeviceContext(); |
|
110 dxContext->Unmap(mBuffer, 0); |
|
111 return true; |
|
112 } |
|
113 else |
|
114 { |
|
115 ERR("Index buffer not initialized."); |
|
116 return false; |
|
117 } |
|
118 } |
|
119 |
|
120 GLenum IndexBuffer11::getIndexType() const |
|
121 { |
|
122 return mIndexType; |
|
123 } |
|
124 |
|
125 unsigned int IndexBuffer11::getBufferSize() const |
|
126 { |
|
127 return mBufferSize; |
|
128 } |
|
129 |
|
130 bool IndexBuffer11::setSize(unsigned int bufferSize, GLenum indexType) |
|
131 { |
|
132 if (bufferSize > mBufferSize || indexType != mIndexType) |
|
133 { |
|
134 return initialize(bufferSize, indexType, mDynamicUsage); |
|
135 } |
|
136 else |
|
137 { |
|
138 return true; |
|
139 } |
|
140 } |
|
141 |
|
142 bool IndexBuffer11::discard() |
|
143 { |
|
144 if (mBuffer) |
|
145 { |
|
146 ID3D11DeviceContext *dxContext = mRenderer->getDeviceContext(); |
|
147 |
|
148 D3D11_MAPPED_SUBRESOURCE mappedResource; |
|
149 HRESULT result = dxContext->Map(mBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource); |
|
150 if (FAILED(result)) |
|
151 { |
|
152 ERR("Index buffer map failed with error 0x%08x", result); |
|
153 return false; |
|
154 } |
|
155 |
|
156 dxContext->Unmap(mBuffer, 0); |
|
157 |
|
158 return true; |
|
159 } |
|
160 else |
|
161 { |
|
162 ERR("Index buffer not initialized."); |
|
163 return false; |
|
164 } |
|
165 } |
|
166 |
|
167 DXGI_FORMAT IndexBuffer11::getIndexFormat() const |
|
168 { |
|
169 switch (mIndexType) |
|
170 { |
|
171 case GL_UNSIGNED_BYTE: return DXGI_FORMAT_R16_UINT; |
|
172 case GL_UNSIGNED_SHORT: return DXGI_FORMAT_R16_UINT; |
|
173 case GL_UNSIGNED_INT: return DXGI_FORMAT_R32_UINT; |
|
174 default: UNREACHABLE(); return DXGI_FORMAT_UNKNOWN; |
|
175 } |
|
176 } |
|
177 |
|
178 ID3D11Buffer *IndexBuffer11::getBuffer() const |
|
179 { |
|
180 return mBuffer; |
|
181 } |
|
182 |
|
183 } |