Commit 95468d17 by Olli Etuaho Committed by Commit Bot

Support multiview in ESSL 1.00 shaders

Support is added according to the proposal for WEBGL_multiview. When the multiview extension is enabled in an ESSL 1.00 shader, num_views can be specified using a layout qualifier. To support this, enabling the multiview extension makes "layout" a keyword rather than an identifier in ESSL 1.00. The type of gl_ViewID_OVR is also different in case of ESSL 1.00: it has to be a signed integer, since unsigned integers are not supported in ESSL 1.00. Some existing tests for multiview shaders are extended in this patch. The changes make sure that vertex shader "in" qualifier is still allowed in ESSL 3.00 multiview shaders, since this patch adds code to disallow it in ESSL 1.00 multiview shaders. BUG=angleproject:1669 TEST=angle_unittests Change-Id: I65dbbbebabdb24cf0bb647d40aa80cebf713c4f7 Reviewed-on: https://chromium-review.googlesource.com/506088Reviewed-by: 's avatarJamie Madill <jmadill@chromium.org> Commit-Queue: Olli Etuaho <oetuaho@nvidia.com>
parent 7d79fe95
...@@ -791,9 +791,15 @@ void IdentifyBuiltIns(sh::GLenum type, ...@@ -791,9 +791,15 @@ void IdentifyBuiltIns(sh::GLenum type,
if (resources.OVR_multiview && type != GL_COMPUTE_SHADER) if (resources.OVR_multiview && type != GL_COMPUTE_SHADER)
{ {
symbolTable.insert(COMMON_BUILTINS, "GL_OVR_multiview", symbolTable.insert(ESSL3_BUILTINS, "GL_OVR_multiview",
new TVariable(NewPoolTString("gl_ViewID_OVR"), new TVariable(NewPoolTString("gl_ViewID_OVR"),
TType(EbtUInt, EbpHigh, EvqViewIDOVR, 1))); TType(EbtUInt, EbpHigh, EvqViewIDOVR, 1)));
// ESSL 1.00 doesn't have unsigned integers, so gl_ViewID_OVR is a signed integer in ESSL
// 1.00. This is specified in the WEBGL_multiview spec.
symbolTable.insert(ESSL1_BUILTINS, "GL_OVR_multiview",
new TVariable(NewPoolTString("gl_ViewID_OVR"),
TType(EbtInt, EbpHigh, EvqViewIDOVR, 1)));
} }
switch (type) switch (type)
......
...@@ -1085,6 +1085,13 @@ void TParseContext::declarationQualifierErrorCheck(const sh::TQualifier qualifie ...@@ -1085,6 +1085,13 @@ void TParseContext::declarationQualifierErrorCheck(const sh::TQualifier qualifie
checkYuvIsNotSpecified(location, layoutQualifier.yuv); checkYuvIsNotSpecified(location, layoutQualifier.yuv);
} }
// If multiview extension is enabled, "in" qualifier is allowed in the vertex shader in previous
// parsing steps. So it needs to be checked here.
if (isMultiviewExtensionEnabled() && mShaderVersion < 300 && qualifier == EvqVertexIn)
{
error(location, "storage qualifier supported in GLSL ES 3.00 and above only", "in");
}
bool canHaveLocation = qualifier == EvqVertexIn || qualifier == EvqFragmentOut; bool canHaveLocation = qualifier == EvqVertexIn || qualifier == EvqFragmentOut;
if (mShaderVersion >= 310 && qualifier == EvqUniform) if (mShaderVersion >= 310 && qualifier == EvqUniform)
{ {
...@@ -2353,9 +2360,7 @@ void TParseContext::parseGlobalLayoutQualifier(const TTypeQualifierBuilder &type ...@@ -2353,9 +2360,7 @@ void TParseContext::parseGlobalLayoutQualifier(const TTypeQualifierBuilder &type
mComputeShaderLocalSizeDeclared = true; mComputeShaderLocalSizeDeclared = true;
} }
else if (mMultiviewAvailable && else if (isMultiviewExtensionEnabled() && typeQualifier.qualifier == EvqVertexIn)
(isExtensionEnabled("GL_OVR_multiview") || isExtensionEnabled("GL_OVR_multiview2")) &&
typeQualifier.qualifier == EvqVertexIn)
{ {
// This error is only specified in WebGL, but tightens unspecified behavior in the native // This error is only specified in WebGL, but tightens unspecified behavior in the native
// specification. // specification.
...@@ -3414,8 +3419,7 @@ TLayoutQualifier TParseContext::parseLayoutQualifier(const TString &qualifierTyp ...@@ -3414,8 +3419,7 @@ TLayoutQualifier TParseContext::parseLayoutQualifier(const TString &qualifierTyp
parseLocalSize(qualifierType, qualifierTypeLine, intValue, intValueLine, intValueString, 2u, parseLocalSize(qualifierType, qualifierTypeLine, intValue, intValueLine, intValueString, 2u,
&qualifier.localSize); &qualifier.localSize);
} }
else if (qualifierType == "num_views" && mMultiviewAvailable && else if (qualifierType == "num_views" && isMultiviewExtensionEnabled() &&
(isExtensionEnabled("GL_OVR_multiview") || isExtensionEnabled("GL_OVR_multiview2")) &&
mShaderType == GL_VERTEX_SHADER) mShaderType == GL_VERTEX_SHADER)
{ {
parseNumViews(intValue, intValueLine, intValueString, &qualifier.numViews); parseNumViews(intValue, intValueLine, intValueString, &qualifier.numViews);
......
...@@ -163,6 +163,11 @@ class TParseContext : angle::NonCopyable ...@@ -163,6 +163,11 @@ class TParseContext : angle::NonCopyable
} }
bool supportsExtension(const char *extension); bool supportsExtension(const char *extension);
bool isExtensionEnabled(const char *extension) const; bool isExtensionEnabled(const char *extension) const;
bool isMultiviewExtensionEnabled() const
{
return mMultiviewAvailable &&
(isExtensionEnabled("GL_OVR_multiview") || isExtensionEnabled("GL_OVR_multiview2"));
}
void handleExtensionDirective(const TSourceLoc &loc, const char *extName, const char *behavior); void handleExtensionDirective(const TSourceLoc &loc, const char *extName, const char *behavior);
void handlePragmaDirective(const TSourceLoc &loc, void handlePragmaDirective(const TSourceLoc &loc,
const char *name, const char *name,
......
...@@ -76,6 +76,7 @@ static int reserved_word(yyscan_t yyscanner); ...@@ -76,6 +76,7 @@ static int reserved_word(yyscan_t yyscanner);
static int ES2_reserved_ES3_keyword(TParseContext *context, int token); static int ES2_reserved_ES3_keyword(TParseContext *context, int token);
static int ES2_keyword_ES3_reserved(TParseContext *context, int token); static int ES2_keyword_ES3_reserved(TParseContext *context, int token);
static int ES2_ident_ES3_keyword(TParseContext *context, int token); static int ES2_ident_ES3_keyword(TParseContext *context, int token);
static int ES2_ident_ES3_keyword_multiview_keyword(TParseContext *context, int token);
static int ES2_ident_ES3_reserved_ES3_1_keyword(TParseContext *context, int token); static int ES2_ident_ES3_reserved_ES3_1_keyword(TParseContext *context, int token);
static int ES2_and_ES3_reserved_ES3_1_keyword(TParseContext *context, int token); static int ES2_and_ES3_reserved_ES3_1_keyword(TParseContext *context, int token);
static int ES2_and_ES3_ident_ES3_1_keyword(TParseContext *context, int token); static int ES2_and_ES3_ident_ES3_1_keyword(TParseContext *context, int token);
...@@ -200,7 +201,7 @@ O [0-7] ...@@ -200,7 +201,7 @@ O [0-7]
"struct" { return STRUCT; } "struct" { return STRUCT; }
"layout" { return ES2_ident_ES3_keyword(context, LAYOUT); } "layout" { return ES2_ident_ES3_keyword_multiview_keyword(context, LAYOUT); }
"yuvCscStandardEXT" { return ES3_extension_keyword_else_ident(context, "GL_EXT_YUV_target", YUVCSCSTANDARDEXT); } "yuvCscStandardEXT" { return ES3_extension_keyword_else_ident(context, "GL_EXT_YUV_target", YUVCSCSTANDARDEXT); }
"itu_601" { return yuvcscstandardext_constant(context); } "itu_601" { return yuvcscstandardext_constant(context); }
...@@ -514,6 +515,22 @@ int ES2_ident_ES3_keyword(TParseContext *context, int token) ...@@ -514,6 +515,22 @@ int ES2_ident_ES3_keyword(TParseContext *context, int token)
return token; return token;
} }
int ES2_ident_ES3_keyword_multiview_keyword(TParseContext *context, int token)
{
struct yyguts_t* yyg = (struct yyguts_t*) context->getScanner();
yyscan_t yyscanner = (yyscan_t) context->getScanner();
// not a reserved word in GLSL ES 1.00, so could be used as an identifier/type name
// except when multiview extension is enabled
if (context->getShaderVersion() < 300 && !context->isMultiviewExtensionEnabled())
{
yylval->lex.string = NewPoolTString(yytext);
return check_type(yyscanner);
}
return token;
}
int ES2_and_ES3_reserved_ES3_1_keyword(TParseContext *context, int token) int ES2_and_ES3_reserved_ES3_1_keyword(TParseContext *context, int token)
{ {
yyscan_t yyscanner = (yyscan_t) context->getScanner(); yyscan_t yyscanner = (yyscan_t) context->getScanner();
......
...@@ -157,6 +157,12 @@ extern void yyerror(YYLTYPE* yylloc, TParseContext* context, void *scanner, cons ...@@ -157,6 +157,12 @@ extern void yyerror(YYLTYPE* yylloc, TParseContext* context, void *scanner, cons
} \ } \
} }
#define ES3_OR_NEWER_OR_MULTIVIEW(TOKEN, LINE, REASON) { \
if (context->getShaderVersion() < 300 && !context->isMultiviewExtensionEnabled()) { \
context->error(LINE, REASON " supported in GLSL ES 3.00 and above only ", TOKEN); \
} \
}
#define ES3_1_ONLY(TOKEN, LINE, REASON) { \ #define ES3_1_ONLY(TOKEN, LINE, REASON) { \
if (context->getShaderVersion() != 310) { \ if (context->getShaderVersion() != 310) { \
context->error(LINE, REASON " supported in GLSL ES 3.10 only ", TOKEN); \ context->error(LINE, REASON " supported in GLSL ES 3.10 only ", TOKEN); \
...@@ -907,7 +913,7 @@ storage_qualifier ...@@ -907,7 +913,7 @@ storage_qualifier
} }
else if (context->getShaderType() == GL_VERTEX_SHADER) else if (context->getShaderType() == GL_VERTEX_SHADER)
{ {
ES3_OR_NEWER("in", @1, "storage qualifier"); ES3_OR_NEWER_OR_MULTIVIEW("in", @1, "storage qualifier");
$$ = new TStorageQualifierWrapper(EvqVertexIn, @1); $$ = new TStorageQualifierWrapper(EvqVertexIn, @1);
} }
else else
...@@ -992,7 +998,7 @@ precision_qualifier ...@@ -992,7 +998,7 @@ precision_qualifier
layout_qualifier layout_qualifier
: LAYOUT LEFT_PAREN layout_qualifier_id_list RIGHT_PAREN { : LAYOUT LEFT_PAREN layout_qualifier_id_list RIGHT_PAREN {
ES3_OR_NEWER("layout", @1, "qualifier"); ES3_OR_NEWER_OR_MULTIVIEW("layout", @1, "qualifier");
$$ = $3; $$ = $3;
} }
; ;
......
...@@ -1100,6 +1100,7 @@ static int reserved_word(yyscan_t yyscanner); ...@@ -1100,6 +1100,7 @@ static int reserved_word(yyscan_t yyscanner);
static int ES2_reserved_ES3_keyword(TParseContext *context, int token); static int ES2_reserved_ES3_keyword(TParseContext *context, int token);
static int ES2_keyword_ES3_reserved(TParseContext *context, int token); static int ES2_keyword_ES3_reserved(TParseContext *context, int token);
static int ES2_ident_ES3_keyword(TParseContext *context, int token); static int ES2_ident_ES3_keyword(TParseContext *context, int token);
static int ES2_ident_ES3_keyword_multiview_keyword(TParseContext *context, int token);
static int ES2_ident_ES3_reserved_ES3_1_keyword(TParseContext *context, int token); static int ES2_ident_ES3_reserved_ES3_1_keyword(TParseContext *context, int token);
static int ES2_and_ES3_reserved_ES3_1_keyword(TParseContext *context, int token); static int ES2_and_ES3_reserved_ES3_1_keyword(TParseContext *context, int token);
static int ES2_and_ES3_ident_ES3_1_keyword(TParseContext *context, int token); static int ES2_and_ES3_ident_ES3_1_keyword(TParseContext *context, int token);
...@@ -1769,7 +1770,7 @@ YY_RULE_SETUP ...@@ -1769,7 +1770,7 @@ YY_RULE_SETUP
YY_BREAK YY_BREAK
case 83: case 83:
YY_RULE_SETUP YY_RULE_SETUP
{ return ES2_ident_ES3_keyword(context, LAYOUT); } { return ES2_ident_ES3_keyword_multiview_keyword(context, LAYOUT); }
YY_BREAK YY_BREAK
case 84: case 84:
YY_RULE_SETUP YY_RULE_SETUP
...@@ -3471,6 +3472,22 @@ int ES2_ident_ES3_keyword(TParseContext *context, int token) ...@@ -3471,6 +3472,22 @@ int ES2_ident_ES3_keyword(TParseContext *context, int token)
return token; return token;
} }
int ES2_ident_ES3_keyword_multiview_keyword(TParseContext *context, int token)
{
struct yyguts_t* yyg = (struct yyguts_t*) context->getScanner();
yyscan_t yyscanner = (yyscan_t) context->getScanner();
// not a reserved word in GLSL ES 1.00, so could be used as an identifier/type name
// except when multiview extension is enabled
if (context->getShaderVersion() < 300 && !context->isMultiviewExtensionEnabled())
{
yylval->lex.string = NewPoolTString(yytext);
return check_type(yyscanner);
}
return token;
}
int ES2_and_ES3_reserved_ES3_1_keyword(TParseContext *context, int token) int ES2_and_ES3_reserved_ES3_1_keyword(TParseContext *context, int token)
{ {
yyscan_t yyscanner = (yyscan_t) context->getScanner(); yyscan_t yyscanner = (yyscan_t) context->getScanner();
......
...@@ -421,6 +421,12 @@ extern void yyerror(YYLTYPE* yylloc, TParseContext* context, void *scanner, cons ...@@ -421,6 +421,12 @@ extern void yyerror(YYLTYPE* yylloc, TParseContext* context, void *scanner, cons
} \ } \
} }
#define ES3_OR_NEWER_OR_MULTIVIEW(TOKEN, LINE, REASON) { \
if (context->getShaderVersion() < 300 && !context->isMultiviewExtensionEnabled()) { \
context->error(LINE, REASON " supported in GLSL ES 3.00 and above only ", TOKEN); \
} \
}
#define ES3_1_ONLY(TOKEN, LINE, REASON) { \ #define ES3_1_ONLY(TOKEN, LINE, REASON) { \
if (context->getShaderVersion() != 310) { \ if (context->getShaderVersion() != 310) { \
context->error(LINE, REASON " supported in GLSL ES 3.10 only ", TOKEN); \ context->error(LINE, REASON " supported in GLSL ES 3.10 only ", TOKEN); \
...@@ -741,36 +747,36 @@ static const yytype_uint8 yytranslate[] = ...@@ -741,36 +747,36 @@ static const yytype_uint8 yytranslate[] =
/* 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, 248, 248, 249, 252, 262, 265, 270, 275, 280, 0, 254, 254, 255, 258, 268, 271, 276, 281, 286,
285, 293, 299, 302, 305, 308, 311, 314, 320, 327, 291, 299, 305, 308, 311, 314, 317, 320, 326, 333,
333, 337, 345, 348, 354, 358, 365, 370, 377, 385, 339, 343, 351, 354, 360, 364, 371, 376, 383, 391,
391, 397, 406, 409, 412, 415, 425, 426, 427, 428, 397, 403, 412, 415, 418, 421, 431, 432, 433, 434,
436, 437, 440, 443, 450, 451, 454, 460, 461, 465, 442, 443, 446, 449, 456, 457, 460, 466, 467, 471,
472, 473, 476, 479, 482, 488, 489, 492, 498, 499, 478, 479, 482, 485, 488, 494, 495, 498, 504, 505,
506, 507, 514, 515, 522, 523, 529, 530, 536, 537, 512, 513, 520, 521, 528, 529, 535, 536, 542, 543,
543, 544, 550, 551, 558, 559, 560, 561, 565, 566, 549, 550, 556, 557, 564, 565, 566, 567, 571, 572,
567, 571, 575, 579, 583, 590, 593, 599, 606, 613, 573, 577, 581, 585, 589, 596, 599, 605, 612, 619,
616, 619, 628, 632, 636, 640, 644, 651, 658, 661, 622, 625, 634, 638, 642, 646, 650, 657, 664, 667,
668, 676, 696, 706, 714, 739, 743, 747, 751, 758, 674, 682, 702, 712, 720, 745, 749, 753, 757, 764,
765, 768, 772, 776, 781, 786, 793, 797, 801, 805, 771, 774, 778, 782, 787, 792, 799, 803, 807, 811,
810, 815, 822, 826, 832, 835, 841, 845, 852, 858, 816, 821, 828, 832, 838, 841, 847, 851, 858, 864,
862, 866, 869, 872, 881, 887, 895, 898, 918, 937, 868, 872, 875, 878, 887, 893, 901, 904, 924, 943,
944, 948, 952, 955, 958, 961, 964, 967, 975, 982, 950, 954, 958, 961, 964, 967, 970, 973, 981, 988,
985, 988, 994, 1001, 1004, 1010, 1013, 1016, 1019, 1025, 991, 994, 1000, 1007, 1010, 1016, 1019, 1022, 1025, 1031,
1028, 1033, 1044, 1047, 1050, 1053, 1056, 1059, 1063, 1067, 1034, 1039, 1050, 1053, 1056, 1059, 1062, 1065, 1069, 1073,
1071, 1075, 1079, 1083, 1087, 1091, 1095, 1099, 1103, 1107, 1077, 1081, 1085, 1089, 1093, 1097, 1101, 1105, 1109, 1113,
1111, 1115, 1119, 1123, 1127, 1131, 1135, 1139, 1143, 1149, 1117, 1121, 1125, 1129, 1133, 1137, 1141, 1145, 1149, 1155,
1152, 1155, 1158, 1161, 1164, 1167, 1170, 1173, 1176, 1179, 1158, 1161, 1164, 1167, 1170, 1173, 1176, 1179, 1182, 1185,
1182, 1185, 1188, 1191, 1194, 1197, 1200, 1203, 1210, 1216, 1188, 1191, 1194, 1197, 1200, 1203, 1206, 1209, 1216, 1222,
1222, 1225, 1228, 1231, 1234, 1237, 1240, 1243, 1246, 1249, 1228, 1231, 1234, 1237, 1240, 1243, 1246, 1249, 1252, 1255,
1252, 1255, 1258, 1261, 1273, 1273, 1276, 1276, 1282, 1285, 1258, 1261, 1264, 1267, 1279, 1279, 1282, 1282, 1288, 1291,
1291, 1294, 1301, 1305, 1311, 1317, 1329, 1333, 1337, 1338, 1297, 1300, 1307, 1311, 1317, 1323, 1335, 1339, 1343, 1344,
1344, 1345, 1346, 1347, 1348, 1349, 1350, 1354, 1355, 1355, 1350, 1351, 1352, 1353, 1354, 1355, 1356, 1360, 1361, 1361,
1355, 1364, 1365, 1369, 1369, 1370, 1370, 1375, 1378, 1387, 1361, 1370, 1371, 1375, 1375, 1376, 1376, 1381, 1384, 1393,
1392, 1399, 1400, 1404, 1411, 1415, 1422, 1422, 1429, 1432, 1398, 1405, 1406, 1410, 1417, 1421, 1428, 1428, 1435, 1438,
1439, 1443, 1456, 1456, 1461, 1461, 1467, 1467, 1475, 1478, 1445, 1449, 1462, 1462, 1467, 1467, 1473, 1473, 1481, 1484,
1484, 1487, 1493, 1497, 1504, 1507, 1510, 1513, 1516, 1525, 1490, 1493, 1499, 1503, 1510, 1513, 1516, 1519, 1522, 1531,
1531, 1537, 1540, 1546, 1546 1537, 1543, 1546, 1552, 1552
}; };
#endif #endif
...@@ -3685,7 +3691,7 @@ yyreduce: ...@@ -3685,7 +3691,7 @@ yyreduce:
} }
else if (context->getShaderType() == GL_VERTEX_SHADER) else if (context->getShaderType() == GL_VERTEX_SHADER)
{ {
ES3_OR_NEWER("in", (yylsp[0]), "storage qualifier"); ES3_OR_NEWER_OR_MULTIVIEW("in", (yylsp[0]), "storage qualifier");
(yyval.interm.qualifierWrapper) = new TStorageQualifierWrapper(EvqVertexIn, (yylsp[0])); (yyval.interm.qualifierWrapper) = new TStorageQualifierWrapper(EvqVertexIn, (yylsp[0]));
} }
else else
...@@ -3836,7 +3842,7 @@ yyreduce: ...@@ -3836,7 +3842,7 @@ yyreduce:
case 152: case 152:
{ {
ES3_OR_NEWER("layout", (yylsp[-3]), "qualifier"); ES3_OR_NEWER_OR_MULTIVIEW("layout", (yylsp[-3]), "qualifier");
(yyval.interm.layoutQualifier) = (yyvsp[-1].interm.layoutQualifier); (yyval.interm.layoutQualifier) = (yyvsp[-1].interm.layoutQualifier);
} }
......
...@@ -142,17 +142,19 @@ TEST_F(WEBGLMultiviewVertexShaderTest, ValidViewIDInIf) ...@@ -142,17 +142,19 @@ TEST_F(WEBGLMultiviewVertexShaderTest, ValidViewIDInIf)
"#version 300 es\n" "#version 300 es\n"
"#extension GL_OVR_multiview : require\n" "#extension GL_OVR_multiview : require\n"
"layout(num_views = 2) in;\n" "layout(num_views = 2) in;\n"
"precision highp float;\n"
"in vec4 pos;\n"
"void main()\n" "void main()\n"
"{\n" "{\n"
" if (gl_ViewID_OVR == 0u)\n" " if (gl_ViewID_OVR == 0u)\n"
" {\n" " {\n"
" gl_Position.x = 1.0;\n" " gl_Position.x = pos.x;\n"
" }\n" " }\n"
" else\n" " else\n"
" {\n" " {\n"
" gl_Position.x = 1.0;\n" " gl_Position.x = 1.0;\n"
" }\n" " }\n"
" gl_Position.yzw = vec3(0, 0, 1);\n" " gl_Position.yzw = pos.yzw;\n"
"}\n"; "}\n";
if (!compile(shaderString)) if (!compile(shaderString))
{ {
...@@ -388,6 +390,7 @@ TEST_F(WEBGLMultiviewVertexShaderTest, AssignmentWithViewIDInsideAssignment) ...@@ -388,6 +390,7 @@ TEST_F(WEBGLMultiviewVertexShaderTest, AssignmentWithViewIDInsideAssignment)
const std::string &shaderString = const std::string &shaderString =
"#version 300 es\n" "#version 300 es\n"
"#extension GL_OVR_multiview : require\n" "#extension GL_OVR_multiview : require\n"
"layout(num_views = 2) in;\n"
"void main()\n" "void main()\n"
"{\n" "{\n"
" gl_Position.y = (gl_Position.x = (gl_ViewID_OVR == 0u) ? 1.0 : 0.0);\n" " gl_Position.y = (gl_Position.x = (gl_ViewID_OVR == 0u) ? 1.0 : 0.0);\n"
...@@ -404,6 +407,7 @@ TEST_F(WEBGLMultiviewVertexShaderTest, ViewIdAsLValue) ...@@ -404,6 +407,7 @@ TEST_F(WEBGLMultiviewVertexShaderTest, ViewIdAsLValue)
const std::string &shaderString = const std::string &shaderString =
"#version 300 es\n" "#version 300 es\n"
"#extension GL_OVR_multiview2 : require\n" "#extension GL_OVR_multiview2 : require\n"
"layout(num_views = 2) in;\n"
"void foo(out uint u)\n" "void foo(out uint u)\n"
"{\n" "{\n"
" u = 3u;\n" " u = 3u;\n"
...@@ -418,3 +422,99 @@ TEST_F(WEBGLMultiviewVertexShaderTest, ViewIdAsLValue) ...@@ -418,3 +422,99 @@ TEST_F(WEBGLMultiviewVertexShaderTest, ViewIdAsLValue)
FAIL() << "Shader compilation succeeded, expecting failure:\n" << mInfoLog; FAIL() << "Shader compilation succeeded, expecting failure:\n" << mInfoLog;
} }
} }
// Test that compiling an ESSL 1.00 shader with multiview support succeeds.
TEST_F(WEBGLMultiviewVertexShaderTest, ESSL1Shader)
{
const std::string &shaderString =
"#extension GL_OVR_multiview2 : require\n"
"layout(num_views = 2) in;\n"
"void main()\n"
"{\n"
" if (gl_ViewID_OVR == 0)\n"
" {\n"
" gl_Position = vec4(-1.0, 0.0, 0.0, 1.0);\n"
" }\n"
" else\n"
" {\n"
" gl_Position = vec4(1.0, 0.0, 0.0, 1.0);\n"
" }\n"
"}\n";
if (!compile(shaderString))
{
FAIL() << "Shader compilation failed, expecting success:\n" << mInfoLog;
}
}
// Test that compiling an ESSL 1.00 shader with an unsupported global layout qualifier fails.
TEST_F(WEBGLMultiviewVertexShaderTest, ESSL1ShaderUnsupportedGlobalLayoutQualifier)
{
const std::string &shaderString =
"#extension GL_OVR_multiview2 : require\n"
"layout(num_views = 2) in;\n"
"layout(std140) uniform;\n"
"void main()\n"
"{\n"
" if (gl_ViewID_OVR == 0)\n"
" {\n"
" gl_Position = vec4(-1.0, 0.0, 0.0, 1.0);\n"
" }\n"
" else\n"
" {\n"
" gl_Position = vec4(1.0, 0.0, 0.0, 1.0);\n"
" }\n"
"}\n";
if (compile(shaderString))
{
FAIL() << "Shader compilation succeeded, expecting failure:\n" << mInfoLog;
}
}
// Test that compiling an ESSL 1.00 vertex shader with an unsupported input storage qualifier fails.
TEST_F(WEBGLMultiviewVertexShaderTest, ESSL1ShaderUnsupportedInputStorageQualifier)
{
const std::string &shaderString =
"#extension GL_OVR_multiview2 : require\n"
"layout(num_views = 2) in;\n"
"in vec4 pos;\n"
"void main()\n"
"{\n"
" if (gl_ViewID_OVR == 0)\n"
" {\n"
" gl_Position = vec4(-1.0, 0.0, 0.0, 1.0);\n"
" }\n"
" else\n"
" {\n"
" gl_Position = vec4(1.0, 0.0, 0.0, 1.0);\n"
" }\n"
"}\n";
if (compile(shaderString))
{
FAIL() << "Shader compilation succeeded, expecting failure:\n" << mInfoLog;
}
}
// Test that compiling an ESSL 1.00 fragment shader with an unsupported input storage qualifier
// fails.
TEST_F(WEBGLMultiviewFragmentShaderTest, ESSL1ShaderUnsupportedInStorageQualifier)
{
const std::string &shaderString =
"#extension GL_OVR_multiview2 : require\n"
"precision highp float;\n"
"in vec4 color;\n"
"void main()\n"
"{\n"
" if (gl_ViewID_OVR == 0)\n"
" {\n"
" gl_FragColor = color;\n"
" }\n"
" else\n"
" {\n"
" gl_FragColor = color + vec4(1.0, 0.0, 0.0, 1.0);\n"
" }\n"
"}\n";
if (compile(shaderString))
{
FAIL() << "Shader compilation succeeded, expecting failure:\n" << mInfoLog;
}
}
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