Commit 7f694d92 by bajones@chromium.org

Added support for EXT_frag_depth

This change also required that support be added for associating built-in variables with an extension, similar to how functions could be associated with extensions previously. R=alokp@chromium.org Review URL: https://codereview.appspot.com/9827044 git-svn-id: https://angleproject.googlecode.com/svn/trunk@2248 736b8ea6-26fd-11df-bfd4-992fa37f6226
parent 4b721cda
...@@ -215,6 +215,7 @@ typedef struct ...@@ -215,6 +215,7 @@ typedef struct
int OES_EGL_image_external; int OES_EGL_image_external;
int ARB_texture_rectangle; int ARB_texture_rectangle;
int EXT_draw_buffers; int EXT_draw_buffers;
int EXT_frag_depth;
// Set to 1 if highp precision is supported in the fragment language. // Set to 1 if highp precision is supported in the fragment language.
// Default is 0. // Default is 0.
......
...@@ -108,6 +108,7 @@ enum TQualifier ...@@ -108,6 +108,7 @@ enum TQualifier
// built-ins written by fragment shader // built-ins written by fragment shader
EvqFragColor, EvqFragColor,
EvqFragData, EvqFragData,
EvqFragDepth,
// end of list // end of list
EvqLast EvqLast
...@@ -139,6 +140,7 @@ inline const char* getQualifierString(TQualifier q) ...@@ -139,6 +140,7 @@ inline const char* getQualifierString(TQualifier q)
case EvqFrontFacing: return "FrontFacing"; break; case EvqFrontFacing: return "FrontFacing"; break;
case EvqFragColor: return "FragColor"; break; case EvqFragColor: return "FragColor"; break;
case EvqFragData: return "FragData"; break; case EvqFragData: return "FragData"; break;
case EvqFragDepth: return "FragDepth"; break;
default: return "unknown qualifier"; default: return "unknown qualifier";
} }
} }
......
...@@ -539,6 +539,10 @@ void IdentifyBuiltIns(ShShaderType type, ShShaderSpec spec, ...@@ -539,6 +539,10 @@ void IdentifyBuiltIns(ShShaderType type, ShShaderSpec spec,
if (spec != SH_CSS_SHADERS_SPEC) { if (spec != SH_CSS_SHADERS_SPEC) {
symbolTable.insert(*new TVariable(NewPoolTString("gl_FragColor"), TType(EbtFloat, EbpMedium, EvqFragColor, 4))); symbolTable.insert(*new TVariable(NewPoolTString("gl_FragColor"), TType(EbtFloat, EbpMedium, EvqFragColor, 4)));
symbolTable.insert(*new TVariable(NewPoolTString("gl_FragData[gl_MaxDrawBuffers]"), TType(EbtFloat, EbpMedium, EvqFragData, 4))); symbolTable.insert(*new TVariable(NewPoolTString("gl_FragData[gl_MaxDrawBuffers]"), TType(EbtFloat, EbpMedium, EvqFragData, 4)));
if (resources.EXT_frag_depth) {
symbolTable.insert(*new TVariable(NewPoolTString("gl_FragDepthEXT"), TType(EbtFloat, resources.FragmentPrecisionHigh ? EbpHigh : EbpMedium, EvqFragDepth, 1)));
symbolTable.relateToExtension("gl_FragDepthEXT", "GL_EXT_frag_depth");
}
} else { } else {
symbolTable.insert(*new TVariable(NewPoolTString("css_MixColor"), TType(EbtFloat, EbpMedium, EvqGlobal, 4))); symbolTable.insert(*new TVariable(NewPoolTString("css_MixColor"), TType(EbtFloat, EbpMedium, EvqGlobal, 4)));
symbolTable.insert(*new TVariable(NewPoolTString("css_ColorMatrix"), TType(EbtFloat, EbpMedium, EvqGlobal, 4, true))); symbolTable.insert(*new TVariable(NewPoolTString("css_ColorMatrix"), TType(EbtFloat, EbpMedium, EvqGlobal, 4, true)));
...@@ -656,4 +660,6 @@ void InitExtensionBehavior(const ShBuiltInResources& resources, ...@@ -656,4 +660,6 @@ void InitExtensionBehavior(const ShBuiltInResources& resources,
extBehavior["GL_ARB_texture_rectangle"] = EBhUndefined; extBehavior["GL_ARB_texture_rectangle"] = EBhUndefined;
if (resources.EXT_draw_buffers) if (resources.EXT_draw_buffers)
extBehavior["GL_EXT_draw_buffers"] = EBhUndefined; extBehavior["GL_EXT_draw_buffers"] = EBhUndefined;
if (resources.EXT_frag_depth)
extBehavior["GL_EXT_frag_depth"] = EBhUndefined;
} }
...@@ -19,3 +19,17 @@ bool TOutputGLSL::writeVariablePrecision(TPrecision) ...@@ -19,3 +19,17 @@ bool TOutputGLSL::writeVariablePrecision(TPrecision)
{ {
return false; return false;
} }
void TOutputGLSL::visitSymbol(TIntermSymbol* node)
{
TInfoSinkBase& out = objSink();
if (node->getSymbol() == "gl_FragDepthEXT")
{
out << "gl_FragDepth";
}
else
{
TOutputGLSLBase::visitSymbol(node);
}
}
...@@ -20,6 +20,7 @@ public: ...@@ -20,6 +20,7 @@ public:
protected: protected:
virtual bool writeVariablePrecision(TPrecision); virtual bool writeVariablePrecision(TPrecision);
virtual void visitSymbol(TIntermSymbol* node);
}; };
#endif // CROSSCOMPILERGLSL_OUTPUTGLSL_H_ #endif // CROSSCOMPILERGLSL_OUTPUTGLSL_H_
...@@ -52,6 +52,7 @@ OutputHLSL::OutputHLSL(TParseContext &context) : TIntermTraverser(true, true, tr ...@@ -52,6 +52,7 @@ OutputHLSL::OutputHLSL(TParseContext &context) : TIntermTraverser(true, true, tr
mUsesPointCoord = false; mUsesPointCoord = false;
mUsesFrontFacing = false; mUsesFrontFacing = false;
mUsesPointSize = false; mUsesPointSize = false;
mUsesFragDepth = false;
mUsesXor = false; mUsesXor = false;
mUsesMod1 = false; mUsesMod1 = false;
mUsesMod2v = false; mUsesMod2v = false;
...@@ -189,6 +190,11 @@ void OutputHLSL::header() ...@@ -189,6 +190,11 @@ void OutputHLSL::header()
out << "\n" out << "\n"
"static float4 gl_Color[1] = {float4(0, 0, 0, 0)};\n"; "static float4 gl_Color[1] = {float4(0, 0, 0, 0)};\n";
if (mUsesFragDepth)
{
out << "static float gl_Depth = 0.0;\n";
}
if (mUsesFragCoord) if (mUsesFragCoord)
{ {
out << "static float4 gl_FragCoord = float4(0, 0, 0, 0);\n"; out << "static float4 gl_FragCoord = float4(0, 0, 0, 0);\n";
...@@ -509,6 +515,11 @@ void OutputHLSL::header() ...@@ -509,6 +515,11 @@ void OutputHLSL::header()
out << "#define GL_USES_POINT_SIZE\n"; out << "#define GL_USES_POINT_SIZE\n";
} }
if (mUsesFragDepth)
{
out << "#define GL_USES_FRAG_DEPTH\n";
}
if (mUsesDepthRange) if (mUsesDepthRange)
{ {
out << "struct gl_DepthRangeParameters\n" out << "struct gl_DepthRangeParameters\n"
...@@ -843,6 +854,11 @@ void OutputHLSL::visitSymbol(TIntermSymbol *node) ...@@ -843,6 +854,11 @@ void OutputHLSL::visitSymbol(TIntermSymbol *node)
mUsesPointSize = true; mUsesPointSize = true;
out << name; out << name;
} }
else if (name == "gl_FragDepthEXT")
{
mUsesFragDepth = true;
out << "gl_Depth";
}
else else
{ {
TQualifier qualifier = node->getQualifier(); TQualifier qualifier = node->getQualifier();
......
...@@ -97,6 +97,7 @@ class OutputHLSL : public TIntermTraverser ...@@ -97,6 +97,7 @@ class OutputHLSL : public TIntermTraverser
bool mUsesPointCoord; bool mUsesPointCoord;
bool mUsesFrontFacing; bool mUsesFrontFacing;
bool mUsesPointSize; bool mUsesPointSize;
bool mUsesFragDepth;
bool mUsesXor; bool mUsesXor;
bool mUsesMod1; bool mUsesMod1;
bool mUsesMod2v; bool mUsesMod2v;
......
...@@ -925,6 +925,27 @@ const TFunction* TParseContext::findFunction(const TSourceLoc& line, TFunction* ...@@ -925,6 +925,27 @@ const TFunction* TParseContext::findFunction(const TSourceLoc& line, TFunction*
return static_cast<const TFunction*>(symbol); return static_cast<const TFunction*>(symbol);
} }
bool TParseContext::isVariableBuiltIn(const TVariable* var)
{
bool builtIn = false;
// First find by unmangled name to check whether the function name has been
// hidden by a variable name or struct typename.
const TSymbol* symbol = symbolTable.find(var->getName(), &builtIn);
if (symbol == 0) {
symbol = symbolTable.find(var->getMangledName(), &builtIn);
}
if (symbol == 0) {
return false;
}
if (!symbol->isVariable()) {
return false;
}
return builtIn;
}
// //
// Initializers show up in several places in the grammar. Have one set of // Initializers show up in several places in the grammar. Have one set of
// code to handle them here. // code to handle them here.
......
...@@ -105,6 +105,7 @@ struct TParseContext { ...@@ -105,6 +105,7 @@ struct TParseContext {
bool containsSampler(TType& type); bool containsSampler(TType& type);
bool areAllChildConst(TIntermAggregate* aggrNode); bool areAllChildConst(TIntermAggregate* aggrNode);
const TFunction* findFunction(const TSourceLoc& line, TFunction* pfnCall, bool *builtIn = 0); const TFunction* findFunction(const TSourceLoc& line, TFunction* pfnCall, bool *builtIn = 0);
bool isVariableBuiltIn(const TVariable* pVar);
bool executeInitializer(const TSourceLoc& line, TString& identifier, TPublicType& pType, bool executeInitializer(const TSourceLoc& line, TString& identifier, TPublicType& pType,
TIntermTyped* initializer, TIntermNode*& intermNode, TVariable* variable = 0); TIntermTyped* initializer, TIntermNode*& intermNode, TVariable* variable = 0);
......
...@@ -126,6 +126,7 @@ void ShInitBuiltInResources(ShBuiltInResources* resources) ...@@ -126,6 +126,7 @@ void ShInitBuiltInResources(ShBuiltInResources* resources)
resources->OES_EGL_image_external = 0; resources->OES_EGL_image_external = 0;
resources->ARB_texture_rectangle = 0; resources->ARB_texture_rectangle = 0;
resources->EXT_draw_buffers = 0; resources->EXT_draw_buffers = 0;
resources->EXT_frag_depth = 0;
// Disable highp precision in fragment shader by default. // Disable highp precision in fragment shader by default.
resources->FragmentPrecisionHigh = 0; resources->FragmentPrecisionHigh = 0;
......
...@@ -223,10 +223,8 @@ void TSymbolTableLevel::relateToOperator(const char* name, TOperator op) ...@@ -223,10 +223,8 @@ void TSymbolTableLevel::relateToOperator(const char* name, TOperator op)
void TSymbolTableLevel::relateToExtension(const char* name, const TString& ext) void TSymbolTableLevel::relateToExtension(const char* name, const TString& ext)
{ {
for (tLevel::iterator it = level.begin(); it != level.end(); ++it) { for (tLevel::iterator it = level.begin(); it != level.end(); ++it) {
if (it->second->isFunction()) { TSymbol* symbol = it->second;
TFunction* function = static_cast<TFunction*>(it->second); if (symbol->getName() == name)
if (function->getName() == name) symbol->relateToExtension(ext);
function->relateToExtension(ext);
}
} }
} }
...@@ -51,12 +51,15 @@ public: ...@@ -51,12 +51,15 @@ public:
void setUniqueId(int id) { uniqueId = id; } void setUniqueId(int id) { uniqueId = id; }
int getUniqueId() const { return uniqueId; } int getUniqueId() const { return uniqueId; }
virtual void dump(TInfoSink &infoSink) const = 0; virtual void dump(TInfoSink &infoSink) const = 0;
void relateToExtension(const TString& ext) { extension = ext; }
const TString& getExtension() const { return extension; }
private: private:
DISALLOW_COPY_AND_ASSIGN(TSymbol); DISALLOW_COPY_AND_ASSIGN(TSymbol);
const TString *name; const TString *name;
unsigned int uniqueId; // For real comparing during code generation unsigned int uniqueId; // For real comparing during code generation
TString extension;
}; };
// //
...@@ -156,9 +159,6 @@ public: ...@@ -156,9 +159,6 @@ public:
void relateToOperator(TOperator o) { op = o; } void relateToOperator(TOperator o) { op = o; }
TOperator getBuiltInOp() const { return op; } TOperator getBuiltInOp() const { return op; }
void relateToExtension(const TString& ext) { extension = ext; }
const TString& getExtension() const { return extension; }
void setDefined() { defined = true; } void setDefined() { defined = true; }
bool isDefined() { return defined; } bool isDefined() { return defined; }
...@@ -175,7 +175,6 @@ private: ...@@ -175,7 +175,6 @@ private:
TType returnType; TType returnType;
TString mangledName; TString mangledName;
TOperator op; TOperator op;
TString extension;
bool defined; bool defined;
}; };
......
...@@ -197,7 +197,14 @@ variable_identifier ...@@ -197,7 +197,14 @@ variable_identifier
context->error(@1, "variable expected", $1.string->c_str()); context->error(@1, "variable expected", $1.string->c_str());
context->recover(); context->recover();
} }
variable = static_cast<const TVariable*>(symbol); variable = static_cast<const TVariable*>(symbol);
if (context->isVariableBuiltIn(variable) &&
!variable->getExtension().empty() &&
context->extensionErrorCheck(@1, variable->getExtension())) {
context->recover();
}
} }
// don't delete $1.string, it's used by error recovery, and the pool // don't delete $1.string, it's used by error recovery, and the pool
......
...@@ -325,6 +325,14 @@ static void yyerror(YYLTYPE* yylloc, TParseContext* context, const char* reason) ...@@ -325,6 +325,14 @@ static void yyerror(YYLTYPE* yylloc, TParseContext* context, const char* reason)
} \ } \
} while (0) } while (0)
#define FRAG_VERT_ONLY(S, L) { \
if (context->shaderType != SH_FRAGMENT_SHADER && \
context->shaderType != SH_VERTEX_SHADER) { \
context->error(L, " supported in vertex/fragment shaders only ", S); \
context->recover(); \
} \
}
#define VERTEX_ONLY(S, L) { \ #define VERTEX_ONLY(S, L) { \
if (context->shaderType != SH_VERTEX_SHADER) { \ if (context->shaderType != SH_VERTEX_SHADER) { \
context->error(L, " supported in vertex shaders only ", S); \ context->error(L, " supported in vertex shaders only ", S); \
...@@ -713,27 +721,27 @@ static const yytype_int16 yyrhs[] = ...@@ -713,27 +721,27 @@ static const yytype_int16 yyrhs[] =
/* YYRLINE[YYN] -- source line where rule number YYN was defined. */ /* YYRLINE[YYN] -- source line where rule number YYN was defined. */
static const yytype_uint16 yyrline[] = static const yytype_uint16 yyrline[] =
{ {
0, 179, 179, 180, 183, 219, 222, 235, 240, 245, 0, 187, 187, 188, 191, 234, 237, 250, 255, 260,
251, 254, 329, 332, 433, 443, 456, 464, 564, 567, 266, 269, 356, 359, 460, 470, 483, 491, 591, 594,
575, 578, 584, 588, 595, 601, 610, 618, 673, 683, 602, 605, 611, 615, 622, 628, 637, 645, 700, 710,
686, 696, 706, 727, 728, 729, 734, 735, 743, 754, 713, 723, 733, 754, 755, 756, 761, 762, 771, 783,
755, 763, 774, 778, 779, 789, 799, 809, 822, 823, 784, 792, 803, 807, 808, 818, 828, 838, 851, 852,
833, 846, 850, 854, 858, 859, 872, 873, 886, 887, 862, 875, 879, 883, 887, 888, 901, 902, 915, 916,
900, 901, 918, 919, 932, 933, 934, 935, 936, 940, 929, 930, 947, 948, 961, 962, 963, 964, 965, 969,
943, 954, 962, 989, 994, 1008, 1045, 1048, 1055, 1063, 972, 983, 991, 1018, 1023, 1037, 1074, 1077, 1084, 1092,
1084, 1105, 1115, 1143, 1148, 1158, 1163, 1173, 1176, 1179, 1113, 1134, 1144, 1172, 1177, 1187, 1192, 1202, 1205, 1208,
1182, 1188, 1195, 1198, 1220, 1238, 1262, 1285, 1289, 1307, 1211, 1217, 1224, 1227, 1249, 1267, 1291, 1314, 1318, 1336,
1315, 1347, 1367, 1388, 1397, 1420, 1423, 1429, 1437, 1445, 1344, 1376, 1396, 1485, 1494, 1517, 1520, 1526, 1534, 1542,
1453, 1463, 1470, 1473, 1476, 1482, 1485, 1500, 1504, 1508, 1550, 1560, 1567, 1570, 1573, 1579, 1582, 1597, 1601, 1605,
1512, 1516, 1521, 1526, 1531, 1536, 1541, 1546, 1551, 1556, 1609, 1618, 1623, 1628, 1633, 1638, 1643, 1648, 1653, 1658,
1561, 1566, 1571, 1576, 1580, 1584, 1592, 1600, 1604, 1617, 1663, 1669, 1675, 1681, 1686, 1691, 1700, 1709, 1714, 1727,
1617, 1631, 1631, 1640, 1643, 1659, 1695, 1699, 1705, 1712, 1727, 1741, 1741, 1750, 1753, 1769, 1805, 1809, 1815, 1822,
1727, 1731, 1735, 1736, 1742, 1743, 1744, 1745, 1746, 1750, 1837, 1841, 1845, 1846, 1852, 1853, 1854, 1855, 1856, 1860,
1751, 1751, 1751, 1761, 1762, 1766, 1766, 1767, 1767, 1772, 1861, 1861, 1861, 1871, 1872, 1876, 1876, 1877, 1877, 1882,
1775, 1785, 1788, 1794, 1795, 1799, 1807, 1811, 1821, 1826, 1885, 1895, 1898, 1904, 1905, 1909, 1917, 1921, 1931, 1936,
1843, 1843, 1848, 1848, 1855, 1855, 1863, 1866, 1872, 1875, 1953, 1953, 1958, 1958, 1965, 1965, 1973, 1976, 1982, 1985,
1881, 1885, 1892, 1899, 1906, 1913, 1924, 1933, 1937, 1944, 1991, 1995, 2002, 2009, 2016, 2023, 2034, 2043, 2047, 2054,
1947, 1953, 1953 2057, 2063, 2063
}; };
#endif #endif
...@@ -2262,7 +2270,14 @@ yyreduce: ...@@ -2262,7 +2270,14 @@ yyreduce:
context->error((yylsp[(1) - (1)]), "variable expected", (yyvsp[(1) - (1)].lex).string->c_str()); context->error((yylsp[(1) - (1)]), "variable expected", (yyvsp[(1) - (1)].lex).string->c_str());
context->recover(); context->recover();
} }
variable = static_cast<const TVariable*>(symbol); variable = static_cast<const TVariable*>(symbol);
if (context->isVariableBuiltIn(variable) &&
!variable->getExtension().empty() &&
context->extensionErrorCheck((yylsp[(1) - (1)]), variable->getExtension())) {
context->recover();
}
} }
// don't delete $1.string, it's used by error recovery, and the pool // don't delete $1.string, it's used by error recovery, and the pool
...@@ -2369,7 +2384,15 @@ yyreduce: ...@@ -2369,7 +2384,15 @@ yyreduce:
} }
} else { } else {
if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isArray()) { if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isArray()) {
if (index >= (yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getArraySize()) { if ((yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getArraySize() == 0) {
if ((yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getMaxArraySize() <= index) {
if (context->arraySetMaxSize((yyvsp[(1) - (4)].interm.intermTypedNode)->getAsSymbolNode(), (yyvsp[(1) - (4)].interm.intermTypedNode)->getTypePointer(), index, true, (yylsp[(2) - (4)])))
context->recover();
} else {
if (context->arraySetMaxSize((yyvsp[(1) - (4)].interm.intermTypedNode)->getAsSymbolNode(), (yyvsp[(1) - (4)].interm.intermTypedNode)->getTypePointer(), 0, false, (yylsp[(2) - (4)])))
context->recover();
}
} else if (index >= (yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getArraySize()) {
std::stringstream extraInfoStream; std::stringstream extraInfoStream;
extraInfoStream << "array index out of range '" << index << "'"; extraInfoStream << "array index out of range '" << index << "'";
std::string extraInfo = extraInfoStream.str(); std::string extraInfo = extraInfoStream.str();
...@@ -2389,6 +2412,10 @@ yyreduce: ...@@ -2389,6 +2412,10 @@ yyreduce:
(yyval.interm.intermTypedNode) = context->intermediate.addIndex(EOpIndexDirect, (yyvsp[(1) - (4)].interm.intermTypedNode), (yyvsp[(3) - (4)].interm.intermTypedNode), (yylsp[(2) - (4)])); (yyval.interm.intermTypedNode) = context->intermediate.addIndex(EOpIndexDirect, (yyvsp[(1) - (4)].interm.intermTypedNode), (yyvsp[(3) - (4)].interm.intermTypedNode), (yylsp[(2) - (4)]));
} }
} else { } else {
if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isArray() && (yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getArraySize() == 0) {
context->error((yylsp[(2) - (4)]), "", "[", "array must be redeclared with a size before being indexed with a variable");
context->recover();
}
(yyval.interm.intermTypedNode) = context->intermediate.addIndex(EOpIndexIndirect, (yyvsp[(1) - (4)].interm.intermTypedNode), (yyvsp[(3) - (4)].interm.intermTypedNode), (yylsp[(2) - (4)])); (yyval.interm.intermTypedNode) = context->intermediate.addIndex(EOpIndexIndirect, (yyvsp[(1) - (4)].interm.intermTypedNode), (yyvsp[(3) - (4)].interm.intermTypedNode), (yylsp[(2) - (4)]));
} }
if ((yyval.interm.intermTypedNode) == 0) { if ((yyval.interm.intermTypedNode) == 0) {
...@@ -2768,17 +2795,17 @@ yyreduce: ...@@ -2768,17 +2795,17 @@ yyreduce:
case EbtInt: case EbtInt:
switch((yyvsp[(1) - (1)].interm.type).size) { switch((yyvsp[(1) - (1)].interm.type).size) {
case 1: op = EOpConstructInt; break; case 1: op = EOpConstructInt; break;
case 2: op = EOpConstructIVec2; break; case 2: FRAG_VERT_ONLY("ivec2", (yylsp[(1) - (1)])); op = EOpConstructIVec2; break;
case 3: op = EOpConstructIVec3; break; case 3: FRAG_VERT_ONLY("ivec3", (yylsp[(1) - (1)])); op = EOpConstructIVec3; break;
case 4: op = EOpConstructIVec4; break; case 4: FRAG_VERT_ONLY("ivec4", (yylsp[(1) - (1)])); op = EOpConstructIVec4; break;
} }
break; break;
case EbtBool: case EbtBool:
switch((yyvsp[(1) - (1)].interm.type).size) { switch((yyvsp[(1) - (1)].interm.type).size) {
case 1: op = EOpConstructBool; break; case 1: op = EOpConstructBool; break;
case 2: op = EOpConstructBVec2; break; case 2: FRAG_VERT_ONLY("bvec2", (yylsp[(1) - (1)])); op = EOpConstructBVec2; break;
case 3: op = EOpConstructBVec3; break; case 3: FRAG_VERT_ONLY("bvec3", (yylsp[(1) - (1)])); op = EOpConstructBVec3; break;
case 4: op = EOpConstructBVec4; break; case 4: FRAG_VERT_ONLY("bvec4", (yylsp[(1) - (1)])); op = EOpConstructBVec4; break;
} }
break; break;
default: break; default: break;
...@@ -2887,6 +2914,7 @@ yyreduce: ...@@ -2887,6 +2914,7 @@ yyreduce:
case 37: case 37:
{ {
FRAG_VERT_ONLY("*", (yylsp[(2) - (3)]));
(yyval.interm.intermTypedNode) = context->intermediate.addBinaryMath(EOpMul, (yyvsp[(1) - (3)].interm.intermTypedNode), (yyvsp[(3) - (3)].interm.intermTypedNode), (yylsp[(2) - (3)]), context->symbolTable); (yyval.interm.intermTypedNode) = context->intermediate.addBinaryMath(EOpMul, (yyvsp[(1) - (3)].interm.intermTypedNode), (yyvsp[(3) - (3)].interm.intermTypedNode), (yylsp[(2) - (3)]), context->symbolTable);
if ((yyval.interm.intermTypedNode) == 0) { if ((yyval.interm.intermTypedNode) == 0) {
context->binaryOpError((yylsp[(2) - (3)]), "*", (yyvsp[(1) - (3)].interm.intermTypedNode)->getCompleteString(), (yyvsp[(3) - (3)].interm.intermTypedNode)->getCompleteString()); context->binaryOpError((yylsp[(2) - (3)]), "*", (yyvsp[(1) - (3)].interm.intermTypedNode)->getCompleteString(), (yyvsp[(3) - (3)].interm.intermTypedNode)->getCompleteString());
...@@ -2899,6 +2927,7 @@ yyreduce: ...@@ -2899,6 +2927,7 @@ yyreduce:
case 38: case 38:
{ {
FRAG_VERT_ONLY("/", (yylsp[(2) - (3)]));
(yyval.interm.intermTypedNode) = context->intermediate.addBinaryMath(EOpDiv, (yyvsp[(1) - (3)].interm.intermTypedNode), (yyvsp[(3) - (3)].interm.intermTypedNode), (yylsp[(2) - (3)]), context->symbolTable); (yyval.interm.intermTypedNode) = context->intermediate.addBinaryMath(EOpDiv, (yyvsp[(1) - (3)].interm.intermTypedNode), (yyvsp[(3) - (3)].interm.intermTypedNode), (yylsp[(2) - (3)]), context->symbolTable);
if ((yyval.interm.intermTypedNode) == 0) { if ((yyval.interm.intermTypedNode) == 0) {
context->binaryOpError((yylsp[(2) - (3)]), "/", (yyvsp[(1) - (3)].interm.intermTypedNode)->getCompleteString(), (yyvsp[(3) - (3)].interm.intermTypedNode)->getCompleteString()); context->binaryOpError((yylsp[(2) - (3)]), "/", (yyvsp[(1) - (3)].interm.intermTypedNode)->getCompleteString(), (yyvsp[(3) - (3)].interm.intermTypedNode)->getCompleteString());
...@@ -3157,12 +3186,12 @@ yyreduce: ...@@ -3157,12 +3186,12 @@ yyreduce:
case 65: case 65:
{ (yyval.interm).op = EOpMulAssign; } { FRAG_VERT_ONLY("*=", (yylsp[(1) - (1)])); (yyval.interm).op = EOpMulAssign; }
break; break;
case 66: case 66:
{ (yyval.interm).op = EOpDivAssign; } { FRAG_VERT_ONLY("/=", (yylsp[(1) - (1)])); (yyval.interm).op = EOpDivAssign; }
break; break;
case 67: case 67:
...@@ -3976,6 +4005,7 @@ yyreduce: ...@@ -3976,6 +4005,7 @@ yyreduce:
case 130: case 130:
{ {
FRAG_VERT_ONLY("mat2", (yylsp[(1) - (1)]));
TQualifier qual = context->symbolTable.atGlobalLevel() ? EvqGlobal : EvqTemporary; TQualifier qual = context->symbolTable.atGlobalLevel() ? EvqGlobal : EvqTemporary;
(yyval.interm.type).setBasic(EbtFloat, qual, (yylsp[(1) - (1)])); (yyval.interm.type).setBasic(EbtFloat, qual, (yylsp[(1) - (1)]));
(yyval.interm.type).setAggregate(2, true); (yyval.interm.type).setAggregate(2, true);
...@@ -3985,6 +4015,7 @@ yyreduce: ...@@ -3985,6 +4015,7 @@ yyreduce:
case 131: case 131:
{ {
FRAG_VERT_ONLY("mat3", (yylsp[(1) - (1)]));
TQualifier qual = context->symbolTable.atGlobalLevel() ? EvqGlobal : EvqTemporary; TQualifier qual = context->symbolTable.atGlobalLevel() ? EvqGlobal : EvqTemporary;
(yyval.interm.type).setBasic(EbtFloat, qual, (yylsp[(1) - (1)])); (yyval.interm.type).setBasic(EbtFloat, qual, (yylsp[(1) - (1)]));
(yyval.interm.type).setAggregate(3, true); (yyval.interm.type).setAggregate(3, true);
...@@ -3994,6 +4025,7 @@ yyreduce: ...@@ -3994,6 +4025,7 @@ yyreduce:
case 132: case 132:
{ {
FRAG_VERT_ONLY("mat4", (yylsp[(1) - (1)]));
TQualifier qual = context->symbolTable.atGlobalLevel() ? EvqGlobal : EvqTemporary; TQualifier qual = context->symbolTable.atGlobalLevel() ? EvqGlobal : EvqTemporary;
(yyval.interm.type).setBasic(EbtFloat, qual, (yylsp[(1) - (1)])); (yyval.interm.type).setBasic(EbtFloat, qual, (yylsp[(1) - (1)]));
(yyval.interm.type).setAggregate(4, true); (yyval.interm.type).setAggregate(4, true);
...@@ -4003,6 +4035,7 @@ yyreduce: ...@@ -4003,6 +4035,7 @@ yyreduce:
case 133: case 133:
{ {
FRAG_VERT_ONLY("sampler2D", (yylsp[(1) - (1)]));
TQualifier qual = context->symbolTable.atGlobalLevel() ? EvqGlobal : EvqTemporary; TQualifier qual = context->symbolTable.atGlobalLevel() ? EvqGlobal : EvqTemporary;
(yyval.interm.type).setBasic(EbtSampler2D, qual, (yylsp[(1) - (1)])); (yyval.interm.type).setBasic(EbtSampler2D, qual, (yylsp[(1) - (1)]));
} }
...@@ -4011,6 +4044,7 @@ yyreduce: ...@@ -4011,6 +4044,7 @@ yyreduce:
case 134: case 134:
{ {
FRAG_VERT_ONLY("samplerCube", (yylsp[(1) - (1)]));
TQualifier qual = context->symbolTable.atGlobalLevel() ? EvqGlobal : EvqTemporary; TQualifier qual = context->symbolTable.atGlobalLevel() ? EvqGlobal : EvqTemporary;
(yyval.interm.type).setBasic(EbtSamplerCube, qual, (yylsp[(1) - (1)])); (yyval.interm.type).setBasic(EbtSamplerCube, qual, (yylsp[(1) - (1)]));
} }
...@@ -4023,6 +4057,7 @@ yyreduce: ...@@ -4023,6 +4057,7 @@ yyreduce:
context->error((yylsp[(1) - (1)]), "unsupported type", "samplerExternalOES"); context->error((yylsp[(1) - (1)]), "unsupported type", "samplerExternalOES");
context->recover(); context->recover();
} }
FRAG_VERT_ONLY("samplerExternalOES", (yylsp[(1) - (1)]));
TQualifier qual = context->symbolTable.atGlobalLevel() ? EvqGlobal : EvqTemporary; TQualifier qual = context->symbolTable.atGlobalLevel() ? EvqGlobal : EvqTemporary;
(yyval.interm.type).setBasic(EbtSamplerExternalOES, qual, (yylsp[(1) - (1)])); (yyval.interm.type).setBasic(EbtSamplerExternalOES, qual, (yylsp[(1) - (1)]));
} }
...@@ -4035,6 +4070,7 @@ yyreduce: ...@@ -4035,6 +4070,7 @@ yyreduce:
context->error((yylsp[(1) - (1)]), "unsupported type", "sampler2DRect"); context->error((yylsp[(1) - (1)]), "unsupported type", "sampler2DRect");
context->recover(); context->recover();
} }
FRAG_VERT_ONLY("sampler2DRect", (yylsp[(1) - (1)]));
TQualifier qual = context->symbolTable.atGlobalLevel() ? EvqGlobal : EvqTemporary; TQualifier qual = context->symbolTable.atGlobalLevel() ? EvqGlobal : EvqTemporary;
(yyval.interm.type).setBasic(EbtSampler2DRect, qual, (yylsp[(1) - (1)])); (yyval.interm.type).setBasic(EbtSampler2DRect, qual, (yylsp[(1) - (1)]));
} }
...@@ -4043,6 +4079,7 @@ yyreduce: ...@@ -4043,6 +4079,7 @@ yyreduce:
case 137: case 137:
{ {
FRAG_VERT_ONLY("struct", (yylsp[(1) - (1)]));
(yyval.interm.type) = (yyvsp[(1) - (1)].interm.type); (yyval.interm.type) = (yyvsp[(1) - (1)].interm.type);
(yyval.interm.type).qualifier = context->symbolTable.atGlobalLevel() ? EvqGlobal : EvqTemporary; (yyval.interm.type).qualifier = context->symbolTable.atGlobalLevel() ? EvqGlobal : EvqTemporary;
} }
......
...@@ -3964,6 +3964,7 @@ void Context::initExtensionString() ...@@ -3964,6 +3964,7 @@ void Context::initExtensionString()
extensionString += "GL_EXT_texture_format_BGRA8888 "; extensionString += "GL_EXT_texture_format_BGRA8888 ";
extensionString += "GL_EXT_texture_storage "; extensionString += "GL_EXT_texture_storage ";
extensionString += "GL_EXT_frag_depth ";
// ANGLE-specific extensions // ANGLE-specific extensions
if (supportsDepthTextures()) if (supportsDepthTextures())
......
...@@ -1549,8 +1549,14 @@ bool ProgramBinary::linkVaryings(InfoLog &infoLog, std::string& pixelHLSL, std:: ...@@ -1549,8 +1549,14 @@ bool ProgramBinary::linkVaryings(InfoLog &infoLog, std::string& pixelHLSL, std::
"\n" "\n"
"struct PS_OUTPUT\n" "struct PS_OUTPUT\n"
"{\n" "{\n"
" float4 gl_Color[1] : COLOR;\n" " float4 gl_Color[1] : COLOR;\n";
"};\n"
if (fragmentShader->mUsesFragDepth)
{
pixelHLSL += " float gl_Depth : DEPTH;\n";
}
pixelHLSL += "};\n"
"\n" "\n"
"PS_OUTPUT main(PS_INPUT input)\n" "PS_OUTPUT main(PS_INPUT input)\n"
"{\n"; "{\n";
...@@ -1626,8 +1632,14 @@ bool ProgramBinary::linkVaryings(InfoLog &infoLog, std::string& pixelHLSL, std:: ...@@ -1626,8 +1632,14 @@ bool ProgramBinary::linkVaryings(InfoLog &infoLog, std::string& pixelHLSL, std::
" gl_main();\n" " gl_main();\n"
"\n" "\n"
" PS_OUTPUT output;\n" " PS_OUTPUT output;\n"
" output.gl_Color[0] = gl_Color[0];\n" " output.gl_Color[0] = gl_Color[0];\n";
"\n"
if (fragmentShader->mUsesFragDepth)
{
pixelHLSL += " output.gl_Depth = gl_Depth;\n";
}
pixelHLSL += "\n"
" return output;\n" " return output;\n"
"}\n"; "}\n";
......
...@@ -238,6 +238,7 @@ void Shader::initializeCompiler() ...@@ -238,6 +238,7 @@ void Shader::initializeCompiler()
resources.OES_standard_derivatives = context->supportsDerivativeInstructions() ? 1 : 0; resources.OES_standard_derivatives = context->supportsDerivativeInstructions() ? 1 : 0;
// resources.OES_EGL_image_external = getDisplay()->isD3d9ExDevice() ? 1 : 0; // TODO: commented out until the extension is actually supported. // resources.OES_EGL_image_external = getDisplay()->isD3d9ExDevice() ? 1 : 0; // TODO: commented out until the extension is actually supported.
resources.FragmentPrecisionHigh = 1; // Shader Model 2+ always supports FP24 (s16e7) which corresponds to highp resources.FragmentPrecisionHigh = 1; // Shader Model 2+ always supports FP24 (s16e7) which corresponds to highp
resources.EXT_frag_depth = 1; // Shader Model 2+ always supports explicit depth output
mFragmentCompiler = ShConstructCompiler(SH_FRAGMENT_SHADER, SH_GLES2_SPEC, SH_HLSL_OUTPUT, &resources); mFragmentCompiler = ShConstructCompiler(SH_FRAGMENT_SHADER, SH_GLES2_SPEC, SH_HLSL_OUTPUT, &resources);
mVertexCompiler = ShConstructCompiler(SH_VERTEX_SHADER, SH_GLES2_SPEC, SH_HLSL_OUTPUT, &resources); mVertexCompiler = ShConstructCompiler(SH_VERTEX_SHADER, SH_GLES2_SPEC, SH_HLSL_OUTPUT, &resources);
...@@ -292,6 +293,7 @@ void Shader::parseVaryings() ...@@ -292,6 +293,7 @@ void Shader::parseVaryings()
mUsesFrontFacing = strstr(mHlsl, "GL_USES_FRONT_FACING") != NULL; mUsesFrontFacing = strstr(mHlsl, "GL_USES_FRONT_FACING") != NULL;
mUsesPointSize = strstr(mHlsl, "GL_USES_POINT_SIZE") != NULL; mUsesPointSize = strstr(mHlsl, "GL_USES_POINT_SIZE") != NULL;
mUsesPointCoord = strstr(mHlsl, "GL_USES_POINT_COORD") != NULL; mUsesPointCoord = strstr(mHlsl, "GL_USES_POINT_COORD") != NULL;
mUsesFragDepth = strstr(mHlsl, "GL_USES_FRAG_DEPTH") != NULL;
} }
} }
...@@ -311,6 +313,7 @@ void Shader::uncompile() ...@@ -311,6 +313,7 @@ void Shader::uncompile()
mUsesFrontFacing = false; mUsesFrontFacing = false;
mUsesPointSize = false; mUsesPointSize = false;
mUsesPointCoord = false; mUsesPointCoord = false;
mUsesFragDepth = false;
} }
void Shader::compileToHLSL(void *compiler) void Shader::compileToHLSL(void *compiler)
......
...@@ -90,6 +90,7 @@ class Shader ...@@ -90,6 +90,7 @@ class Shader
bool mUsesFrontFacing; bool mUsesFrontFacing;
bool mUsesPointSize; bool mUsesPointSize;
bool mUsesPointCoord; bool mUsesPointCoord;
bool mUsesFragDepth;
static void *mFragmentCompiler; static void *mFragmentCompiler;
static void *mVertexCompiler; static void *mVertexCompiler;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment