blob: 7e10cb20a2b122ed1d1b115f7cc66af2dd3473cf [file] [log] [blame]
Greg Daniel94403452017-04-18 15:52:36 -04001/*
2 * Copyright 2017 Google Inc.
3 *
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#include "GrBackendSurface.h"
9
Greg Daniele7d8da42017-12-04 11:23:19 -050010#include "gl/GrGLUtil.h"
11
Greg Daniel94403452017-04-18 15:52:36 -040012#ifdef SK_VULKAN
Greg Daniel52e16d92018-04-10 09:34:07 -040013#include "vk/GrVkImageLayout.h"
Greg Daniel94403452017-04-18 15:52:36 -040014#include "vk/GrVkTypes.h"
15#include "vk/GrVkUtil.h"
Greg Daniel7ef28f32017-04-20 16:41:55 +000016#endif
Timothy Liang4e85e802018-06-28 16:37:18 -040017#ifdef SK_METAL
18#include "mtl/GrMtlTypes.h"
19#endif
Greg Daniel7ef28f32017-04-20 16:41:55 +000020
Robert Phillipsfc711a22018-02-13 17:03:00 -050021GrBackendFormat::GrBackendFormat(GrGLenum format, GrGLenum target)
22 : fBackend(kOpenGL_GrBackend)
23 , fValid(true) {
24 fGL.fTarget = target;
25 fGL.fFormat = format;
26}
27
28const GrGLenum* GrBackendFormat::getGLFormat() const {
29 if (this->isValid() && kOpenGL_GrBackend == fBackend) {
30 return &fGL.fFormat;
31 }
32 return nullptr;
33}
34
35const GrGLenum* GrBackendFormat::getGLTarget() const {
36 if (this->isValid() && kOpenGL_GrBackend == fBackend) {
37 return &fGL.fTarget;
38 }
39 return nullptr;
40}
41
42#ifdef SK_VULKAN
43GrBackendFormat::GrBackendFormat(VkFormat vkFormat)
44 : fBackend(kVulkan_GrBackend)
45 , fValid(true)
46 , fVkFormat(vkFormat) {
47}
48
49const VkFormat* GrBackendFormat::getVkFormat() const {
50 if (this->isValid() && kVulkan_GrBackend == fBackend) {
51 return &fVkFormat;
52 }
53 return nullptr;
54}
55#endif
56
Timothy Liang4e85e802018-06-28 16:37:18 -040057#ifdef SK_METAL
58GrBackendFormat::GrBackendFormat(GrMTLPixelFormat mtlFormat)
59 : fBackend(kMetal_GrBackend)
60 , fValid(true)
61 , fMtlFormat(mtlFormat) {
62}
63
64const GrMTLPixelFormat* GrBackendFormat::getMtlFormat() const {
65 if (this->isValid() && kMetal_GrBackend == fBackend) {
66 return &fMtlFormat;
67 }
68 return nullptr;
69}
70#endif
71
Robert Phillipsfc711a22018-02-13 17:03:00 -050072GrBackendFormat::GrBackendFormat(GrPixelConfig config)
73 : fBackend(kMock_GrBackend)
74 , fValid(true)
75 , fMockFormat(config) {
76}
77
78const GrPixelConfig* GrBackendFormat::getMockFormat() const {
79 if (this->isValid() && kMock_GrBackend == fBackend) {
80 return &fMockFormat;
81 }
82 return nullptr;
83}
84
Robert Phillipsfcd5fdd2017-06-14 01:43:29 +000085#ifdef SK_VULKAN
Greg Daniel94403452017-04-18 15:52:36 -040086GrBackendTexture::GrBackendTexture(int width,
87 int height,
Greg Daniel207282e2017-04-26 13:29:21 -040088 const GrVkImageInfo& vkInfo)
Greg Daniel52e16d92018-04-10 09:34:07 -040089 : GrBackendTexture(width, height, vkInfo,
90 sk_sp<GrVkImageLayout>(new GrVkImageLayout(vkInfo.fImageLayout))) {}
91
92GrBackendTexture::GrBackendTexture(int width,
93 int height,
94 const GrVkImageInfo& vkInfo,
95 sk_sp<GrVkImageLayout> layout)
Greg Daniel9ca30652018-04-06 09:27:20 -040096 : fIsValid(true)
97 , fWidth(width)
Greg Daniel94403452017-04-18 15:52:36 -040098 , fHeight(height)
Greg Daniel108bb232018-07-03 16:18:29 -040099 , fConfig(kUnknown_GrPixelConfig)
Chris Dalton3b51df12017-11-27 14:33:06 -0700100 , fMipMapped(GrMipMapped(vkInfo.fLevelCount > 1))
Greg Daniel94403452017-04-18 15:52:36 -0400101 , fBackend(kVulkan_GrBackend)
Greg Daniel52e16d92018-04-10 09:34:07 -0400102 , fVkInfo(vkInfo, layout.release()) {
103}
Robert Phillipsfcd5fdd2017-06-14 01:43:29 +0000104#endif
Greg Daniel94403452017-04-18 15:52:36 -0400105
Timothy Liang4e85e802018-06-28 16:37:18 -0400106#ifdef SK_METAL
107GrBackendTexture::GrBackendTexture(int width,
108 int height,
109 GrMipMapped mipMapped,
110 const GrMtlTextureInfo& mtlInfo)
111 : fIsValid(true)
112 , fWidth(width)
113 , fHeight(height)
114 , fConfig(GrPixelConfig::kUnknown_GrPixelConfig)
115 , fMipMapped(mipMapped)
116 , fBackend(kMetal_GrBackend)
117 , fMtlInfo(mtlInfo) {}
118#endif
119
Brian Salomon8fe24272017-07-07 12:56:11 -0400120GrBackendTexture::GrBackendTexture(int width,
121 int height,
Greg Daniele7d8da42017-12-04 11:23:19 -0500122 GrMipMapped mipMapped,
123 const GrGLTextureInfo& glInfo)
Greg Daniel9ca30652018-04-06 09:27:20 -0400124 : fIsValid(true)
125 , fWidth(width)
Greg Daniele7d8da42017-12-04 11:23:19 -0500126 , fHeight(height)
Greg Daniel108bb232018-07-03 16:18:29 -0400127 , fConfig(kUnknown_GrPixelConfig)
Greg Daniele7d8da42017-12-04 11:23:19 -0500128 , fMipMapped(mipMapped)
129 , fBackend(kOpenGL_GrBackend)
130 , fGLInfo(glInfo) {}
131
132GrBackendTexture::GrBackendTexture(int width,
133 int height,
Greg Daniel177e6952017-10-12 12:27:11 -0400134 GrMipMapped mipMapped,
135 const GrMockTextureInfo& mockInfo)
Greg Daniel9ca30652018-04-06 09:27:20 -0400136 : fIsValid(true)
137 , fWidth(width)
Brian Salomon8fe24272017-07-07 12:56:11 -0400138 , fHeight(height)
Brian Salomon0c51eea2018-03-09 17:02:09 -0500139 , fConfig(mockInfo.fConfig)
Greg Daniel177e6952017-10-12 12:27:11 -0400140 , fMipMapped(mipMapped)
Brian Salomon8fe24272017-07-07 12:56:11 -0400141 , fBackend(kMock_GrBackend)
142 , fMockInfo(mockInfo) {}
143
Greg Daniel52e16d92018-04-10 09:34:07 -0400144GrBackendTexture::~GrBackendTexture() {
145 this->cleanup();
146}
147
148void GrBackendTexture::cleanup() {
Robert Phillipsfcd5fdd2017-06-14 01:43:29 +0000149#ifdef SK_VULKAN
Brian Salomon8fe24272017-07-07 12:56:11 -0400150 if (this->isValid() && kVulkan_GrBackend == fBackend) {
Greg Daniel52e16d92018-04-10 09:34:07 -0400151 fVkInfo.cleanup();
152 }
153#endif
154}
155
156GrBackendTexture::GrBackendTexture(const GrBackendTexture& that) : fIsValid(false) {
157 *this = that;
158}
159
160GrBackendTexture& GrBackendTexture::operator=(const GrBackendTexture& that) {
161 if (!that.isValid()) {
162 this->cleanup();
163 fIsValid = false;
164 return *this;
165 }
166 fWidth = that.fWidth;
167 fHeight = that.fHeight;
168 fConfig = that.fConfig;
169 fMipMapped = that.fMipMapped;
170 fBackend = that.fBackend;
171
172 switch (that.fBackend) {
173 case kOpenGL_GrBackend:
174 fGLInfo = that.fGLInfo;
175 break;
176#ifdef SK_VULKAN
177 case kVulkan_GrBackend:
178 fVkInfo.assign(that.fVkInfo, this->isValid());
179 break;
180#endif
181#ifdef SK_METAL
182 case kMetal_GrBackend:
Timothy Liang4e85e802018-06-28 16:37:18 -0400183 fMtlInfo = that.fMtlInfo;
Greg Daniel52e16d92018-04-10 09:34:07 -0400184 break;
185#endif
186 case kMock_GrBackend:
187 fMockInfo = that.fMockInfo;
188 break;
189 default:
190 SK_ABORT("Unknown GrBackend");
191 }
192 fIsValid = that.fIsValid;
193 return *this;
194}
195
196#ifdef SK_VULKAN
197bool GrBackendTexture::getVkImageInfo(GrVkImageInfo* outInfo) const {
198 if (this->isValid() && kVulkan_GrBackend == fBackend) {
199 *outInfo = fVkInfo.snapImageInfo();
200 return true;
201 }
202 return false;
203}
204
205void GrBackendTexture::setVkImageLayout(VkImageLayout layout) {
206 if (this->isValid() && kVulkan_GrBackend == fBackend) {
207 fVkInfo.setImageLayout(layout);
208 }
209}
210
211sk_sp<GrVkImageLayout> GrBackendTexture::getGrVkImageLayout() const {
212 if (this->isValid() && kVulkan_GrBackend == fBackend) {
213 return fVkInfo.getGrVkImageLayout();
Greg Daniel94403452017-04-18 15:52:36 -0400214 }
215 return nullptr;
216}
Robert Phillipsfcd5fdd2017-06-14 01:43:29 +0000217#endif
Greg Daniel94403452017-04-18 15:52:36 -0400218
Timothy Liang4e85e802018-06-28 16:37:18 -0400219#ifdef SK_METAL
220bool GrBackendTexture::getMtlTextureInfo(GrMtlTextureInfo* outInfo) const {
221 if (this->isValid() && kMetal_GrBackend == fBackend) {
222 *outInfo = fMtlInfo;
223 return true;
224 }
225 return false;
226}
227#endif
228
Greg Daniel52e16d92018-04-10 09:34:07 -0400229bool GrBackendTexture::getGLTextureInfo(GrGLTextureInfo* outInfo) const {
Brian Salomon8fe24272017-07-07 12:56:11 -0400230 if (this->isValid() && kOpenGL_GrBackend == fBackend) {
Greg Daniel52e16d92018-04-10 09:34:07 -0400231 *outInfo = fGLInfo;
232 return true;
Greg Daniel94403452017-04-18 15:52:36 -0400233 }
Greg Daniel52e16d92018-04-10 09:34:07 -0400234 return false;
Greg Daniel94403452017-04-18 15:52:36 -0400235}
236
Greg Daniel52e16d92018-04-10 09:34:07 -0400237bool GrBackendTexture::getMockTextureInfo(GrMockTextureInfo* outInfo) const {
Brian Salomon8fe24272017-07-07 12:56:11 -0400238 if (this->isValid() && kMock_GrBackend == fBackend) {
Greg Daniel52e16d92018-04-10 09:34:07 -0400239 *outInfo = fMockInfo;
240 return true;
Brian Salomon8fe24272017-07-07 12:56:11 -0400241 }
Greg Daniel52e16d92018-04-10 09:34:07 -0400242 return false;
Brian Salomon8fe24272017-07-07 12:56:11 -0400243}
244
Robert Phillipsc5509952018-04-04 15:54:55 -0400245#if GR_TEST_UTILS
246bool GrBackendTexture::TestingOnly_Equals(const GrBackendTexture& t0, const GrBackendTexture& t1) {
247 if (!t0.isValid() || !t1.isValid()) {
248 return false; // two invalid backend textures are not considered equal
249 }
250
251 if (t0.fWidth != t1.fWidth ||
252 t0.fHeight != t1.fHeight ||
253 t0.fConfig != t1.fConfig ||
254 t0.fMipMapped != t1.fMipMapped ||
255 t0.fBackend != t1.fBackend) {
256 return false;
257 }
258
259 switch (t0.fBackend) {
260 case kOpenGL_GrBackend:
261 return t0.fGLInfo == t1.fGLInfo;
262 case kMock_GrBackend:
263 return t0.fMockInfo == t1.fMockInfo;
264 case kVulkan_GrBackend:
265#ifdef SK_VULKAN
266 return t0.fVkInfo == t1.fVkInfo;
267#else
268 // fall through
269#endif
Timothy Liang4e85e802018-06-28 16:37:18 -0400270 case kMetal_GrBackend:
271#ifdef SK_METAL
272 return t0.fMtlInfo == t1.fMtlInfo;
273#else
274 // fall through
275#endif
Robert Phillipsc5509952018-04-04 15:54:55 -0400276 default:
277 return false;
278 }
279
280 SkASSERT(0);
281 return false;
282}
283#endif
284
Greg Daniel94403452017-04-18 15:52:36 -0400285////////////////////////////////////////////////////////////////////////////////////////////////////
286
Robert Phillipsfcd5fdd2017-06-14 01:43:29 +0000287#ifdef SK_VULKAN
Greg Daniel94403452017-04-18 15:52:36 -0400288GrBackendRenderTarget::GrBackendRenderTarget(int width,
289 int height,
290 int sampleCnt,
291 int stencilBits,
Greg Danielbcf612b2017-05-01 13:50:58 +0000292 const GrVkImageInfo& vkInfo)
Brian Salomonafdc6b12018-03-09 12:02:32 -0500293 : GrBackendRenderTarget(width, height, sampleCnt, vkInfo) {
294 // This is a deprecated constructor that takes a bogus stencil bits.
295 SkASSERT(0 == stencilBits);
296}
297
298GrBackendRenderTarget::GrBackendRenderTarget(int width,
299 int height,
300 int sampleCnt,
301 const GrVkImageInfo& vkInfo)
Greg Daniel323fbcf2018-04-10 13:46:30 -0400302 : GrBackendRenderTarget(width, height, sampleCnt, vkInfo,
303 sk_sp<GrVkImageLayout>(new GrVkImageLayout(vkInfo.fImageLayout))) {}
304
305GrBackendRenderTarget::GrBackendRenderTarget(int width,
306 int height,
307 int sampleCnt,
308 const GrVkImageInfo& vkInfo,
309 sk_sp<GrVkImageLayout> layout)
Greg Daniel9ca30652018-04-06 09:27:20 -0400310 : fIsValid(true)
311 , fWidth(width)
Greg Daniel94403452017-04-18 15:52:36 -0400312 , fHeight(height)
Brian Salomonbdecacf2018-02-02 20:32:49 -0500313 , fSampleCnt(SkTMax(1, sampleCnt))
Brian Salomonafdc6b12018-03-09 12:02:32 -0500314 , fStencilBits(0) // We always create stencil buffers internally for vulkan
Greg Daniel108bb232018-07-03 16:18:29 -0400315 , fConfig(kUnknown_GrPixelConfig)
Greg Daniel94403452017-04-18 15:52:36 -0400316 , fBackend(kVulkan_GrBackend)
Greg Daniel323fbcf2018-04-10 13:46:30 -0400317 , fVkInfo(vkInfo, layout.release()) {}
Robert Phillipsfcd5fdd2017-06-14 01:43:29 +0000318#endif
Greg Daniel94403452017-04-18 15:52:36 -0400319
Timothy Liang4e85e802018-06-28 16:37:18 -0400320#ifdef SK_METAL
321GrBackendRenderTarget::GrBackendRenderTarget(int width,
322 int height,
323 int sampleCnt,
324 const GrMtlTextureInfo& mtlInfo)
325 : fIsValid(true)
326 , fWidth(width)
327 , fHeight(height)
328 , fSampleCnt(SkTMax(1, sampleCnt))
329 , fStencilBits(0)
330 , fConfig(GrPixelConfig::kUnknown_GrPixelConfig)
331 , fBackend(kMetal_GrBackend)
332 , fMtlInfo(mtlInfo) {}
333#endif
334
Greg Danielfaa095e2017-12-19 13:15:02 -0500335GrBackendRenderTarget::GrBackendRenderTarget(int width,
336 int height,
337 int sampleCnt,
338 int stencilBits,
339 const GrGLFramebufferInfo& glInfo)
Greg Daniel9ca30652018-04-06 09:27:20 -0400340 : fIsValid(true)
341 , fWidth(width)
Greg Danielfaa095e2017-12-19 13:15:02 -0500342 , fHeight(height)
Brian Salomonbdecacf2018-02-02 20:32:49 -0500343 , fSampleCnt(SkTMax(1, sampleCnt))
Greg Danielfaa095e2017-12-19 13:15:02 -0500344 , fStencilBits(stencilBits)
Greg Daniel108bb232018-07-03 16:18:29 -0400345 , fConfig(kUnknown_GrPixelConfig)
Greg Danielfaa095e2017-12-19 13:15:02 -0500346 , fBackend(kOpenGL_GrBackend)
347 , fGLInfo(glInfo) {}
348
Brian Salomon0c51eea2018-03-09 17:02:09 -0500349GrBackendRenderTarget::GrBackendRenderTarget(int width,
350 int height,
351 int sampleCnt,
352 int stencilBits,
353 const GrMockRenderTargetInfo& mockInfo)
Greg Daniel9ca30652018-04-06 09:27:20 -0400354 : fIsValid(true)
355 , fWidth(width)
Brian Salomon0c51eea2018-03-09 17:02:09 -0500356 , fHeight(height)
357 , fSampleCnt(SkTMax(1, sampleCnt))
358 , fStencilBits(stencilBits)
359 , fConfig(mockInfo.fConfig)
360 , fMockInfo(mockInfo) {}
361
Greg Daniel323fbcf2018-04-10 13:46:30 -0400362GrBackendRenderTarget::~GrBackendRenderTarget() {
363 this->cleanup();
364}
365
366void GrBackendRenderTarget::cleanup() {
Robert Phillipsfcd5fdd2017-06-14 01:43:29 +0000367#ifdef SK_VULKAN
Greg Daniel323fbcf2018-04-10 13:46:30 -0400368 if (this->isValid() && kVulkan_GrBackend == fBackend) {
369 fVkInfo.cleanup();
370 }
371#endif
372}
373
374GrBackendRenderTarget::GrBackendRenderTarget(const GrBackendRenderTarget& that) : fIsValid(false) {
375 *this = that;
376}
377
378GrBackendRenderTarget& GrBackendRenderTarget::operator=(const GrBackendRenderTarget& that) {
379 if (!that.isValid()) {
380 this->cleanup();
381 fIsValid = false;
382 return *this;
383 }
384 fWidth = that.fWidth;
385 fHeight = that.fHeight;
386 fSampleCnt = that.fSampleCnt;
387 fStencilBits = that.fStencilBits;
388 fConfig = that.fConfig;
389 fBackend = that.fBackend;
390
391 switch (that.fBackend) {
392 case kOpenGL_GrBackend:
393 fGLInfo = that.fGLInfo;
394 break;
395#ifdef SK_VULKAN
396 case kVulkan_GrBackend:
397 fVkInfo.assign(that.fVkInfo, this->isValid());
398 break;
399#endif
400#ifdef SK_METAL
401 case kMetal_GrBackend:
Timothy Liang4e85e802018-06-28 16:37:18 -0400402 fMtlInfo = that.fMtlInfo;
Greg Daniel323fbcf2018-04-10 13:46:30 -0400403 break;
404#endif
405 case kMock_GrBackend:
406 fMockInfo = that.fMockInfo;
407 break;
408 default:
409 SK_ABORT("Unknown GrBackend");
410 }
411 fIsValid = that.fIsValid;
412 return *this;
413}
414
415#ifdef SK_VULKAN
416bool GrBackendRenderTarget::getVkImageInfo(GrVkImageInfo* outInfo) const {
417 if (this->isValid() && kVulkan_GrBackend == fBackend) {
418 *outInfo = fVkInfo.snapImageInfo();
419 return true;
420 }
421 return false;
422}
423
424void GrBackendRenderTarget::setVkImageLayout(VkImageLayout layout) {
425 if (this->isValid() && kVulkan_GrBackend == fBackend) {
426 fVkInfo.setImageLayout(layout);
427 }
428}
429
430sk_sp<GrVkImageLayout> GrBackendRenderTarget::getGrVkImageLayout() const {
431 if (this->isValid() && kVulkan_GrBackend == fBackend) {
432 return fVkInfo.getGrVkImageLayout();
Greg Daniel94403452017-04-18 15:52:36 -0400433 }
434 return nullptr;
435}
Robert Phillipsfcd5fdd2017-06-14 01:43:29 +0000436#endif
Greg Daniel94403452017-04-18 15:52:36 -0400437
Timothy Liang4e85e802018-06-28 16:37:18 -0400438#ifdef SK_METAL
439bool GrBackendRenderTarget::getMtlTextureInfo(GrMtlTextureInfo* outInfo) const {
440 if (this->isValid() && kMetal_GrBackend == fBackend) {
441 *outInfo = fMtlInfo;
442 return true;
443 }
444 return false;
445}
446#endif
447
Greg Daniel323fbcf2018-04-10 13:46:30 -0400448bool GrBackendRenderTarget::getGLFramebufferInfo(GrGLFramebufferInfo* outInfo) const {
449 if (this->isValid() && kOpenGL_GrBackend == fBackend) {
450 *outInfo = fGLInfo;
451 return true;
Greg Daniel94403452017-04-18 15:52:36 -0400452 }
Greg Daniel323fbcf2018-04-10 13:46:30 -0400453 return false;
Greg Daniel94403452017-04-18 15:52:36 -0400454}
455
Greg Daniel323fbcf2018-04-10 13:46:30 -0400456bool GrBackendRenderTarget::getMockRenderTargetInfo(GrMockRenderTargetInfo* outInfo) const {
457 if (this->isValid() && kMock_GrBackend == fBackend) {
458 *outInfo = fMockInfo;
459 return true;
Brian Salomon0c51eea2018-03-09 17:02:09 -0500460 }
Greg Daniel323fbcf2018-04-10 13:46:30 -0400461 return false;
Brian Salomon0c51eea2018-03-09 17:02:09 -0500462}
Robert Phillips8caf85f2018-04-05 09:30:38 -0400463
464#if GR_TEST_UTILS
465bool GrBackendRenderTarget::TestingOnly_Equals(const GrBackendRenderTarget& r0,
466 const GrBackendRenderTarget& r1) {
467 if (!r0.isValid() || !r1.isValid()) {
468 return false; // two invalid backend rendertargets are not considered equal
469 }
470
471 if (r0.fWidth != r1.fWidth ||
472 r0.fHeight != r1.fHeight ||
473 r0.fSampleCnt != r1.fSampleCnt ||
474 r0.fStencilBits != r1.fStencilBits ||
475 r0.fConfig != r1.fConfig ||
476 r0.fBackend != r1.fBackend) {
477 return false;
478 }
479
480 switch (r0.fBackend) {
481 case kOpenGL_GrBackend:
482 return r0.fGLInfo == r1.fGLInfo;
483 case kMock_GrBackend:
484 return r0.fMockInfo == r1.fMockInfo;
485 case kVulkan_GrBackend:
486#ifdef SK_VULKAN
487 return r0.fVkInfo == r1.fVkInfo;
488#else
489 // fall through
490#endif
Timothy Liang4e85e802018-06-28 16:37:18 -0400491 case kMetal_GrBackend:
492#ifdef SK_METAL
493 return r0.fMtlInfo == r1.fMtlInfo;
494#else
495 // fall through
496#endif
Robert Phillips8caf85f2018-04-05 09:30:38 -0400497 default:
498 return false;
499 }
500
501 SkASSERT(0);
502 return false;
503}
504#endif