CVE-2023-46046 (C++, published 2024-03-27T05:15Z)
Description: value: An issue in MiniZinc before 2.8.0 allows a NULL pointer dereference via ti_expr in a crafted .mzn file. NOTE: this is disputed because there is no common libminizinc use case in which an unattended process is supposed to run forever to process a series of atttacker-controlled .mzn files.
Severity: nan (CVSS v3 base score: )
Weakness: NVD-CWE-noinfo \u2014 Insufficient Information
There is insufficient information about the issue to classify it; details are unkown or unspecified.
Repository: https://github.com/MiniZinc/libminizinc
Files changed:
changes.rst
lib/cached/md5_cached.cmake
lib/cached/minizinc/parser.tab.hh
lib/cached/parser.tab.cpp
lib/parser.yxx
tests/spec/unit/regression/github_730.mzn
Commit message: Fix missing nullptr check in ti_expr in the parser

Resolves #730 on GitHub


Vulnerable code:
set(parser_yxx_md5_cached "a1a3ad0d5717f0cc50417099ff2ae02f")
/* A Bison parser, made by GNU Bison 3.7.6.  */
#ifndef YY_MZN_YY_USERS_GUIDOT_PROGRAMMING_MINIZINC_LIBMZN_BUILD_XCODE_INCLUDE_MINIZINC_PARSER_TAB_HH_INCLUDED
# define YY_MZN_YY_USERS_GUIDOT_PROGRAMMING_MINIZINC_LIBMZN_BUILD_XCODE_INCLUDE_MINIZINC_PARSER_TAB_HH_INCLUDED
#endif /* !YY_MZN_YY_USERS_GUIDOT_PROGRAMMING_MINIZINC_LIBMZN_BUILD_XCODE_INCLUDE_MINIZINC_PARSER_TAB_HH_INCLUDED  */
/* A Bison parser, made by GNU Bison 3.7.6.  */
#define YYBISON 30706
#define YYBISON_VERSION "3.7.6"
#if defined __GNUC__ && ! defined __ICC && 407 <= __GNUC__ * 100 + __GNUC_MINOR__
# define YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN                            \
  /* YYRLINE[YYN] -- Source line where rule number YYN was defined.  */
     852,   856,   858,   862,   863,   869,   876,   888,   891,   900,
     912,   925,   933,   943,   956,   970,   974,   979,   980,   984,
     986,   988,   990,   992,   994,  1001,  1011,  1013,  1018,  1024,
    1027,  1029,  1033,  1035,  1037,  1039,  1041,  1044,  1047,  1049,
    1055,  1056,  1058,  1060,  1062,  1064,  1073,  1075,  1077,  1079,
    1081,  1083,  1085,  1087,  1089,  1091,  1093,  1095,  1097,  1099,
    1101,  1110,  1112,  1114,  1116,  1118,  1120,  1122,  1124,  1126,
    1128,  1130,  1132,  1134,  1139,  1144,  1149,  1154,  1159,  1164,
    1169,  1175,  1181,  1183,  1196,  1197,  1199,  1201,  1203,  1205,
    1207,  1209,  1211,  1213,  1215,  1217,  1219,  1221,  1223,  1225,
    1227,  1229,  1231,  1233,  1235,  1244,  1246,  1248,  1250,  1252,
    1254,  1256,  1258,  1260,  1262,  1264,  1266,  1268,  1270,  1272,
    1281,  1283,  1285,  1287,  1289,  1291,  1293,  1295,  1297,  1299,
    1301,  1303,  1305,  1307,  1312,  1317,  1322,  1327,  1332,  1337,
    1342,  1347,  1353,  1355,  1362,  1374,  1376,  1380,  1382,  1384,
    1386,  1388,  1390,  1393,  1395,  1398,  1400,  1403,  1405,  1408,
    1410,  1412,  1414,  1416,  1418,  1420,  1422,  1424,  1426,  1428,
    1429,  1432,  1434,  1437,  1438,  1441,  1443,  1446,  1447,  1450,
    1452,  1455,  1456,  1459,  1461,  1464,  1465,  1468,  1470,  1473,
    1474,  1477,  1479,  1482,  1483,  1484,  1487,  1488,  1491,  1492,
    1495,  1497,  1500,  1501,  1504,  1506,  1511,  1513,  1519,  1524,
    1532,  1541,  1547,  1556,  1565,  1567,  1572,  1577,  1591,  1599,
    1601,  1605,  1612,  1618,  1621,  1624,  1626,  1628,  1634,  1636,
    1638,  1646,  1648,  1651,  1654,  1657,  1659,  1661,  1663,  1667,
    1669,  1716,  1718,  1779,  1819,  1822,  1827,  1834,  1839,  1842,
    1845,  1855,  1867,  1878,  1881,  1885,  1896,  1907,  1926,  1933,
    1937,  1940,  1944,  1955,  1975,  1982,  1998,  1999,  2003,  2005,
    2007,  2009,  2011,  2013,  2015,  2017,  2019,  2021,  2023,  2025,
    2027,  2029,  2031,  2033,  2035,  2037,  2039,  2041,  2043,  2045,
    2047,  2049,  2051,  2053,  2055,  2057,  2061,  2069,  2101,  2103,
    2105,  2106,  2126,  2180,  2200,  2255,  2258,  2264,  2270,  2272,
    2276,  2278,  2285,  2294,  2296,  2304,  2306,  2315,  2315,  2318,
    2326,  2337,  2338,  2341,  2343,  2345,  2349,  2353,  2357,  2359,
    2361,  2363,  2365,  2367,  2369,  2371,  2373,  2375,  2377,  2379,
    2381,  2383,  2385,  2387,  2389,  2391,  2393,  2395,  2397,  2399,
    2401,  2403,  2405,  2407,  2409,  2411,  2413,  2415,  2417,  2419,
    2421,  2423
#ifdef YYPRINT
/* YYTOKNUM[NUM] -- (External) token number corresponding to the
   (internal) symbol number NUM (which must be that of a token).  */
static const yytype_int16 yytoknum[] =
{
       0,   256,   257,   258,   259,   260,   261,   262,   263,   264,
     265,   266,   267,   268,   269,   270,   271,   272,   273,   274,
     275,   276,   277,   278,   279,   280,   281,   282,   283,   284,
     285,   286,   287,   288,   289,   290,   291,   292,   293,   294,
     295,   296,   297,   298,   299,   300,   301,   302,   303,   304,
     305,   306,   307,   308,   309,   310,   311,   312,   313,   314,
     315,   316,   317,   318,   319,   320,   321,   322,   323,   324,
     325,   326,   327,   328,   329,   330,   331,   332,   333,   334,
     335,   336,   337,   338,   339,   340,   341,   342,   343,   344,
     345,   346,   347,   348,   349,   350,   351,   352,   353,   354,
     355,   356,   357,   358,   359,   360,   361,   362,   363,   364,
     365,   366,   367,   368,   369,   370,   371,   372,   373,   374,
     375,   376,   377,   378,   379,   380,   381,   382,   383,   384,
     385,   386,   387,   388,   389,   390,   391,   392,   393,   394,
     395,   396,   397,   398,    59,   123,   125,    40,    41,    44,
      58,   124
};
#endif

  /* YYPACT[STATE-NUM] -- Index in YYTABLE of the portion describing
     STATE-NUM.  */
  /* YYDEFACT[STATE-NUM] -- Default reduction number in state STATE-NUM.
     Performed when YYTABLE does not specify something else to do.  Zero
     means the default is an error.  */
  /* YYPGOTO[NTERM-NUM].  */
  /* YYDEFGOTO[NTERM-NUM].  */
  /* YYTABLE[YYPACT[STATE-NUM]] -- What to do in state STATE-NUM.  If
     positive, shift that token.  If negative, reduce the rule whose
     number is the opposite.  If YYTABLE_NINF, syntax error.  */
  /* YYSTOS[STATE-NUM] -- The (internal number of the) accessing
     symbol of state STATE-NUM.  */
  /* YYR1[YYN] -- Symbol number of symbol that rule YYN derives.  */
  /* YYR2[YYN] -- Number of symbols on the right hand side of rule YYN.  */
/* YY_LOCATION_PRINT -- Print the location on the stream.
# ifndef YY_LOCATION_PRINT
#  if defined YYLTYPE_IS_TRIVIAL && YYLTYPE_IS_TRIVIAL
 }
#   define YY_LOCATION_PRINT(File, Loc)          \
  yy_location_print_ (File, &(Loc))
#   define YY_LOCATION_PRINT(File, Loc) ((void) 0)
# endif /* !defined YY_LOCATION_PRINT */
# ifdef YYPRINT
  if (yykind < YYNTOKENS)
    YYPRINT (yyo, yytoknum[yykind], *yyvaluep);
# endif
  YY_LOCATION_PRINT (yyo, *yylocationp);
    goto yyexhaustedlab;
        goto yyexhaustedlab;
          goto yyexhaustedlab;
        if ((yyval.tiexpr) && (yyvsp[-3].tiexprs)) (yyval.tiexpr)->setRanges(*(yyvsp[-3].tiexprs));
        if ((yyval.tiexpr)) (yyval.tiexpr)->setRanges(ti);
        Type tt = Expression::type((yyval.tiexpr));
        tt.dim(0);
        TypeInst* lhs = new TypeInst((yyloc), tt, (yyvsp[-2].tiexpr)->domain());
        BinOp* bop = new BinOp((yyloc), lhs, BOT_PLUSPLUS, (yyvsp[0].tiexpr));
        bop->type(tt);
        (yyval.tiexpr)->domain(bop);
        if ((yyval.tiexpr)) {
        if ((yyval.tiexpr)) {
        Type tt = Expression::type((yyval.tiexpr));
        if ((yyval.tiexpr)) {
        if ((yyval.tiexpr)) {
        if ((yyval.tiexpr)) {
        if ((yyval.tiexpr)) {
        if ((yyval.tiexpr)) {
          goto yyexhaustedlab;
  goto yyreturn;
  goto yyreturn;
#if 1
/*-------------------------------------------------.
| yyexhaustedlab -- memory exhaustion comes here.  |
`-------------------------------------------------*/
  goto yyreturn;
#endif
/*-------------------------------------------------------.
| yyreturn -- parsing is finished, clean up and return.  |
`-------------------------------------------------------*/
yyreturn:
        if ($$ && $3) $$->setRanges(*$3);
        if ($$) $$->setRanges(ti);
        Type tt = Expression::type($$);
        tt.dim(0);
        TypeInst* lhs = new TypeInst(@$, tt, $1->domain());
        BinOp* bop = new BinOp(@$, lhs, BOT_PLUSPLUS, $3);
        bop->type(tt);
        $$->domain(bop);
        if ($$) {
        if ($$) {
        Type tt = Expression::type($$);
        if ($$) {
        if ($$) {
        if ($$) {
        if ($$) {
        if ($$) {

Fixed code:
-  Fix a problem in the parser where a nullptr would be used before a syntax
   error was thrown (:bugref:`730`).
set(parser_yxx_md5_cached "a49d72232e30c06667be4eb862bc67eb")
/* A Bison parser, made by GNU Bison 3.8.2.  */
#ifndef YY_MZN_YY_USERS_DEKKER1_LIBRARY_MOBILE_DOCUMENTS_COM_APPLE_CLOUDDOCS_CODE_GITHUB_COM_MINIZINC_LIBMINIZINC_BUILD_NOSYNC_INCLUDE_MINIZINC_PARSER_TAB_HH_INCLUDED
# define YY_MZN_YY_USERS_DEKKER1_LIBRARY_MOBILE_DOCUMENTS_COM_APPLE_CLOUDDOCS_CODE_GITHUB_COM_MINIZINC_LIBMINIZINC_BUILD_NOSYNC_INCLUDE_MINIZINC_PARSER_TAB_HH_INCLUDED


#endif /* !YY_MZN_YY_USERS_DEKKER1_LIBRARY_MOBILE_DOCUMENTS_COM_APPLE_CLOUDDOCS_CODE_GITHUB_COM_MINIZINC_LIBMINIZINC_BUILD_NOSYNC_INCLUDE_MINIZINC_PARSER_TAB_HH_INCLUDED  */
/* A Bison parser, made by GNU Bison 3.8.2.  */
#define YYBISON 30802
#define YYBISON_VERSION "3.8.2"
#if defined __GNUC__ && ! defined __ICC && 406 <= __GNUC__ * 100 + __GNUC_MINOR__
# if __GNUC__ * 100 + __GNUC_MINOR__ < 407
#  define YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN                           \
    _Pragma ("GCC diagnostic push")                                     \
    _Pragma ("GCC diagnostic ignored \"-Wuninitialized\"")
# else
#  define YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN                           \
# endif
/* YYRLINE[YYN] -- Source line where rule number YYN was defined.  */
     852,   856,   858,   862,   863,   871,   880,   894,   897,   906,
     918,   931,   939,   949,   962,   976,   980,   985,   986,   990,
     992,   994,   996,   998,  1000,  1007,  1017,  1019,  1024,  1030,
    1033,  1035,  1039,  1041,  1043,  1045,  1047,  1050,  1053,  1055,
    1061,  1062,  1064,  1066,  1068,  1070,  1079,  1081,  1083,  1085,
    1087,  1089,  1091,  1093,  1095,  1097,  1099,  1101,  1103,  1105,
    1107,  1116,  1118,  1120,  1122,  1124,  1126,  1128,  1130,  1132,
    1134,  1136,  1138,  1140,  1145,  1150,  1155,  1160,  1165,  1170,
    1175,  1181,  1187,  1189,  1202,  1203,  1205,  1207,  1209,  1211,
    1213,  1215,  1217,  1219,  1221,  1223,  1225,  1227,  1229,  1231,
    1233,  1235,  1237,  1239,  1241,  1250,  1252,  1254,  1256,  1258,
    1260,  1262,  1264,  1266,  1268,  1270,  1272,  1274,  1276,  1278,
    1287,  1289,  1291,  1293,  1295,  1297,  1299,  1301,  1303,  1305,
    1307,  1309,  1311,  1313,  1318,  1323,  1328,  1333,  1338,  1343,
    1348,  1353,  1359,  1361,  1368,  1380,  1382,  1386,  1388,  1390,
    1392,  1394,  1396,  1399,  1401,  1404,  1406,  1409,  1411,  1414,
    1416,  1418,  1420,  1422,  1424,  1426,  1428,  1430,  1432,  1434,
    1435,  1438,  1440,  1443,  1444,  1447,  1449,  1452,  1453,  1456,
    1458,  1461,  1462,  1465,  1467,  1470,  1471,  1474,  1476,  1479,
    1480,  1483,  1485,  1488,  1489,  1490,  1493,  1494,  1497,  1498,
    1501,  1503,  1506,  1507,  1510,  1512,  1517,  1519,  1525,  1530,
    1538,  1547,  1553,  1562,  1571,  1573,  1578,  1583,  1597,  1605,
    1607,  1611,  1618,  1624,  1627,  1630,  1632,  1634,  1640,  1642,
    1644,  1652,  1654,  1657,  1660,  1663,  1665,  1667,  1669,  1673,
    1675,  1722,  1724,  1785,  1825,  1828,  1833,  1840,  1845,  1848,
    1851,  1861,  1873,  1884,  1887,  1891,  1902,  1913,  1932,  1939,
    1943,  1946,  1950,  1961,  1981,  1988,  2004,  2005,  2009,  2011,
    2013,  2015,  2017,  2019,  2021,  2023,  2025,  2027,  2029,  2031,
    2033,  2035,  2037,  2039,  2041,  2043,  2045,  2047,  2049,  2051,
    2053,  2055,  2057,  2059,  2061,  2063,  2067,  2075,  2107,  2109,
    2111,  2112,  2132,  2186,  2206,  2261,  2264,  2270,  2276,  2278,
    2282,  2284,  2291,  2300,  2302,  2310,  2312,  2321,  2321,  2324,
    2332,  2343,  2344,  2347,  2349,  2351,  2355,  2359,  2363,  2365,
    2367,  2369,  2371,  2373,  2375,  2377,  2379,  2381,  2383,  2385,
    2387,  2389,  2391,  2393,  2395,  2397,  2399,  2401,  2403,  2405,
    2407,  2409,  2411,  2413,  2415,  2417,  2419,  2421,  2423,  2425,
    2427,  2429
/* YYPACT[STATE-NUM] -- Index in YYTABLE of the portion describing
   STATE-NUM.  */
/* YYDEFACT[STATE-NUM] -- Default reduction number in state STATE-NUM.
   Performed when YYTABLE does not specify something else to do.  Zero
   means the default is an error.  */
/* YYPGOTO[NTERM-NUM].  */
/* YYDEFGOTO[NTERM-NUM].  */
/* YYTABLE[YYPACT[STATE-NUM]] -- What to do in state STATE-NUM.  If
   positive, shift that token.  If negative, reduce the rule whose
   number is the opposite.  If YYTABLE_NINF, syntax error.  */
/* YYSTOS[STATE-NUM] -- The symbol kind of the accessing symbol of
   state STATE-NUM.  */
/* YYR1[RULE-NUM] -- Symbol kind of the left-hand side of rule RULE-NUM.  */
/* YYR2[RULE-NUM] -- Number of symbols on the right-hand side of rule RULE-NUM.  */
#define YYNOMEM         goto yyexhaustedlab
/* YYLOCATION_PRINT -- Print the location on the stream.
# ifndef YYLOCATION_PRINT

#  if defined YY_LOCATION_PRINT

   /* Temporary convenience wrapper in case some people defined the
      undocumented and private YY_LOCATION_PRINT macros.  */
#   define YYLOCATION_PRINT(File, Loc)  YY_LOCATION_PRINT(File, *(Loc))

#  elif defined YYLTYPE_IS_TRIVIAL && YYLTYPE_IS_TRIVIAL
}

#   define YYLOCATION_PRINT  yy_location_print_
    /* Temporary convenience wrapper in case some people defined the
       undocumented and private YY_LOCATION_PRINT macros.  */
#   define YY_LOCATION_PRINT(File, Loc)  YYLOCATION_PRINT(File, &(Loc))

#   define YYLOCATION_PRINT(File, Loc) ((void) 0)
    /* Temporary convenience wrapper in case some people defined the
       undocumented and private YY_LOCATION_PRINT macros.  */
#   define YY_LOCATION_PRINT  YYLOCATION_PRINT

# endif /* !defined YYLOCATION_PRINT */
  YYLOCATION_PRINT (yyo, yylocationp);

    YYNOMEM;
        YYNOMEM;
          YYNOMEM;

        if ((yyval.tiexpr) != nullptr && (yyvsp[-3].tiexprs) != nullptr) {
          (yyval.tiexpr)->setRanges(*(yyvsp[-3].tiexprs));
        }
        if ((yyval.tiexpr) != nullptr){
          (yyval.tiexpr)->setRanges(ti);
        }
        if ((yyval.tiexpr) != nullptr) {
          Type tt = Expression::type((yyval.tiexpr));
          tt.dim(0);
          TypeInst* lhs = new TypeInst((yyloc), tt, (yyvsp[-2].tiexpr)->domain());
          BinOp* bop = new BinOp((yyloc), lhs, BOT_PLUSPLUS, (yyvsp[0].tiexpr));
          bop->type(tt);
          (yyval.tiexpr)->domain(bop);
        }
        if ((yyval.tiexpr) != nullptr) {
        if ((yyval.tiexpr) != nullptr) {
        if ((yyval.tiexpr) != nullptr) {
          Type tt = Expression::type((yyval.tiexpr));
        if ((yyval.tiexpr) != nullptr) {
        if ((yyval.tiexpr) != nullptr) {
        if ((yyval.tiexpr) != nullptr) {
        if ((yyval.tiexpr) != nullptr) {
          YYNOMEM;
  ++yynerrs;
  goto yyreturnlab;
  goto yyreturnlab;
/*-----------------------------------------------------------.
| yyexhaustedlab -- YYNOMEM (memory exhaustion) comes here.  |
`-----------------------------------------------------------*/
  goto yyreturnlab;
/*----------------------------------------------------------.
| yyreturnlab -- parsing is finished, clean up and return.  |
`----------------------------------------------------------*/
yyreturnlab:
        if ($$ != nullptr && $3 != nullptr) {
          $$->setRanges(*$3);
        }
        if ($$ != nullptr){
          $$->setRanges(ti);
        }
        if ($$ != nullptr) {
          Type tt = Expression::type($$);
          tt.dim(0);
          TypeInst* lhs = new TypeInst(@$, tt, $1->domain());
          BinOp* bop = new BinOp(@$, lhs, BOT_PLUSPLUS, $3);
          bop->type(tt);
          $$->domain(bop);
        }
        if ($$ != nullptr) {
        if ($$ != nullptr) {
        if ($$ != nullptr) {
          Type tt = Expression::type($$);
        if ($$ != nullptr) {
        if ($$ != nullptr) {
        if ($$ != nullptr) {
        if ($$ != nullptr) {
/***
!Test
solvers: [gecode]
expected:
- !Error
  type: SyntaxError
type: compile
***/

/** @group stdlib.output Create string to visualise a 2D boolean array \a !9Mã™a checkered board. */
function string: show_array2d_bool(array[int,int] of var bool: x) ::output_only;
function string: show_array2d_bool(array[int,int] of bool: x) =
	if length(x) != 0 then
		let {
			int: one_digits!9Mã™a checkered board. */
function string: show_array2d_bool(array[int,int] of var bool: x) ::output_only;
function string: show_array2d_bool(array[intt(q in 1..one_digits)(" ") ++ " "
			++ concat(j in index_set_2of2(x))(
				let {
					int: digit = (j div pow(10, two_digits - i)) mod 10;
				} in if digit != 0 \/ j > pow(10, two_digits - i) then show (digit) else " " endif
			)
			++ "\n"
		) ++
		concat(i in index_set_1of2(x))(
			concat(q in 1..(one_digits - (floor(log10(i)) + 1)))(" ")
			++ "\(i) "
			++ concat(j in index_set_2of2(x))(if x[i,j] then "‚ñà" else " " endif)
			++ "\n"
		)
	endif;