Add flags to shader translator to emulate gl_DrawID
Adds support for translating gl_DrawID for implementation of
GL_ANGLE_multi_draw.
Currently the change only supports and allows emulation of the
draw id using a uniform variable named `gl_DrawID`. This uniform is
mapped in the translated shader to a hashed name that does not
use the gl_ namespace
Bug: chromium:890539
Change-Id: I08a246ca911e88e733ccdf22f1ed69dcae948e05
Reviewed-on: https://chromium-review.googlesource.com/c/1271957
Commit-Queue: Austin Eng <enga@chromium.org>
Reviewed-by: Kai Ninomiya <kainino@chromium.org>
diff --git a/src/compiler/translator/BaseTypes.h b/src/compiler/translator/BaseTypes.h
index 60e5898..af3c12e 100644
--- a/src/compiler/translator/BaseTypes.h
+++ b/src/compiler/translator/BaseTypes.h
@@ -620,6 +620,8 @@
EvqPosition,
EvqPointSize,
+ EvqDrawID, // ANGLE_multi_draw
+
// built-ins read by fragment shader
EvqFragCoord,
EvqFrontFacing,
@@ -906,6 +908,7 @@
case EvqVertexID: return "VertexID";
case EvqPosition: return "Position";
case EvqPointSize: return "PointSize";
+ case EvqDrawID: return "DrawID";
case EvqFragCoord: return "FragCoord";
case EvqFrontFacing: return "FrontFacing";
case EvqPointCoord: return "PointCoord";
diff --git a/src/compiler/translator/CollectVariables.cpp b/src/compiler/translator/CollectVariables.cpp
index aa00fdb..0e0ef62 100644
--- a/src/compiler/translator/CollectVariables.cpp
+++ b/src/compiler/translator/CollectVariables.cpp
@@ -174,6 +174,7 @@
bool mInstanceIDAdded;
bool mVertexIDAdded;
bool mPointSizeAdded;
+ bool mDrawIDAdded;
// Vertex Shader and Geometry Shader builtins
bool mPositionAdded;
@@ -231,6 +232,7 @@
mInstanceIDAdded(false),
mVertexIDAdded(false),
mPointSizeAdded(false),
+ mDrawIDAdded(false),
mPositionAdded(false),
mPointCoordAdded(false),
mFrontFacingAdded(false),
@@ -485,6 +487,9 @@
case EvqPointSize:
recordBuiltInVaryingUsed(symbol->variable(), &mPointSizeAdded, mOutputVaryings);
return;
+ case EvqDrawID:
+ recordBuiltInAttributeUsed(symbol->variable(), &mDrawIDAdded);
+ return;
case EvqLastFragData:
recordBuiltInVaryingUsed(symbol->variable(), &mLastFragDataAdded, mInputVaryings);
return;
diff --git a/src/compiler/translator/Compiler.cpp b/src/compiler/translator/Compiler.cpp
index e93e80f..6f9b7e1 100644
--- a/src/compiler/translator/Compiler.cpp
+++ b/src/compiler/translator/Compiler.cpp
@@ -26,6 +26,7 @@
#include "compiler/translator/tree_ops/ClampPointSize.h"
#include "compiler/translator/tree_ops/DeclareAndInitBuiltinsForInstancedMultiview.h"
#include "compiler/translator/tree_ops/DeferGlobalInitializers.h"
+#include "compiler/translator/tree_ops/EmulateGLDrawID.h"
#include "compiler/translator/tree_ops/EmulateGLFragColorBroadcast.h"
#include "compiler/translator/tree_ops/EmulatePrecision.h"
#include "compiler/translator/tree_ops/FoldExpressions.h"
@@ -346,6 +347,18 @@
// Reset the extension behavior for each compilation unit.
ResetExtensionBehavior(mExtensionBehavior);
+ // If gl_DrawID is not supported, remove it from the available extensions
+ // Currently we only allow emulation of gl_DrawID
+ const bool glDrawIDSupported = (compileOptions & SH_EMULATE_GL_DRAW_ID) != 0u;
+ if (!glDrawIDSupported)
+ {
+ auto it = mExtensionBehavior.find(TExtension::ANGLE_multi_draw);
+ if (it != mExtensionBehavior.end())
+ {
+ mExtensionBehavior.erase(it);
+ }
+ }
+
// First string is path of source file if flag is set. The actual source follows.
size_t firstSource = 0;
if (compileOptions & SH_SOURCE_PATH)
@@ -573,6 +586,16 @@
root->traverse(&gen);
}
+ if (mShaderType == GL_VERTEX_SHADER &&
+ IsExtensionEnabled(mExtensionBehavior, TExtension::ANGLE_multi_draw))
+ {
+ if ((compileOptions & SH_EMULATE_GL_DRAW_ID) != 0)
+ {
+ EmulateGLDrawID(root, &mSymbolTable, &mUniforms,
+ shouldCollectVariables(compileOptions));
+ }
+ }
+
if (mShaderType == GL_FRAGMENT_SHADER && mShaderVersion == 100 && mResources.EXT_draw_buffers &&
mResources.MaxDrawBuffers > 1 &&
IsExtensionEnabled(mExtensionBehavior, TExtension::EXT_draw_buffers))
@@ -762,6 +785,22 @@
translate(root, compileOptions, &perfDiagnostics);
}
+ if (mShaderType == GL_VERTEX_SHADER &&
+ IsExtensionEnabled(mExtensionBehavior, TExtension::ANGLE_multi_draw))
+ {
+ if ((compileOptions & SH_EMULATE_GL_DRAW_ID) != 0)
+ {
+ for (auto& uniform : mUniforms)
+ {
+ if (uniform.name == "angle_DrawID" && uniform.mappedName == "angle_DrawID")
+ {
+ uniform.name = "gl_DrawID";
+ break;
+ }
+ }
+ }
+ }
+
// The IntermNode tree doesn't need to be deleted here, since the
// memory will be freed in a big chunk by the PoolAllocator.
return true;
@@ -825,6 +864,7 @@
<< ":MaxViewsOVR:" << mResources.MaxViewsOVR
<< ":NV_draw_buffers:" << mResources.NV_draw_buffers
<< ":WEBGL_debug_shader_precision:" << mResources.WEBGL_debug_shader_precision
+ << ":ANGLE_multi_draw:" << mResources.ANGLE_multi_draw
<< ":MinProgramTextureGatherOffset:" << mResources.MinProgramTextureGatherOffset
<< ":MaxProgramTextureGatherOffset:" << mResources.MaxProgramTextureGatherOffset
<< ":MaxImageUnits:" << mResources.MaxImageUnits
diff --git a/src/compiler/translator/ExtensionBehavior.cpp b/src/compiler/translator/ExtensionBehavior.cpp
index 98cfb0d..faf1d83 100644
--- a/src/compiler/translator/ExtensionBehavior.cpp
+++ b/src/compiler/translator/ExtensionBehavior.cpp
@@ -29,7 +29,8 @@
OP(OES_EGL_image_external_essl3) \
OP(OES_standard_derivatives) \
OP(OES_texture_storage_multisample_2d_array) \
- OP(OVR_multiview)
+ OP(OVR_multiview) \
+ OP(ANGLE_multi_draw)
namespace sh
{
diff --git a/src/compiler/translator/ExtensionBehavior.h b/src/compiler/translator/ExtensionBehavior.h
index 332a64b..e55484f 100644
--- a/src/compiler/translator/ExtensionBehavior.h
+++ b/src/compiler/translator/ExtensionBehavior.h
@@ -34,7 +34,8 @@
OES_EGL_image_external_essl3,
OES_standard_derivatives,
OES_texture_storage_multisample_2d_array,
- OVR_multiview
+ OVR_multiview,
+ ANGLE_multi_draw,
};
enum TBehavior
diff --git a/src/compiler/translator/Initialize.cpp b/src/compiler/translator/Initialize.cpp
index e12a9b7..e362edb 100644
--- a/src/compiler/translator/Initialize.cpp
+++ b/src/compiler/translator/Initialize.cpp
@@ -81,6 +81,10 @@
{
extBehavior[TExtension::ANGLE_texture_multisample] = EBhUndefined;
}
+ if (resources.ANGLE_multi_draw)
+ {
+ extBehavior[TExtension::ANGLE_multi_draw] = EBhUndefined;
+ }
}
void ResetExtensionBehavior(TExtensionBehavior &extBehavior)
diff --git a/src/compiler/translator/ShaderLang.cpp b/src/compiler/translator/ShaderLang.cpp
index 62d5d7e..cf59782 100644
--- a/src/compiler/translator/ShaderLang.cpp
+++ b/src/compiler/translator/ShaderLang.cpp
@@ -204,6 +204,7 @@
resources->EXT_geometry_shader = 0;
resources->OES_texture_storage_multisample_2d_array = 0;
resources->ANGLE_texture_multisample = 0;
+ resources->ANGLE_multi_draw = 0;
resources->NV_draw_buffers = 0;
diff --git a/src/compiler/translator/SymbolTable_autogen.cpp b/src/compiler/translator/SymbolTable_autogen.cpp
index 0a03cf0..0c0d27e 100644
--- a/src/compiler/translator/SymbolTable_autogen.cpp
+++ b/src/compiler/translator/SymbolTable_autogen.cpp
@@ -970,6 +970,7 @@
constexpr const TSymbolUniqueId BuiltInId::gl_VertexID;
constexpr const TSymbolUniqueId BuiltInId::gl_ViewportIndex;
constexpr const TSymbolUniqueId BuiltInId::gl_LayerVS;
+constexpr const TSymbolUniqueId BuiltInId::gl_DrawID;
constexpr const TSymbolUniqueId BuiltInId::gl_NumWorkGroups;
constexpr const TSymbolUniqueId BuiltInId::gl_WorkGroupSize;
constexpr const TSymbolUniqueId BuiltInId::gl_WorkGroupID;
@@ -987,7 +988,7 @@
constexpr const TSymbolUniqueId BuiltInId::gl_ViewID_OVR;
constexpr const TSymbolUniqueId BuiltInId::gl_ViewID_OVRESSL1;
-const int TSymbolTable::kLastBuiltInId = 1023;
+const int TSymbolTable::kLastBuiltInId = 1024;
namespace BuiltInName
{
@@ -1076,6 +1077,7 @@
constexpr const ImmutableString fwidthExt("fwidth");
constexpr const ImmutableString gl_DepthRange("gl_DepthRange");
constexpr const ImmutableString gl_DepthRangeParameters("gl_DepthRangeParameters");
+constexpr const ImmutableString gl_DrawID("gl_DrawID");
constexpr const ImmutableString gl_FragColor("gl_FragColor");
constexpr const ImmutableString gl_FragCoord("gl_FragCoord");
constexpr const ImmutableString gl_FragData("gl_FragData");
@@ -1453,6 +1455,11 @@
namespace BuiltInVariable
{
+constexpr const TVariable kVar_gl_DrawID(BuiltInId::gl_DrawID,
+ BuiltInName::gl_DrawID,
+ SymbolType::BuiltIn,
+ TExtension::ANGLE_multi_draw,
+ StaticType::Get<EbtInt, EbpHigh, EvqDrawID, 1, 1>());
constexpr const TVariable kVar_gl_FragColor(
BuiltInId::gl_FragColor,
BuiltInName::gl_FragColor,
@@ -2031,6 +2038,11 @@
TExtension::UNDEFINED,
StaticType::Get<EbtUInt, EbpUndefined, EvqOut, 4, 1>());
+const TVariable *gl_DrawID()
+{
+ return &kVar_gl_DrawID;
+}
+
const TVariable *gl_FragColor()
{
return &kVar_gl_FragColor;
@@ -7324,7 +7336,7 @@
BuiltInId::texture_USamplerCube1_Float3,
BuiltInName::texture,
TExtension::UNDEFINED,
- BuiltInParameters::p0Y2B0B,
+ BuiltInParameters::p0Y2B2B2B,
2,
StaticType::Get<EbtUInt, EbpUndefined, EvqGlobal, 4, 1>(),
EOpCallBuiltInFunction,
@@ -9601,7 +9613,7 @@
BuiltInId::textureGather_USamplerCube1_Float3,
BuiltInName::textureGather,
TExtension::UNDEFINED,
- BuiltInParameters::p0Y2B0B,
+ BuiltInParameters::p0Y2B2B2B,
2,
StaticType::Get<EbtUInt, EbpUndefined, EvqGlobal, 4, 1>(),
EOpCallBuiltInFunction,
@@ -17245,6 +17257,20 @@
}
}
}
+ if ((mShaderType == GL_VERTEX_SHADER) && (mResources.ANGLE_multi_draw))
+ {
+ switch (nameHash)
+ {
+ case 0x7e4c3c42u:
+ {
+ if (name == BuiltInName::gl_DrawID)
+ {
+ return &BuiltInVariable::kVar_gl_DrawID;
+ }
+ break;
+ }
+ }
+ }
if (mResources.OVR_multiview && mShaderType != GL_COMPUTE_SHADER)
{
switch (nameHash)
diff --git a/src/compiler/translator/TranslatorESSL.cpp b/src/compiler/translator/TranslatorESSL.cpp
index a5ae3ec..c240f6b 100644
--- a/src/compiler/translator/TranslatorESSL.cpp
+++ b/src/compiler/translator/TranslatorESSL.cpp
@@ -172,6 +172,12 @@
}
sink << "#endif\n";
}
+ else if (iter->first == TExtension::ANGLE_multi_draw)
+ {
+ // Don't emit anything. This extension is emulated
+ ASSERT((compileOptions & SH_EMULATE_GL_DRAW_ID) != 0);
+ continue;
+ }
else
{
sink << "#extension " << GetExtensionNameString(iter->first) << " : "
diff --git a/src/compiler/translator/TranslatorVulkan.cpp b/src/compiler/translator/TranslatorVulkan.cpp
index add2069..ae6f6e4 100644
--- a/src/compiler/translator/TranslatorVulkan.cpp
+++ b/src/compiler/translator/TranslatorVulkan.cpp
@@ -138,7 +138,8 @@
{
const ImmutableString &name = symbol->variable().name();
ASSERT(!name.beginsWith("gl_"));
- (*mSink) << HashName(name, mHashFunction, mNameMap) << ArrayString(symbol->getType());
+ (*mSink) << HashName(&symbol->variable(), mHashFunction, mNameMap)
+ << ArrayString(symbol->getType());
}
}
diff --git a/src/compiler/translator/builtin_symbols_hash_autogen.txt b/src/compiler/translator/builtin_symbols_hash_autogen.txt
index d1f5e0a..6cde7cd 100644
--- a/src/compiler/translator/builtin_symbols_hash_autogen.txt
+++ b/src/compiler/translator/builtin_symbols_hash_autogen.txt
@@ -1 +1 @@
-be8880d407c36c696b4ef362988abd50
\ No newline at end of file
+cb342c375ea32f16c747342b0dca0c18
\ No newline at end of file
diff --git a/src/compiler/translator/builtin_variables.json b/src/compiler/translator/builtin_variables.json
index 291eab3..6e26451 100644
--- a/src/compiler/translator/builtin_variables.json
+++ b/src/compiler/translator/builtin_variables.json
@@ -671,6 +671,22 @@
"qualifier":"Layer"
}
}
+ },
+ "subgroups":{
+ "ANGLEMultiDraw":{
+ "condition": "mResources.ANGLE_multi_draw",
+ "variables":{
+ "gl_DrawID":{
+ "level":"ESSL1_BUILTINS",
+ "extension":"ANGLE_multi_draw",
+ "type":{
+ "basic":"Int",
+ "precision":"High",
+ "qualifier":"DrawID"
+ }
+ }
+ }
+ }
}
},
"ComputeShader":{
@@ -852,4 +868,4 @@
}
}
}
-}
\ No newline at end of file
+}
diff --git a/src/compiler/translator/tree_ops/EmulateGLDrawID.cpp b/src/compiler/translator/tree_ops/EmulateGLDrawID.cpp
new file mode 100644
index 0000000..090b62b
--- /dev/null
+++ b/src/compiler/translator/tree_ops/EmulateGLDrawID.cpp
@@ -0,0 +1,87 @@
+//
+// Copyright 2018 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+// EmulateGLDrawID is an AST traverser to convert the gl_DrawID builtin
+// to a uniform int
+//
+
+#include "compiler/translator/tree_ops/EmulateGLDrawID.h"
+
+#include "angle_gl.h"
+#include "compiler/translator/StaticType.h"
+#include "compiler/translator/Symbol.h"
+#include "compiler/translator/SymbolTable.h"
+#include "compiler/translator/tree_util/BuiltIn_autogen.h"
+#include "compiler/translator/tree_util/IntermTraverse.h"
+#include "compiler/translator/tree_util/ReplaceVariable.h"
+#include "compiler/translator/util.h"
+
+namespace sh
+{
+
+namespace
+{
+
+constexpr const ImmutableString kEmulatedGLDrawIDName("angle_DrawID");
+
+class FindGLDrawIDTraverser : public TIntermTraverser
+{
+ public:
+ FindGLDrawIDTraverser() : TIntermTraverser(true, false, false), mFound(false) {}
+
+ bool isGLDrawIDUsed() const { return mFound; }
+
+ protected:
+ void visitSymbol(TIntermSymbol *node) override
+ {
+ if (&node->variable() == BuiltInVariable::gl_DrawID())
+ {
+ mFound = true;
+ }
+ }
+
+ private:
+ bool mFound;
+};
+
+} // namespace anonymous
+
+void EmulateGLDrawID(TIntermBlock *root,
+ TSymbolTable *symbolTable,
+ std::vector<sh::Uniform> *uniforms,
+ bool shouldCollect)
+{
+ FindGLDrawIDTraverser traverser;
+ root->traverse(&traverser);
+ if (traverser.isGLDrawIDUsed())
+ {
+ const TType *type = StaticType::Get<EbtInt, EbpHigh, EvqUniform, 1, 1>();
+ const TVariable *drawID =
+ new TVariable(symbolTable, kEmulatedGLDrawIDName, type, SymbolType::AngleInternal);
+
+ // AngleInternal variables don't get collected
+ if (shouldCollect)
+ {
+ Uniform uniform;
+ uniform.name = kEmulatedGLDrawIDName.data();
+ uniform.mappedName = kEmulatedGLDrawIDName.data();
+ uniform.type = GLVariableType(*type);
+ uniform.precision = GLVariablePrecision(*type);
+ uniform.staticUse = symbolTable->isStaticallyUsed(*BuiltInVariable::gl_DrawID());
+ uniform.active = true;
+ uniform.binding = type->getLayoutQualifier().binding;
+ uniform.location = type->getLayoutQualifier().location;
+ uniform.offset = type->getLayoutQualifier().offset;
+ uniform.readonly = type->getMemoryQualifier().readonly;
+ uniform.writeonly = type->getMemoryQualifier().writeonly;
+ uniforms->push_back(uniform);
+ }
+
+ DeclareGlobalVariable(root, drawID);
+ ReplaceVariable(root, BuiltInVariable::gl_DrawID(), drawID);
+ }
+}
+
+} // namespace sh
diff --git a/src/compiler/translator/tree_ops/EmulateGLDrawID.h b/src/compiler/translator/tree_ops/EmulateGLDrawID.h
new file mode 100644
index 0000000..db295e9
--- /dev/null
+++ b/src/compiler/translator/tree_ops/EmulateGLDrawID.h
@@ -0,0 +1,31 @@
+//
+// Copyright 2018 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+// EmulateGLDrawID is an AST traverser to convert the gl_DrawID builtin
+// to a uniform int
+//
+
+#ifndef COMPILER_TRANSLATOR_TREEOPS_EMULATEGLDRAWID_H_
+#define COMPILER_TRANSLATOR_TREEOPS_EMULATEGLDRAWID_H_
+
+#include <GLSLANG/ShaderLang.h>
+#include <vector>
+
+#include "compiler/translator/HashNames.h"
+
+namespace sh
+{
+struct Uniform;
+class TIntermBlock;
+class TSymbolTable;
+
+void EmulateGLDrawID(TIntermBlock *root,
+ TSymbolTable *symbolTable,
+ std::vector<sh::Uniform> *uniforms,
+ bool shouldCollect);
+
+} // namespace sh
+
+#endif // COMPILER_TRANSLATOR_TREEOPS_EMULATEGLDRAWID_H_
diff --git a/src/compiler/translator/tree_util/BuiltIn_autogen.h b/src/compiler/translator/tree_util/BuiltIn_autogen.h
index 3b4b543..95af600 100644
--- a/src/compiler/translator/tree_util/BuiltIn_autogen.h
+++ b/src/compiler/translator/tree_util/BuiltIn_autogen.h
@@ -1297,28 +1297,30 @@
static constexpr const TSymbolUniqueId gl_VertexID = TSymbolUniqueId(1005);
static constexpr const TSymbolUniqueId gl_ViewportIndex = TSymbolUniqueId(1006);
static constexpr const TSymbolUniqueId gl_LayerVS = TSymbolUniqueId(1007);
- static constexpr const TSymbolUniqueId gl_NumWorkGroups = TSymbolUniqueId(1008);
- static constexpr const TSymbolUniqueId gl_WorkGroupSize = TSymbolUniqueId(1009);
- static constexpr const TSymbolUniqueId gl_WorkGroupID = TSymbolUniqueId(1010);
- static constexpr const TSymbolUniqueId gl_LocalInvocationID = TSymbolUniqueId(1011);
- static constexpr const TSymbolUniqueId gl_GlobalInvocationID = TSymbolUniqueId(1012);
- static constexpr const TSymbolUniqueId gl_LocalInvocationIndex = TSymbolUniqueId(1013);
- static constexpr const TSymbolUniqueId gl_PrimitiveIDIn = TSymbolUniqueId(1014);
- static constexpr const TSymbolUniqueId gl_InvocationID = TSymbolUniqueId(1015);
- static constexpr const TSymbolUniqueId gl_PrimitiveIDGS = TSymbolUniqueId(1016);
- static constexpr const TSymbolUniqueId gl_LayerGS = TSymbolUniqueId(1017);
- static constexpr const TSymbolUniqueId gl_PerVertex = TSymbolUniqueId(1018);
- static constexpr const TSymbolUniqueId gl_in = TSymbolUniqueId(1019);
- static constexpr const TSymbolUniqueId gl_PerVertexOutBlock = TSymbolUniqueId(1020);
- static constexpr const TSymbolUniqueId gl_PositionGS = TSymbolUniqueId(1021);
- static constexpr const TSymbolUniqueId gl_ViewID_OVR = TSymbolUniqueId(1022);
- static constexpr const TSymbolUniqueId gl_ViewID_OVRESSL1 = TSymbolUniqueId(1023);
+ static constexpr const TSymbolUniqueId gl_DrawID = TSymbolUniqueId(1008);
+ static constexpr const TSymbolUniqueId gl_NumWorkGroups = TSymbolUniqueId(1009);
+ static constexpr const TSymbolUniqueId gl_WorkGroupSize = TSymbolUniqueId(1010);
+ static constexpr const TSymbolUniqueId gl_WorkGroupID = TSymbolUniqueId(1011);
+ static constexpr const TSymbolUniqueId gl_LocalInvocationID = TSymbolUniqueId(1012);
+ static constexpr const TSymbolUniqueId gl_GlobalInvocationID = TSymbolUniqueId(1013);
+ static constexpr const TSymbolUniqueId gl_LocalInvocationIndex = TSymbolUniqueId(1014);
+ static constexpr const TSymbolUniqueId gl_PrimitiveIDIn = TSymbolUniqueId(1015);
+ static constexpr const TSymbolUniqueId gl_InvocationID = TSymbolUniqueId(1016);
+ static constexpr const TSymbolUniqueId gl_PrimitiveIDGS = TSymbolUniqueId(1017);
+ static constexpr const TSymbolUniqueId gl_LayerGS = TSymbolUniqueId(1018);
+ static constexpr const TSymbolUniqueId gl_PerVertex = TSymbolUniqueId(1019);
+ static constexpr const TSymbolUniqueId gl_in = TSymbolUniqueId(1020);
+ static constexpr const TSymbolUniqueId gl_PerVertexOutBlock = TSymbolUniqueId(1021);
+ static constexpr const TSymbolUniqueId gl_PositionGS = TSymbolUniqueId(1022);
+ static constexpr const TSymbolUniqueId gl_ViewID_OVR = TSymbolUniqueId(1023);
+ static constexpr const TSymbolUniqueId gl_ViewID_OVRESSL1 = TSymbolUniqueId(1024);
}; // class BuiltInId
namespace BuiltInVariable
{
+const TVariable *gl_DrawID();
const TVariable *gl_FragColor();
const TVariable *gl_FragCoord();
const TVariable *gl_FragDepth();