Make mixed samples contingent on auxiliary extensions

Moves the cap for mixed samples into GrShaderCaps and does not enable
it unless we have support for both dual source blending and
multisample disable.

Creates a dedicated cap for multisample disable.

Reconfigures the mixed samples cap to indicate the collective
capability of three different extensions:

  GL_NV_framebuffer_mixed_samples
  GL_NV_sample_mask_override_coverage
  GL_EXT_raster_multisample

Imports tokens and procedures for GL_EXT_raster_multisample.

BUG=skia:

Review URL: https://codereview.chromium.org/1151793002
This commit is contained in:
cdalton 2015-05-21 08:27:44 -07:00 committed by Commit bot
parent e797d0de67
commit 0edea2c8e7
10 changed files with 52 additions and 5 deletions

View File

@ -164,6 +164,7 @@ extern "C" {
typedef GrGLvoid (GR_GL_FUNCTION_TYPE* GrGLPopGroupMarkerProc)();
typedef GrGLvoid (GR_GL_FUNCTION_TYPE* GrGLPushGroupMarkerProc)(GrGLsizei length, const char* marker);
typedef GrGLvoid (GR_GL_FUNCTION_TYPE* GrGLQueryCounterProc)(GrGLuint id, GrGLenum target);
typedef GrGLvoid (GR_GL_FUNCTION_TYPE* GrGLRasterSamplesProc)(GrGLuint samples, GrGLboolean fixedsamplelocations);
typedef GrGLvoid (GR_GL_FUNCTION_TYPE* GrGLReadBufferProc)(GrGLenum src);
typedef GrGLvoid (GR_GL_FUNCTION_TYPE* GrGLReadPixelsProc)(GrGLint x, GrGLint y, GrGLsizei width, GrGLsizei height, GrGLenum format, GrGLenum type, GrGLvoid* pixels);
typedef GrGLvoid (GR_GL_FUNCTION_TYPE* GrGLRenderbufferStorageProc)(GrGLenum target, GrGLenum internalformat, GrGLsizei width, GrGLsizei height);

View File

@ -246,6 +246,7 @@ public:
GLPtr<GrGLPopGroupMarkerProc> fPopGroupMarker;
GLPtr<GrGLPushGroupMarkerProc> fPushGroupMarker;
GLPtr<GrGLQueryCounterProc> fQueryCounter;
GLPtr<GrGLRasterSamplesProc> fRasterSamples;
GLPtr<GrGLReadBufferProc> fReadBuffer;
GLPtr<GrGLReadPixelsProc> fReadPixels;
GLPtr<GrGLRenderbufferStorageProc> fRenderbufferStorage;

View File

@ -538,6 +538,7 @@ void GrShaderCaps::reset() {
fPathRenderingSupport = false;
fDstReadInShaderSupport = false;
fDualSourceBlendingSupport = false;
fMixedSamplesSupport = false;
fShaderPrecisionVaries = false;
}
@ -548,6 +549,7 @@ GrShaderCaps& GrShaderCaps::operator=(const GrShaderCaps& other) {
fPathRenderingSupport = other.fPathRenderingSupport;
fDstReadInShaderSupport = other.fDstReadInShaderSupport;
fDualSourceBlendingSupport = other.fDualSourceBlendingSupport;
fMixedSamplesSupport = other.fMixedSamplesSupport;
fShaderPrecisionVaries = other.fShaderPrecisionVaries;
for (int s = 0; s < kGrShaderTypeCount; ++s) {
@ -590,6 +592,7 @@ SkString GrShaderCaps::dump() const {
r.appendf("Path Rendering Support : %s\n", gNY[fPathRenderingSupport]);
r.appendf("Dst Read In Shader Support : %s\n", gNY[fDstReadInShaderSupport]);
r.appendf("Dual Source Blending Support : %s\n", gNY[fDualSourceBlendingSupport]);
r.appendf("Mixed Samples Support : %s\n", gNY[fMixedSamplesSupport]);
r.appendf("Shader Float Precisions (varies: %s):\n", gNY[fShaderPrecisionVaries]);

View File

@ -69,6 +69,7 @@ public:
bool pathRenderingSupport() const { return fPathRenderingSupport; }
bool dstReadInShaderSupport() const { return fDstReadInShaderSupport; }
bool dualSourceBlendingSupport() const { return fDualSourceBlendingSupport; }
bool mixedSamplesSupport() const { return fMixedSamplesSupport; }
/**
* Get the precision info for a variable of type kFloat_GrSLType, kVec2f_GrSLType, etc in a
@ -94,6 +95,7 @@ protected:
bool fPathRenderingSupport : 1;
bool fDstReadInShaderSupport : 1;
bool fDualSourceBlendingSupport : 1;
bool fMixedSamplesSupport : 1;
bool fShaderPrecisionVaries;
PrecisionInfo fFloatPrecisions[kGrShaderTypeCount][kGrSLPrecisionCount];

View File

@ -158,6 +158,9 @@ const GrGLInterface* GrGLAssembleGLInterface(void* ctx, GrGLGetProc get) {
GET_PROC_SUFFIX(MatrixLoadIdentity, EXT);
}
GET_PROC(PixelStorei);
if (extensions.has("GL_EXT_raster_multisample")) {
GET_PROC_SUFFIX(RasterSamples, EXT);
}
GET_PROC(ReadBuffer);
GET_PROC(ReadPixels);
GET_PROC(Scissor);
@ -411,6 +414,11 @@ const GrGLInterface* GrGLAssembleGLESInterface(void* ctx, GrGLGetProc get) {
GET_PROC(LineWidth);
GET_PROC(LinkProgram);
GET_PROC(PixelStorei);
if (extensions.has("GL_EXT_raster_multisample")) {
GET_PROC_SUFFIX(RasterSamples, EXT);
}
GET_PROC(ReadPixels);
GET_PROC(Scissor);
GET_PROC(ShaderSource);

View File

@ -44,10 +44,10 @@ void GrGLCaps::reset() {
fFragCoordsConventionSupport = false;
fVertexArrayObjectSupport = false;
fES2CompatibilitySupport = false;
fMultisampleDisableSupport = false;
fUseNonVBOVertexAndIndexDynamicData = false;
fIsCoreProfile = false;
fFullClearIsFree = false;
fFBMixedSamplesSupport = false;
fReadPixelsSupportedCache.reset();
@ -86,10 +86,10 @@ GrGLCaps& GrGLCaps::operator= (const GrGLCaps& caps) {
fFragCoordsConventionSupport = caps.fFragCoordsConventionSupport;
fVertexArrayObjectSupport = caps.fVertexArrayObjectSupport;
fES2CompatibilitySupport = caps.fES2CompatibilitySupport;
fMultisampleDisableSupport = caps.fMultisampleDisableSupport;
fUseNonVBOVertexAndIndexDynamicData = caps.fUseNonVBOVertexAndIndexDynamicData;
fIsCoreProfile = caps.fIsCoreProfile;
fFullClearIsFree = caps.fFullClearIsFree;
fFBMixedSamplesSupport = caps.fFBMixedSamplesSupport;
*(reinterpret_cast<GrGLSLCaps*>(fShaderCaps.get())) =
*(reinterpret_cast<GrGLSLCaps*>(caps.fShaderCaps.get()));
@ -252,6 +252,12 @@ bool GrGLCaps::init(const GrGLContextInfo& ctxInfo, const GrGLInterface* gli) {
fES2CompatibilitySupport = true;
}
if (kGL_GrGLStandard == standard) {
fMultisampleDisableSupport = true;
} else {
fMultisampleDisableSupport = false;
}
this->initFSAASupport(ctxInfo, gli);
this->initStencilFormats(ctxInfo);
@ -336,8 +342,6 @@ bool GrGLCaps::init(const GrGLContextInfo& ctxInfo, const GrGLInterface* gli) {
// attachment, hence this min:
fMaxRenderTargetSize = SkTMin(fMaxTextureSize, fMaxRenderTargetSize);
fFBMixedSamplesSupport = ctxInfo.hasExtension("GL_NV_framebuffer_mixed_samples");
fGpuTracingSupport = ctxInfo.hasExtension("GL_EXT_debug_marker");
// Disable scratch texture reuse on Mali and Adreno devices
@ -935,6 +939,7 @@ SkString GrGLCaps::dump() const {
r.appendf("Fragment coord conventions support: %s\n",
(fFragCoordsConventionSupport ? "YES": "NO"));
r.appendf("Vertex array object support: %s\n", (fVertexArrayObjectSupport ? "YES": "NO"));
r.appendf("Multisample disable support: %s\n", (fMultisampleDisableSupport ? "YES" : "NO"));
r.appendf("Use non-VBO for dynamic data: %s\n",
(fUseNonVBOVertexAndIndexDynamicData ? "YES" : "NO"));
r.appendf("Full screen clear is free: %s\n", (fFullClearIsFree ? "YES" : "NO"));
@ -1054,6 +1059,15 @@ bool GrGLSLCaps::init(const GrGLContextInfo& ctxInfo,
ctxInfo.hasExtension("GL_OES_standard_derivatives");
}
// We need dual source blending and the ability to disable multisample in order to support mixed
// samples in every corner case.
if (fDualSourceBlendingSupport && glCaps.multisampleDisableSupport()) {
// We understand "mixed samples" to mean the collective capability of 3 different extensions
fMixedSamplesSupport = ctxInfo.hasExtension("GL_NV_framebuffer_mixed_samples") &&
ctxInfo.hasExtension("GL_NV_sample_mask_override_coverage") &&
ctxInfo.hasExtension("GL_EXT_raster_multisample");
}
if (glCaps.advancedBlendEquationSupport()) {
bool coherent = glCaps.advancedCoherentBlendEquationSupport();
if (ctxInfo.hasExtension(coherent ? "GL_NV_blend_equation_advanced_coherent"

View File

@ -237,6 +237,9 @@ public:
/// Is there support for ES2 compatability?
bool ES2CompatibilitySupport() const { return fES2CompatibilitySupport; }
/// Can we call glDisable(GL_MULTISAMPLE)?
bool multisampleDisableSupport() const { return fMultisampleDisableSupport; }
/// Use indices or vertices in CPU arrays rather than VBOs for dynamic content.
bool useNonVBOVertexAndIndexDynamicData() const {
return fUseNonVBOVertexAndIndexDynamicData;
@ -353,6 +356,7 @@ private:
bool fFragCoordsConventionSupport : 1;
bool fVertexArrayObjectSupport : 1;
bool fES2CompatibilitySupport : 1;
bool fMultisampleDisableSupport : 1;
bool fUseNonVBOVertexAndIndexDynamicData : 1;
bool fIsCoreProfile : 1;
bool fFullClearIsFree : 1;

View File

@ -880,4 +880,12 @@
/* ARM specific define for MSAA support on framebuffer fetch */
#define GR_GL_FETCH_PER_SAMPLE_ARM 0x8F65
/* GL_EXT_raster_multisample */
#define GR_GL_RASTER_MULTISAMPLE 0x9327
#define GR_GL_RASTER_SAMPLES 0x9328
#define GR_GL_MAX_RASTER_SAMPLES 0x9329
#define GR_GL_RASTER_FIXED_SAMPLE_LOCATIONS 0x932A
#define GR_GL_MULTISAMPLE_RASTERIZATION_ALLOWED 0x932B
#define GR_GL_EFFECTIVE_RASTER_SAMPLES 0x932C
#endif

View File

@ -2101,7 +2101,7 @@ void GrGLGpu::flushStencil(const GrStencilSettings& stencilSettings) {
void GrGLGpu::flushHWAAState(GrRenderTarget* rt, bool useHWAA) {
SkASSERT(!useHWAA || rt->isMultisampled());
if (kGL_GrGLStandard == this->glStandard()) {
if (this->glCaps().multisampleDisableSupport()) {
if (useHWAA) {
if (kYes_TriState != fMSAAEnabled) {
GL_CALL(Enable(GR_GL_MULTISAMPLE));

View File

@ -528,6 +528,12 @@ bool GrGLInterface::validate() const {
}
}
if (fExtensions.has("GL_EXT_raster_multisample")) {
if (NULL == fFunctions.fRasterSamples) {
RETURN_FALSE_INTERFACE
}
}
if (fExtensions.has("GL_NV_framebuffer_mixed_samples")) {
if (NULL == fFunctions.fCoverageModulation) {
RETURN_FALSE_INTERFACE