Commit d6b14287 by Olli Etuaho

Move binary op array check to ParseContext

Also piece together an addAssign function in ParseContext that uses the binary op array check. This will make it easier to change the array-related checks in the future to use shaderVersion. Moving validation out from IntermBinary::promote also makes the architecture clearer, promote()'s role should be mainly to determine the type of the return value of the binary operation, not to do validation. BUG=angleproject:941 TEST=angle_unittests, WebGL conformance tests Change-Id: If1de33ea250893527be7f0d7930d4678a0864684 Reviewed-on: https://chromium-review.googlesource.com/260571Reviewed-by: 's avatarJamie Madill <jmadill@chromium.org> Tested-by: 's avatarOlli Etuaho <oetuaho@nvidia.com>
parent b2983c95
......@@ -388,12 +388,7 @@ bool TIntermUnary::promote(TInfoSink &)
bool TIntermBinary::promote(TInfoSink &infoSink)
{
// This function only handles scalars, vectors, and matrices.
if (mLeft->isArray() || mRight->isArray())
{
infoSink.info.message(EPrefixInternalError, getLine(),
"Invalid operation for arrays");
return false;
}
ASSERT(!mLeft->isArray() && !mRight->isArray());
// GLSL ES 2.0 does not support implicit type casting.
// So the basic type should usually match.
......
......@@ -1198,7 +1198,7 @@ bool TParseContext::executeInitializer(const TSourceLoc& line, const TString& id
if (qualifier != EvqConst) {
TIntermSymbol* intermSymbol = intermediate.addSymbol(variable->getUniqueId(), variable->getName(), variable->getType(), line);
intermNode = intermediate.addAssign(EOpInitialize, intermSymbol, initializer, line);
intermNode = createAssign(EOpInitialize, intermSymbol, initializer, line);
if (intermNode == 0) {
assignError(line, "=", intermSymbol->getCompleteString(), initializer->getCompleteString());
return true;
......@@ -2716,21 +2716,34 @@ TIntermTyped *TParseContext::addUnaryMathLValue(TOperator op, TIntermTyped *chil
return addUnaryMath(op, child, loc);
}
bool TParseContext::binaryOpArrayCheck(TOperator op, TIntermTyped *left, TIntermTyped *right,
const TSourceLoc &loc)
{
if (left->isArray() || right->isArray())
{
error(loc, "Invalid operation for arrays", GetOperatorString(op));
return false;
}
return true;
}
TIntermTyped *TParseContext::addBinaryMathInternal(TOperator op, TIntermTyped *left, TIntermTyped *right,
const TSourceLoc &loc)
{
if (!binaryOpArrayCheck(op, left, right, loc))
return nullptr;
switch (op)
{
case EOpEqual:
case EOpNotEqual:
if (left->isArray())
return nullptr;
break;
case EOpLessThan:
case EOpGreaterThan:
case EOpLessThanEqual:
case EOpGreaterThanEqual:
if (left->isMatrix() || left->isArray() || left->isVector() ||
ASSERT(!left->isArray() && !right->isArray());
if (left->isMatrix() || left->isVector() ||
left->getBasicType() == EbtStruct)
{
return nullptr;
......@@ -2739,8 +2752,9 @@ TIntermTyped *TParseContext::addBinaryMathInternal(TOperator op, TIntermTyped *l
case EOpLogicalOr:
case EOpLogicalXor:
case EOpLogicalAnd:
ASSERT(!left->isArray() && !right->isArray());
if (left->getBasicType() != EbtBool ||
left->isMatrix() || left->isArray() || left->isVector())
left->isMatrix() || left->isVector())
{
return nullptr;
}
......@@ -2749,12 +2763,14 @@ TIntermTyped *TParseContext::addBinaryMathInternal(TOperator op, TIntermTyped *l
case EOpSub:
case EOpDiv:
case EOpMul:
ASSERT(!left->isArray() && !right->isArray());
if (left->getBasicType() == EbtStruct || left->getBasicType() == EbtBool)
{
return nullptr;
}
break;
case EOpIMod:
ASSERT(!left->isArray() && !right->isArray());
// Note that this is only for the % operator, not for mod()
if (left->getBasicType() == EbtStruct || left->getBasicType() == EbtBool || left->getBasicType() == EbtFloat)
{
......@@ -2804,6 +2820,29 @@ TIntermTyped *TParseContext::addBinaryMathBooleanResult(TOperator op, TIntermTyp
return node;
}
TIntermTyped *TParseContext::createAssign(TOperator op, TIntermTyped *left, TIntermTyped *right,
const TSourceLoc &loc)
{
if (binaryOpArrayCheck(op, left, right, loc))
{
return intermediate.addAssign(op, left, right, loc);
}
return nullptr;
}
TIntermTyped *TParseContext::addAssign(TOperator op, TIntermTyped *left, TIntermTyped *right,
const TSourceLoc &loc)
{
TIntermTyped *node = createAssign(op, left, right, loc);
if (node == nullptr)
{
assignError(loc, "assign", left->getCompleteString(), right->getCompleteString());
recover();
return left;
}
return node;
}
TIntermBranch *TParseContext::addBranch(TOperator op, const TSourceLoc &loc)
{
switch (op)
......
......@@ -177,6 +177,8 @@ struct TParseContext {
const TSourceLoc &);
TIntermTyped *addBinaryMathBooleanResult(TOperator op, TIntermTyped *left, TIntermTyped *right,
const TSourceLoc &);
TIntermTyped *addAssign(TOperator op, TIntermTyped *left, TIntermTyped *right,
const TSourceLoc &loc);
TIntermBranch *addBranch(TOperator op, const TSourceLoc &loc);
TIntermBranch *addBranch(TOperator op, TIntermTyped *returnValue, const TSourceLoc &loc);
......@@ -187,6 +189,12 @@ struct TParseContext {
private:
TIntermTyped *addBinaryMathInternal(TOperator op, TIntermTyped *left, TIntermTyped *right,
const TSourceLoc &loc);
TIntermTyped *createAssign(TOperator op, TIntermTyped *left, TIntermTyped *right,
const TSourceLoc &loc);
// Return true if array-related checks pass
bool binaryOpArrayCheck(TOperator op, TIntermTyped *left, TIntermTyped *right,
const TSourceLoc &loc);
};
int PaParseStrings(size_t count, const char* const string[], const int length[],
......
......@@ -536,12 +536,7 @@ assignment_expression
| unary_expression assignment_operator assignment_expression {
if (context->lValueErrorCheck(@2, "assign", $1))
context->recover();
$$ = context->intermediate.addAssign($2.op, $1, $3, @2);
if ($$ == 0) {
context->assignError(@2, "assign", $1->getCompleteString(), $3->getCompleteString());
context->recover();
$$ = $1;
}
$$ = context->addAssign($2.op, $1, $3, @2);
}
;
......
......@@ -696,27 +696,27 @@ static const yytype_uint16 yyrline[] =
411, 414, 417, 424, 425, 428, 434, 435, 439, 446,
447, 450, 453, 456, 462, 463, 466, 472, 473, 480,
481, 488, 489, 496, 497, 503, 504, 510, 511, 517,
518, 535, 536, 549, 550, 551, 552, 556, 557, 558,
562, 566, 570, 574, 581, 584, 595, 603, 611, 638,
644, 655, 659, 663, 667, 674, 730, 733, 740, 748,
769, 790, 800, 828, 833, 843, 848, 858, 861, 864,
867, 873, 880, 883, 887, 891, 895, 902, 906, 910,
917, 921, 925, 932, 941, 947, 950, 956, 962, 969,
978, 987, 995, 998, 1005, 1009, 1016, 1019, 1023, 1027,
1036, 1045, 1053, 1063, 1075, 1078, 1081, 1087, 1094, 1097,
1103, 1106, 1109, 1115, 1118, 1133, 1137, 1141, 1145, 1149,
1153, 1158, 1163, 1168, 1173, 1178, 1183, 1188, 1193, 1198,
1203, 1208, 1213, 1218, 1223, 1228, 1233, 1238, 1243, 1248,
1253, 1258, 1262, 1266, 1270, 1274, 1278, 1282, 1286, 1290,
1294, 1298, 1302, 1306, 1310, 1314, 1318, 1326, 1334, 1338,
1351, 1351, 1354, 1354, 1360, 1363, 1379, 1382, 1391, 1395,
1401, 1408, 1423, 1427, 1431, 1432, 1438, 1439, 1440, 1441,
1442, 1443, 1444, 1448, 1449, 1449, 1449, 1459, 1460, 1464,
1464, 1465, 1465, 1470, 1473, 1483, 1486, 1492, 1493, 1497,
1505, 1509, 1516, 1516, 1523, 1526, 1533, 1538, 1555, 1555,
1560, 1560, 1567, 1567, 1575, 1578, 1584, 1587, 1593, 1597,
1604, 1607, 1610, 1613, 1616, 1625, 1629, 1636, 1639, 1645,
1645
518, 535, 536, 544, 545, 546, 547, 551, 552, 553,
557, 561, 565, 569, 576, 579, 590, 598, 606, 633,
639, 650, 654, 658, 662, 669, 725, 728, 735, 743,
764, 785, 795, 823, 828, 838, 843, 853, 856, 859,
862, 868, 875, 878, 882, 886, 890, 897, 901, 905,
912, 916, 920, 927, 936, 942, 945, 951, 957, 964,
973, 982, 990, 993, 1000, 1004, 1011, 1014, 1018, 1022,
1031, 1040, 1048, 1058, 1070, 1073, 1076, 1082, 1089, 1092,
1098, 1101, 1104, 1110, 1113, 1128, 1132, 1136, 1140, 1144,
1148, 1153, 1158, 1163, 1168, 1173, 1178, 1183, 1188, 1193,
1198, 1203, 1208, 1213, 1218, 1223, 1228, 1233, 1238, 1243,
1248, 1253, 1257, 1261, 1265, 1269, 1273, 1277, 1281, 1285,
1289, 1293, 1297, 1301, 1305, 1309, 1313, 1321, 1329, 1333,
1346, 1346, 1349, 1349, 1355, 1358, 1374, 1377, 1386, 1390,
1396, 1403, 1418, 1422, 1426, 1427, 1433, 1434, 1435, 1436,
1437, 1438, 1439, 1443, 1444, 1444, 1444, 1454, 1455, 1459,
1459, 1460, 1460, 1465, 1468, 1478, 1481, 1487, 1488, 1492,
1500, 1504, 1511, 1511, 1518, 1521, 1528, 1533, 1550, 1550,
1555, 1555, 1562, 1562, 1570, 1573, 1579, 1582, 1588, 1592,
1599, 1602, 1605, 1608, 1611, 1620, 1624, 1631, 1634, 1640,
1640
};
#endif
......@@ -2897,12 +2897,7 @@ yyreduce:
{
if (context->lValueErrorCheck((yylsp[-1]), "assign", (yyvsp[-2].interm.intermTypedNode)))
context->recover();
(yyval.interm.intermTypedNode) = context->intermediate.addAssign((yyvsp[-1].interm).op, (yyvsp[-2].interm.intermTypedNode), (yyvsp[0].interm.intermTypedNode), (yylsp[-1]));
if ((yyval.interm.intermTypedNode) == 0) {
context->assignError((yylsp[-1]), "assign", (yyvsp[-2].interm.intermTypedNode)->getCompleteString(), (yyvsp[0].interm.intermTypedNode)->getCompleteString());
context->recover();
(yyval.interm.intermTypedNode) = (yyvsp[-2].interm.intermTypedNode);
}
(yyval.interm.intermTypedNode) = context->addAssign((yyvsp[-1].interm).op, (yyvsp[-2].interm.intermTypedNode), (yyvsp[0].interm.intermTypedNode), (yylsp[-1]));
}
break;
......
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