Clamped negative index access.

Fixed error that allowed negative index for accessing
vector, matrix, and array. Now we report compile error
and clamp the index to 0.

Re-arranged code around it to handle negative index
at the one location.

BUG=crbug.com/239411
TEST=bug test case
R=aedla@chromium.org, kbr@chromium.org

Review URL: https://codereview.appspot.com/9193045

git-svn-id: http://angleproject.googlecode.com/svn/trunk@2207 736b8ea6-26fd-11df-bfd4-992fa37f6226
diff --git a/src/compiler/glslang.y b/src/compiler/glslang.y
index 4a386ba..6f6700a 100644
--- a/src/compiler/glslang.y
+++ b/src/compiler/glslang.y
@@ -267,53 +267,62 @@
                 context->error(@2, " left of '[' is not of type array, matrix, or vector ", "expression");
             context->recover();
         }
-        if ($1->getType().getQualifier() == EvqConst && $3->getQualifier() == EvqConst) {
-            if ($1->isArray()) { // constant folding for arrays
-                $$ = context->addConstArrayNode($3->getAsConstantUnion()->getIConst(0), $1, @2);
-            } else if ($1->isVector()) {  // constant folding for vectors
-                TVectorFields fields;
-                fields.num = 1;
-                fields.offsets[0] = $3->getAsConstantUnion()->getIConst(0); // need to do it this way because v.xy sends fields integer array
-                $$ = context->addConstVectorNode(fields, $1, @2);
-            } else if ($1->isMatrix()) { // constant folding for matrices
-                $$ = context->addConstMatrixNode($3->getAsConstantUnion()->getIConst(0), $1, @2);
+        if ($3->getQualifier() == EvqConst) {
+            int index = $3->getAsConstantUnion()->getIConst(0);
+            if (index < 0) {
+                std::stringstream infoStream;
+                infoStream << index;
+                std::string info = infoStream.str();
+                context->error(@3, "negative index", info.c_str());
+                context->recover();
+                index = 0;
             }
-        } else {
-            if ($3->getQualifier() == EvqConst) {
-                if (($1->isVector() || $1->isMatrix()) && $1->getType().getNominalSize() <= $3->getAsConstantUnion()->getIConst(0) && !$1->isArray() ) {
+            if ($1->getType().getQualifier() == EvqConst) {
+                if ($1->isArray()) { // constant folding for arrays
+                    $$ = context->addConstArrayNode(index, $1, @2);
+                } else if ($1->isVector()) {  // constant folding for vectors
+                    TVectorFields fields;
+                    fields.num = 1;
+                    fields.offsets[0] = index; // need to do it this way because v.xy sends fields integer array
+                    $$ = context->addConstVectorNode(fields, $1, @2);
+                } else if ($1->isMatrix()) { // constant folding for matrices
+                    $$ = context->addConstMatrixNode(index, $1, @2);
+                }
+            } else {
+                if ($1->isArray()) {
+                    if ($1->getType().getArraySize() == 0) {
+                        if ($1->getType().getMaxArraySize() <= index) {
+                            if (context->arraySetMaxSize($1->getAsSymbolNode(), $1->getTypePointer(), index, true, @2))
+                                context->recover();
+                        } else {
+                            if (context->arraySetMaxSize($1->getAsSymbolNode(), $1->getTypePointer(), 0, false, @2))
+                                context->recover();
+                        }
+                    } else if (index >= $1->getType().getArraySize()) {
+                        std::stringstream extraInfoStream;
+                        extraInfoStream << "array index out of range '" << index << "'";
+                        std::string extraInfo = extraInfoStream.str();
+                        context->error(@2, "", "[", extraInfo.c_str());
+                        context->recover();
+                        index = $1->getType().getArraySize() - 1;
+                    }
+                } else if (($1->isVector() || $1->isMatrix()) && $1->getType().getNominalSize() <= index) {
                     std::stringstream extraInfoStream;
-                    extraInfoStream << "field selection out of range '" << $3->getAsConstantUnion()->getIConst(0) << "'";
+                    extraInfoStream << "field selection out of range '" << index << "'";
                     std::string extraInfo = extraInfoStream.str();
                     context->error(@2, "", "[", extraInfo.c_str());
                     context->recover();
-                } else {
-                    if ($1->isArray()) {
-                        if ($1->getType().getArraySize() == 0) {
-                            if ($1->getType().getMaxArraySize() <= $3->getAsConstantUnion()->getIConst(0)) {
-                                if (context->arraySetMaxSize($1->getAsSymbolNode(), $1->getTypePointer(), $3->getAsConstantUnion()->getIConst(0), true, @2))
-                                    context->recover();
-                            } else {
-                                if (context->arraySetMaxSize($1->getAsSymbolNode(), $1->getTypePointer(), 0, false, @2))
-                                    context->recover();
-                            }
-                        } else if ( $3->getAsConstantUnion()->getIConst(0) >= $1->getType().getArraySize()) {
-                            std::stringstream extraInfoStream;
-                            extraInfoStream << "array index out of range '" << $3->getAsConstantUnion()->getIConst(0) << "'";
-                            std::string extraInfo = extraInfoStream.str();
-                            context->error(@2, "", "[", extraInfo.c_str());
-                            context->recover();
-                        }
-                    }
-                    $$ = context->intermediate.addIndex(EOpIndexDirect, $1, $3, @2);
+                    index =  $1->getType().getNominalSize() - 1;
                 }
-            } else {
-                if ($1->isArray() && $1->getType().getArraySize() == 0) {
-                    context->error(@2, "", "[", "array must be redeclared with a size before being indexed with a variable");
-                    context->recover();
-                }
-
-                $$ = context->intermediate.addIndex(EOpIndexIndirect, $1, $3, @2);
+                $3->getAsConstantUnion()->getUnionArrayPointer()->setIConst(index);
+                $$ = context->intermediate.addIndex(EOpIndexDirect, $1, $3, @2);
             }
+        } else {
+            if ($1->isArray() && $1->getType().getArraySize() == 0) {
+                context->error(@2, "", "[", "array must be redeclared with a size before being indexed with a variable");
+                context->recover();
+            }
+            $$ = context->intermediate.addIndex(EOpIndexIndirect, $1, $3, @2);
         }
         if ($$ == 0) {
             ConstantUnion *unionArray = new ConstantUnion[1];
@@ -327,16 +336,15 @@
 
             if ($1->getType().getQualifier() == EvqConst)
                 $$->getTypePointer()->setQualifier(EvqConst);
-        } else if ($1->isMatrix() && $1->getType().getQualifier() == EvqConst)
-            $$->setType(TType($1->getBasicType(), $1->getPrecision(), EvqConst, $1->getNominalSize()));
-        else if ($1->isMatrix())
-            $$->setType(TType($1->getBasicType(), $1->getPrecision(), EvqTemporary, $1->getNominalSize()));
-        else if ($1->isVector() && $1->getType().getQualifier() == EvqConst)
-            $$->setType(TType($1->getBasicType(), $1->getPrecision(), EvqConst));
-        else if ($1->isVector())
-            $$->setType(TType($1->getBasicType(), $1->getPrecision(), EvqTemporary));
-        else
+        } else if ($1->isMatrix()) {
+            TQualifier qualifier = $1->getType().getQualifier() == EvqConst ? EvqConst : EvqTemporary;
+            $$->setType(TType($1->getBasicType(), $1->getPrecision(), qualifier, $1->getNominalSize()));
+        } else if ($1->isVector()) {
+            TQualifier qualifier = $1->getType().getQualifier() == EvqConst ? EvqConst : EvqTemporary;
+            $$->setType(TType($1->getBasicType(), $1->getPrecision(), qualifier));
+        } else {
             $$->setType($1->getType());
+        }
     }
     | function_call {
         $$ = $1;
diff --git a/src/compiler/glslang_tab.cpp b/src/compiler/glslang_tab.cpp
index 87c6472..10fae97 100644
--- a/src/compiler/glslang_tab.cpp
+++ b/src/compiler/glslang_tab.cpp
@@ -696,26 +696,26 @@
 static const yytype_uint16 yyrline[] =
 {
        0,   187,   187,   188,   191,   227,   230,   243,   248,   253,
-     259,   262,   341,   344,   445,   455,   468,   476,   576,   579,
-     587,   590,   596,   600,   607,   613,   622,   630,   685,   695,
-     698,   708,   718,   739,   740,   741,   746,   747,   756,   768,
-     769,   777,   788,   792,   793,   803,   813,   823,   836,   837,
-     847,   860,   864,   868,   872,   873,   886,   887,   900,   901,
-     914,   915,   932,   933,   946,   947,   948,   949,   950,   954,
-     957,   968,   976,  1003,  1008,  1022,  1059,  1062,  1069,  1077,
-    1098,  1119,  1129,  1157,  1162,  1172,  1177,  1187,  1190,  1193,
-    1196,  1202,  1209,  1212,  1234,  1252,  1276,  1299,  1303,  1321,
-    1329,  1361,  1381,  1470,  1479,  1502,  1505,  1511,  1519,  1527,
-    1535,  1545,  1552,  1555,  1558,  1564,  1567,  1582,  1586,  1590,
-    1594,  1603,  1608,  1613,  1618,  1623,  1628,  1633,  1638,  1643,
-    1648,  1654,  1660,  1666,  1671,  1676,  1685,  1694,  1699,  1712,
-    1712,  1726,  1726,  1735,  1738,  1754,  1790,  1794,  1800,  1807,
-    1822,  1826,  1830,  1831,  1837,  1838,  1839,  1840,  1841,  1845,
-    1846,  1846,  1846,  1856,  1857,  1861,  1861,  1862,  1862,  1867,
-    1870,  1880,  1883,  1889,  1890,  1894,  1902,  1906,  1916,  1921,
-    1938,  1938,  1943,  1943,  1950,  1950,  1958,  1961,  1967,  1970,
-    1976,  1980,  1987,  1994,  2001,  2008,  2019,  2028,  2032,  2039,
-    2042,  2048,  2048
+     259,   262,   349,   352,   453,   463,   476,   484,   584,   587,
+     595,   598,   604,   608,   615,   621,   630,   638,   693,   703,
+     706,   716,   726,   747,   748,   749,   754,   755,   764,   776,
+     777,   785,   796,   800,   801,   811,   821,   831,   844,   845,
+     855,   868,   872,   876,   880,   881,   894,   895,   908,   909,
+     922,   923,   940,   941,   954,   955,   956,   957,   958,   962,
+     965,   976,   984,  1011,  1016,  1030,  1067,  1070,  1077,  1085,
+    1106,  1127,  1137,  1165,  1170,  1180,  1185,  1195,  1198,  1201,
+    1204,  1210,  1217,  1220,  1242,  1260,  1284,  1307,  1311,  1329,
+    1337,  1369,  1389,  1478,  1487,  1510,  1513,  1519,  1527,  1535,
+    1543,  1553,  1560,  1563,  1566,  1572,  1575,  1590,  1594,  1598,
+    1602,  1611,  1616,  1621,  1626,  1631,  1636,  1641,  1646,  1651,
+    1656,  1662,  1668,  1674,  1679,  1684,  1693,  1702,  1707,  1720,
+    1720,  1734,  1734,  1743,  1746,  1762,  1798,  1802,  1808,  1815,
+    1830,  1834,  1838,  1839,  1845,  1846,  1847,  1848,  1849,  1853,
+    1854,  1854,  1854,  1864,  1865,  1869,  1869,  1870,  1870,  1875,
+    1878,  1888,  1891,  1897,  1898,  1902,  1910,  1914,  1924,  1929,
+    1946,  1946,  1951,  1951,  1958,  1958,  1966,  1969,  1975,  1978,
+    1984,  1988,  1995,  2002,  2009,  2016,  2027,  2036,  2040,  2047,
+    2050,  2056,  2056
 };
 #endif
 
@@ -2256,53 +2256,62 @@
                 context->error((yylsp[(2) - (4)]), " left of '[' is not of type array, matrix, or vector ", "expression");
             context->recover();
         }
-        if ((yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getQualifier() == EvqConst && (yyvsp[(3) - (4)].interm.intermTypedNode)->getQualifier() == EvqConst) {
-            if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isArray()) { // constant folding for arrays
-                (yyval.interm.intermTypedNode) = context->addConstArrayNode((yyvsp[(3) - (4)].interm.intermTypedNode)->getAsConstantUnion()->getIConst(0), (yyvsp[(1) - (4)].interm.intermTypedNode), (yylsp[(2) - (4)]));
-            } else if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isVector()) {  // constant folding for vectors
-                TVectorFields fields;
-                fields.num = 1;
-                fields.offsets[0] = (yyvsp[(3) - (4)].interm.intermTypedNode)->getAsConstantUnion()->getIConst(0); // need to do it this way because v.xy sends fields integer array
-                (yyval.interm.intermTypedNode) = context->addConstVectorNode(fields, (yyvsp[(1) - (4)].interm.intermTypedNode), (yylsp[(2) - (4)]));
-            } else if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isMatrix()) { // constant folding for matrices
-                (yyval.interm.intermTypedNode) = context->addConstMatrixNode((yyvsp[(3) - (4)].interm.intermTypedNode)->getAsConstantUnion()->getIConst(0), (yyvsp[(1) - (4)].interm.intermTypedNode), (yylsp[(2) - (4)]));
+        if ((yyvsp[(3) - (4)].interm.intermTypedNode)->getQualifier() == EvqConst) {
+            int index = (yyvsp[(3) - (4)].interm.intermTypedNode)->getAsConstantUnion()->getIConst(0);
+            if (index < 0) {
+                std::stringstream infoStream;
+                infoStream << index;
+                std::string info = infoStream.str();
+                context->error((yylsp[(3) - (4)]), "negative index", info.c_str());
+                context->recover();
+                index = 0;
             }
-        } else {
-            if ((yyvsp[(3) - (4)].interm.intermTypedNode)->getQualifier() == EvqConst) {
-                if (((yyvsp[(1) - (4)].interm.intermTypedNode)->isVector() || (yyvsp[(1) - (4)].interm.intermTypedNode)->isMatrix()) && (yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getNominalSize() <= (yyvsp[(3) - (4)].interm.intermTypedNode)->getAsConstantUnion()->getIConst(0) && !(yyvsp[(1) - (4)].interm.intermTypedNode)->isArray() ) {
+            if ((yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getQualifier() == EvqConst) {
+                if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isArray()) { // constant folding for arrays
+                    (yyval.interm.intermTypedNode) = context->addConstArrayNode(index, (yyvsp[(1) - (4)].interm.intermTypedNode), (yylsp[(2) - (4)]));
+                } else if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isVector()) {  // constant folding for vectors
+                    TVectorFields fields;
+                    fields.num = 1;
+                    fields.offsets[0] = index; // need to do it this way because v.xy sends fields integer array
+                    (yyval.interm.intermTypedNode) = context->addConstVectorNode(fields, (yyvsp[(1) - (4)].interm.intermTypedNode), (yylsp[(2) - (4)]));
+                } else if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isMatrix()) { // constant folding for matrices
+                    (yyval.interm.intermTypedNode) = context->addConstMatrixNode(index, (yyvsp[(1) - (4)].interm.intermTypedNode), (yylsp[(2) - (4)]));
+                }
+            } else {
+                if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isArray()) {
+                    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;
+                        extraInfoStream << "array index out of range '" << index << "'";
+                        std::string extraInfo = extraInfoStream.str();
+                        context->error((yylsp[(2) - (4)]), "", "[", extraInfo.c_str());
+                        context->recover();
+                        index = (yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getArraySize() - 1;
+                    }
+                } else if (((yyvsp[(1) - (4)].interm.intermTypedNode)->isVector() || (yyvsp[(1) - (4)].interm.intermTypedNode)->isMatrix()) && (yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getNominalSize() <= index) {
                     std::stringstream extraInfoStream;
-                    extraInfoStream << "field selection out of range '" << (yyvsp[(3) - (4)].interm.intermTypedNode)->getAsConstantUnion()->getIConst(0) << "'";
+                    extraInfoStream << "field selection out of range '" << index << "'";
                     std::string extraInfo = extraInfoStream.str();
                     context->error((yylsp[(2) - (4)]), "", "[", extraInfo.c_str());
                     context->recover();
-                } else {
-                    if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isArray()) {
-                        if ((yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getArraySize() == 0) {
-                            if ((yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getMaxArraySize() <= (yyvsp[(3) - (4)].interm.intermTypedNode)->getAsConstantUnion()->getIConst(0)) {
-                                if (context->arraySetMaxSize((yyvsp[(1) - (4)].interm.intermTypedNode)->getAsSymbolNode(), (yyvsp[(1) - (4)].interm.intermTypedNode)->getTypePointer(), (yyvsp[(3) - (4)].interm.intermTypedNode)->getAsConstantUnion()->getIConst(0), 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 ( (yyvsp[(3) - (4)].interm.intermTypedNode)->getAsConstantUnion()->getIConst(0) >= (yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getArraySize()) {
-                            std::stringstream extraInfoStream;
-                            extraInfoStream << "array index out of range '" << (yyvsp[(3) - (4)].interm.intermTypedNode)->getAsConstantUnion()->getIConst(0) << "'";
-                            std::string extraInfo = extraInfoStream.str();
-                            context->error((yylsp[(2) - (4)]), "", "[", extraInfo.c_str());
-                            context->recover();
-                        }
-                    }
-                    (yyval.interm.intermTypedNode) = context->intermediate.addIndex(EOpIndexDirect, (yyvsp[(1) - (4)].interm.intermTypedNode), (yyvsp[(3) - (4)].interm.intermTypedNode), (yylsp[(2) - (4)]));
+                    index =  (yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getNominalSize() - 1;
                 }
-            } 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)]));
+                (yyvsp[(3) - (4)].interm.intermTypedNode)->getAsConstantUnion()->getUnionArrayPointer()->setIConst(index);
+                (yyval.interm.intermTypedNode) = context->intermediate.addIndex(EOpIndexDirect, (yyvsp[(1) - (4)].interm.intermTypedNode), (yyvsp[(3) - (4)].interm.intermTypedNode), (yylsp[(2) - (4)]));
             }
+        } 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)]));
         }
         if ((yyval.interm.intermTypedNode) == 0) {
             ConstantUnion *unionArray = new ConstantUnion[1];
@@ -2316,16 +2325,15 @@
 
             if ((yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getQualifier() == EvqConst)
                 (yyval.interm.intermTypedNode)->getTypePointer()->setQualifier(EvqConst);
-        } else if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isMatrix() && (yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getQualifier() == EvqConst)
-            (yyval.interm.intermTypedNode)->setType(TType((yyvsp[(1) - (4)].interm.intermTypedNode)->getBasicType(), (yyvsp[(1) - (4)].interm.intermTypedNode)->getPrecision(), EvqConst, (yyvsp[(1) - (4)].interm.intermTypedNode)->getNominalSize()));
-        else if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isMatrix())
-            (yyval.interm.intermTypedNode)->setType(TType((yyvsp[(1) - (4)].interm.intermTypedNode)->getBasicType(), (yyvsp[(1) - (4)].interm.intermTypedNode)->getPrecision(), EvqTemporary, (yyvsp[(1) - (4)].interm.intermTypedNode)->getNominalSize()));
-        else if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isVector() && (yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getQualifier() == EvqConst)
-            (yyval.interm.intermTypedNode)->setType(TType((yyvsp[(1) - (4)].interm.intermTypedNode)->getBasicType(), (yyvsp[(1) - (4)].interm.intermTypedNode)->getPrecision(), EvqConst));
-        else if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isVector())
-            (yyval.interm.intermTypedNode)->setType(TType((yyvsp[(1) - (4)].interm.intermTypedNode)->getBasicType(), (yyvsp[(1) - (4)].interm.intermTypedNode)->getPrecision(), EvqTemporary));
-        else
+        } else if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isMatrix()) {
+            TQualifier qualifier = (yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getQualifier() == EvqConst ? EvqConst : EvqTemporary;
+            (yyval.interm.intermTypedNode)->setType(TType((yyvsp[(1) - (4)].interm.intermTypedNode)->getBasicType(), (yyvsp[(1) - (4)].interm.intermTypedNode)->getPrecision(), qualifier, (yyvsp[(1) - (4)].interm.intermTypedNode)->getNominalSize()));
+        } else if ((yyvsp[(1) - (4)].interm.intermTypedNode)->isVector()) {
+            TQualifier qualifier = (yyvsp[(1) - (4)].interm.intermTypedNode)->getType().getQualifier() == EvqConst ? EvqConst : EvqTemporary;
+            (yyval.interm.intermTypedNode)->setType(TType((yyvsp[(1) - (4)].interm.intermTypedNode)->getBasicType(), (yyvsp[(1) - (4)].interm.intermTypedNode)->getPrecision(), qualifier));
+        } else {
             (yyval.interm.intermTypedNode)->setType((yyvsp[(1) - (4)].interm.intermTypedNode)->getType());
+        }
     }
     break;