| 12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664166516661667166816691670167116721673167416751676167716781679168016811682168316841685168616871688168916901691169216931694169516961697169816991700170117021703170417051706170717081709171017111712171317141715171617171718171917201721172217231724172517261727172817291730173117321733173417351736173717381739174017411742174317441745174617471748174917501751175217531754175517561757175817591760176117621763176417651766176717681769177017711772177317741775177617771778177917801781178217831784178517861787178817891790179117921793179417951796179717981799180018011802180318041805180618071808180918101811181218131814181518161817181818191820182118221823182418251826182718281829183018311832183318341835183618371838183918401841184218431844184518461847184818491850185118521853185418551856185718581859186018611862186318641865186618671868186918701871187218731874187518761877187818791880188118821883188418851886188718881889189018911892189318941895189618971898189919001901190219031904190519061907190819091910191119121913191419151916191719181919192019211922192319241925192619271928192919301931193219331934193519361937193819391940194119421943194419451946194719481949195019511952195319541955195619571958195919601961196219631964196519661967196819691970197119721973197419751976197719781979198019811982198319841985198619871988198919901991199219931994199519961997199819992000200120022003200420052006200720082009201020112012201320142015201620172018201920202021202220232024202520262027202820292030203120322033203420352036203720382039204020412042204320442045204620472048204920502051205220532054205520562057205820592060206120622063206420652066206720682069207020712072207320742075207620772078207920802081208220832084208520862087208820892090209120922093209420952096209720982099210021012102210321042105210621072108210921102111211221132114211521162117211821192120212121222123212421252126212721282129213021312132213321342135213621372138213921402141214221432144214521462147214821492150215121522153215421552156215721582159216021612162216321642165216621672168216921702171217221732174217521762177217821792180218121822183218421852186218721882189219021912192219321942195219621972198219922002201220222032204220522062207220822092210221122122213221422152216221722182219222022212222222322242225222622272228222922302231223222332234223522362237223822392240224122422243224422452246224722482249225022512252225322542255225622572258225922602261226222632264226522662267226822692270227122722273227422752276227722782279228022812282228322842285228622872288228922902291229222932294229522962297229822992300230123022303230423052306230723082309231023112312231323142315231623172318231923202321232223232324232523262327232823292330233123322333233423352336233723382339234023412342234323442345234623472348234923502351235223532354235523562357235823592360236123622363236423652366236723682369237023712372237323742375237623772378237923802381238223832384238523862387238823892390 |
- /* Tests in the "allocation" test case for the Expat test suite
- __ __ _
- ___\ \/ /_ __ __ _| |_
- / _ \\ /| '_ \ / _` | __|
- | __// \| |_) | (_| | |_
- \___/_/\_\ .__/ \__,_|\__|
- |_| XML parser
- Copyright (c) 2001-2006 Fred L. Drake, Jr. <[email protected]>
- Copyright (c) 2003 Greg Stein <[email protected]>
- Copyright (c) 2005-2007 Steven Solie <[email protected]>
- Copyright (c) 2005-2012 Karl Waclawek <[email protected]>
- Copyright (c) 2016-2025 Sebastian Pipping <[email protected]>
- Copyright (c) 2017-2022 Rhodri James <[email protected]>
- Copyright (c) 2017 Joe Orton <[email protected]>
- Copyright (c) 2017 José Gutiérrez de la Concha <[email protected]>
- Copyright (c) 2018 Marco Maggi <[email protected]>
- Copyright (c) 2019 David Loffredo <[email protected]>
- Copyright (c) 2020 Tim Gates <[email protected]>
- Copyright (c) 2021 Donghee Na <[email protected]>
- Copyright (c) 2023 Sony Corporation / Snild Dolkow <[email protected]>
- Copyright (c) 2025 Berkay Eren Ürün <[email protected]>
- Licensed under the MIT license:
- Permission is hereby granted, free of charge, to any person obtaining
- a copy of this software and associated documentation files (the
- "Software"), to deal in the Software without restriction, including
- without limitation the rights to use, copy, modify, merge, publish,
- distribute, sublicense, and/or sell copies of the Software, and to permit
- persons to whom the Software is furnished to do so, subject to the
- following conditions:
- The above copyright notice and this permission notice shall be included
- in all copies or substantial portions of the Software.
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN
- NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
- DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
- OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
- USE OR OTHER DEALINGS IN THE SOFTWARE.
- */
- #if defined(NDEBUG)
- # undef NDEBUG /* because test suite relies on assert(...) at the moment */
- #endif
- #include <math.h> /* NAN, INFINITY */
- #include <stdbool.h>
- #include <stdint.h> /* for SIZE_MAX */
- #include <string.h>
- #include <assert.h>
- #include "expat_config.h"
- #include "expat.h"
- #include "internal.h"
- #include "common.h"
- #include "minicheck.h"
- #include "dummy.h"
- #include "handlers.h"
- #include "alloc_tests.h"
- static void
- alloc_setup(void) {
- XML_Memory_Handling_Suite memsuite = {duff_allocator, duff_reallocator, free};
- /* Ensure the parser creation will go through */
- g_allocation_count = ALLOC_ALWAYS_SUCCEED;
- g_reallocation_count = REALLOC_ALWAYS_SUCCEED;
- g_parser = XML_ParserCreate_MM(NULL, &memsuite, NULL);
- if (g_parser == NULL)
- fail("Parser not created");
- }
- static void
- alloc_teardown(void) {
- basic_teardown();
- }
- /* Test the effects of allocation failures on xml declaration processing */
- START_TEST(test_alloc_parse_xdecl) {
- const char *text = "<?xml version='1.0' encoding='utf-8'?>\n"
- "<doc>Hello, world</doc>";
- int i;
- const int max_alloc_count = 15;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetXmlDeclHandler(g_parser, dummy_xdecl_handler);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* Resetting the parser is insufficient, because some memory
- * allocations are cached within the parser. Instead we use
- * the teardown and setup routines to ensure that we have the
- * right sort of parser back in our hands.
- */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed with max allocations");
- }
- END_TEST
- /* As above, but with an encoding big enough to cause storing the
- * version information to expand the string pool being used.
- */
- START_TEST(test_alloc_parse_xdecl_2) {
- const char *text
- = "<?xml version='1.0' encoding='"
- /* Each line is 64 characters */
- "ThisIsAStupidlyLongEncodingNameIntendedToTriggerPoolGrowth123456"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMN"
- "'?>"
- "<doc>Hello, world</doc>";
- int i;
- const int max_alloc_count = 20;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetXmlDeclHandler(g_parser, dummy_xdecl_handler);
- XML_SetUnknownEncodingHandler(g_parser, long_encoding_handler, NULL);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed with max allocations");
- }
- END_TEST
- /* Test the effects of allocation failures on a straightforward parse */
- START_TEST(test_alloc_parse_pi) {
- const char *text = "<?xml version='1.0' encoding='utf-8'?>\n"
- "<?pi unknown?>\n"
- "<doc>"
- "Hello, world"
- "</doc>";
- int i;
- const int max_alloc_count = 15;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetProcessingInstructionHandler(g_parser, dummy_pi_handler);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed with max allocations");
- }
- END_TEST
- START_TEST(test_alloc_parse_pi_2) {
- const char *text = "<?xml version='1.0' encoding='utf-8'?>\n"
- "<doc>"
- "Hello, world"
- "<?pi unknown?>\n"
- "</doc>";
- int i;
- const int max_alloc_count = 15;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetProcessingInstructionHandler(g_parser, dummy_pi_handler);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed with max allocations");
- }
- END_TEST
- START_TEST(test_alloc_parse_pi_3) {
- const char *text
- = "<?"
- /* 64 characters per line */
- "This processing instruction should be long enough to ensure that"
- "it triggers the growth of an internal string pool when the "
- "allocator fails at a cruicial moment FGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "Q?><doc/>";
- int i;
- const int max_alloc_count = 20;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetProcessingInstructionHandler(g_parser, dummy_pi_handler);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed with max allocations");
- }
- END_TEST
- START_TEST(test_alloc_parse_comment) {
- const char *text = "<?xml version='1.0' encoding='utf-8'?>\n"
- "<!-- Test parsing this comment -->"
- "<doc>Hi</doc>";
- int i;
- const int max_alloc_count = 15;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetCommentHandler(g_parser, dummy_comment_handler);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed with max allocations");
- }
- END_TEST
- START_TEST(test_alloc_parse_comment_2) {
- const char *text = "<?xml version='1.0' encoding='utf-8'?>\n"
- "<doc>"
- "Hello, world"
- "<!-- Parse this comment too -->"
- "</doc>";
- int i;
- const int max_alloc_count = 15;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetCommentHandler(g_parser, dummy_comment_handler);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed with max allocations");
- }
- END_TEST
- /* Test that external parser creation running out of memory is
- * correctly reported. Based on the external entity test cases.
- */
- START_TEST(test_alloc_create_external_parser) {
- const char *text = "<?xml version='1.0' encoding='us-ascii'?>\n"
- "<!DOCTYPE doc SYSTEM 'foo'>\n"
- "<doc>&entity;</doc>";
- char foo_text[] = "<!ELEMENT doc (#PCDATA)*>";
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- XML_SetUserData(g_parser, foo_text);
- XML_SetExternalEntityRefHandler(g_parser, external_entity_duff_loader);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR) {
- fail("External parser allocator returned success incorrectly");
- }
- }
- END_TEST
- /* More external parser memory allocation testing */
- START_TEST(test_alloc_run_external_parser) {
- const char *text = "<?xml version='1.0' encoding='us-ascii'?>\n"
- "<!DOCTYPE doc SYSTEM 'foo'>\n"
- "<doc>&entity;</doc>";
- char foo_text[] = "<!ELEMENT doc (#PCDATA)*>";
- unsigned int i;
- const unsigned int max_alloc_count = 15;
- for (i = 0; i < max_alloc_count; i++) {
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- XML_SetUserData(g_parser, foo_text);
- XML_SetExternalEntityRefHandler(g_parser, external_entity_null_loader);
- g_allocation_count = (int)i;
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parsing ignored failing allocator");
- else if (i == max_alloc_count)
- fail("Parsing failed with allocation count 10");
- }
- END_TEST
- /* Test that running out of memory in dtdCopy is correctly reported.
- * Based on test_default_ns_from_ext_subset_and_ext_ge()
- */
- START_TEST(test_alloc_dtd_copy_default_atts) {
- const char *text = "<?xml version='1.0'?>\n"
- "<!DOCTYPE doc SYSTEM 'http://example.org/doc.dtd' [\n"
- " <!ENTITY en SYSTEM 'http://example.org/entity.ent'>\n"
- "]>\n"
- "<doc xmlns='http://example.org/ns1'>\n"
- "&en;\n"
- "</doc>";
- int callno = 0;
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- XML_SetExternalEntityRefHandler(g_parser, external_entity_dbl_handler);
- XML_SetUserData(g_parser, &callno);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- == XML_STATUS_ERROR)
- xml_failure(g_parser);
- }
- END_TEST
- /* Test more external entity allocation failure paths */
- START_TEST(test_alloc_external_entity) {
- const char *text = "<?xml version='1.0'?>\n"
- "<!DOCTYPE doc SYSTEM 'http://example.org/doc.dtd' [\n"
- " <!ENTITY en SYSTEM 'http://example.org/entity.ent'>\n"
- "]>\n"
- "<doc xmlns='http://example.org/ns1'>\n"
- "&en;\n"
- "</doc>";
- int i;
- const int alloc_test_max_repeats = 50;
- int callno = 0;
- for (i = 0; i < alloc_test_max_repeats; i++) {
- g_allocation_count = -1;
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- XML_SetExternalEntityRefHandler(g_parser, external_entity_dbl_handler_2);
- callno = 0;
- XML_SetUserData(g_parser, &callno);
- g_allocation_count = i;
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- == XML_STATUS_OK)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- g_allocation_count = -1;
- if (i == 0)
- fail("External entity parsed despite duff allocator");
- if (i == alloc_test_max_repeats)
- fail("External entity not parsed at max allocation count");
- }
- END_TEST
- /* Test more allocation failure paths */
- START_TEST(test_alloc_ext_entity_set_encoding) {
- const char *text = "<!DOCTYPE doc [\n"
- " <!ENTITY en SYSTEM 'http://example.org/dummy.ent'>\n"
- "]>\n"
- "<doc>&en;</doc>";
- int i;
- const int max_allocation_count = 30;
- for (i = 0; i < max_allocation_count; i++) {
- XML_SetExternalEntityRefHandler(g_parser,
- external_entity_alloc_set_encoding);
- g_allocation_count = i;
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- == XML_STATUS_OK)
- break;
- g_allocation_count = -1;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Encoding check succeeded despite failing allocator");
- if (i == max_allocation_count)
- fail("Encoding failed at max allocation count");
- }
- END_TEST
- /* Test the effects of allocation failure in internal entities.
- * Based on test_unknown_encoding_internal_entity
- */
- START_TEST(test_alloc_internal_entity) {
- const char *text = "<?xml version='1.0' encoding='unsupported-encoding'?>\n"
- "<!DOCTYPE test [<!ENTITY foo 'bar'>]>\n"
- "<test a='&foo;'/>";
- unsigned int i;
- const unsigned int max_alloc_count = 20;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = (int)i;
- XML_SetUnknownEncodingHandler(g_parser, unknown_released_encoding_handler,
- NULL);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Internal entity worked despite failing allocations");
- else if (i == max_alloc_count)
- fail("Internal entity failed at max allocation count");
- }
- END_TEST
- START_TEST(test_alloc_parameter_entity) {
- const char *text = "<!DOCTYPE foo ["
- "<!ENTITY % param1 \"<!ENTITY internal 'some_text'>\">"
- "%param1;"
- "]> <foo>&internal;content</foo>";
- int i;
- const int alloc_test_max_repeats = 30;
- for (i = 0; i < alloc_test_max_repeats; i++) {
- g_allocation_count = i;
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- alloc_teardown();
- alloc_setup();
- }
- g_allocation_count = -1;
- if (i == 0)
- fail("Parameter entity processed despite duff allocator");
- if (i == alloc_test_max_repeats)
- fail("Parameter entity not processed at max allocation count");
- }
- END_TEST
- /* Test the robustness against allocation failure of element handling
- * Based on test_dtd_default_handling().
- */
- START_TEST(test_alloc_dtd_default_handling) {
- const char *text = "<!DOCTYPE doc [\n"
- "<!ENTITY e SYSTEM 'http://example.org/e'>\n"
- "<!NOTATION n SYSTEM 'http://example.org/n'>\n"
- "<!ENTITY e1 SYSTEM 'http://example.org/e' NDATA n>\n"
- "<!ELEMENT doc (#PCDATA)>\n"
- "<!ATTLIST doc a CDATA #IMPLIED>\n"
- "<?pi in dtd?>\n"
- "<!--comment in dtd-->\n"
- "]>\n"
- "<doc><![CDATA[text in doc]]></doc>";
- const XML_Char *expected = XCS("\n\n\n\n\n\n\n\n\n<doc>text in doc</doc>");
- CharData storage;
- int i;
- const int max_alloc_count = 25;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- init_dummy_handlers();
- XML_SetDefaultHandler(g_parser, accumulate_characters);
- XML_SetDoctypeDeclHandler(g_parser, dummy_start_doctype_handler,
- dummy_end_doctype_handler);
- XML_SetEntityDeclHandler(g_parser, dummy_entity_decl_handler);
- XML_SetNotationDeclHandler(g_parser, dummy_notation_decl_handler);
- XML_SetElementDeclHandler(g_parser, dummy_element_decl_handler);
- XML_SetAttlistDeclHandler(g_parser, dummy_attlist_decl_handler);
- XML_SetProcessingInstructionHandler(g_parser, dummy_pi_handler);
- XML_SetCommentHandler(g_parser, dummy_comment_handler);
- XML_SetCdataSectionHandler(g_parser, dummy_start_cdata_handler,
- dummy_end_cdata_handler);
- XML_SetUnparsedEntityDeclHandler(g_parser,
- dummy_unparsed_entity_decl_handler);
- CharData_Init(&storage);
- XML_SetUserData(g_parser, &storage);
- XML_SetCharacterDataHandler(g_parser, accumulate_characters);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Default DTD parsed despite allocation failures");
- if (i == max_alloc_count)
- fail("Default DTD not parsed with maximum alloc count");
- CharData_CheckXMLChars(&storage, expected);
- if (get_dummy_handler_flags()
- != (DUMMY_START_DOCTYPE_HANDLER_FLAG | DUMMY_END_DOCTYPE_HANDLER_FLAG
- | DUMMY_ENTITY_DECL_HANDLER_FLAG | DUMMY_NOTATION_DECL_HANDLER_FLAG
- | DUMMY_ELEMENT_DECL_HANDLER_FLAG | DUMMY_ATTLIST_DECL_HANDLER_FLAG
- | DUMMY_COMMENT_HANDLER_FLAG | DUMMY_PI_HANDLER_FLAG
- | DUMMY_START_CDATA_HANDLER_FLAG | DUMMY_END_CDATA_HANDLER_FLAG
- | DUMMY_UNPARSED_ENTITY_DECL_HANDLER_FLAG))
- fail("Not all handlers were called");
- }
- END_TEST
- /* Test robustness of XML_SetEncoding() with a failing allocator */
- START_TEST(test_alloc_explicit_encoding) {
- int i;
- const int max_alloc_count = 5;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- if (XML_SetEncoding(g_parser, XCS("us-ascii")) == XML_STATUS_OK)
- break;
- }
- if (i == 0)
- fail("Encoding set despite failing allocator");
- else if (i == max_alloc_count)
- fail("Encoding not set at max allocation count");
- }
- END_TEST
- /* Test robustness of XML_SetBase against a failing allocator */
- START_TEST(test_alloc_set_base) {
- const XML_Char *new_base = XCS("/local/file/name.xml");
- int i;
- const int max_alloc_count = 5;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- if (XML_SetBase(g_parser, new_base) == XML_STATUS_OK)
- break;
- }
- if (i == 0)
- fail("Base set despite failing allocator");
- else if (i == max_alloc_count)
- fail("Base not set with max allocation count");
- }
- END_TEST
- /* Test buffer extension in the face of a duff reallocator */
- START_TEST(test_alloc_realloc_buffer) {
- const char *text = get_buffer_test_text;
- void *buffer;
- int i;
- const int max_realloc_count = 10;
- /* Get a smallish buffer */
- for (i = 0; i < max_realloc_count; i++) {
- g_reallocation_count = i;
- buffer = XML_GetBuffer(g_parser, 1536);
- if (buffer == NULL)
- fail("1.5K buffer reallocation failed");
- assert(buffer != NULL);
- memcpy(buffer, text, strlen(text));
- if (XML_ParseBuffer(g_parser, (int)strlen(text), XML_FALSE)
- == XML_STATUS_OK)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- g_reallocation_count = -1;
- if (i == 0)
- fail("Parse succeeded with no reallocation");
- else if (i == max_realloc_count)
- fail("Parse failed with max reallocation count");
- }
- END_TEST
- /* Same test for external entity parsers */
- START_TEST(test_alloc_ext_entity_realloc_buffer) {
- const char *text = "<!DOCTYPE doc [\n"
- " <!ENTITY en SYSTEM 'http://example.org/dummy.ent'>\n"
- "]>\n"
- "<doc>&en;</doc>";
- int i;
- const int max_realloc_count = 10;
- for (i = 0; i < max_realloc_count; i++) {
- XML_SetExternalEntityRefHandler(g_parser, external_entity_reallocator);
- XML_SetUserData(g_parser, &i);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- == XML_STATUS_OK)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Succeeded with no reallocations");
- if (i == max_realloc_count)
- fail("Failed with max reallocations");
- }
- END_TEST
- /* Test elements with many attributes are handled correctly */
- START_TEST(test_alloc_realloc_many_attributes) {
- const char *text = "<!DOCTYPE doc [\n"
- "<!ATTLIST doc za CDATA 'default'>\n"
- "<!ATTLIST doc zb CDATA 'def2'>\n"
- "<!ATTLIST doc zc CDATA 'def3'>\n"
- "]>\n"
- "<doc a='1'"
- " b='2'"
- " c='3'"
- " d='4'"
- " e='5'"
- " f='6'"
- " g='7'"
- " h='8'"
- " i='9'"
- " j='10'"
- " k='11'"
- " l='12'"
- " m='13'"
- " n='14'"
- " p='15'"
- " q='16'"
- " r='17'"
- " s='18'>"
- "</doc>";
- int i;
- const int max_realloc_count = 10;
- for (i = 0; i < max_realloc_count; i++) {
- g_reallocation_count = i;
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite no reallocations");
- if (i == max_realloc_count)
- fail("Parse failed at max reallocations");
- }
- END_TEST
- /* Test handling of a public entity with failing allocator */
- START_TEST(test_alloc_public_entity_value) {
- const char *text = "<!DOCTYPE doc SYSTEM 'http://example.org/'>\n"
- "<doc></doc>\n";
- char dtd_text[]
- = "<!ELEMENT doc EMPTY>\n"
- "<!ENTITY % e1 PUBLIC 'foo' 'bar.ent'>\n"
- "<!ENTITY % "
- /* Each line is 64 characters */
- "ThisIsAStupidlyLongParameterNameIntendedToTriggerPoolGrowth12345"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- " '%e1;'>\n"
- "%e1;\n";
- int i;
- const int max_alloc_count = 50;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- init_dummy_handlers();
- XML_SetUserData(g_parser, dtd_text);
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- XML_SetExternalEntityRefHandler(g_parser, external_entity_public);
- /* Provoke a particular code path */
- XML_SetEntityDeclHandler(g_parser, dummy_entity_decl_handler);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parsing worked despite failing allocation");
- if (i == max_alloc_count)
- fail("Parsing failed at max allocation count");
- if (get_dummy_handler_flags() != DUMMY_ENTITY_DECL_HANDLER_FLAG)
- fail("Entity declaration handler not called");
- }
- END_TEST
- START_TEST(test_alloc_realloc_subst_public_entity_value) {
- const char *text = "<!DOCTYPE doc SYSTEM 'http://example.org/'>\n"
- "<doc></doc>\n";
- char dtd_text[]
- = "<!ELEMENT doc EMPTY>\n"
- "<!ENTITY % "
- /* Each line is 64 characters */
- "ThisIsAStupidlyLongParameterNameIntendedToTriggerPoolGrowth12345"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- " PUBLIC 'foo' 'bar.ent'>\n"
- "%ThisIsAStupidlyLongParameterNameIntendedToTriggerPoolGrowth12345"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP;";
- int i;
- const int max_realloc_count = 10;
- for (i = 0; i < max_realloc_count; i++) {
- g_reallocation_count = i;
- XML_SetUserData(g_parser, dtd_text);
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- XML_SetExternalEntityRefHandler(g_parser, external_entity_public);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parsing worked despite failing reallocation");
- if (i == max_realloc_count)
- fail("Parsing failed at max reallocation count");
- }
- END_TEST
- START_TEST(test_alloc_parse_public_doctype) {
- const char *text
- = "<?xml version='1.0' encoding='utf-8'?>\n"
- "<!DOCTYPE doc PUBLIC '"
- /* 64 characters per line */
- "http://example.com/a/long/enough/name/to/trigger/pool/growth/zz/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "' 'test'>\n"
- "<doc></doc>";
- int i;
- const int max_alloc_count = 25;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- init_dummy_handlers();
- XML_SetDoctypeDeclHandler(g_parser, dummy_start_doctype_decl_handler,
- dummy_end_doctype_decl_handler);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed at maximum allocation count");
- if (get_dummy_handler_flags()
- != (DUMMY_START_DOCTYPE_DECL_HANDLER_FLAG
- | DUMMY_END_DOCTYPE_DECL_HANDLER_FLAG))
- fail("Doctype handler functions not called");
- }
- END_TEST
- START_TEST(test_alloc_parse_public_doctype_long_name) {
- const char *text
- = "<?xml version='1.0' encoding='utf-8'?>\n"
- "<!DOCTYPE doc PUBLIC 'http://example.com/foo' '"
- /* 64 characters per line */
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNOP"
- "'>\n"
- "<doc></doc>";
- int i;
- const int max_alloc_count = 25;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetDoctypeDeclHandler(g_parser, dummy_start_doctype_decl_handler,
- dummy_end_doctype_decl_handler);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed at maximum allocation count");
- }
- END_TEST
- /* Test foreign DTD handling */
- START_TEST(test_alloc_set_foreign_dtd) {
- const char *text1 = "<?xml version='1.0' encoding='us-ascii'?>\n"
- "<doc>&entity;</doc>";
- char text2[] = "<!ELEMENT doc (#PCDATA)*>";
- int i;
- const int max_alloc_count = 25;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- XML_SetUserData(g_parser, &text2);
- XML_SetExternalEntityRefHandler(g_parser, external_entity_alloc);
- if (XML_UseForeignDTD(g_parser, XML_TRUE) != XML_ERROR_NONE)
- fail("Could not set foreign DTD");
- if (_XML_Parse_SINGLE_BYTES(g_parser, text1, (int)strlen(text1), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed at maximum allocation count");
- }
- END_TEST
- /* Test based on ibm/valid/P32/ibm32v04.xml */
- START_TEST(test_alloc_attribute_enum_value) {
- const char *text = "<?xml version='1.0' standalone='no'?>\n"
- "<!DOCTYPE animal SYSTEM 'test.dtd'>\n"
- "<animal>This is a \n <a/> \n\nyellow tiger</animal>";
- char dtd_text[] = "<!ELEMENT animal (#PCDATA|a)*>\n"
- "<!ELEMENT a EMPTY>\n"
- "<!ATTLIST animal xml:space (default|preserve) 'preserve'>";
- int i;
- const int max_alloc_count = 30;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetExternalEntityRefHandler(g_parser, external_entity_alloc);
- XML_SetUserData(g_parser, dtd_text);
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- /* An attribute list handler provokes a different code path */
- XML_SetAttlistDeclHandler(g_parser, dummy_attlist_decl_handler);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed at maximum allocation count");
- }
- END_TEST
- /* Test attribute enums sufficient to overflow the string pool */
- START_TEST(test_alloc_realloc_attribute_enum_value) {
- const char *text = "<?xml version='1.0' standalone='no'?>\n"
- "<!DOCTYPE animal SYSTEM 'test.dtd'>\n"
- "<animal>This is a yellow tiger</animal>";
- /* We wish to define a collection of attribute enums that will
- * cause the string pool storing them to have to expand. This
- * means more than 1024 bytes, including the parentheses and
- * separator bars.
- */
- char dtd_text[]
- = "<!ELEMENT animal (#PCDATA)*>\n"
- "<!ATTLIST animal thing "
- "(default"
- /* Each line is 64 characters */
- "|ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|BBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|CBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|DBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|EBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|FBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|GBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|HBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|IBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|JBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|KBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|LBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|MBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|NBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|OBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|PBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO)"
- " 'default'>";
- int i;
- const int max_realloc_count = 10;
- for (i = 0; i < max_realloc_count; i++) {
- g_reallocation_count = i;
- XML_SetExternalEntityRefHandler(g_parser, external_entity_alloc);
- XML_SetUserData(g_parser, dtd_text);
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- /* An attribute list handler provokes a different code path */
- XML_SetAttlistDeclHandler(g_parser, dummy_attlist_decl_handler);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing reallocator");
- if (i == max_realloc_count)
- fail("Parse failed at maximum reallocation count");
- }
- END_TEST
- /* Test attribute enums in a #IMPLIED attribute forcing pool growth */
- START_TEST(test_alloc_realloc_implied_attribute) {
- /* Forcing this particular code path is a balancing act. The
- * addition of the closing parenthesis and terminal NUL must be
- * what pushes the string of enums over the 1024-byte limit,
- * otherwise a different code path will pick up the realloc.
- */
- const char *text
- = "<!DOCTYPE doc [\n"
- "<!ELEMENT doc EMPTY>\n"
- "<!ATTLIST doc a "
- /* Each line is 64 characters */
- "(ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|BBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|CBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|DBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|EBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|FBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|GBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|HBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|IBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|JBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|KBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|LBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|MBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|NBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|OBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|PBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMN)"
- " #IMPLIED>\n"
- "]><doc/>";
- int i;
- const int max_realloc_count = 10;
- for (i = 0; i < max_realloc_count; i++) {
- g_reallocation_count = i;
- XML_SetAttlistDeclHandler(g_parser, dummy_attlist_decl_handler);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing reallocator");
- if (i == max_realloc_count)
- fail("Parse failed at maximum reallocation count");
- }
- END_TEST
- /* Test attribute enums in a defaulted attribute forcing pool growth */
- START_TEST(test_alloc_realloc_default_attribute) {
- /* Forcing this particular code path is a balancing act. The
- * addition of the closing parenthesis and terminal NUL must be
- * what pushes the string of enums over the 1024-byte limit,
- * otherwise a different code path will pick up the realloc.
- */
- const char *text
- = "<!DOCTYPE doc [\n"
- "<!ELEMENT doc EMPTY>\n"
- "<!ATTLIST doc a "
- /* Each line is 64 characters */
- "(ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|BBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|CBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|DBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|EBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|FBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|GBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|HBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|IBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|JBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|KBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|LBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|MBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|NBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|OBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO"
- "|PBCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMN)"
- " 'ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNO'"
- ">\n]><doc/>";
- int i;
- const int max_realloc_count = 10;
- for (i = 0; i < max_realloc_count; i++) {
- g_reallocation_count = i;
- XML_SetAttlistDeclHandler(g_parser, dummy_attlist_decl_handler);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing reallocator");
- if (i == max_realloc_count)
- fail("Parse failed at maximum reallocation count");
- }
- END_TEST
- /* Test long notation name with dodgy allocator */
- START_TEST(test_alloc_notation) {
- const char *text
- = "<!DOCTYPE doc [\n"
- "<!NOTATION "
- /* Each line is 64 characters */
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- " SYSTEM 'http://example.org/n'>\n"
- "<!ENTITY e SYSTEM 'http://example.org/e' NDATA "
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- ">\n"
- "<!ELEMENT doc EMPTY>\n"
- "]>\n<doc/>";
- int i;
- const int max_alloc_count = 20;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- init_dummy_handlers();
- XML_SetNotationDeclHandler(g_parser, dummy_notation_decl_handler);
- XML_SetEntityDeclHandler(g_parser, dummy_entity_decl_handler);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite allocation failures");
- if (i == max_alloc_count)
- fail("Parse failed at maximum allocation count");
- if (get_dummy_handler_flags()
- != (DUMMY_ENTITY_DECL_HANDLER_FLAG | DUMMY_NOTATION_DECL_HANDLER_FLAG))
- fail("Entity declaration handler not called");
- }
- END_TEST
- /* Test public notation with dodgy allocator */
- START_TEST(test_alloc_public_notation) {
- const char *text
- = "<!DOCTYPE doc [\n"
- "<!NOTATION note PUBLIC '"
- /* 64 characters per line */
- "http://example.com/a/long/enough/name/to/trigger/pool/growth/zz/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "' 'foo'>\n"
- "<!ENTITY e SYSTEM 'http://example.com/e' NDATA note>\n"
- "<!ELEMENT doc EMPTY>\n"
- "]>\n<doc/>";
- int i;
- const int max_alloc_count = 20;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- init_dummy_handlers();
- XML_SetNotationDeclHandler(g_parser, dummy_notation_decl_handler);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite allocation failures");
- if (i == max_alloc_count)
- fail("Parse failed at maximum allocation count");
- if (get_dummy_handler_flags() != DUMMY_NOTATION_DECL_HANDLER_FLAG)
- fail("Notation handler not called");
- }
- END_TEST
- /* Test public notation with dodgy allocator */
- START_TEST(test_alloc_system_notation) {
- const char *text
- = "<!DOCTYPE doc [\n"
- "<!NOTATION note SYSTEM '"
- /* 64 characters per line */
- "http://example.com/a/long/enough/name/to/trigger/pool/growth/zz/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/ABCDEFGHIJKLMNO/"
- "'>\n"
- "<!ENTITY e SYSTEM 'http://example.com/e' NDATA note>\n"
- "<!ELEMENT doc EMPTY>\n"
- "]>\n<doc/>";
- int i;
- const int max_alloc_count = 20;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- init_dummy_handlers();
- XML_SetNotationDeclHandler(g_parser, dummy_notation_decl_handler);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite allocation failures");
- if (i == max_alloc_count)
- fail("Parse failed at maximum allocation count");
- if (get_dummy_handler_flags() != DUMMY_NOTATION_DECL_HANDLER_FLAG)
- fail("Notation handler not called");
- }
- END_TEST
- START_TEST(test_alloc_nested_groups) {
- const char *text
- = "<!DOCTYPE doc [\n"
- "<!ELEMENT doc "
- /* Sixteen elements per line */
- "(e,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,"
- "(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?"
- "))))))))))))))))))))))))))))))))>\n"
- "<!ELEMENT e EMPTY>"
- "]>\n"
- "<doc><e/></doc>";
- CharData storage;
- int i;
- const int max_alloc_count = 20;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- CharData_Init(&storage);
- XML_SetElementDeclHandler(g_parser, dummy_element_decl_handler);
- XML_SetStartElementHandler(g_parser, record_element_start_handler);
- XML_SetUserData(g_parser, &storage);
- init_dummy_handlers();
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing reallocator");
- if (i == max_alloc_count)
- fail("Parse failed at maximum reallocation count");
- CharData_CheckXMLChars(&storage, XCS("doce"));
- if (get_dummy_handler_flags() != DUMMY_ELEMENT_DECL_HANDLER_FLAG)
- fail("Element handler not fired");
- }
- END_TEST
- START_TEST(test_alloc_realloc_nested_groups) {
- const char *text
- = "<!DOCTYPE doc [\n"
- "<!ELEMENT doc "
- /* Sixteen elements per line */
- "(e,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,"
- "(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?,(e?"
- "))))))))))))))))))))))))))))))))>\n"
- "<!ELEMENT e EMPTY>"
- "]>\n"
- "<doc><e/></doc>";
- CharData storage;
- int i;
- const int max_realloc_count = 10;
- for (i = 0; i < max_realloc_count; i++) {
- g_reallocation_count = i;
- CharData_Init(&storage);
- XML_SetElementDeclHandler(g_parser, dummy_element_decl_handler);
- XML_SetStartElementHandler(g_parser, record_element_start_handler);
- XML_SetUserData(g_parser, &storage);
- init_dummy_handlers();
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing reallocator");
- if (i == max_realloc_count)
- fail("Parse failed at maximum reallocation count");
- CharData_CheckXMLChars(&storage, XCS("doce"));
- if (get_dummy_handler_flags() != DUMMY_ELEMENT_DECL_HANDLER_FLAG)
- fail("Element handler not fired");
- }
- END_TEST
- START_TEST(test_alloc_large_group) {
- const char *text = "<!DOCTYPE doc [\n"
- "<!ELEMENT doc ("
- "a1|a2|a3|a4|a5|a6|a7|a8|"
- "b1|b2|b3|b4|b5|b6|b7|b8|"
- "c1|c2|c3|c4|c5|c6|c7|c8|"
- "d1|d2|d3|d4|d5|d6|d7|d8|"
- "e1"
- ")+>\n"
- "]>\n"
- "<doc>\n"
- "<a1/>\n"
- "</doc>\n";
- int i;
- const int max_alloc_count = 50;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetElementDeclHandler(g_parser, dummy_element_decl_handler);
- init_dummy_handlers();
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed at maximum allocation count");
- if (get_dummy_handler_flags() != DUMMY_ELEMENT_DECL_HANDLER_FLAG)
- fail("Element handler flag not raised");
- }
- END_TEST
- START_TEST(test_alloc_realloc_group_choice) {
- const char *text = "<!DOCTYPE doc [\n"
- "<!ELEMENT doc ("
- "a1|a2|a3|a4|a5|a6|a7|a8|"
- "b1|b2|b3|b4|b5|b6|b7|b8|"
- "c1|c2|c3|c4|c5|c6|c7|c8|"
- "d1|d2|d3|d4|d5|d6|d7|d8|"
- "e1"
- ")+>\n"
- "]>\n"
- "<doc>\n"
- "<a1/>\n"
- "<b2 attr='foo'>This is a foo</b2>\n"
- "<c3></c3>\n"
- "</doc>\n";
- int i;
- const int max_realloc_count = 10;
- for (i = 0; i < max_realloc_count; i++) {
- g_reallocation_count = i;
- XML_SetElementDeclHandler(g_parser, dummy_element_decl_handler);
- init_dummy_handlers();
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing reallocator");
- if (i == max_realloc_count)
- fail("Parse failed at maximum reallocation count");
- if (get_dummy_handler_flags() != DUMMY_ELEMENT_DECL_HANDLER_FLAG)
- fail("Element handler flag not raised");
- }
- END_TEST
- START_TEST(test_alloc_pi_in_epilog) {
- const char *text = "<doc></doc>\n"
- "<?pi in epilog?>";
- int i;
- const int max_alloc_count = 15;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetProcessingInstructionHandler(g_parser, dummy_pi_handler);
- init_dummy_handlers();
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse completed despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed at maximum allocation count");
- if (get_dummy_handler_flags() != DUMMY_PI_HANDLER_FLAG)
- fail("Processing instruction handler not invoked");
- }
- END_TEST
- START_TEST(test_alloc_comment_in_epilog) {
- const char *text = "<doc></doc>\n"
- "<!-- comment in epilog -->";
- int i;
- const int max_alloc_count = 15;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetCommentHandler(g_parser, dummy_comment_handler);
- init_dummy_handlers();
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse completed despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed at maximum allocation count");
- if (get_dummy_handler_flags() != DUMMY_COMMENT_HANDLER_FLAG)
- fail("Processing instruction handler not invoked");
- }
- END_TEST
- START_TEST(test_alloc_realloc_long_attribute_value) {
- const char *text
- = "<!DOCTYPE doc [<!ENTITY foo '"
- /* Each line is 64 characters */
- "This entity will be substituted as an attribute value, and is "
- "calculated to be exactly long enough that the terminating NUL "
- "that the library adds internally will trigger the string pool to"
- "grow. GHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "'>]>\n"
- "<doc a='&foo;'></doc>";
- int i;
- const int max_realloc_count = 10;
- for (i = 0; i < max_realloc_count; i++) {
- g_reallocation_count = i;
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing reallocator");
- if (i == max_realloc_count)
- fail("Parse failed at maximum reallocation count");
- }
- END_TEST
- START_TEST(test_alloc_attribute_whitespace) {
- const char *text = "<doc a=' '></doc>";
- int i;
- const int max_alloc_count = 15;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed at maximum allocation count");
- }
- END_TEST
- START_TEST(test_alloc_attribute_predefined_entity) {
- const char *text = "<doc a='&'></doc>";
- int i;
- const int max_alloc_count = 15;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed at maximum allocation count");
- }
- END_TEST
- /* Test that a character reference at the end of a suitably long
- * default value for an attribute can trigger pool growth, and recovers
- * if the allocator fails on it.
- */
- START_TEST(test_alloc_long_attr_default_with_char_ref) {
- const char *text
- = "<!DOCTYPE doc [<!ATTLIST doc a CDATA '"
- /* 64 characters per line */
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHI"
- "1'>]>\n"
- "<doc/>";
- int i;
- const int max_alloc_count = 20;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed at maximum allocation count");
- }
- END_TEST
- /* Test that a long character reference substitution triggers a pool
- * expansion correctly for an attribute value.
- */
- START_TEST(test_alloc_long_attr_value) {
- const char *text
- = "<!DOCTYPE test [<!ENTITY foo '\n"
- /* 64 characters per line */
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "'>]>\n"
- "<test a='&foo;'/>";
- int i;
- const int max_alloc_count = 25;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing allocator");
- if (i == max_alloc_count)
- fail("Parse failed at maximum allocation count");
- }
- END_TEST
- /* Test that an error in a nested parameter entity substitution is
- * handled correctly. It seems unlikely that the code path being
- * exercised can be reached purely by carefully crafted XML, but an
- * allocation error in the right place will definitely do it.
- */
- START_TEST(test_alloc_nested_entities) {
- const char *text = "<!DOCTYPE doc SYSTEM 'http://example.org/one.ent'>\n"
- "<doc />";
- ExtFaults test_data
- = {"<!ENTITY % pe1 '"
- /* 64 characters per line */
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "'>\n"
- "<!ENTITY % pe2 '%pe1;'>\n"
- "<!ENTITY % pe3 '%pe2;'>",
- "Memory Fail not faulted", NULL, XML_ERROR_NO_MEMORY};
- /* Causes an allocation error in a nested storeEntityValue() */
- g_allocation_count = 12;
- XML_SetUserData(g_parser, &test_data);
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- XML_SetExternalEntityRefHandler(g_parser, external_entity_faulter);
- expect_failure(text, XML_ERROR_EXTERNAL_ENTITY_HANDLING,
- "Entity allocation failure not noted");
- }
- END_TEST
- START_TEST(test_alloc_realloc_param_entity_newline) {
- const char *text = "<!DOCTYPE doc SYSTEM 'http://example.org/'>\n"
- "<doc/>";
- char dtd_text[]
- = "<!ENTITY % pe '<!ATTLIST doc att CDATA \""
- /* 64 characters per line */
- "This default value is carefully crafted so that the carriage "
- "return right at the end of the entity string causes an internal "
- "string pool to have to grow. This allows us to test the alloc "
- "failure path from that point. OPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDE"
- "\">\n'>"
- "%pe;\n";
- int i;
- const int max_realloc_count = 5;
- for (i = 0; i < max_realloc_count; i++) {
- g_reallocation_count = i;
- XML_SetUserData(g_parser, dtd_text);
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- XML_SetExternalEntityRefHandler(g_parser, external_entity_alloc);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing reallocator");
- if (i == max_realloc_count)
- fail("Parse failed at maximum reallocation count");
- }
- END_TEST
- START_TEST(test_alloc_realloc_ce_extends_pe) {
- const char *text = "<!DOCTYPE doc SYSTEM 'http://example.org/'>\n"
- "<doc/>";
- char dtd_text[]
- = "<!ENTITY % pe '<!ATTLIST doc att CDATA \""
- /* 64 characters per line */
- "This default value is carefully crafted so that the character "
- "entity at the end causes an internal string pool to have to "
- "grow. This allows us to test the allocation failure path from "
- "that point onwards. EFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGHIJKLMNOP"
- "ABCDEFGHIJKLMNOPABCDEFGHIJKLMNOPABCDEFGQ"
- "\">\n'>"
- "%pe;\n";
- int i;
- const int max_realloc_count = 5;
- for (i = 0; i < max_realloc_count; i++) {
- g_reallocation_count = i;
- XML_SetUserData(g_parser, dtd_text);
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- XML_SetExternalEntityRefHandler(g_parser, external_entity_alloc);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing reallocator");
- if (i == max_realloc_count)
- fail("Parse failed at maximum reallocation count");
- }
- END_TEST
- START_TEST(test_alloc_realloc_attributes) {
- const char *text = "<!DOCTYPE doc [\n"
- " <!ATTLIST doc\n"
- " a1 (a|b|c) 'a'\n"
- " a2 (foo|bar) #IMPLIED\n"
- " a3 NMTOKEN #IMPLIED\n"
- " a4 NMTOKENS #IMPLIED\n"
- " a5 ID #IMPLIED\n"
- " a6 IDREF #IMPLIED\n"
- " a7 IDREFS #IMPLIED\n"
- " a8 ENTITY #IMPLIED\n"
- " a9 ENTITIES #IMPLIED\n"
- " a10 CDATA #IMPLIED\n"
- " >]>\n"
- "<doc>wombat</doc>\n";
- int i;
- const int max_realloc_count = 5;
- for (i = 0; i < max_realloc_count; i++) {
- g_reallocation_count = i;
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parse succeeded despite failing reallocator");
- if (i == max_realloc_count)
- fail("Parse failed at maximum reallocation count");
- }
- END_TEST
- START_TEST(test_alloc_long_doc_name) {
- const char *text =
- /* 64 characters per line */
- "<LongRootElementNameThatWillCauseTheNextAllocationToExpandTheStr"
- "ingPoolForTheDTDQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AZ"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AZ"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AZ"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AZ"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AZ"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AZ"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AZ"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AZ"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AZ"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AZ"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AZ"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AZ"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AZ"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AZ"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AZ"
- " a='1'/>";
- int i;
- const int max_alloc_count = 20;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parsing worked despite failing reallocations");
- else if (i == max_alloc_count)
- fail("Parsing failed even at max reallocation count");
- }
- END_TEST
- START_TEST(test_alloc_long_base) {
- const char *text = "<!DOCTYPE doc [\n"
- " <!ENTITY e SYSTEM 'foo'>\n"
- "]>\n"
- "<doc>&e;</doc>";
- char entity_text[] = "Hello world";
- const XML_Char *base =
- /* 64 characters per line */
- /* clang-format off */
- XCS("LongBaseURI/that/will/overflow/an/internal/buffer/and/cause/it/t")
- XCS("o/have/to/grow/PQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789A/")
- XCS("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789A/")
- XCS("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789A/")
- XCS("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789A/")
- XCS("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789A/")
- XCS("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789A/")
- XCS("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789A/")
- XCS("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789A/")
- XCS("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789A/")
- XCS("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789A/")
- XCS("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789A/")
- XCS("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789A/")
- XCS("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789A/")
- XCS("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789A/")
- XCS("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789A/");
- /* clang-format on */
- int i;
- const int max_alloc_count = 25;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetUserData(g_parser, entity_text);
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- XML_SetExternalEntityRefHandler(g_parser, external_entity_alloc);
- if (XML_SetBase(g_parser, base) == XML_STATUS_ERROR) {
- XML_ParserReset(g_parser, NULL);
- continue;
- }
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parsing worked despite failing allocations");
- else if (i == max_alloc_count)
- fail("Parsing failed even at max allocation count");
- }
- END_TEST
- START_TEST(test_alloc_long_public_id) {
- const char *text
- = "<!DOCTYPE doc [\n"
- " <!ENTITY e PUBLIC '"
- /* 64 characters per line */
- "LongPublicIDThatShouldResultInAnInternalStringPoolGrowingAtASpec"
- "ificMomentKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "' 'bar'>\n"
- "]>\n"
- "<doc>&e;</doc>";
- char entity_text[] = "Hello world";
- int i;
- const int max_alloc_count = 40;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetUserData(g_parser, entity_text);
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- XML_SetExternalEntityRefHandler(g_parser, external_entity_alloc);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parsing worked despite failing allocations");
- else if (i == max_alloc_count)
- fail("Parsing failed even at max allocation count");
- }
- END_TEST
- START_TEST(test_alloc_long_entity_value) {
- const char *text
- = "<!DOCTYPE doc [\n"
- " <!ENTITY e1 '"
- /* 64 characters per line */
- "Long entity value that should provoke a string pool to grow whil"
- "e setting up to parse the external entity below. xyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "'>\n"
- " <!ENTITY e2 SYSTEM 'bar'>\n"
- "]>\n"
- "<doc>&e2;</doc>";
- char entity_text[] = "Hello world";
- int i;
- const int max_alloc_count = 40;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetUserData(g_parser, entity_text);
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- XML_SetExternalEntityRefHandler(g_parser, external_entity_alloc);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parsing worked despite failing allocations");
- else if (i == max_alloc_count)
- fail("Parsing failed even at max allocation count");
- }
- END_TEST
- START_TEST(test_alloc_long_notation) {
- const char *text
- = "<!DOCTYPE doc [\n"
- " <!NOTATION note SYSTEM '"
- /* 64 characters per line */
- "ALongNotationNameThatShouldProvokeStringPoolGrowthWhileCallingAn"
- "ExternalEntityParserUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "'>\n"
- " <!ENTITY e1 SYSTEM 'foo' NDATA "
- /* 64 characters per line */
- "ALongNotationNameThatShouldProvokeStringPoolGrowthWhileCallingAn"
- "ExternalEntityParserUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789AB"
- ">\n"
- " <!ENTITY e2 SYSTEM 'bar'>\n"
- "]>\n"
- "<doc>&e2;</doc>";
- ExtOption options[]
- = {{XCS("foo"), "Entity Foo"}, {XCS("bar"), "Entity Bar"}, {NULL, NULL}};
- int i;
- const int max_alloc_count = 40;
- for (i = 0; i < max_alloc_count; i++) {
- g_allocation_count = i;
- XML_SetUserData(g_parser, options);
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- XML_SetExternalEntityRefHandler(g_parser, external_entity_optioner);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- break;
- /* See comment in test_alloc_parse_xdecl() */
- alloc_teardown();
- alloc_setup();
- }
- if (i == 0)
- fail("Parsing worked despite failing allocations");
- else if (i == max_alloc_count)
- fail("Parsing failed even at max allocation count");
- }
- END_TEST
- START_TEST(test_alloc_reset_after_external_entity_parser_create_fail) {
- const char *const text = "<!DOCTYPE doc SYSTEM 'foo'><doc/>";
- XML_SetExternalEntityRefHandler(
- g_parser, external_entity_parser_create_alloc_fail_handler);
- XML_SetParamEntityParsing(g_parser, XML_PARAM_ENTITY_PARSING_ALWAYS);
- if (_XML_Parse_SINGLE_BYTES(g_parser, text, (int)strlen(text), XML_TRUE)
- != XML_STATUS_ERROR)
- fail("Call to parse was expected to fail");
- if (XML_GetErrorCode(g_parser) != XML_ERROR_EXTERNAL_ENTITY_HANDLING)
- fail("Call to parse was expected to fail from the external entity handler");
- XML_ParserReset(g_parser, NULL);
- }
- END_TEST
- #if XML_GE == 1
- static size_t
- sizeRecordedFor(void *ptr) {
- return *(size_t *)((char *)ptr - EXPAT_MALLOC_PADDING - sizeof(size_t));
- }
- #endif // XML_GE == 1
- START_TEST(test_alloc_tracker_size_recorded) {
- XML_Memory_Handling_Suite memsuite = {malloc, realloc, free};
- bool values[] = {true, false};
- for (size_t i = 0; i < sizeof(values) / sizeof(values[0]); i++) {
- const bool useMemSuite = values[i];
- set_subtest("useMemSuite=%d", (int)useMemSuite);
- XML_Parser parser = useMemSuite
- ? XML_ParserCreate_MM(NULL, &memsuite, XCS("|"))
- : XML_ParserCreate(NULL);
- #if XML_GE == 1
- void *ptr = expat_malloc(parser, 10, -1);
- assert_true(ptr != NULL);
- assert_true(sizeRecordedFor(ptr) == 10);
- assert_true(expat_realloc(parser, ptr, SIZE_MAX / 2, -1) == NULL);
- assert_true(sizeRecordedFor(ptr) == 10); // i.e. unchanged
- ptr = expat_realloc(parser, ptr, 20, -1);
- assert_true(ptr != NULL);
- assert_true(sizeRecordedFor(ptr) == 20);
- expat_free(parser, ptr, -1);
- #endif
- XML_ParserFree(parser);
- }
- }
- END_TEST
- START_TEST(test_alloc_tracker_pointer_alignment) {
- XML_Parser parser = XML_ParserCreate(NULL);
- #if XML_GE == 1
- assert_true(sizeof(long long) >= sizeof(size_t)); // self-test
- long long *const ptr
- = (long long *)expat_malloc(parser, 4 * sizeof(long long), -1);
- ptr[0] = 0LL;
- ptr[1] = 1LL;
- ptr[2] = 2LL;
- ptr[3] = 3LL;
- expat_free(parser, ptr, -1);
- #endif
- XML_ParserFree(parser);
- }
- END_TEST
- START_TEST(test_alloc_tracker_maximum_amplification) {
- if (g_reparseDeferralEnabledDefault == XML_TRUE) {
- return;
- }
- XML_Parser parser = XML_ParserCreate(NULL);
- // Get .m_accounting.countBytesDirect from 0 to 3
- const char *const chunk = "<e>";
- assert_true(_XML_Parse_SINGLE_BYTES(parser, chunk, (int)strlen(chunk),
- /*isFinal=*/XML_FALSE)
- == XML_STATUS_OK);
- #if XML_GE == 1
- // Stop activation threshold from interfering
- assert_true(XML_SetAllocTrackerActivationThreshold(parser, 0) == XML_TRUE);
- // Exceed maximum amplification: should be rejected.
- assert_true(expat_malloc(parser, 1000, -1) == NULL);
- // Increase maximum amplification, and try the same amount once more: should
- // work.
- assert_true(XML_SetAllocTrackerMaximumAmplification(parser, 3000.0f)
- == XML_TRUE);
- void *const ptr = expat_malloc(parser, 1000, -1);
- assert_true(ptr != NULL);
- expat_free(parser, ptr, -1);
- #endif
- XML_ParserFree(parser);
- }
- END_TEST
- START_TEST(test_alloc_tracker_threshold) {
- XML_Parser parser = XML_ParserCreate(NULL);
- #if XML_GE == 1
- // Exceed maximum amplification *before* (default) threshold: should work.
- void *const ptr = expat_malloc(parser, 1000, -1);
- assert_true(ptr != NULL);
- expat_free(parser, ptr, -1);
- // Exceed maximum amplification *after* threshold: should be rejected.
- assert_true(XML_SetAllocTrackerActivationThreshold(parser, 999) == XML_TRUE);
- assert_true(expat_malloc(parser, 1000, -1) == NULL);
- #endif
- XML_ParserFree(parser);
- }
- END_TEST
- START_TEST(test_alloc_tracker_getbuffer_unlimited) {
- XML_Parser parser = XML_ParserCreate(NULL);
- #if XML_GE == 1
- // Artificially lower threshold
- assert_true(XML_SetAllocTrackerActivationThreshold(parser, 0) == XML_TRUE);
- // Self-test: Prove that threshold is as rejecting as expected
- assert_true(expat_malloc(parser, 1000, -1) == NULL);
- #endif
- // XML_GetBuffer should be allowed to pass, though
- assert_true(XML_GetBuffer(parser, 1000) != NULL);
- XML_ParserFree(parser);
- }
- END_TEST
- START_TEST(test_alloc_tracker_api) {
- XML_Parser parserWithoutParent = XML_ParserCreate(NULL);
- XML_Parser parserWithParent = XML_ExternalEntityParserCreate(
- parserWithoutParent, XCS("entity123"), NULL);
- if (parserWithoutParent == NULL)
- fail("parserWithoutParent is NULL");
- if (parserWithParent == NULL)
- fail("parserWithParent is NULL");
- #if XML_GE == 1
- // XML_SetAllocTrackerMaximumAmplification, error cases
- if (XML_SetAllocTrackerMaximumAmplification(NULL, 123.0f) == XML_TRUE)
- fail("Call with NULL parser is NOT supposed to succeed");
- if (XML_SetAllocTrackerMaximumAmplification(parserWithParent, 123.0f)
- == XML_TRUE)
- fail("Call with non-root parser is NOT supposed to succeed");
- if (XML_SetAllocTrackerMaximumAmplification(parserWithoutParent, NAN)
- == XML_TRUE)
- fail("Call with NaN limit is NOT supposed to succeed");
- if (XML_SetAllocTrackerMaximumAmplification(parserWithoutParent, -1.0f)
- == XML_TRUE)
- fail("Call with negative limit is NOT supposed to succeed");
- if (XML_SetAllocTrackerMaximumAmplification(parserWithoutParent, 0.9f)
- == XML_TRUE)
- fail("Call with positive limit <1.0 is NOT supposed to succeed");
- // XML_SetAllocTrackerMaximumAmplification, success cases
- if (XML_SetAllocTrackerMaximumAmplification(parserWithoutParent, 1.0f)
- == XML_FALSE)
- fail("Call with positive limit >=1.0 is supposed to succeed");
- if (XML_SetAllocTrackerMaximumAmplification(parserWithoutParent, 123456.789f)
- == XML_FALSE)
- fail("Call with positive limit >=1.0 is supposed to succeed");
- if (XML_SetAllocTrackerMaximumAmplification(parserWithoutParent, INFINITY)
- == XML_FALSE)
- fail("Call with positive limit >=1.0 is supposed to succeed");
- // XML_SetAllocTrackerActivationThreshold, error cases
- if (XML_SetAllocTrackerActivationThreshold(NULL, 123) == XML_TRUE)
- fail("Call with NULL parser is NOT supposed to succeed");
- if (XML_SetAllocTrackerActivationThreshold(parserWithParent, 123) == XML_TRUE)
- fail("Call with non-root parser is NOT supposed to succeed");
- // XML_SetAllocTrackerActivationThreshold, success cases
- if (XML_SetAllocTrackerActivationThreshold(parserWithoutParent, 123)
- == XML_FALSE)
- fail("Call with non-NULL parentless parser is supposed to succeed");
- #endif // XML_GE == 1
- XML_ParserFree(parserWithParent);
- XML_ParserFree(parserWithoutParent);
- }
- END_TEST
- START_TEST(test_mem_api_cycle) {
- XML_Parser parser = XML_ParserCreate(NULL);
- void *ptr = XML_MemMalloc(parser, 10);
- assert_true(ptr != NULL);
- memset(ptr, 'x', 10); // assert writability, with ASan in mind
- ptr = XML_MemRealloc(parser, ptr, 20);
- assert_true(ptr != NULL);
- memset(ptr, 'y', 20); // assert writability, with ASan in mind
- XML_MemFree(parser, ptr);
- XML_ParserFree(parser);
- }
- END_TEST
- START_TEST(test_mem_api_unlimited) {
- XML_Parser parser = XML_ParserCreate(NULL);
- #if XML_GE == 1
- assert_true(XML_SetAllocTrackerActivationThreshold(parser, 0) == XML_TRUE);
- #endif
- void *ptr = XML_MemMalloc(parser, 1000);
- assert_true(ptr != NULL);
- ptr = XML_MemRealloc(parser, ptr, 2000);
- assert_true(ptr != NULL);
- XML_MemFree(parser, ptr);
- XML_ParserFree(parser);
- }
- END_TEST
- void
- make_alloc_test_case(Suite *s) {
- TCase *tc_alloc = tcase_create("allocation tests");
- suite_add_tcase(s, tc_alloc);
- tcase_add_checked_fixture(tc_alloc, alloc_setup, alloc_teardown);
- tcase_add_test(tc_alloc, test_alloc_parse_xdecl);
- tcase_add_test(tc_alloc, test_alloc_parse_xdecl_2);
- tcase_add_test(tc_alloc, test_alloc_parse_pi);
- tcase_add_test(tc_alloc, test_alloc_parse_pi_2);
- tcase_add_test(tc_alloc, test_alloc_parse_pi_3);
- tcase_add_test(tc_alloc, test_alloc_parse_comment);
- tcase_add_test(tc_alloc, test_alloc_parse_comment_2);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_create_external_parser);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_run_external_parser);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_dtd_copy_default_atts);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_external_entity);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_ext_entity_set_encoding);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_internal_entity);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_parameter_entity);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_dtd_default_handling);
- tcase_add_test(tc_alloc, test_alloc_explicit_encoding);
- tcase_add_test(tc_alloc, test_alloc_set_base);
- tcase_add_test(tc_alloc, test_alloc_realloc_buffer);
- tcase_add_test__if_xml_ge(tc_alloc, test_alloc_ext_entity_realloc_buffer);
- tcase_add_test(tc_alloc, test_alloc_realloc_many_attributes);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_public_entity_value);
- tcase_add_test__ifdef_xml_dtd(tc_alloc,
- test_alloc_realloc_subst_public_entity_value);
- tcase_add_test(tc_alloc, test_alloc_parse_public_doctype);
- tcase_add_test(tc_alloc, test_alloc_parse_public_doctype_long_name);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_set_foreign_dtd);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_attribute_enum_value);
- tcase_add_test__ifdef_xml_dtd(tc_alloc,
- test_alloc_realloc_attribute_enum_value);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_realloc_implied_attribute);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_realloc_default_attribute);
- tcase_add_test__if_xml_ge(tc_alloc, test_alloc_notation);
- tcase_add_test(tc_alloc, test_alloc_public_notation);
- tcase_add_test(tc_alloc, test_alloc_system_notation);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_nested_groups);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_realloc_nested_groups);
- tcase_add_test(tc_alloc, test_alloc_large_group);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_realloc_group_choice);
- tcase_add_test(tc_alloc, test_alloc_pi_in_epilog);
- tcase_add_test(tc_alloc, test_alloc_comment_in_epilog);
- tcase_add_test__ifdef_xml_dtd(tc_alloc,
- test_alloc_realloc_long_attribute_value);
- tcase_add_test(tc_alloc, test_alloc_attribute_whitespace);
- tcase_add_test(tc_alloc, test_alloc_attribute_predefined_entity);
- tcase_add_test(tc_alloc, test_alloc_long_attr_default_with_char_ref);
- tcase_add_test__if_xml_ge(tc_alloc, test_alloc_long_attr_value);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_nested_entities);
- tcase_add_test__ifdef_xml_dtd(tc_alloc,
- test_alloc_realloc_param_entity_newline);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_realloc_ce_extends_pe);
- tcase_add_test__ifdef_xml_dtd(tc_alloc, test_alloc_realloc_attributes);
- tcase_add_test(tc_alloc, test_alloc_long_doc_name);
- tcase_add_test__if_xml_ge(tc_alloc, test_alloc_long_base);
- tcase_add_test__if_xml_ge(tc_alloc, test_alloc_long_public_id);
- tcase_add_test__if_xml_ge(tc_alloc, test_alloc_long_entity_value);
- tcase_add_test__if_xml_ge(tc_alloc, test_alloc_long_notation);
- tcase_add_test__ifdef_xml_dtd(
- tc_alloc, test_alloc_reset_after_external_entity_parser_create_fail);
- tcase_add_test__if_xml_ge(tc_alloc, test_alloc_tracker_size_recorded);
- tcase_add_test__if_xml_ge(tc_alloc, test_alloc_tracker_pointer_alignment);
- tcase_add_test__if_xml_ge(tc_alloc, test_alloc_tracker_maximum_amplification);
- tcase_add_test__if_xml_ge(tc_alloc, test_alloc_tracker_threshold);
- tcase_add_test__if_xml_ge(tc_alloc, test_alloc_tracker_getbuffer_unlimited);
- tcase_add_test__if_xml_ge(tc_alloc, test_alloc_tracker_api);
- tcase_add_test(tc_alloc, test_mem_api_cycle);
- tcase_add_test__if_xml_ge(tc_alloc, test_mem_api_unlimited);
- }
|