1From c846986356fc149915a74972bf198abc266bc2c0 Mon Sep 17 00:00:00 2001 2From: Nick Wellnhofer <wellnhofer@aevum.de> 3Date: Thu, 25 Aug 2022 17:43:08 +0200 4Subject: [PATCH] [CVE-2022-40303] Fix integer overflows with XML_PARSE_HUGE 5 6Also impose size limits when XML_PARSE_HUGE is set. Limit size of names 7to XML_MAX_TEXT_LENGTH (10 million bytes) and other content to 8XML_MAX_HUGE_LENGTH (1 billion bytes). 9 10Move some the length checks to the end of the respective loop to make 11them strict. 12 13xmlParseEntityValue didn't have a length limitation at all. But without 14XML_PARSE_HUGE, this should eventually trigger an error in xmlGROW. 15 16Thanks to Maddie Stone working with Google Project Zero for the report! 17--- 18 parser.c | 233 +++++++++++++++++++++++++++++-------------------------- 19 1 file changed, 121 insertions(+), 112 deletions(-) 20 21diff --git a/parser.c b/parser.c 22index 93f031be..79479979 100644 23--- a/parser.c 24+++ b/parser.c 25@@ -102,6 +102,8 @@ xmlParseElementEnd(xmlParserCtxtPtr ctxt); 26 * * 27 ************************************************************************/ 28 29+#define XML_MAX_HUGE_LENGTH 1000000000 30+ 31 #define XML_PARSER_BIG_ENTITY 1000 32 #define XML_PARSER_LOT_ENTITY 5000 33 34@@ -552,7 +554,7 @@ xmlFatalErr(xmlParserCtxtPtr ctxt, xmlParserErrors error, const char *info) 35 errmsg = "Malformed declaration expecting version"; 36 break; 37 case XML_ERR_NAME_TOO_LONG: 38- errmsg = "Name too long use XML_PARSE_HUGE option"; 39+ errmsg = "Name too long"; 40 break; 41 #if 0 42 case: 43@@ -3202,6 +3204,9 @@ xmlParseNameComplex(xmlParserCtxtPtr ctxt) { 44 int len = 0, l; 45 int c; 46 int count = 0; 47+ int maxLength = (ctxt->options & XML_PARSE_HUGE) ? 48+ XML_MAX_TEXT_LENGTH : 49+ XML_MAX_NAME_LENGTH; 50 51 #ifdef DEBUG 52 nbParseNameComplex++; 53@@ -3267,7 +3272,8 @@ xmlParseNameComplex(xmlParserCtxtPtr ctxt) { 54 if (ctxt->instate == XML_PARSER_EOF) 55 return(NULL); 56 } 57- len += l; 58+ if (len <= INT_MAX - l) 59+ len += l; 60 NEXTL(l); 61 c = CUR_CHAR(l); 62 } 63@@ -3293,13 +3299,13 @@ xmlParseNameComplex(xmlParserCtxtPtr ctxt) { 64 if (ctxt->instate == XML_PARSER_EOF) 65 return(NULL); 66 } 67- len += l; 68+ if (len <= INT_MAX - l) 69+ len += l; 70 NEXTL(l); 71 c = CUR_CHAR(l); 72 } 73 } 74- if ((len > XML_MAX_NAME_LENGTH) && 75- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 76+ if (len > maxLength) { 77 xmlFatalErr(ctxt, XML_ERR_NAME_TOO_LONG, "Name"); 78 return(NULL); 79 } 80@@ -3338,7 +3344,10 @@ const xmlChar * 81 xmlParseName(xmlParserCtxtPtr ctxt) { 82 const xmlChar *in; 83 const xmlChar *ret; 84- int count = 0; 85+ size_t count = 0; 86+ size_t maxLength = (ctxt->options & XML_PARSE_HUGE) ? 87+ XML_MAX_TEXT_LENGTH : 88+ XML_MAX_NAME_LENGTH; 89 90 GROW; 91 92@@ -3362,8 +3371,7 @@ xmlParseName(xmlParserCtxtPtr ctxt) { 93 in++; 94 if ((*in > 0) && (*in < 0x80)) { 95 count = in - ctxt->input->cur; 96- if ((count > XML_MAX_NAME_LENGTH) && 97- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 98+ if (count > maxLength) { 99 xmlFatalErr(ctxt, XML_ERR_NAME_TOO_LONG, "Name"); 100 return(NULL); 101 } 102@@ -3384,6 +3392,9 @@ xmlParseNCNameComplex(xmlParserCtxtPtr ctxt) { 103 int len = 0, l; 104 int c; 105 int count = 0; 106+ int maxLength = (ctxt->options & XML_PARSE_HUGE) ? 107+ XML_MAX_TEXT_LENGTH : 108+ XML_MAX_NAME_LENGTH; 109 size_t startPosition = 0; 110 111 #ifdef DEBUG 112@@ -3404,17 +3415,13 @@ xmlParseNCNameComplex(xmlParserCtxtPtr ctxt) { 113 while ((c != ' ') && (c != '>') && (c != '/') && /* test bigname.xml */ 114 (xmlIsNameChar(ctxt, c) && (c != ':'))) { 115 if (count++ > XML_PARSER_CHUNK_SIZE) { 116- if ((len > XML_MAX_NAME_LENGTH) && 117- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 118- xmlFatalErr(ctxt, XML_ERR_NAME_TOO_LONG, "NCName"); 119- return(NULL); 120- } 121 count = 0; 122 GROW; 123 if (ctxt->instate == XML_PARSER_EOF) 124 return(NULL); 125 } 126- len += l; 127+ if (len <= INT_MAX - l) 128+ len += l; 129 NEXTL(l); 130 c = CUR_CHAR(l); 131 if (c == 0) { 132@@ -3432,8 +3439,7 @@ xmlParseNCNameComplex(xmlParserCtxtPtr ctxt) { 133 c = CUR_CHAR(l); 134 } 135 } 136- if ((len > XML_MAX_NAME_LENGTH) && 137- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 138+ if (len > maxLength) { 139 xmlFatalErr(ctxt, XML_ERR_NAME_TOO_LONG, "NCName"); 140 return(NULL); 141 } 142@@ -3459,7 +3465,10 @@ static const xmlChar * 143 xmlParseNCName(xmlParserCtxtPtr ctxt) { 144 const xmlChar *in, *e; 145 const xmlChar *ret; 146- int count = 0; 147+ size_t count = 0; 148+ size_t maxLength = (ctxt->options & XML_PARSE_HUGE) ? 149+ XML_MAX_TEXT_LENGTH : 150+ XML_MAX_NAME_LENGTH; 151 152 #ifdef DEBUG 153 nbParseNCName++; 154@@ -3484,8 +3493,7 @@ xmlParseNCName(xmlParserCtxtPtr ctxt) { 155 goto complex; 156 if ((*in > 0) && (*in < 0x80)) { 157 count = in - ctxt->input->cur; 158- if ((count > XML_MAX_NAME_LENGTH) && 159- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 160+ if (count > maxLength) { 161 xmlFatalErr(ctxt, XML_ERR_NAME_TOO_LONG, "NCName"); 162 return(NULL); 163 } 164@@ -3567,6 +3575,9 @@ xmlParseStringName(xmlParserCtxtPtr ctxt, const xmlChar** str) { 165 const xmlChar *cur = *str; 166 int len = 0, l; 167 int c; 168+ int maxLength = (ctxt->options & XML_PARSE_HUGE) ? 169+ XML_MAX_TEXT_LENGTH : 170+ XML_MAX_NAME_LENGTH; 171 172 #ifdef DEBUG 173 nbParseStringName++; 174@@ -3602,12 +3613,6 @@ xmlParseStringName(xmlParserCtxtPtr ctxt, const xmlChar** str) { 175 if (len + 10 > max) { 176 xmlChar *tmp; 177 178- if ((len > XML_MAX_NAME_LENGTH) && 179- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 180- xmlFatalErr(ctxt, XML_ERR_NAME_TOO_LONG, "NCName"); 181- xmlFree(buffer); 182- return(NULL); 183- } 184 max *= 2; 185 tmp = (xmlChar *) xmlRealloc(buffer, 186 max * sizeof(xmlChar)); 187@@ -3621,14 +3626,18 @@ xmlParseStringName(xmlParserCtxtPtr ctxt, const xmlChar** str) { 188 COPY_BUF(l,buffer,len,c); 189 cur += l; 190 c = CUR_SCHAR(cur, l); 191+ if (len > maxLength) { 192+ xmlFatalErr(ctxt, XML_ERR_NAME_TOO_LONG, "NCName"); 193+ xmlFree(buffer); 194+ return(NULL); 195+ } 196 } 197 buffer[len] = 0; 198 *str = cur; 199 return(buffer); 200 } 201 } 202- if ((len > XML_MAX_NAME_LENGTH) && 203- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 204+ if (len > maxLength) { 205 xmlFatalErr(ctxt, XML_ERR_NAME_TOO_LONG, "NCName"); 206 return(NULL); 207 } 208@@ -3655,6 +3664,9 @@ xmlParseNmtoken(xmlParserCtxtPtr ctxt) { 209 int len = 0, l; 210 int c; 211 int count = 0; 212+ int maxLength = (ctxt->options & XML_PARSE_HUGE) ? 213+ XML_MAX_TEXT_LENGTH : 214+ XML_MAX_NAME_LENGTH; 215 216 #ifdef DEBUG 217 nbParseNmToken++; 218@@ -3706,12 +3718,6 @@ xmlParseNmtoken(xmlParserCtxtPtr ctxt) { 219 if (len + 10 > max) { 220 xmlChar *tmp; 221 222- if ((max > XML_MAX_NAME_LENGTH) && 223- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 224- xmlFatalErr(ctxt, XML_ERR_NAME_TOO_LONG, "NmToken"); 225- xmlFree(buffer); 226- return(NULL); 227- } 228 max *= 2; 229 tmp = (xmlChar *) xmlRealloc(buffer, 230 max * sizeof(xmlChar)); 231@@ -3725,6 +3731,11 @@ xmlParseNmtoken(xmlParserCtxtPtr ctxt) { 232 COPY_BUF(l,buffer,len,c); 233 NEXTL(l); 234 c = CUR_CHAR(l); 235+ if (len > maxLength) { 236+ xmlFatalErr(ctxt, XML_ERR_NAME_TOO_LONG, "NmToken"); 237+ xmlFree(buffer); 238+ return(NULL); 239+ } 240 } 241 buffer[len] = 0; 242 return(buffer); 243@@ -3732,8 +3743,7 @@ xmlParseNmtoken(xmlParserCtxtPtr ctxt) { 244 } 245 if (len == 0) 246 return(NULL); 247- if ((len > XML_MAX_NAME_LENGTH) && 248- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 249+ if (len > maxLength) { 250 xmlFatalErr(ctxt, XML_ERR_NAME_TOO_LONG, "NmToken"); 251 return(NULL); 252 } 253@@ -3759,6 +3769,9 @@ xmlParseEntityValue(xmlParserCtxtPtr ctxt, xmlChar **orig) { 254 int len = 0; 255 int size = XML_PARSER_BUFFER_SIZE; 256 int c, l; 257+ int maxLength = (ctxt->options & XML_PARSE_HUGE) ? 258+ XML_MAX_HUGE_LENGTH : 259+ XML_MAX_TEXT_LENGTH; 260 xmlChar stop; 261 xmlChar *ret = NULL; 262 const xmlChar *cur = NULL; 263@@ -3818,6 +3831,12 @@ xmlParseEntityValue(xmlParserCtxtPtr ctxt, xmlChar **orig) { 264 GROW; 265 c = CUR_CHAR(l); 266 } 267+ 268+ if (len > maxLength) { 269+ xmlFatalErrMsg(ctxt, XML_ERR_ENTITY_NOT_FINISHED, 270+ "entity value too long\n"); 271+ goto error; 272+ } 273 } 274 buf[len] = 0; 275 if (ctxt->instate == XML_PARSER_EOF) 276@@ -3905,6 +3924,9 @@ xmlParseAttValueComplex(xmlParserCtxtPtr ctxt, int *attlen, int normalize) { 277 xmlChar *rep = NULL; 278 size_t len = 0; 279 size_t buf_size = 0; 280+ size_t maxLength = (ctxt->options & XML_PARSE_HUGE) ? 281+ XML_MAX_HUGE_LENGTH : 282+ XML_MAX_TEXT_LENGTH; 283 int c, l, in_space = 0; 284 xmlChar *current = NULL; 285 xmlEntityPtr ent; 286@@ -3936,16 +3958,6 @@ xmlParseAttValueComplex(xmlParserCtxtPtr ctxt, int *attlen, int normalize) { 287 while (((NXT(0) != limit) && /* checked */ 288 (IS_CHAR(c)) && (c != '<')) && 289 (ctxt->instate != XML_PARSER_EOF)) { 290- /* 291- * Impose a reasonable limit on attribute size, unless XML_PARSE_HUGE 292- * special option is given 293- */ 294- if ((len > XML_MAX_TEXT_LENGTH) && 295- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 296- xmlFatalErrMsg(ctxt, XML_ERR_ATTRIBUTE_NOT_FINISHED, 297- "AttValue length too long\n"); 298- goto mem_error; 299- } 300 if (c == '&') { 301 in_space = 0; 302 if (NXT(1) == '#') { 303@@ -4093,6 +4105,11 @@ xmlParseAttValueComplex(xmlParserCtxtPtr ctxt, int *attlen, int normalize) { 304 } 305 GROW; 306 c = CUR_CHAR(l); 307+ if (len > maxLength) { 308+ xmlFatalErrMsg(ctxt, XML_ERR_ATTRIBUTE_NOT_FINISHED, 309+ "AttValue length too long\n"); 310+ goto mem_error; 311+ } 312 } 313 if (ctxt->instate == XML_PARSER_EOF) 314 goto error; 315@@ -4114,16 +4131,6 @@ xmlParseAttValueComplex(xmlParserCtxtPtr ctxt, int *attlen, int normalize) { 316 } else 317 NEXT; 318 319- /* 320- * There we potentially risk an overflow, don't allow attribute value of 321- * length more than INT_MAX it is a very reasonable assumption ! 322- */ 323- if (len >= INT_MAX) { 324- xmlFatalErrMsg(ctxt, XML_ERR_ATTRIBUTE_NOT_FINISHED, 325- "AttValue length too long\n"); 326- goto mem_error; 327- } 328- 329 if (attlen != NULL) *attlen = (int) len; 330 return(buf); 331 332@@ -4194,6 +4201,9 @@ xmlParseSystemLiteral(xmlParserCtxtPtr ctxt) { 333 int len = 0; 334 int size = XML_PARSER_BUFFER_SIZE; 335 int cur, l; 336+ int maxLength = (ctxt->options & XML_PARSE_HUGE) ? 337+ XML_MAX_TEXT_LENGTH : 338+ XML_MAX_NAME_LENGTH; 339 xmlChar stop; 340 int state = ctxt->instate; 341 int count = 0; 342@@ -4221,13 +4231,6 @@ xmlParseSystemLiteral(xmlParserCtxtPtr ctxt) { 343 if (len + 5 >= size) { 344 xmlChar *tmp; 345 346- if ((size > XML_MAX_NAME_LENGTH) && 347- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 348- xmlFatalErr(ctxt, XML_ERR_NAME_TOO_LONG, "SystemLiteral"); 349- xmlFree(buf); 350- ctxt->instate = (xmlParserInputState) state; 351- return(NULL); 352- } 353 size *= 2; 354 tmp = (xmlChar *) xmlRealloc(buf, size * sizeof(xmlChar)); 355 if (tmp == NULL) { 356@@ -4256,6 +4259,12 @@ xmlParseSystemLiteral(xmlParserCtxtPtr ctxt) { 357 SHRINK; 358 cur = CUR_CHAR(l); 359 } 360+ if (len > maxLength) { 361+ xmlFatalErr(ctxt, XML_ERR_NAME_TOO_LONG, "SystemLiteral"); 362+ xmlFree(buf); 363+ ctxt->instate = (xmlParserInputState) state; 364+ return(NULL); 365+ } 366 } 367 buf[len] = 0; 368 ctxt->instate = (xmlParserInputState) state; 369@@ -4283,6 +4292,9 @@ xmlParsePubidLiteral(xmlParserCtxtPtr ctxt) { 370 xmlChar *buf = NULL; 371 int len = 0; 372 int size = XML_PARSER_BUFFER_SIZE; 373+ int maxLength = (ctxt->options & XML_PARSE_HUGE) ? 374+ XML_MAX_TEXT_LENGTH : 375+ XML_MAX_NAME_LENGTH; 376 xmlChar cur; 377 xmlChar stop; 378 int count = 0; 379@@ -4310,12 +4322,6 @@ xmlParsePubidLiteral(xmlParserCtxtPtr ctxt) { 380 if (len + 1 >= size) { 381 xmlChar *tmp; 382 383- if ((size > XML_MAX_NAME_LENGTH) && 384- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 385- xmlFatalErr(ctxt, XML_ERR_NAME_TOO_LONG, "Public ID"); 386- xmlFree(buf); 387- return(NULL); 388- } 389 size *= 2; 390 tmp = (xmlChar *) xmlRealloc(buf, size * sizeof(xmlChar)); 391 if (tmp == NULL) { 392@@ -4343,6 +4349,11 @@ xmlParsePubidLiteral(xmlParserCtxtPtr ctxt) { 393 SHRINK; 394 cur = CUR; 395 } 396+ if (len > maxLength) { 397+ xmlFatalErr(ctxt, XML_ERR_NAME_TOO_LONG, "Public ID"); 398+ xmlFree(buf); 399+ return(NULL); 400+ } 401 } 402 buf[len] = 0; 403 if (cur != stop) { 404@@ -4742,6 +4753,9 @@ xmlParseCommentComplex(xmlParserCtxtPtr ctxt, xmlChar *buf, 405 int r, rl; 406 int cur, l; 407 size_t count = 0; 408+ size_t maxLength = (ctxt->options & XML_PARSE_HUGE) ? 409+ XML_MAX_HUGE_LENGTH : 410+ XML_MAX_TEXT_LENGTH; 411 int inputid; 412 413 inputid = ctxt->input->id; 414@@ -4787,13 +4801,6 @@ xmlParseCommentComplex(xmlParserCtxtPtr ctxt, xmlChar *buf, 415 if ((r == '-') && (q == '-')) { 416 xmlFatalErr(ctxt, XML_ERR_HYPHEN_IN_COMMENT, NULL); 417 } 418- if ((len > XML_MAX_TEXT_LENGTH) && 419- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 420- xmlFatalErrMsgStr(ctxt, XML_ERR_COMMENT_NOT_FINISHED, 421- "Comment too big found", NULL); 422- xmlFree (buf); 423- return; 424- } 425 if (len + 5 >= size) { 426 xmlChar *new_buf; 427 size_t new_size; 428@@ -4831,6 +4838,13 @@ xmlParseCommentComplex(xmlParserCtxtPtr ctxt, xmlChar *buf, 429 GROW; 430 cur = CUR_CHAR(l); 431 } 432+ 433+ if (len > maxLength) { 434+ xmlFatalErrMsgStr(ctxt, XML_ERR_COMMENT_NOT_FINISHED, 435+ "Comment too big found", NULL); 436+ xmlFree (buf); 437+ return; 438+ } 439 } 440 buf[len] = 0; 441 if (cur == 0) { 442@@ -4875,6 +4889,9 @@ xmlParseComment(xmlParserCtxtPtr ctxt) { 443 xmlChar *buf = NULL; 444 size_t size = XML_PARSER_BUFFER_SIZE; 445 size_t len = 0; 446+ size_t maxLength = (ctxt->options & XML_PARSE_HUGE) ? 447+ XML_MAX_HUGE_LENGTH : 448+ XML_MAX_TEXT_LENGTH; 449 xmlParserInputState state; 450 const xmlChar *in; 451 size_t nbchar = 0; 452@@ -4958,8 +4975,7 @@ get_more: 453 buf[len] = 0; 454 } 455 } 456- if ((len > XML_MAX_TEXT_LENGTH) && 457- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 458+ if (len > maxLength) { 459 xmlFatalErrMsgStr(ctxt, XML_ERR_COMMENT_NOT_FINISHED, 460 "Comment too big found", NULL); 461 xmlFree (buf); 462@@ -5159,6 +5175,9 @@ xmlParsePI(xmlParserCtxtPtr ctxt) { 463 xmlChar *buf = NULL; 464 size_t len = 0; 465 size_t size = XML_PARSER_BUFFER_SIZE; 466+ size_t maxLength = (ctxt->options & XML_PARSE_HUGE) ? 467+ XML_MAX_HUGE_LENGTH : 468+ XML_MAX_TEXT_LENGTH; 469 int cur, l; 470 const xmlChar *target; 471 xmlParserInputState state; 472@@ -5234,14 +5253,6 @@ xmlParsePI(xmlParserCtxtPtr ctxt) { 473 return; 474 } 475 count = 0; 476- if ((len > XML_MAX_TEXT_LENGTH) && 477- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 478- xmlFatalErrMsgStr(ctxt, XML_ERR_PI_NOT_FINISHED, 479- "PI %s too big found", target); 480- xmlFree(buf); 481- ctxt->instate = state; 482- return; 483- } 484 } 485 COPY_BUF(l,buf,len,cur); 486 NEXTL(l); 487@@ -5251,15 +5262,14 @@ xmlParsePI(xmlParserCtxtPtr ctxt) { 488 GROW; 489 cur = CUR_CHAR(l); 490 } 491+ if (len > maxLength) { 492+ xmlFatalErrMsgStr(ctxt, XML_ERR_PI_NOT_FINISHED, 493+ "PI %s too big found", target); 494+ xmlFree(buf); 495+ ctxt->instate = state; 496+ return; 497+ } 498 } 499- if ((len > XML_MAX_TEXT_LENGTH) && 500- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 501- xmlFatalErrMsgStr(ctxt, XML_ERR_PI_NOT_FINISHED, 502- "PI %s too big found", target); 503- xmlFree(buf); 504- ctxt->instate = state; 505- return; 506- } 507 buf[len] = 0; 508 if (cur != '?') { 509 xmlFatalErrMsgStr(ctxt, XML_ERR_PI_NOT_FINISHED, 510@@ -8954,6 +8964,9 @@ xmlParseAttValueInternal(xmlParserCtxtPtr ctxt, int *len, int *alloc, 511 const xmlChar *in = NULL, *start, *end, *last; 512 xmlChar *ret = NULL; 513 int line, col; 514+ int maxLength = (ctxt->options & XML_PARSE_HUGE) ? 515+ XML_MAX_HUGE_LENGTH : 516+ XML_MAX_TEXT_LENGTH; 517 518 GROW; 519 in = (xmlChar *) CUR_PTR; 520@@ -8993,8 +9006,7 @@ xmlParseAttValueInternal(xmlParserCtxtPtr ctxt, int *len, int *alloc, 521 start = in; 522 if (in >= end) { 523 GROW_PARSE_ATT_VALUE_INTERNAL(ctxt, in, start, end) 524- if (((in - start) > XML_MAX_TEXT_LENGTH) && 525- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 526+ if ((in - start) > maxLength) { 527 xmlFatalErrMsg(ctxt, XML_ERR_ATTRIBUTE_NOT_FINISHED, 528 "AttValue length too long\n"); 529 return(NULL); 530@@ -9007,8 +9019,7 @@ xmlParseAttValueInternal(xmlParserCtxtPtr ctxt, int *len, int *alloc, 531 if ((*in++ == 0x20) && (*in == 0x20)) break; 532 if (in >= end) { 533 GROW_PARSE_ATT_VALUE_INTERNAL(ctxt, in, start, end) 534- if (((in - start) > XML_MAX_TEXT_LENGTH) && 535- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 536+ if ((in - start) > maxLength) { 537 xmlFatalErrMsg(ctxt, XML_ERR_ATTRIBUTE_NOT_FINISHED, 538 "AttValue length too long\n"); 539 return(NULL); 540@@ -9041,16 +9052,14 @@ xmlParseAttValueInternal(xmlParserCtxtPtr ctxt, int *len, int *alloc, 541 last = last + delta; 542 } 543 end = ctxt->input->end; 544- if (((in - start) > XML_MAX_TEXT_LENGTH) && 545- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 546+ if ((in - start) > maxLength) { 547 xmlFatalErrMsg(ctxt, XML_ERR_ATTRIBUTE_NOT_FINISHED, 548 "AttValue length too long\n"); 549 return(NULL); 550 } 551 } 552 } 553- if (((in - start) > XML_MAX_TEXT_LENGTH) && 554- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 555+ if ((in - start) > maxLength) { 556 xmlFatalErrMsg(ctxt, XML_ERR_ATTRIBUTE_NOT_FINISHED, 557 "AttValue length too long\n"); 558 return(NULL); 559@@ -9063,8 +9072,7 @@ xmlParseAttValueInternal(xmlParserCtxtPtr ctxt, int *len, int *alloc, 560 col++; 561 if (in >= end) { 562 GROW_PARSE_ATT_VALUE_INTERNAL(ctxt, in, start, end) 563- if (((in - start) > XML_MAX_TEXT_LENGTH) && 564- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 565+ if ((in - start) > maxLength) { 566 xmlFatalErrMsg(ctxt, XML_ERR_ATTRIBUTE_NOT_FINISHED, 567 "AttValue length too long\n"); 568 return(NULL); 569@@ -9072,8 +9080,7 @@ xmlParseAttValueInternal(xmlParserCtxtPtr ctxt, int *len, int *alloc, 570 } 571 } 572 last = in; 573- if (((in - start) > XML_MAX_TEXT_LENGTH) && 574- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 575+ if ((in - start) > maxLength) { 576 xmlFatalErrMsg(ctxt, XML_ERR_ATTRIBUTE_NOT_FINISHED, 577 "AttValue length too long\n"); 578 return(NULL); 579@@ -9763,6 +9770,9 @@ xmlParseCDSect(xmlParserCtxtPtr ctxt) { 580 int s, sl; 581 int cur, l; 582 int count = 0; 583+ int maxLength = (ctxt->options & XML_PARSE_HUGE) ? 584+ XML_MAX_HUGE_LENGTH : 585+ XML_MAX_TEXT_LENGTH; 586 587 /* Check 2.6.0 was NXT(0) not RAW */ 588 if (CMP9(CUR_PTR, '<', '!', '[', 'C', 'D', 'A', 'T', 'A', '[')) { 589@@ -9796,13 +9806,6 @@ xmlParseCDSect(xmlParserCtxtPtr ctxt) { 590 if (len + 5 >= size) { 591 xmlChar *tmp; 592 593- if ((size > XML_MAX_TEXT_LENGTH) && 594- ((ctxt->options & XML_PARSE_HUGE) == 0)) { 595- xmlFatalErrMsgStr(ctxt, XML_ERR_CDATA_NOT_FINISHED, 596- "CData section too big found", NULL); 597- xmlFree (buf); 598- return; 599- } 600 tmp = (xmlChar *) xmlRealloc(buf, size * 2 * sizeof(xmlChar)); 601 if (tmp == NULL) { 602 xmlFree(buf); 603@@ -9829,6 +9832,12 @@ xmlParseCDSect(xmlParserCtxtPtr ctxt) { 604 } 605 NEXTL(l); 606 cur = CUR_CHAR(l); 607+ if (len > maxLength) { 608+ xmlFatalErrMsg(ctxt, XML_ERR_CDATA_NOT_FINISHED, 609+ "CData section too big found\n"); 610+ xmlFree(buf); 611+ return; 612+ } 613 } 614 buf[len] = 0; 615 ctxt->instate = XML_PARSER_CONTENT; 616-- 6172.27.0 618 619