Ternary selection cleanup Moved the ternary selection code to TParseContext where checks were added to make sure arrays and structs can't use it. Change-Id: If3c007820870276cdf540005e095d89d54949bc4 Reviewed-on: https://swiftshader-review.googlesource.com/3669 Tested-by: Alexis Hétu <sugoi@google.com> Reviewed-by: Nicolas Capens <capn@google.com>
diff --git a/src/OpenGL/compiler/ParseHelper.cpp b/src/OpenGL/compiler/ParseHelper.cpp index 899bac2..e75f0ba 100644 --- a/src/OpenGL/compiler/ParseHelper.cpp +++ b/src/OpenGL/compiler/ParseHelper.cpp
@@ -3403,6 +3403,29 @@ return callNode; } +TIntermTyped *TParseContext::addTernarySelection(TIntermTyped *cond, TIntermTyped *trueBlock, TIntermTyped *falseBlock, const TSourceLoc &loc) +{ + if(boolErrorCheck(loc, cond)) + recover(); + + if(trueBlock->getType() != falseBlock->getType()) + { + binaryOpError(loc, ":", trueBlock->getCompleteString(), falseBlock->getCompleteString()); + recover(); + return falseBlock; + } + // ESSL1 sections 5.2 and 5.7: + // ESSL3 section 5.7: + // Ternary operator is not among the operators allowed for structures/arrays. + if(trueBlock->isArray() || trueBlock->getBasicType() == EbtStruct) + { + error(loc, "ternary operator is not allowed for structures or arrays", ":"); + recover(); + return falseBlock; + } + return intermediate.addSelection(cond, trueBlock, falseBlock, loc); +} + // // Parse an array of strings using yyparse. //
diff --git a/src/OpenGL/compiler/ParseHelper.h b/src/OpenGL/compiler/ParseHelper.h index 145d3f7..52a644e 100644 --- a/src/OpenGL/compiler/ParseHelper.h +++ b/src/OpenGL/compiler/ParseHelper.h
@@ -223,6 +223,8 @@ TIntermTyped *addFunctionCallOrMethod(TFunction *fnCall, TIntermNode *paramNode, TIntermNode *thisNode, const TSourceLoc &loc, bool *fatalError); + TIntermTyped *addTernarySelection(TIntermTyped *cond, TIntermTyped *trueBlock, TIntermTyped *falseBlock, const TSourceLoc &line); + private: bool declareVariable(const TSourceLoc &line, const TString &identifier, const TType &type, TVariable **variable);
diff --git a/src/OpenGL/compiler/glslang.y b/src/OpenGL/compiler/glslang.y index b591ee5..daeb4e7 100644 --- a/src/OpenGL/compiler/glslang.y +++ b/src/OpenGL/compiler/glslang.y
@@ -293,11 +293,11 @@ function_call : function_call_or_method { - bool fatalError = false; - $$ = context->addFunctionCallOrMethod($1.function, $1.intermNode, nullptr, @1, &fatalError); - if (fatalError) + bool fatalError = false; + $$ = context->addFunctionCallOrMethod($1.function, $1.intermNode, nullptr, @1, &fatalError); + if (fatalError) { - YYERROR; + YYERROR; } } ; @@ -550,18 +550,7 @@ conditional_expression : logical_or_expression { $$ = $1; } | logical_or_expression QUESTION expression COLON assignment_expression { - if (context->boolErrorCheck(@2, $1)) - context->recover(); - - $$ = context->intermediate.addSelection($1, $3, $5, @2); - if ($3->getType() != $5->getType()) - $$ = 0; - - if ($$ == 0) { - context->binaryOpError(@2, ":", $3->getCompleteString(), $5->getCompleteString()); - context->recover(); - $$ = $5; - } + $$ = context->addTernarySelection($1, $3, $5, @2); } ;
diff --git a/src/OpenGL/compiler/glslang_tab.cpp b/src/OpenGL/compiler/glslang_tab.cpp index 9ecc6aa..01272ff 100644 --- a/src/OpenGL/compiler/glslang_tab.cpp +++ b/src/OpenGL/compiler/glslang_tab.cpp
@@ -771,28 +771,28 @@ 388, 398, 408, 430, 431, 432, 433, 441, 442, 446, 450, 458, 459, 462, 468, 469, 473, 480, 481, 484, 487, 490, 496, 497, 500, 506, 507, 514, 515, 522, - 523, 530, 531, 537, 538, 544, 545, 551, 552, 569, - 570, 578, 579, 580, 581, 583, 584, 585, 587, 589, - 591, 593, 598, 601, 612, 620, 628, 655, 661, 668, - 672, 676, 680, 687, 725, 728, 735, 743, 764, 785, - 796, 825, 830, 840, 845, 855, 858, 861, 864, 870, - 877, 880, 884, 888, 893, 898, 905, 909, 913, 917, - 922, 927, 931, 1007, 1017, 1023, 1026, 1032, 1038, 1045, - 1054, 1063, 1066, 1069, 1076, 1080, 1087, 1091, 1096, 1101, - 1111, 1121, 1130, 1140, 1147, 1150, 1153, 1159, 1166, 1169, - 1175, 1178, 1181, 1187, 1190, 1195, 1210, 1214, 1218, 1222, - 1226, 1230, 1235, 1240, 1245, 1250, 1255, 1260, 1265, 1270, - 1275, 1280, 1285, 1290, 1296, 1302, 1308, 1314, 1320, 1326, - 1332, 1338, 1344, 1349, 1354, 1363, 1368, 1373, 1378, 1383, - 1388, 1393, 1398, 1403, 1408, 1413, 1418, 1423, 1428, 1433, - 1446, 1446, 1449, 1449, 1455, 1458, 1474, 1477, 1486, 1490, - 1496, 1503, 1518, 1522, 1526, 1527, 1533, 1534, 1535, 1536, - 1537, 1538, 1539, 1543, 1544, 1544, 1544, 1554, 1555, 1559, - 1559, 1560, 1560, 1565, 1568, 1578, 1581, 1587, 1588, 1592, - 1600, 1604, 1611, 1611, 1618, 1621, 1630, 1635, 1652, 1652, - 1657, 1657, 1664, 1664, 1672, 1675, 1681, 1684, 1690, 1694, - 1701, 1704, 1707, 1710, 1713, 1722, 1726, 1733, 1736, 1742, - 1742 + 523, 530, 531, 537, 538, 544, 545, 551, 552, 558, + 559, 567, 568, 569, 570, 572, 573, 574, 576, 578, + 580, 582, 587, 590, 601, 609, 617, 644, 650, 657, + 661, 665, 669, 676, 714, 717, 724, 732, 753, 774, + 785, 814, 819, 829, 834, 844, 847, 850, 853, 859, + 866, 869, 873, 877, 882, 887, 894, 898, 902, 906, + 911, 916, 920, 996, 1006, 1012, 1015, 1021, 1027, 1034, + 1043, 1052, 1055, 1058, 1065, 1069, 1076, 1080, 1085, 1090, + 1100, 1110, 1119, 1129, 1136, 1139, 1142, 1148, 1155, 1158, + 1164, 1167, 1170, 1176, 1179, 1184, 1199, 1203, 1207, 1211, + 1215, 1219, 1224, 1229, 1234, 1239, 1244, 1249, 1254, 1259, + 1264, 1269, 1274, 1279, 1285, 1291, 1297, 1303, 1309, 1315, + 1321, 1327, 1333, 1338, 1343, 1352, 1357, 1362, 1367, 1372, + 1377, 1382, 1387, 1392, 1397, 1402, 1407, 1412, 1417, 1422, + 1435, 1435, 1438, 1438, 1444, 1447, 1463, 1466, 1475, 1479, + 1485, 1492, 1507, 1511, 1515, 1516, 1522, 1523, 1524, 1525, + 1526, 1527, 1528, 1532, 1533, 1533, 1533, 1543, 1544, 1548, + 1548, 1549, 1549, 1554, 1557, 1567, 1570, 1576, 1577, 1581, + 1589, 1593, 1600, 1600, 1607, 1610, 1619, 1624, 1641, 1641, + 1646, 1646, 1653, 1653, 1661, 1664, 1670, 1673, 1679, 1683, + 1690, 1693, 1696, 1699, 1702, 1711, 1715, 1722, 1725, 1731, + 1731 }; #endif @@ -3026,18 +3026,7 @@ case 68: { - if (context->boolErrorCheck((yylsp[(2) - (5)]), (yyvsp[(1) - (5)].interm.intermTypedNode))) - context->recover(); - - (yyval.interm.intermTypedNode) = context->intermediate.addSelection((yyvsp[(1) - (5)].interm.intermTypedNode), (yyvsp[(3) - (5)].interm.intermTypedNode), (yyvsp[(5) - (5)].interm.intermTypedNode), (yylsp[(2) - (5)])); - if ((yyvsp[(3) - (5)].interm.intermTypedNode)->getType() != (yyvsp[(5) - (5)].interm.intermTypedNode)->getType()) - (yyval.interm.intermTypedNode) = 0; - - if ((yyval.interm.intermTypedNode) == 0) { - context->binaryOpError((yylsp[(2) - (5)]), ":", (yyvsp[(3) - (5)].interm.intermTypedNode)->getCompleteString(), (yyvsp[(5) - (5)].interm.intermTypedNode)->getCompleteString()); - context->recover(); - (yyval.interm.intermTypedNode) = (yyvsp[(5) - (5)].interm.intermTypedNode); - } + (yyval.interm.intermTypedNode) = context->addTernarySelection((yyvsp[(1) - (5)].interm.intermTypedNode), (yyvsp[(3) - (5)].interm.intermTypedNode), (yyvsp[(5) - (5)].interm.intermTypedNode), (yylsp[(2) - (5)])); } break;