| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205220622072208220922102211221222132214221522162217221822192220222122222223222422252226222722282229223022312232223322342235223622372238223922402241224222432244224522462247224822492250225122522253225422552256225722582259226022612262226322642265226622672268226922702271227222732274227522762277227822792280228122822283228422852286228722882289229022912292229322942295229622972298229923002301230223032304230523062307230823092310231123122313231423152316231723182319232023212322232323242325232623272328232923302331233223332334233523362337233823392340234123422343234423452346234723482349235023512352235323542355235623572358235923602361236223632364236523662367236823692370237123722373237423752376237723782379238023812382238323842385238623872388238923902391239223932394239523962397239823992400240124022403240424052406240724082409241024112412241324142415241624172418241924202421242224232424242524262427242824292430243124322433243424352436243724382439244024412442244324442445244624472448244924502451245224532454245524562457245824592460246124622463246424652466246724682469247024712472247324742475247624772478247924802481248224832484248524862487248824892490249124922493249424952496249724982499250025012502250325042505250625072508250925102511251225132514251525162517251825192520252125222523252425252526252725282529253025312532253325342535253625372538253925402541254225432544254525462547254825492550255125522553255425552556255725582559256025612562256325642565256625672568256925702571257225732574257525762577257825792580258125822583258425852586258725882589259025912592259325942595259625972598259926002601260226032604260526062607260826092610261126122613261426152616261726182619262026212622262326242625262626272628262926302631263226332634263526362637263826392640264126422643264426452646264726482649265026512652265326542655265626572658265926602661266226632664266526662667266826692670267126722673267426752676267726782679268026812682268326842685268626872688268926902691269226932694269526962697269826992700270127022703270427052706270727082709271027112712271327142715271627172718271927202721272227232724272527262727272827292730273127322733273427352736273727382739274027412742274327442745274627472748274927502751275227532754275527562757275827592760276127622763276427652766276727682769277027712772277327742775277627772778277927802781278227832784278527862787278827892790279127922793279427952796279727982799280028012802280328042805280628072808280928102811281228132814281528162817281828192820282128222823282428252826282728282829283028312832283328342835283628372838283928402841284228432844284528462847284828492850285128522853285428552856285728582859286028612862286328642865286628672868286928702871287228732874287528762877287828792880288128822883288428852886288728882889289028912892289328942895289628972898289929002901290229032904290529062907290829092910291129122913291429152916291729182919292029212922292329242925292629272928292929302931293229332934293529362937293829392940294129422943294429452946294729482949295029512952295329542955295629572958295929602961296229632964296529662967296829692970297129722973297429752976297729782979298029812982298329842985298629872988298929902991299229932994299529962997299829993000300130023003300430053006300730083009301030113012301330143015301630173018301930203021302230233024302530263027302830293030303130323033303430353036303730383039304030413042304330443045304630473048304930503051305230533054305530563057305830593060306130623063306430653066306730683069307030713072307330743075307630773078307930803081308230833084308530863087308830893090309130923093309430953096309730983099310031013102310331043105310631073108310931103111311231133114311531163117311831193120312131223123312431253126312731283129313031313132313331343135313631373138313931403141314231433144314531463147314831493150315131523153315431553156315731583159316031613162316331643165316631673168316931703171317231733174317531763177317831793180318131823183318431853186318731883189319031913192319331943195319631973198319932003201320232033204320532063207320832093210321132123213321432153216321732183219322032213222322332243225322632273228322932303231323232333234323532363237323832393240324132423243324432453246324732483249325032513252325332543255325632573258325932603261326232633264326532663267326832693270327132723273327432753276327732783279328032813282328332843285328632873288328932903291329232933294329532963297329832993300330133023303330433053306330733083309331033113312331333143315331633173318331933203321332233233324332533263327332833293330333133323333333433353336333733383339334033413342334333443345334633473348334933503351335233533354335533563357335833593360336133623363336433653366336733683369337033713372337333743375337633773378337933803381338233833384338533863387338833893390339133923393339433953396339733983399340034013402340334043405340634073408340934103411341234133414341534163417341834193420342134223423342434253426342734283429343034313432343334343435343634373438343934403441344234433444344534463447344834493450345134523453345434553456345734583459346034613462346334643465346634673468346934703471347234733474347534763477347834793480348134823483348434853486348734883489349034913492349334943495349634973498349935003501350235033504350535063507350835093510351135123513351435153516351735183519352035213522352335243525352635273528352935303531353235333534353535363537353835393540354135423543354435453546354735483549355035513552355335543555355635573558355935603561356235633564356535663567356835693570357135723573357435753576357735783579358035813582358335843585358635873588358935903591359235933594359535963597359835993600360136023603360436053606360736083609361036113612361336143615361636173618361936203621362236233624362536263627362836293630363136323633363436353636363736383639364036413642364336443645364636473648364936503651365236533654365536563657365836593660366136623663366436653666366736683669367036713672367336743675367636773678367936803681368236833684368536863687368836893690369136923693369436953696369736983699370037013702370337043705370637073708370937103711371237133714371537163717371837193720372137223723372437253726372737283729373037313732373337343735373637373738373937403741374237433744374537463747374837493750375137523753375437553756375737583759376037613762376337643765376637673768376937703771377237733774377537763777377837793780378137823783378437853786378737883789379037913792379337943795379637973798379938003801380238033804380538063807380838093810381138123813381438153816381738183819382038213822382338243825382638273828382938303831383238333834383538363837383838393840384138423843384438453846384738483849385038513852385338543855385638573858385938603861386238633864386538663867386838693870387138723873387438753876387738783879388038813882388338843885388638873888388938903891389238933894389538963897389838993900390139023903390439053906390739083909391039113912391339143915391639173918391939203921392239233924392539263927392839293930393139323933393439353936393739383939394039413942394339443945394639473948394939503951395239533954395539563957395839593960396139623963396439653966396739683969397039713972397339743975397639773978397939803981398239833984398539863987398839893990399139923993399439953996399739983999400040014002400340044005400640074008400940104011401240134014401540164017401840194020402140224023402440254026402740284029403040314032403340344035403640374038403940404041404240434044404540464047404840494050405140524053405440554056405740584059406040614062406340644065406640674068406940704071407240734074407540764077407840794080408140824083408440854086408740884089409040914092409340944095409640974098409941004101410241034104410541064107410841094110411141124113411441154116411741184119412041214122412341244125412641274128412941304131413241334134413541364137413841394140414141424143414441454146414741484149415041514152415341544155415641574158415941604161416241634164416541664167416841694170417141724173417441754176417741784179418041814182418341844185418641874188418941904191419241934194419541964197419841994200420142024203420442054206420742084209421042114212421342144215421642174218421942204221422242234224422542264227422842294230423142324233423442354236423742384239424042414242424342444245424642474248424942504251425242534254425542564257425842594260426142624263426442654266426742684269427042714272427342744275427642774278427942804281428242834284428542864287428842894290429142924293429442954296429742984299430043014302430343044305430643074308430943104311431243134314431543164317431843194320432143224323432443254326432743284329433043314332433343344335433643374338433943404341434243434344434543464347434843494350435143524353435443554356435743584359436043614362436343644365436643674368436943704371437243734374437543764377437843794380438143824383438443854386438743884389439043914392439343944395439643974398439944004401440244034404440544064407440844094410441144124413441444154416441744184419442044214422442344244425442644274428442944304431443244334434443544364437443844394440444144424443444444454446444744484449445044514452445344544455445644574458445944604461446244634464446544664467446844694470447144724473447444754476447744784479448044814482448344844485448644874488448944904491449244934494449544964497449844994500450145024503450445054506450745084509451045114512451345144515451645174518451945204521452245234524452545264527452845294530453145324533453445354536453745384539454045414542454345444545454645474548454945504551455245534554455545564557455845594560456145624563456445654566456745684569457045714572457345744575457645774578457945804581458245834584458545864587458845894590459145924593459445954596459745984599460046014602460346044605460646074608460946104611461246134614461546164617461846194620462146224623462446254626462746284629463046314632463346344635463646374638463946404641464246434644464546464647464846494650465146524653465446554656465746584659466046614662466346644665466646674668466946704671467246734674467546764677467846794680468146824683468446854686468746884689469046914692469346944695469646974698469947004701470247034704470547064707470847094710471147124713 | 
/* * xmlwriter.c: XML text writer implementation * * For license and disclaimer see the license and disclaimer of * libxml2. * * alfred@mickautsch.de */#define IN_LIBXML#include "libxml.h"#include <string.h>#include <libxml/xmlmemory.h>#include <libxml/parser.h>#include <libxml/uri.h>#include <libxml/HTMLtree.h>#ifdef LIBXML_WRITER_ENABLED#include <libxml/xmlwriter.h>#define B64LINELEN 72#define B64CRLF "\r\n"/* * The following VA_COPY was coded following an example in * the Samba project.  It may not be sufficient for some * esoteric implementations of va_list (i.e. it may need * something involving a memcpy) but (hopefully) will be * sufficient for libxml2. */#ifndef VA_COPY  #ifdef HAVE_VA_COPY    #define VA_COPY(dest, src) va_copy(dest, src)  #else    #ifdef HAVE___VA_COPY      #define VA_COPY(dest,src) __va_copy(dest, src)    #else      #define VA_COPY(dest,src) (dest) = (src)    #endif  #endif#endif/* * Types are kept private */typedef enum {    XML_TEXTWRITER_NONE = 0,    XML_TEXTWRITER_NAME,    XML_TEXTWRITER_ATTRIBUTE,    XML_TEXTWRITER_TEXT,    XML_TEXTWRITER_PI,    XML_TEXTWRITER_PI_TEXT,    XML_TEXTWRITER_CDATA,    XML_TEXTWRITER_DTD,    XML_TEXTWRITER_DTD_TEXT,    XML_TEXTWRITER_DTD_ELEM,    XML_TEXTWRITER_DTD_ELEM_TEXT,    XML_TEXTWRITER_DTD_ATTL,    XML_TEXTWRITER_DTD_ATTL_TEXT,    XML_TEXTWRITER_DTD_ENTY,    /* entity */    XML_TEXTWRITER_DTD_ENTY_TEXT,    XML_TEXTWRITER_DTD_PENT,    /* parameter entity */    XML_TEXTWRITER_COMMENT} xmlTextWriterState;typedef struct _xmlTextWriterStackEntry xmlTextWriterStackEntry;struct _xmlTextWriterStackEntry {    xmlChar *name;    xmlTextWriterState state;};typedef struct _xmlTextWriterNsStackEntry xmlTextWriterNsStackEntry;struct _xmlTextWriterNsStackEntry {    xmlChar *prefix;    xmlChar *uri;    xmlLinkPtr elem;};struct _xmlTextWriter {    xmlOutputBufferPtr out;     /* output buffer */    xmlListPtr nodes;           /* element name stack */    xmlListPtr nsstack;         /* name spaces stack */    int level;    int indent;                 /* enable indent */    int doindent;               /* internal indent flag */    xmlChar *ichar;             /* indent character */    char qchar;                 /* character used for quoting attribute values */    xmlParserCtxtPtr ctxt;    int no_doc_free;    xmlDocPtr doc;};static void xmlFreeTextWriterStackEntry(xmlLinkPtr lk);static int xmlCmpTextWriterStackEntry(const void *data0,                                      const void *data1);static int xmlTextWriterOutputNSDecl(xmlTextWriterPtr writer);static void xmlFreeTextWriterNsStackEntry(xmlLinkPtr lk);static int xmlCmpTextWriterNsStackEntry(const void *data0,                                        const void *data1);static int xmlTextWriterWriteDocCallback(void *context,                                         const xmlChar * str, int len);static int xmlTextWriterCloseDocCallback(void *context);static xmlChar *xmlTextWriterVSprintf(const char *format, va_list argptr);static int xmlOutputBufferWriteBase64(xmlOutputBufferPtr out, int len,                                      const unsigned char *data);static void xmlTextWriterStartDocumentCallback(void *ctx);static int xmlTextWriterWriteIndent(xmlTextWriterPtr writer);static int  xmlTextWriterHandleStateDependencies(xmlTextWriterPtr writer,                                       xmlTextWriterStackEntry * p);/** * xmlWriterErrMsg: * @ctxt:  a writer context * @error:  the error number * @msg:  the error message * * Handle a writer error */static voidxmlWriterErrMsg(xmlTextWriterPtr ctxt, xmlParserErrors error,               const char *msg){    if (ctxt != NULL) {	__xmlRaiseError(NULL, NULL, NULL, ctxt->ctxt,	            NULL, XML_FROM_WRITER, error, XML_ERR_FATAL,		    NULL, 0, NULL, NULL, NULL, 0, 0, "%s", msg);    } else {	__xmlRaiseError(NULL, NULL, NULL, NULL, NULL, XML_FROM_WRITER, error,                    XML_ERR_FATAL, NULL, 0, NULL, NULL, NULL, 0, 0, "%s", msg);    }}/** * xmlWriterErrMsgInt: * @ctxt:  a writer context * @error:  the error number * @msg:  the error message * @val:  an int * * Handle a writer error */static voidxmlWriterErrMsgInt(xmlTextWriterPtr ctxt, xmlParserErrors error,               const char *msg, int val){    if (ctxt != NULL) {	__xmlRaiseError(NULL, NULL, NULL, ctxt->ctxt,	            NULL, XML_FROM_WRITER, error, XML_ERR_FATAL,		    NULL, 0, NULL, NULL, NULL, val, 0, msg, val);    } else {	__xmlRaiseError(NULL, NULL, NULL, NULL, NULL, XML_FROM_WRITER, error,                    XML_ERR_FATAL, NULL, 0, NULL, NULL, NULL, val, 0, msg, val);    }}/** * xmlNewTextWriter: * @out:  an xmlOutputBufferPtr * * Create a new xmlNewTextWriter structure using an xmlOutputBufferPtr * NOTE: the @out parameter will be deallocated when the writer is closed *       (if the call succeed.) * * Returns the new xmlTextWriterPtr or NULL in case of error */xmlTextWriterPtrxmlNewTextWriter(xmlOutputBufferPtr out){    xmlTextWriterPtr ret;    ret = (xmlTextWriterPtr) xmlMalloc(sizeof(xmlTextWriter));    if (ret == NULL) {        xmlWriterErrMsg(NULL, XML_ERR_NO_MEMORY,                        "xmlNewTextWriter : out of memory!\n");        return NULL;    }    memset(ret, 0, (size_t) sizeof(xmlTextWriter));    ret->nodes = xmlListCreate((xmlListDeallocator)                               xmlFreeTextWriterStackEntry,                               (xmlListDataCompare)                               xmlCmpTextWriterStackEntry);    if (ret->nodes == NULL) {        xmlWriterErrMsg(NULL, XML_ERR_NO_MEMORY,                        "xmlNewTextWriter : out of memory!\n");        xmlFree(ret);        return NULL;    }    ret->nsstack = xmlListCreate((xmlListDeallocator)                                 xmlFreeTextWriterNsStackEntry,                                 (xmlListDataCompare)                                 xmlCmpTextWriterNsStackEntry);    if (ret->nsstack == NULL) {        xmlWriterErrMsg(NULL, XML_ERR_NO_MEMORY,                        "xmlNewTextWriter : out of memory!\n");        xmlListDelete(ret->nodes);        xmlFree(ret);        return NULL;    }    ret->out = out;    ret->ichar = xmlStrdup(BAD_CAST " ");    ret->qchar = '"';    if (!ret->ichar) {        xmlListDelete(ret->nodes);        xmlListDelete(ret->nsstack);        xmlFree(ret);        xmlWriterErrMsg(NULL, XML_ERR_NO_MEMORY,                        "xmlNewTextWriter : out of memory!\n");        return NULL;    }    ret->doc = xmlNewDoc(NULL);    ret->no_doc_free = 0;    return ret;}/** * xmlNewTextWriterFilename: * @uri:  the URI of the resource for the output * @compression:  compress the output? * * Create a new xmlNewTextWriter structure with @uri as output * * Returns the new xmlTextWriterPtr or NULL in case of error */xmlTextWriterPtrxmlNewTextWriterFilename(const char *uri, int compression){    xmlTextWriterPtr ret;    xmlOutputBufferPtr out;    out = xmlOutputBufferCreateFilename(uri, NULL, compression);    if (out == NULL) {        xmlWriterErrMsg(NULL, XML_IO_EIO,                        "xmlNewTextWriterFilename : cannot open uri\n");        return NULL;    }    ret = xmlNewTextWriter(out);    if (ret == NULL) {        xmlWriterErrMsg(NULL, XML_ERR_NO_MEMORY,                        "xmlNewTextWriterFilename : out of memory!\n");        xmlOutputBufferClose(out);        return NULL;    }    ret->indent = 0;    ret->doindent = 0;    return ret;}/** * xmlNewTextWriterMemory: * @buf:  xmlBufferPtr * @compression:  compress the output? * * Create a new xmlNewTextWriter structure with @buf as output * TODO: handle compression * * Returns the new xmlTextWriterPtr or NULL in case of error */xmlTextWriterPtrxmlNewTextWriterMemory(xmlBufferPtr buf, int compression ATTRIBUTE_UNUSED){    xmlTextWriterPtr ret;    xmlOutputBufferPtr out;/*::todo handle compression */    out = xmlOutputBufferCreateBuffer(buf, NULL);    if (out == NULL) {        xmlWriterErrMsg(NULL, XML_ERR_NO_MEMORY,                        "xmlNewTextWriterMemory : out of memory!\n");        return NULL;    }    ret = xmlNewTextWriter(out);    if (ret == NULL) {        xmlWriterErrMsg(NULL, XML_ERR_NO_MEMORY,                        "xmlNewTextWriterMemory : out of memory!\n");        xmlOutputBufferClose(out);        return NULL;    }    return ret;}/** * xmlNewTextWriterPushParser: * @ctxt: xmlParserCtxtPtr to hold the new XML document tree * @compression:  compress the output? * * Create a new xmlNewTextWriter structure with @ctxt as output * NOTE: the @ctxt context will be freed with the resulting writer *       (if the call succeeds). * TODO: handle compression * * Returns the new xmlTextWriterPtr or NULL in case of error */xmlTextWriterPtrxmlNewTextWriterPushParser(xmlParserCtxtPtr ctxt,                           int compression ATTRIBUTE_UNUSED){    xmlTextWriterPtr ret;    xmlOutputBufferPtr out;    if (ctxt == NULL) {        xmlWriterErrMsg(NULL, XML_ERR_INTERNAL_ERROR,                        "xmlNewTextWriterPushParser : invalid context!\n");        return NULL;    }    out = xmlOutputBufferCreateIO((xmlOutputWriteCallback)                                  xmlTextWriterWriteDocCallback,                                  (xmlOutputCloseCallback)                                  xmlTextWriterCloseDocCallback,                                  (void *) ctxt, NULL);    if (out == NULL) {        xmlWriterErrMsg(NULL, XML_ERR_INTERNAL_ERROR,                        "xmlNewTextWriterPushParser : error at xmlOutputBufferCreateIO!\n");        return NULL;    }    ret = xmlNewTextWriter(out);    if (ret == NULL) {        xmlWriterErrMsg(NULL, XML_ERR_INTERNAL_ERROR,                        "xmlNewTextWriterPushParser : error at xmlNewTextWriter!\n");        xmlOutputBufferClose(out);        return NULL;    }    ret->ctxt = ctxt;    return ret;}/** * xmlNewTextWriterDoc: * @doc: address of a xmlDocPtr to hold the new XML document tree * @compression:  compress the output? * * Create a new xmlNewTextWriter structure with @*doc as output * * Returns the new xmlTextWriterPtr or NULL in case of error */xmlTextWriterPtrxmlNewTextWriterDoc(xmlDocPtr * doc, int compression){    xmlTextWriterPtr ret;    xmlSAXHandler saxHandler;    xmlParserCtxtPtr ctxt;    memset(&saxHandler, '\0', sizeof(saxHandler));    xmlSAX2InitDefaultSAXHandler(&saxHandler, 1);    saxHandler.startDocument = xmlTextWriterStartDocumentCallback;    saxHandler.startElement = xmlSAX2StartElement;    saxHandler.endElement = xmlSAX2EndElement;    ctxt = xmlCreatePushParserCtxt(&saxHandler, NULL, NULL, 0, NULL);    if (ctxt == NULL) {        xmlWriterErrMsg(NULL, XML_ERR_INTERNAL_ERROR,                "xmlNewTextWriterDoc : error at xmlCreatePushParserCtxt!\n");        return NULL;    }    /*     * For some reason this seems to completely break if node names     * are interned.     */    ctxt->dictNames = 0;    ctxt->myDoc = xmlNewDoc(BAD_CAST XML_DEFAULT_VERSION);    if (ctxt->myDoc == NULL) {        xmlFreeParserCtxt(ctxt);        xmlWriterErrMsg(NULL, XML_ERR_INTERNAL_ERROR,                        "xmlNewTextWriterDoc : error at xmlNewDoc!\n");        return NULL;    }    ret = xmlNewTextWriterPushParser(ctxt, compression);    if (ret == NULL) {        xmlFreeDoc(ctxt->myDoc);        xmlFreeParserCtxt(ctxt);        xmlWriterErrMsg(NULL, XML_ERR_INTERNAL_ERROR,                "xmlNewTextWriterDoc : error at xmlNewTextWriterPushParser!\n");        return NULL;    }    xmlSetDocCompressMode(ctxt->myDoc, compression);    if (doc != NULL) {        *doc = ctxt->myDoc;	ret->no_doc_free = 1;    }    return ret;}/** * xmlNewTextWriterTree: * @doc: xmlDocPtr * @node: xmlNodePtr or NULL for doc->children * @compression:  compress the output? * * Create a new xmlNewTextWriter structure with @doc as output * starting at @node * * Returns the new xmlTextWriterPtr or NULL in case of error */xmlTextWriterPtrxmlNewTextWriterTree(xmlDocPtr doc, xmlNodePtr node, int compression){    xmlTextWriterPtr ret;    xmlSAXHandler saxHandler;    xmlParserCtxtPtr ctxt;    if (doc == NULL) {        xmlWriterErrMsg(NULL, XML_ERR_INTERNAL_ERROR,                        "xmlNewTextWriterTree : invalid document tree!\n");        return NULL;    }    memset(&saxHandler, '\0', sizeof(saxHandler));    xmlSAX2InitDefaultSAXHandler(&saxHandler, 1);    saxHandler.startDocument = xmlTextWriterStartDocumentCallback;    saxHandler.startElement = xmlSAX2StartElement;    saxHandler.endElement = xmlSAX2EndElement;    ctxt = xmlCreatePushParserCtxt(&saxHandler, NULL, NULL, 0, NULL);    if (ctxt == NULL) {        xmlWriterErrMsg(NULL, XML_ERR_INTERNAL_ERROR,                        "xmlNewTextWriterDoc : error at xmlCreatePushParserCtxt!\n");        return NULL;    }    /*     * For some reason this seems to completely break if node names     * are interned.     */    ctxt->dictNames = 0;    ret = xmlNewTextWriterPushParser(ctxt, compression);    if (ret == NULL) {        xmlFreeParserCtxt(ctxt);        xmlWriterErrMsg(NULL, XML_ERR_INTERNAL_ERROR,                        "xmlNewTextWriterDoc : error at xmlNewTextWriterPushParser!\n");        return NULL;    }    ctxt->myDoc = doc;    ctxt->node = node;    ret->no_doc_free = 1;    xmlSetDocCompressMode(doc, compression);    return ret;}/** * xmlFreeTextWriter: * @writer:  the xmlTextWriterPtr * * Deallocate all the resources associated to the writer */voidxmlFreeTextWriter(xmlTextWriterPtr writer){    if (writer == NULL)        return;    if (writer->out != NULL)        xmlOutputBufferClose(writer->out);    if (writer->nodes != NULL)        xmlListDelete(writer->nodes);    if (writer->nsstack != NULL)        xmlListDelete(writer->nsstack);    if (writer->ctxt != NULL) {        if ((writer->ctxt->myDoc != NULL) && (writer->no_doc_free == 0)) {	    xmlFreeDoc(writer->ctxt->myDoc);	    writer->ctxt->myDoc = NULL;	}        xmlFreeParserCtxt(writer->ctxt);    }    if (writer->doc != NULL)        xmlFreeDoc(writer->doc);    if (writer->ichar != NULL)        xmlFree(writer->ichar);    xmlFree(writer);}/** * xmlTextWriterStartDocument: * @writer:  the xmlTextWriterPtr * @version:  the xml version ("1.0") or NULL for default ("1.0") * @encoding:  the encoding or NULL for default * @standalone: "yes" or "no" or NULL for default * * Start a new xml document * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterStartDocument(xmlTextWriterPtr writer, const char *version,                           const char *encoding, const char *standalone){    int count;    int sum;    xmlLinkPtr lk;    xmlCharEncodingHandlerPtr encoder;    if ((writer == NULL) || (writer->out == NULL)) {        xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                        "xmlTextWriterStartDocument : invalid writer!\n");        return -1;    }    lk = xmlListFront(writer->nodes);    if ((lk != NULL) && (xmlLinkGetData(lk) != NULL)) {        xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                        "xmlTextWriterStartDocument : not allowed in this context!\n");        return -1;    }    encoder = NULL;    if (encoding != NULL) {        encoder = xmlFindCharEncodingHandler(encoding);        if (encoder == NULL) {            xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                            "xmlTextWriterStartDocument : out of memory!\n");            return -1;        }    }    writer->out->encoder = encoder;    if (encoder != NULL) {	if (writer->out->conv == NULL) {	    writer->out->conv = xmlBufferCreateSize(4000);	}        xmlCharEncOutFunc(encoder, writer->out->conv, NULL);        if ((writer->doc != NULL) && (writer->doc->encoding == NULL))            writer->doc->encoding = xmlStrdup((xmlChar *)writer->out->encoder->name);    } else        writer->out->conv = NULL;    sum = 0;    count = xmlOutputBufferWriteString(writer->out, "<?xml version=");    if (count < 0)        return -1;    sum += count;    count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);    if (count < 0)        return -1;    sum += count;    if (version != 0)        count = xmlOutputBufferWriteString(writer->out, version);    else        count = xmlOutputBufferWriteString(writer->out, "1.0");    if (count < 0)        return -1;    sum += count;    count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);    if (count < 0)        return -1;    sum += count;    if (writer->out->encoder != 0) {        count = xmlOutputBufferWriteString(writer->out, " encoding=");        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);        if (count < 0)            return -1;        sum += count;        count =            xmlOutputBufferWriteString(writer->out,                                       writer->out->encoder->name);        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);        if (count < 0)            return -1;        sum += count;    }    if (standalone != 0) {        count = xmlOutputBufferWriteString(writer->out, " standalone=");        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWriteString(writer->out, standalone);        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);        if (count < 0)            return -1;        sum += count;    }    count = xmlOutputBufferWriteString(writer->out, "?>\n");    if (count < 0)        return -1;    sum += count;    return sum;}/** * xmlTextWriterEndDocument: * @writer:  the xmlTextWriterPtr * * End an xml document. All open elements are closed, and * the content is flushed to the output. * * Returns the bytes written or -1 in case of error */intxmlTextWriterEndDocument(xmlTextWriterPtr writer){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL) {        xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                        "xmlTextWriterEndDocument : invalid writer!\n");        return -1;    }    sum = 0;    while ((lk = xmlListFront(writer->nodes)) != NULL) {        p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);        if (p == 0)            break;        switch (p->state) {            case XML_TEXTWRITER_NAME:            case XML_TEXTWRITER_ATTRIBUTE:            case XML_TEXTWRITER_TEXT:                count = xmlTextWriterEndElement(writer);                if (count < 0)                    return -1;                sum += count;                break;            case XML_TEXTWRITER_PI:            case XML_TEXTWRITER_PI_TEXT:                count = xmlTextWriterEndPI(writer);                if (count < 0)                    return -1;                sum += count;                break;            case XML_TEXTWRITER_CDATA:                count = xmlTextWriterEndCDATA(writer);                if (count < 0)                    return -1;                sum += count;                break;            case XML_TEXTWRITER_DTD:            case XML_TEXTWRITER_DTD_TEXT:            case XML_TEXTWRITER_DTD_ELEM:            case XML_TEXTWRITER_DTD_ELEM_TEXT:            case XML_TEXTWRITER_DTD_ATTL:            case XML_TEXTWRITER_DTD_ATTL_TEXT:            case XML_TEXTWRITER_DTD_ENTY:            case XML_TEXTWRITER_DTD_ENTY_TEXT:            case XML_TEXTWRITER_DTD_PENT:                count = xmlTextWriterEndDTD(writer);                if (count < 0)                    return -1;                sum += count;                break;            case XML_TEXTWRITER_COMMENT:                count = xmlTextWriterEndComment(writer);                if (count < 0)                    return -1;                sum += count;                break;            default:                break;        }    }    if (!writer->indent) {        count = xmlOutputBufferWriteString(writer->out, "\n");        if (count < 0)            return -1;        sum += count;    }    sum += xmlTextWriterFlush(writer);    return sum;}/** * xmlTextWriterStartComment: * @writer:  the xmlTextWriterPtr * * Start an xml comment. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterStartComment(xmlTextWriterPtr writer){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL) {        xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                        "xmlTextWriterStartComment : invalid writer!\n");        return -1;    }    sum = 0;    lk = xmlListFront(writer->nodes);    if (lk != 0) {        p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);        if (p != 0) {            switch (p->state) {                case XML_TEXTWRITER_TEXT:                case XML_TEXTWRITER_NONE:                    break;                case XML_TEXTWRITER_NAME:                    /* Output namespace declarations */                    count = xmlTextWriterOutputNSDecl(writer);                    if (count < 0)                        return -1;                    sum += count;                    count = xmlOutputBufferWriteString(writer->out, ">");                    if (count < 0)                        return -1;                    sum += count;                    if (writer->indent) {                        count =                            xmlOutputBufferWriteString(writer->out, "\n");                        if (count < 0)                            return -1;                        sum += count;                    }                    p->state = XML_TEXTWRITER_TEXT;                    break;                default:                    return -1;            }        }    }    p = (xmlTextWriterStackEntry *)        xmlMalloc(sizeof(xmlTextWriterStackEntry));    if (p == 0) {        xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                        "xmlTextWriterStartElement : out of memory!\n");        return -1;    }    p->name = NULL;    p->state = XML_TEXTWRITER_COMMENT;    xmlListPushFront(writer->nodes, p);    if (writer->indent) {        count = xmlTextWriterWriteIndent(writer);        if (count < 0)            return -1;        sum += count;    }    count = xmlOutputBufferWriteString(writer->out, "<!--");    if (count < 0)        return -1;    sum += count;    return sum;}/** * xmlTextWriterEndComment: * @writer:  the xmlTextWriterPtr * * End the current xml coment. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterEndComment(xmlTextWriterPtr writer){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL) {        xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                        "xmlTextWriterEndComment : invalid writer!\n");        return -1;    }    lk = xmlListFront(writer->nodes);    if (lk == 0) {        xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                        "xmlTextWriterEndComment : not allowed in this context!\n");        return -1;    }    p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);    if (p == 0)        return -1;    sum = 0;    switch (p->state) {        case XML_TEXTWRITER_COMMENT:            count = xmlOutputBufferWriteString(writer->out, "-->");            if (count < 0)                return -1;            sum += count;            break;        default:            return -1;    }    if (writer->indent) {        count = xmlOutputBufferWriteString(writer->out, "\n");        if (count < 0)            return -1;        sum += count;    }    xmlListPopFront(writer->nodes);    return sum;}/** * xmlTextWriterWriteFormatComment: * @writer:  the xmlTextWriterPtr * @format:  format string (see printf) * @...:  extra parameters for the format * * Write an xml comment. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */int XMLCDECLxmlTextWriterWriteFormatComment(xmlTextWriterPtr writer,                                const char *format, ...){    int rc;    va_list ap;    va_start(ap, format);    rc = xmlTextWriterWriteVFormatComment(writer, format, ap);    va_end(ap);    return rc;}/** * xmlTextWriterWriteVFormatComment: * @writer:  the xmlTextWriterPtr * @format:  format string (see printf) * @argptr:  pointer to the first member of the variable argument list. * * Write an xml comment. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteVFormatComment(xmlTextWriterPtr writer,                                 const char *format, va_list argptr){    int rc;    xmlChar *buf;    if (writer == NULL) {        xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                        "xmlTextWriterWriteVFormatComment : invalid writer!\n");        return -1;    }    buf = xmlTextWriterVSprintf(format, argptr);    if (buf == NULL)        return -1;    rc = xmlTextWriterWriteComment(writer, buf);    xmlFree(buf);    return rc;}/** * xmlTextWriterWriteComment: * @writer:  the xmlTextWriterPtr * @content:  comment string * * Write an xml comment. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteComment(xmlTextWriterPtr writer, const xmlChar * content){    int count;    int sum;    sum = 0;    count = xmlTextWriterStartComment(writer);    if (count < 0)        return -1;    sum += count;    count = xmlTextWriterWriteString(writer, content);    if (count < 0)        return -1;    sum += count;    count = xmlTextWriterEndComment(writer);    if (count < 0)        return -1;    sum += count;    return sum;}/** * xmlTextWriterStartElement: * @writer:  the xmlTextWriterPtr * @name:  element name * * Start an xml element. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterStartElement(xmlTextWriterPtr writer, const xmlChar * name){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if ((writer == NULL) || (name == NULL) || (*name == '\0'))        return -1;    sum = 0;    lk = xmlListFront(writer->nodes);    if (lk != 0) {        p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);        if (p != 0) {            switch (p->state) {                case XML_TEXTWRITER_PI:                case XML_TEXTWRITER_PI_TEXT:                    return -1;                case XML_TEXTWRITER_NONE:                    break;				case XML_TEXTWRITER_ATTRIBUTE:					count = xmlTextWriterEndAttribute(writer);					if (count < 0)						return -1;					sum += count;					/* fallthrough */                case XML_TEXTWRITER_NAME:                    /* Output namespace declarations */                    count = xmlTextWriterOutputNSDecl(writer);                    if (count < 0)                        return -1;                    sum += count;                    count = xmlOutputBufferWriteString(writer->out, ">");                    if (count < 0)                        return -1;                    sum += count;                    if (writer->indent)                        count =                            xmlOutputBufferWriteString(writer->out, "\n");                    p->state = XML_TEXTWRITER_TEXT;                    break;                default:                    break;            }        }    }    p = (xmlTextWriterStackEntry *)        xmlMalloc(sizeof(xmlTextWriterStackEntry));    if (p == 0) {        xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                        "xmlTextWriterStartElement : out of memory!\n");        return -1;    }    p->name = xmlStrdup(name);    if (p->name == 0) {        xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                        "xmlTextWriterStartElement : out of memory!\n");        xmlFree(p);        return -1;    }    p->state = XML_TEXTWRITER_NAME;    xmlListPushFront(writer->nodes, p);    if (writer->indent) {        count = xmlTextWriterWriteIndent(writer);        sum += count;    }    count = xmlOutputBufferWriteString(writer->out, "<");    if (count < 0)        return -1;    sum += count;    count =        xmlOutputBufferWriteString(writer->out, (const char *) p->name);    if (count < 0)        return -1;    sum += count;    return sum;}/** * xmlTextWriterStartElementNS: * @writer:  the xmlTextWriterPtr * @prefix:  namespace prefix or NULL * @name:  element local name * @namespaceURI:  namespace URI or NULL * * Start an xml element with namespace support. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterStartElementNS(xmlTextWriterPtr writer,                            const xmlChar * prefix, const xmlChar * name,                            const xmlChar * namespaceURI){    int count;    int sum;    xmlChar *buf;    if ((writer == NULL) || (name == NULL) || (*name == '\0'))        return -1;    buf = NULL;    if (prefix != 0) {        buf = xmlStrdup(prefix);        buf = xmlStrcat(buf, BAD_CAST ":");    }    buf = xmlStrcat(buf, name);    sum = 0;    count = xmlTextWriterStartElement(writer, buf);    xmlFree(buf);    if (count < 0)        return -1;    sum += count;    if (namespaceURI != 0) {        xmlTextWriterNsStackEntry *p = (xmlTextWriterNsStackEntry *)         xmlMalloc(sizeof(xmlTextWriterNsStackEntry));        if (p == 0) {            xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                             "xmlTextWriterStartElementNS : out of memory!\n");            return -1;        }        buf = xmlStrdup(BAD_CAST "xmlns");        if (prefix != 0) {            buf = xmlStrcat(buf, BAD_CAST ":");            buf = xmlStrcat(buf, prefix);        }        p->prefix = buf;        p->uri = xmlStrdup(namespaceURI);        if (p->uri == 0) {            xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                            "xmlTextWriterStartElementNS : out of memory!\n");            xmlFree(p);            return -1;        }        p->elem = xmlListFront(writer->nodes);        xmlListPushFront(writer->nsstack, p);    }    return sum;}/** * xmlTextWriterEndElement: * @writer:  the xmlTextWriterPtr * * End the current xml element. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterEndElement(xmlTextWriterPtr writer){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL)        return -1;    lk = xmlListFront(writer->nodes);    if (lk == 0) {        xmlListDelete(writer->nsstack);        writer->nsstack = NULL;        return -1;    }    p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);    if (p == 0) {        xmlListDelete(writer->nsstack);        writer->nsstack = NULL;        return -1;    }    sum = 0;    switch (p->state) {        case XML_TEXTWRITER_ATTRIBUTE:            count = xmlTextWriterEndAttribute(writer);            if (count < 0) {                xmlListDelete(writer->nsstack);                writer->nsstack = NULL;                return -1;            }            sum += count;            /* fallthrough */        case XML_TEXTWRITER_NAME:            /* Output namespace declarations */            count = xmlTextWriterOutputNSDecl(writer);            if (count < 0)                return -1;            sum += count;            if (writer->indent) /* next element needs indent */                writer->doindent = 1;            count = xmlOutputBufferWriteString(writer->out, "/>");            if (count < 0)                return -1;            sum += count;            break;        case XML_TEXTWRITER_TEXT:            if ((writer->indent) && (writer->doindent)) {                count = xmlTextWriterWriteIndent(writer);                sum += count;                writer->doindent = 1;            } else                writer->doindent = 1;            count = xmlOutputBufferWriteString(writer->out, "</");            if (count < 0)                return -1;            sum += count;            count = xmlOutputBufferWriteString(writer->out,                                               (const char *) p->name);            if (count < 0)                return -1;            sum += count;            count = xmlOutputBufferWriteString(writer->out, ">");            if (count < 0)                return -1;            sum += count;            break;        default:            return -1;    }    if (writer->indent) {        count = xmlOutputBufferWriteString(writer->out, "\n");        sum += count;    }    xmlListPopFront(writer->nodes);    return sum;}/** * xmlTextWriterFullEndElement: * @writer:  the xmlTextWriterPtr * * End the current xml element. Writes an end tag even if the element is empty * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterFullEndElement(xmlTextWriterPtr writer){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL)        return -1;    lk = xmlListFront(writer->nodes);    if (lk == 0)        return -1;    p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);    if (p == 0)        return -1;    sum = 0;    switch (p->state) {        case XML_TEXTWRITER_ATTRIBUTE:            count = xmlTextWriterEndAttribute(writer);            if (count < 0)                return -1;            sum += count;            /* fallthrough */        case XML_TEXTWRITER_NAME:            /* Output namespace declarations */            count = xmlTextWriterOutputNSDecl(writer);            if (count < 0)                return -1;            sum += count;            count = xmlOutputBufferWriteString(writer->out, ">");            if (count < 0)                return -1;            sum += count;            if (writer->indent)                writer->doindent = 0;            /* fallthrough */        case XML_TEXTWRITER_TEXT:            if ((writer->indent) && (writer->doindent)) {                count = xmlTextWriterWriteIndent(writer);                sum += count;                writer->doindent = 1;            } else                writer->doindent = 1;            count = xmlOutputBufferWriteString(writer->out, "</");            if (count < 0)                return -1;            sum += count;            count = xmlOutputBufferWriteString(writer->out,                                               (const char *) p->name);            if (count < 0)                return -1;            sum += count;            count = xmlOutputBufferWriteString(writer->out, ">");            if (count < 0)                return -1;            sum += count;            break;        default:            return -1;    }    if (writer->indent) {        count = xmlOutputBufferWriteString(writer->out, "\n");        sum += count;    }    xmlListPopFront(writer->nodes);    return sum;}/** * xmlTextWriterWriteFormatRaw: * @writer:  the xmlTextWriterPtr * @format:  format string (see printf) * @...:  extra parameters for the format * * Write a formatted raw xml text. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */int XMLCDECLxmlTextWriterWriteFormatRaw(xmlTextWriterPtr writer, const char *format,                            ...){    int rc;    va_list ap;    va_start(ap, format);    rc = xmlTextWriterWriteVFormatRaw(writer, format, ap);    va_end(ap);    return rc;}/** * xmlTextWriterWriteVFormatRaw: * @writer:  the xmlTextWriterPtr * @format:  format string (see printf) * @argptr:  pointer to the first member of the variable argument list. * * Write a formatted raw xml text. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteVFormatRaw(xmlTextWriterPtr writer, const char *format,                             va_list argptr){    int rc;    xmlChar *buf;    if (writer == NULL)        return -1;    buf = xmlTextWriterVSprintf(format, argptr);    if (buf == NULL)        return -1;    rc = xmlTextWriterWriteRaw(writer, buf);    xmlFree(buf);    return rc;}/** * xmlTextWriterWriteRawLen: * @writer:  the xmlTextWriterPtr * @content:  text string * @len:  length of the text string * * Write an xml text. * TODO: what about entities and special chars?? * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteRawLen(xmlTextWriterPtr writer, const xmlChar * content,                         int len){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL) {        xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                        "xmlTextWriterWriteRawLen : invalid writer!\n");        return -1;    }    if ((content == NULL) || (len < 0)) {        xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                        "xmlTextWriterWriteRawLen : invalid content!\n");        return -1;    }    sum = 0;    lk = xmlListFront(writer->nodes);    if (lk != 0) {        p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);        count = xmlTextWriterHandleStateDependencies(writer, p);        if (count < 0)            return -1;        sum += count;    }    if (writer->indent)        writer->doindent = 0;    if (content != NULL) {        count =            xmlOutputBufferWrite(writer->out, len, (const char *) content);        if (count < 0)            return -1;        sum += count;    }    return sum;}/** * xmlTextWriterWriteRaw: * @writer:  the xmlTextWriterPtr * @content:  text string * * Write a raw xml text. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteRaw(xmlTextWriterPtr writer, const xmlChar * content){    return xmlTextWriterWriteRawLen(writer, content, xmlStrlen(content));}/** * xmlTextWriterWriteFormatString: * @writer:  the xmlTextWriterPtr * @format:  format string (see printf) * @...:  extra parameters for the format * * Write a formatted xml text. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */int XMLCDECLxmlTextWriterWriteFormatString(xmlTextWriterPtr writer, const char *format,                               ...){    int rc;    va_list ap;    if ((writer == NULL) || (format == NULL))        return -1;    va_start(ap, format);    rc = xmlTextWriterWriteVFormatString(writer, format, ap);    va_end(ap);    return rc;}/** * xmlTextWriterWriteVFormatString: * @writer:  the xmlTextWriterPtr * @format:  format string (see printf) * @argptr:  pointer to the first member of the variable argument list. * * Write a formatted xml text. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteVFormatString(xmlTextWriterPtr writer,                                const char *format, va_list argptr){    int rc;    xmlChar *buf;    if ((writer == NULL) || (format == NULL))        return -1;    buf = xmlTextWriterVSprintf(format, argptr);    if (buf == NULL)        return -1;    rc = xmlTextWriterWriteString(writer, buf);    xmlFree(buf);    return rc;}/** * xmlTextWriterWriteString: * @writer:  the xmlTextWriterPtr * @content:  text string * * Write an xml text. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteString(xmlTextWriterPtr writer, const xmlChar * content){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    xmlChar *buf;    if ((writer == NULL) || (content == NULL))        return -1;    sum = 0;    buf = (xmlChar *) content;    lk = xmlListFront(writer->nodes);    if (lk != 0) {        p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);        if (p != 0) {            switch (p->state) {                case XML_TEXTWRITER_NAME:                case XML_TEXTWRITER_TEXT:#if 0                    buf = NULL;		    xmlOutputBufferWriteEscape(writer->out, content, NULL);#endif                    buf = xmlEncodeSpecialChars(NULL, content);                    break;                case XML_TEXTWRITER_ATTRIBUTE:                    buf = NULL;                    xmlAttrSerializeTxtContent(writer->out->buffer, writer->doc,                                               NULL, content);                    break;		default:		    break;            }        }    }    if (buf != NULL) {        count = xmlTextWriterWriteRaw(writer, buf);        if (buf != content)     /* buf was allocated by us, so free it */            xmlFree(buf);        if (count < 0)            return -1;        sum += count;    }    return sum;}/** * xmlOutputBufferWriteBase64: * @out: the xmlOutputBufferPtr * @data:   binary data * @len:  the number of bytes to encode * * Write base64 encoded data to an xmlOutputBuffer. * Adapted from John Walker's base64.c (http://www.fourmilab.ch/). * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */static intxmlOutputBufferWriteBase64(xmlOutputBufferPtr out, int len,                           const unsigned char *data){    static unsigned char dtable[64] =            {'A','B','C','D','E','F','G','H','I','J','K','L','M',	     'N','O','P','Q','R','S','T','U','V','W','X','Y','Z',	     'a','b','c','d','e','f','g','h','i','j','k','l','m',	     'n','o','p','q','r','s','t','u','v','w','x','y','z',	     '0','1','2','3','4','5','6','7','8','9','+','/'};    int i;    int linelen;    int count;    int sum;    if ((out == NULL) || (len < 0) || (data == NULL))        return(-1);    linelen = 0;    sum = 0;    i = 0;    while (1) {        unsigned char igroup[3];        unsigned char ogroup[4];        int c;        int n;        igroup[0] = igroup[1] = igroup[2] = 0;        for (n = 0; n < 3 && i < len; n++, i++) {            c = data[i];            igroup[n] = (unsigned char) c;        }        if (n > 0) {            ogroup[0] = dtable[igroup[0] >> 2];            ogroup[1] = dtable[((igroup[0] & 3) << 4) | (igroup[1] >> 4)];            ogroup[2] =                dtable[((igroup[1] & 0xF) << 2) | (igroup[2] >> 6)];            ogroup[3] = dtable[igroup[2] & 0x3F];            if (n < 3) {                ogroup[3] = '=';                if (n < 2) {                    ogroup[2] = '=';                }            }            if (linelen >= B64LINELEN) {                count = xmlOutputBufferWrite(out, 2, B64CRLF);                if (count == -1)                    return -1;                sum += count;                linelen = 0;            }            count = xmlOutputBufferWrite(out, 4, (const char *) ogroup);            if (count == -1)                return -1;            sum += count;            linelen += 4;        }        if (i >= len)            break;    }    return sum;}/** * xmlTextWriterWriteBase64: * @writer: the xmlTextWriterPtr * @data:   binary data * @start:  the position within the data of the first byte to encode * @len:  the number of bytes to encode * * Write an base64 encoded xml text. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteBase64(xmlTextWriterPtr writer, const char *data,                         int start, int len){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if ((writer == NULL) || (data == NULL) || (start < 0) || (len < 0))        return -1;    sum = 0;    lk = xmlListFront(writer->nodes);    if (lk != 0) {        p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);        if (p != 0) {            count = xmlTextWriterHandleStateDependencies(writer, p);            if (count < 0)                return -1;            sum += count;        }    }    if (writer->indent)        writer->doindent = 0;    count =        xmlOutputBufferWriteBase64(writer->out, len,                                   (unsigned char *) data + start);    if (count < 0)        return -1;    sum += count;    return sum;}/** * xmlOutputBufferWriteBinHex: * @out: the xmlOutputBufferPtr * @data:   binary data * @len:  the number of bytes to encode * * Write hqx encoded data to an xmlOutputBuffer. * ::todo * * Returns the bytes written (may be 0 because of buffering)  * or -1 in case of error */static intxmlOutputBufferWriteBinHex(xmlOutputBufferPtr out,                           int len, const unsigned char *data){    int count;    int sum;    static char hex[16] =     	{'0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'};    int i;    if ((out == NULL) || (data == NULL) || (len < 0)) {        return -1;    }    sum = 0;    for (i = 0; i < len; i++) {        count =            xmlOutputBufferWrite(out, 1,                                 (const char *) &hex[data[i] >> 4]);        if (count == -1)            return -1;        sum += count;        count =            xmlOutputBufferWrite(out, 1,                                 (const char *) &hex[data[i] & 0xF]);        if (count == -1)            return -1;        sum += count;    }    return sum;}/** * xmlTextWriterWriteBinHex: * @writer: the xmlTextWriterPtr * @data:   binary data * @start:  the position within the data of the first byte to encode * @len:  the number of bytes to encode * * Write a BinHex encoded xml text. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteBinHex(xmlTextWriterPtr writer, const char *data,                         int start, int len){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if ((writer == NULL) || (data == NULL) || (start < 0) || (len < 0))        return -1;    sum = 0;    lk = xmlListFront(writer->nodes);    if (lk != 0) {        p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);        if (p != 0) {            count = xmlTextWriterHandleStateDependencies(writer, p);            if (count < 0)                return -1;            sum += count;        }    }    if (writer->indent)        writer->doindent = 0;    count =        xmlOutputBufferWriteBinHex(writer->out, len,                                   (unsigned char *) data + start);    if (count < 0)        return -1;    sum += count;    return sum;}/** * xmlTextWriterStartAttribute: * @writer:  the xmlTextWriterPtr * @name:  element name * * Start an xml attribute. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterStartAttribute(xmlTextWriterPtr writer, const xmlChar * name){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if ((writer == NULL) || (name == NULL) || (*name == '\0'))        return -1;    sum = 0;    lk = xmlListFront(writer->nodes);    if (lk == 0)        return -1;    p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);    if (p == 0)        return -1;    switch (p->state) {        case XML_TEXTWRITER_ATTRIBUTE:            count = xmlTextWriterEndAttribute(writer);            if (count < 0)                return -1;            sum += count;            /* fallthrough */        case XML_TEXTWRITER_NAME:            count = xmlOutputBufferWriteString(writer->out, " ");            if (count < 0)                return -1;            sum += count;            count =                xmlOutputBufferWriteString(writer->out,                                           (const char *) name);            if (count < 0)                return -1;            sum += count;            count = xmlOutputBufferWriteString(writer->out, "=");            if (count < 0)                return -1;            sum += count;            count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);            if (count < 0)                return -1;            sum += count;            p->state = XML_TEXTWRITER_ATTRIBUTE;            break;        default:            return -1;    }    return sum;}/** * xmlTextWriterStartAttributeNS: * @writer:  the xmlTextWriterPtr * @prefix:  namespace prefix or NULL * @name:  element local name * @namespaceURI:  namespace URI or NULL * * Start an xml attribute with namespace support. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterStartAttributeNS(xmlTextWriterPtr writer,                              const xmlChar * prefix, const xmlChar * name,                              const xmlChar * namespaceURI){    int count;    int sum;    xmlChar *buf;    xmlTextWriterNsStackEntry *p;    if ((writer == NULL) || (name == NULL) || (*name == '\0'))        return -1;    /* Handle namespace first in case of error */    if (namespaceURI != 0) {        xmlTextWriterNsStackEntry nsentry, *curns;        buf = xmlStrdup(BAD_CAST "xmlns");        if (prefix != 0) {            buf = xmlStrcat(buf, BAD_CAST ":");            buf = xmlStrcat(buf, prefix);        }        nsentry.prefix = buf;        nsentry.uri = (xmlChar *)namespaceURI;        nsentry.elem = xmlListFront(writer->nodes);        curns = (xmlTextWriterNsStackEntry *)xmlListSearch(writer->nsstack,                                                            (void *)&nsentry);        if ((curns != NULL)) {            xmlFree(buf);            if (xmlStrcmp(curns->uri, namespaceURI) == 0) {                /* Namespace already defined on element skip */                buf = NULL;            } else {                /* Prefix mismatch so error out */                return -1;            }        }        /* Do not add namespace decl to list - it is already there */        if (buf != NULL) {            p = (xmlTextWriterNsStackEntry *)                xmlMalloc(sizeof(xmlTextWriterNsStackEntry));            if (p == 0) {                xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,								        "xmlTextWriterStartAttributeNS : out of memory!\n");                return -1;            }            p->prefix = buf;            p->uri = xmlStrdup(namespaceURI);            if (p->uri == 0) {                xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                        "xmlTextWriterStartAttributeNS : out of memory!\n");                xmlFree(p);                return -1;            }            p->elem = xmlListFront(writer->nodes);            xmlListPushFront(writer->nsstack, p);        }    }    buf = NULL;    if (prefix != 0) {        buf = xmlStrdup(prefix);        buf = xmlStrcat(buf, BAD_CAST ":");    }    buf = xmlStrcat(buf, name);    sum = 0;    count = xmlTextWriterStartAttribute(writer, buf);    xmlFree(buf);    if (count < 0)        return -1;    sum += count;    return sum;}/** * xmlTextWriterEndAttribute: * @writer:  the xmlTextWriterPtr * * End the current xml element. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterEndAttribute(xmlTextWriterPtr writer){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL)        return -1;    lk = xmlListFront(writer->nodes);    if (lk == 0) {        return -1;    }    p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);    if (p == 0) {        return -1;    }    sum = 0;    switch (p->state) {        case XML_TEXTWRITER_ATTRIBUTE:            p->state = XML_TEXTWRITER_NAME;            count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);            if (count < 0) {                return -1;            }            sum += count;            break;        default:            return -1;    }    return sum;}/** * xmlTextWriterWriteFormatAttribute: * @writer:  the xmlTextWriterPtr * @name:  attribute name * @format:  format string (see printf) * @...:  extra parameters for the format * * Write a formatted xml attribute. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */int XMLCDECLxmlTextWriterWriteFormatAttribute(xmlTextWriterPtr writer,                                  const xmlChar * name, const char *format,                                  ...){    int rc;    va_list ap;    va_start(ap, format);    rc = xmlTextWriterWriteVFormatAttribute(writer, name, format, ap);    va_end(ap);    return rc;}/** * xmlTextWriterWriteVFormatAttribute: * @writer:  the xmlTextWriterPtr * @name:  attribute name * @format:  format string (see printf) * @argptr:  pointer to the first member of the variable argument list. * * Write a formatted xml attribute. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteVFormatAttribute(xmlTextWriterPtr writer,                                   const xmlChar * name,                                   const char *format, va_list argptr){    int rc;    xmlChar *buf;    if (writer == NULL)        return -1;    buf = xmlTextWriterVSprintf(format, argptr);    if (buf == NULL)        return -1;    rc = xmlTextWriterWriteAttribute(writer, name, buf);    xmlFree(buf);    return rc;}/** * xmlTextWriterWriteAttribute: * @writer:  the xmlTextWriterPtr * @name:  attribute name * @content:  attribute content * * Write an xml attribute. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteAttribute(xmlTextWriterPtr writer, const xmlChar * name,                            const xmlChar * content){    int count;    int sum;    sum = 0;    count = xmlTextWriterStartAttribute(writer, name);    if (count < 0)        return -1;    sum += count;    count = xmlTextWriterWriteString(writer, content);    if (count < 0)        return -1;    sum += count;    count = xmlTextWriterEndAttribute(writer);    if (count < 0)        return -1;    sum += count;    return sum;}/** * xmlTextWriterWriteFormatAttributeNS: * @writer:  the xmlTextWriterPtr * @prefix:  namespace prefix * @name:  attribute local name * @namespaceURI:  namespace URI * @format:  format string (see printf) * @...:  extra parameters for the format * * Write a formatted xml attribute.with namespace support * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */int XMLCDECLxmlTextWriterWriteFormatAttributeNS(xmlTextWriterPtr writer,                                    const xmlChar * prefix,                                    const xmlChar * name,                                    const xmlChar * namespaceURI,                                    const char *format, ...){    int rc;    va_list ap;    va_start(ap, format);    rc = xmlTextWriterWriteVFormatAttributeNS(writer, prefix, name,                                              namespaceURI, format, ap);    va_end(ap);    return rc;}/** * xmlTextWriterWriteVFormatAttributeNS: * @writer:  the xmlTextWriterPtr * @prefix:  namespace prefix * @name:  attribute local name * @namespaceURI:  namespace URI * @format:  format string (see printf) * @argptr:  pointer to the first member of the variable argument list. * * Write a formatted xml attribute.with namespace support * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteVFormatAttributeNS(xmlTextWriterPtr writer,                                     const xmlChar * prefix,                                     const xmlChar * name,                                     const xmlChar * namespaceURI,                                     const char *format, va_list argptr){    int rc;    xmlChar *buf;    if (writer == NULL)        return -1;    buf = xmlTextWriterVSprintf(format, argptr);    if (buf == NULL)        return -1;    rc = xmlTextWriterWriteAttributeNS(writer, prefix, name, namespaceURI,                                       buf);    xmlFree(buf);    return rc;}/** * xmlTextWriterWriteAttributeNS: * @writer:  the xmlTextWriterPtr * @prefix:  namespace prefix * @name:  attribute local name * @namespaceURI:  namespace URI * @content:  attribute content * * Write an xml attribute. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteAttributeNS(xmlTextWriterPtr writer,                              const xmlChar * prefix, const xmlChar * name,                              const xmlChar * namespaceURI,                              const xmlChar * content){    int count;    int sum;    if ((writer == NULL) || (name == NULL) || (*name == '\0'))        return -1;    sum = 0;    count = xmlTextWriterStartAttributeNS(writer, prefix, name, namespaceURI);    if (count < 0)        return -1;    sum += count;    count = xmlTextWriterWriteString(writer, content);    if (count < 0)        return -1;    sum += count;    count = xmlTextWriterEndAttribute(writer);    if (count < 0)        return -1;    sum += count;    return sum;}/** * xmlTextWriterWriteFormatElement: * @writer:  the xmlTextWriterPtr * @name:  element name * @format:  format string (see printf) * @...:  extra parameters for the format * * Write a formatted xml element. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */int XMLCDECLxmlTextWriterWriteFormatElement(xmlTextWriterPtr writer,                                const xmlChar * name, const char *format,                                ...){    int rc;    va_list ap;    va_start(ap, format);    rc = xmlTextWriterWriteVFormatElement(writer, name, format, ap);    va_end(ap);    return rc;}/** * xmlTextWriterWriteVFormatElement: * @writer:  the xmlTextWriterPtr * @name:  element name * @format:  format string (see printf) * @argptr:  pointer to the first member of the variable argument list. * * Write a formatted xml element. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteVFormatElement(xmlTextWriterPtr writer,                                 const xmlChar * name, const char *format,                                 va_list argptr){    int rc;    xmlChar *buf;    if (writer == NULL)        return -1;    buf = xmlTextWriterVSprintf(format, argptr);    if (buf == NULL)        return -1;    rc = xmlTextWriterWriteElement(writer, name, buf);    xmlFree(buf);    return rc;}/** * xmlTextWriterWriteElement: * @writer:  the xmlTextWriterPtr * @name:  element name * @content:  element content * * Write an xml element. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteElement(xmlTextWriterPtr writer, const xmlChar * name,                          const xmlChar * content){    int count;    int sum;    sum = 0;    count = xmlTextWriterStartElement(writer, name);    if (count == -1)        return -1;    sum += count;    count = xmlTextWriterWriteString(writer, content);    if (count == -1)        return -1;    sum += count;    count = xmlTextWriterEndElement(writer);    if (count == -1)        return -1;    sum += count;    return sum;}/** * xmlTextWriterWriteFormatElementNS: * @writer:  the xmlTextWriterPtr * @prefix:  namespace prefix * @name:  element local name * @namespaceURI:  namespace URI * @format:  format string (see printf) * @...:  extra parameters for the format * * Write a formatted xml element with namespace support. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */int XMLCDECLxmlTextWriterWriteFormatElementNS(xmlTextWriterPtr writer,                                  const xmlChar * prefix,                                  const xmlChar * name,                                  const xmlChar * namespaceURI,                                  const char *format, ...){    int rc;    va_list ap;    va_start(ap, format);    rc = xmlTextWriterWriteVFormatElementNS(writer, prefix, name,                                            namespaceURI, format, ap);    va_end(ap);    return rc;}/** * xmlTextWriterWriteVFormatElementNS: * @writer:  the xmlTextWriterPtr * @prefix:  namespace prefix * @name:  element local name * @namespaceURI:  namespace URI * @format:  format string (see printf) * @argptr:  pointer to the first member of the variable argument list. * * Write a formatted xml element with namespace support. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteVFormatElementNS(xmlTextWriterPtr writer,                                   const xmlChar * prefix,                                   const xmlChar * name,                                   const xmlChar * namespaceURI,                                   const char *format, va_list argptr){    int rc;    xmlChar *buf;    if (writer == NULL)        return -1;    buf = xmlTextWriterVSprintf(format, argptr);    if (buf == NULL)        return -1;    rc = xmlTextWriterWriteElementNS(writer, prefix, name, namespaceURI,                                     buf);    xmlFree(buf);    return rc;}/** * xmlTextWriterWriteElementNS: * @writer:  the xmlTextWriterPtr * @prefix:  namespace prefix * @name:  element local name * @namespaceURI:  namespace URI * @content:  element content * * Write an xml element with namespace support. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteElementNS(xmlTextWriterPtr writer,                            const xmlChar * prefix, const xmlChar * name,                            const xmlChar * namespaceURI,                            const xmlChar * content){    int count;    int sum;    if ((writer == NULL) || (name == NULL) || (*name == '\0'))        return -1;    sum = 0;    count =        xmlTextWriterStartElementNS(writer, prefix, name, namespaceURI);    if (count < 0)        return -1;    sum += count;    count = xmlTextWriterWriteString(writer, content);    if (count == -1)        return -1;    sum += count;    count = xmlTextWriterEndElement(writer);    if (count == -1)        return -1;    sum += count;    return sum;}/** * xmlTextWriterStartPI: * @writer:  the xmlTextWriterPtr * @target:  PI target * * Start an xml PI. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterStartPI(xmlTextWriterPtr writer, const xmlChar * target){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if ((writer == NULL) || (target == NULL) || (*target == '\0'))        return -1;    if (xmlStrcasecmp(target, (const xmlChar *) "xml") == 0) {        xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                        "xmlTextWriterStartPI : target name [Xx][Mm][Ll] is reserved for xml standardization!\n");        return -1;    }    sum = 0;    lk = xmlListFront(writer->nodes);    if (lk != 0) {        p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);        if (p != 0) {            switch (p->state) {                case XML_TEXTWRITER_ATTRIBUTE:                    count = xmlTextWriterEndAttribute(writer);                    if (count < 0)                        return -1;                    sum += count;                    /* fallthrough */                case XML_TEXTWRITER_NAME:                    /* Output namespace declarations */                    count = xmlTextWriterOutputNSDecl(writer);                    if (count < 0)                        return -1;                    sum += count;                    count = xmlOutputBufferWriteString(writer->out, ">");                    if (count < 0)                        return -1;                    sum += count;                    p->state = XML_TEXTWRITER_TEXT;                    break;                case XML_TEXTWRITER_NONE:                case XML_TEXTWRITER_TEXT:                case XML_TEXTWRITER_DTD:                    break;                case XML_TEXTWRITER_PI:                case XML_TEXTWRITER_PI_TEXT:                    xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                                    "xmlTextWriterStartPI : nested PI!\n");                    return -1;                default:                    return -1;            }        }    }    p = (xmlTextWriterStackEntry *)        xmlMalloc(sizeof(xmlTextWriterStackEntry));    if (p == 0) {        xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                        "xmlTextWriterStartPI : out of memory!\n");        return -1;    }    p->name = xmlStrdup(target);    if (p->name == 0) {        xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                        "xmlTextWriterStartPI : out of memory!\n");        xmlFree(p);        return -1;    }    p->state = XML_TEXTWRITER_PI;    xmlListPushFront(writer->nodes, p);    count = xmlOutputBufferWriteString(writer->out, "<?");    if (count < 0)        return -1;    sum += count;    count =        xmlOutputBufferWriteString(writer->out, (const char *) p->name);    if (count < 0)        return -1;    sum += count;    return sum;}/** * xmlTextWriterEndPI: * @writer:  the xmlTextWriterPtr * * End the current xml PI. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterEndPI(xmlTextWriterPtr writer){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL)        return -1;    lk = xmlListFront(writer->nodes);    if (lk == 0)        return 0;    p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);    if (p == 0)        return 0;    sum = 0;    switch (p->state) {        case XML_TEXTWRITER_PI:        case XML_TEXTWRITER_PI_TEXT:            count = xmlOutputBufferWriteString(writer->out, "?>");            if (count < 0)                return -1;            sum += count;            break;        default:            return -1;    }    if (writer->indent) {        count = xmlOutputBufferWriteString(writer->out, "\n");      	if (count < 0)       	return -1;        sum += count;    }    xmlListPopFront(writer->nodes);    return sum;}/** * xmlTextWriterWriteFormatPI: * @writer:  the xmlTextWriterPtr * @target:  PI target * @format:  format string (see printf) * @...:  extra parameters for the format * * Write a formatted PI. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */int XMLCDECLxmlTextWriterWriteFormatPI(xmlTextWriterPtr writer, const xmlChar * target,                           const char *format, ...){    int rc;    va_list ap;    va_start(ap, format);    rc = xmlTextWriterWriteVFormatPI(writer, target, format, ap);    va_end(ap);    return rc;}/** * xmlTextWriterWriteVFormatPI: * @writer:  the xmlTextWriterPtr * @target:  PI target * @format:  format string (see printf) * @argptr:  pointer to the first member of the variable argument list. * * Write a formatted xml PI. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteVFormatPI(xmlTextWriterPtr writer,                            const xmlChar * target, const char *format,                            va_list argptr){    int rc;    xmlChar *buf;    if (writer == NULL)        return -1;    buf = xmlTextWriterVSprintf(format, argptr);    if (buf == NULL)        return -1;    rc = xmlTextWriterWritePI(writer, target, buf);    xmlFree(buf);    return rc;}/** * xmlTextWriterWritePI: * @writer:  the xmlTextWriterPtr * @target:  PI target * @content:  PI content * * Write an xml PI. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWritePI(xmlTextWriterPtr writer, const xmlChar * target,                     const xmlChar * content){    int count;    int sum;    sum = 0;    count = xmlTextWriterStartPI(writer, target);    if (count == -1)        return -1;    sum += count;    if (content != 0) {        count = xmlTextWriterWriteString(writer, content);        if (count == -1)            return -1;        sum += count;    }    count = xmlTextWriterEndPI(writer);    if (count == -1)        return -1;    sum += count;    return sum;}/** * xmlTextWriterStartCDATA: * @writer:  the xmlTextWriterPtr * * Start an xml CDATA section. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterStartCDATA(xmlTextWriterPtr writer){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL)        return -1;    sum = 0;    lk = xmlListFront(writer->nodes);    if (lk != 0) {        p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);        if (p != 0) {            switch (p->state) {                case XML_TEXTWRITER_NONE:		case XML_TEXTWRITER_TEXT:                case XML_TEXTWRITER_PI:                case XML_TEXTWRITER_PI_TEXT:                    break;                case XML_TEXTWRITER_ATTRIBUTE:                    count = xmlTextWriterEndAttribute(writer);                    if (count < 0)                        return -1;                    sum += count;                    /* fallthrough */                case XML_TEXTWRITER_NAME:                    /* Output namespace declarations */                    count = xmlTextWriterOutputNSDecl(writer);                    if (count < 0)                        return -1;                    sum += count;                    count = xmlOutputBufferWriteString(writer->out, ">");                    if (count < 0)                        return -1;                    sum += count;                    p->state = XML_TEXTWRITER_TEXT;                    break;                case XML_TEXTWRITER_CDATA:                    xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                                    "xmlTextWriterStartCDATA : CDATA not allowed in this context!\n");                    return -1;                default:                    return -1;            }        }    }    p = (xmlTextWriterStackEntry *)        xmlMalloc(sizeof(xmlTextWriterStackEntry));    if (p == 0) {        xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                        "xmlTextWriterStartCDATA : out of memory!\n");        return -1;    }    p->name = NULL;    p->state = XML_TEXTWRITER_CDATA;    xmlListPushFront(writer->nodes, p);    count = xmlOutputBufferWriteString(writer->out, "<![CDATA[");    if (count < 0)        return -1;    sum += count;    return sum;}/** * xmlTextWriterEndCDATA: * @writer:  the xmlTextWriterPtr * * End an xml CDATA section. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterEndCDATA(xmlTextWriterPtr writer){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL)        return -1;    lk = xmlListFront(writer->nodes);    if (lk == 0)        return -1;    p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);    if (p == 0)        return -1;    sum = 0;    switch (p->state) {        case XML_TEXTWRITER_CDATA:            count = xmlOutputBufferWriteString(writer->out, "]]>");            if (count < 0)                return -1;            sum += count;            break;        default:            return -1;    }    xmlListPopFront(writer->nodes);    return sum;}/** * xmlTextWriterWriteFormatCDATA: * @writer:  the xmlTextWriterPtr * @format:  format string (see printf) * @...:  extra parameters for the format * * Write a formatted xml CDATA. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */int XMLCDECLxmlTextWriterWriteFormatCDATA(xmlTextWriterPtr writer, const char *format,                              ...){    int rc;    va_list ap;    va_start(ap, format);    rc = xmlTextWriterWriteVFormatCDATA(writer, format, ap);    va_end(ap);    return rc;}/** * xmlTextWriterWriteVFormatCDATA: * @writer:  the xmlTextWriterPtr * @format:  format string (see printf) * @argptr:  pointer to the first member of the variable argument list. * * Write a formatted xml CDATA. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteVFormatCDATA(xmlTextWriterPtr writer, const char *format,                               va_list argptr){    int rc;    xmlChar *buf;    if (writer == NULL)        return -1;    buf = xmlTextWriterVSprintf(format, argptr);    if (buf == NULL)        return -1;    rc = xmlTextWriterWriteCDATA(writer, buf);    xmlFree(buf);    return rc;}/** * xmlTextWriterWriteCDATA: * @writer:  the xmlTextWriterPtr * @content:  CDATA content * * Write an xml CDATA. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteCDATA(xmlTextWriterPtr writer, const xmlChar * content){    int count;    int sum;    sum = 0;    count = xmlTextWriterStartCDATA(writer);    if (count == -1)        return -1;    sum += count;    if (content != 0) {        count = xmlTextWriterWriteString(writer, content);        if (count == -1)            return -1;        sum += count;    }    count = xmlTextWriterEndCDATA(writer);    if (count == -1)        return -1;    sum += count;    return sum;}/** * xmlTextWriterStartDTD: * @writer:  the xmlTextWriterPtr * @name:  the name of the DTD * @pubid:  the public identifier, which is an alternative to the system identifier * @sysid:  the system identifier, which is the URI of the DTD * * Start an xml DTD. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterStartDTD(xmlTextWriterPtr writer,                      const xmlChar * name,                      const xmlChar * pubid, const xmlChar * sysid){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL || name == NULL || *name == '\0')        return -1;    sum = 0;    lk = xmlListFront(writer->nodes);    if ((lk != NULL) && (xmlLinkGetData(lk) != NULL)) {        xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                        "xmlTextWriterStartDTD : DTD allowed only in prolog!\n");        return -1;    }    p = (xmlTextWriterStackEntry *)        xmlMalloc(sizeof(xmlTextWriterStackEntry));    if (p == 0) {        xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                        "xmlTextWriterStartDTD : out of memory!\n");        return -1;    }    p->name = xmlStrdup(name);    if (p->name == 0) {        xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                        "xmlTextWriterStartDTD : out of memory!\n");        xmlFree(p);        return -1;    }    p->state = XML_TEXTWRITER_DTD;    xmlListPushFront(writer->nodes, p);    count = xmlOutputBufferWriteString(writer->out, "<!DOCTYPE ");    if (count < 0)        return -1;    sum += count;    count = xmlOutputBufferWriteString(writer->out, (const char *) name);    if (count < 0)        return -1;    sum += count;    if (pubid != 0) {        if (sysid == 0) {            xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                            "xmlTextWriterStartDTD : system identifier needed!\n");            return -1;        }        if (writer->indent)            count = xmlOutputBufferWrite(writer->out, 1, "\n");        else            count = xmlOutputBufferWrite(writer->out, 1, " ");        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWriteString(writer->out, "PUBLIC ");        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);        if (count < 0)            return -1;        sum += count;        count =            xmlOutputBufferWriteString(writer->out, (const char *) pubid);        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);        if (count < 0)            return -1;        sum += count;    }    if (sysid != 0) {        if (pubid == 0) {            if (writer->indent)                count = xmlOutputBufferWrite(writer->out, 1, "\n");            else                count = xmlOutputBufferWrite(writer->out, 1, " ");            if (count < 0)                return -1;            sum += count;            count = xmlOutputBufferWriteString(writer->out, "SYSTEM ");            if (count < 0)                return -1;            sum += count;        } else {			if (writer->indent)            count = xmlOutputBufferWriteString(writer->out, "\n       ");            else                count = xmlOutputBufferWrite(writer->out, 1, " ");            if (count < 0)                return -1;            sum += count;        }        count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);        if (count < 0)            return -1;        sum += count;        count =            xmlOutputBufferWriteString(writer->out, (const char *) sysid);        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);        if (count < 0)            return -1;        sum += count;    }    return sum;}/** * xmlTextWriterEndDTD: * @writer:  the xmlTextWriterPtr * * End an xml DTD. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterEndDTD(xmlTextWriterPtr writer){    int loop;    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL)        return -1;    sum = 0;    loop = 1;    while (loop) {        lk = xmlListFront(writer->nodes);        if (lk == NULL)            break;        p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);        if (p == 0)            break;        switch (p->state) {            case XML_TEXTWRITER_DTD_TEXT:                count = xmlOutputBufferWriteString(writer->out, "]");                if (count < 0)                    return -1;                sum += count;                /* fallthrough */            case XML_TEXTWRITER_DTD:                count = xmlOutputBufferWriteString(writer->out, ">");                if (writer->indent) {                    if (count < 0)                        return -1;                    sum += count;                    count = xmlOutputBufferWriteString(writer->out, "\n");                }                xmlListPopFront(writer->nodes);                break;            case XML_TEXTWRITER_DTD_ELEM:            case XML_TEXTWRITER_DTD_ELEM_TEXT:                count = xmlTextWriterEndDTDElement(writer);                break;            case XML_TEXTWRITER_DTD_ATTL:            case XML_TEXTWRITER_DTD_ATTL_TEXT:                count = xmlTextWriterEndDTDAttlist(writer);                break;            case XML_TEXTWRITER_DTD_ENTY:            case XML_TEXTWRITER_DTD_PENT:            case XML_TEXTWRITER_DTD_ENTY_TEXT:                count = xmlTextWriterEndDTDEntity(writer);                break;            case XML_TEXTWRITER_COMMENT:                count = xmlTextWriterEndComment(writer);                break;            default:                loop = 0;                continue;        }        if (count < 0)            return -1;        sum += count;    }    return sum;}/** * xmlTextWriterWriteFormatDTD: * @writer:  the xmlTextWriterPtr * @name:  the name of the DTD * @pubid:  the public identifier, which is an alternative to the system identifier * @sysid:  the system identifier, which is the URI of the DTD * @format:  format string (see printf) * @...:  extra parameters for the format * * Write a DTD with a formatted markup declarations part. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */int XMLCDECLxmlTextWriterWriteFormatDTD(xmlTextWriterPtr writer,                            const xmlChar * name,                            const xmlChar * pubid,                            const xmlChar * sysid, const char *format, ...){    int rc;    va_list ap;    va_start(ap, format);    rc = xmlTextWriterWriteVFormatDTD(writer, name, pubid, sysid, format,                                      ap);    va_end(ap);    return rc;}/** * xmlTextWriterWriteVFormatDTD: * @writer:  the xmlTextWriterPtr * @name:  the name of the DTD * @pubid:  the public identifier, which is an alternative to the system identifier * @sysid:  the system identifier, which is the URI of the DTD * @format:  format string (see printf) * @argptr:  pointer to the first member of the variable argument list. * * Write a DTD with a formatted markup declarations part. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteVFormatDTD(xmlTextWriterPtr writer,                             const xmlChar * name,                             const xmlChar * pubid,                             const xmlChar * sysid,                             const char *format, va_list argptr){    int rc;    xmlChar *buf;    if (writer == NULL)        return -1;    buf = xmlTextWriterVSprintf(format, argptr);    if (buf == NULL)        return -1;    rc = xmlTextWriterWriteDTD(writer, name, pubid, sysid, buf);    xmlFree(buf);    return rc;}/** * xmlTextWriterWriteDTD: * @writer:  the xmlTextWriterPtr * @name:  the name of the DTD * @pubid:  the public identifier, which is an alternative to the system identifier * @sysid:  the system identifier, which is the URI of the DTD * @subset:  string content of the DTD * * Write a DTD. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteDTD(xmlTextWriterPtr writer,                      const xmlChar * name,                      const xmlChar * pubid,                      const xmlChar * sysid, const xmlChar * subset){    int count;    int sum;    sum = 0;    count = xmlTextWriterStartDTD(writer, name, pubid, sysid);    if (count == -1)        return -1;    sum += count;    if (subset != 0) {        count = xmlTextWriterWriteString(writer, subset);        if (count == -1)            return -1;        sum += count;    }    count = xmlTextWriterEndDTD(writer);    if (count == -1)        return -1;    sum += count;    return sum;}/** * xmlTextWriterStartDTDElement: * @writer:  the xmlTextWriterPtr * @name:  the name of the DTD element * * Start an xml DTD element. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterStartDTDElement(xmlTextWriterPtr writer, const xmlChar * name){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL || name == NULL || *name == '\0')        return -1;    sum = 0;    lk = xmlListFront(writer->nodes);    if (lk == 0) {        return -1;    }    p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);    if (p != 0) {        switch (p->state) {            case XML_TEXTWRITER_DTD:                count = xmlOutputBufferWriteString(writer->out, " [");                if (count < 0)                    return -1;                sum += count;                if (writer->indent) {                    count = xmlOutputBufferWriteString(writer->out, "\n");                    if (count < 0)                        return -1;                    sum += count;                }                p->state = XML_TEXTWRITER_DTD_TEXT;                /* fallthrough */            case XML_TEXTWRITER_DTD_TEXT:            case XML_TEXTWRITER_NONE:                break;            default:                return -1;        }    }    p = (xmlTextWriterStackEntry *)        xmlMalloc(sizeof(xmlTextWriterStackEntry));    if (p == 0) {        xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                        "xmlTextWriterStartDTDElement : out of memory!\n");        return -1;    }    p->name = xmlStrdup(name);    if (p->name == 0) {        xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                        "xmlTextWriterStartDTDElement : out of memory!\n");        xmlFree(p);        return -1;    }    p->state = XML_TEXTWRITER_DTD_ELEM;    xmlListPushFront(writer->nodes, p);    if (writer->indent) {        count = xmlTextWriterWriteIndent(writer);        if (count < 0)            return -1;        sum += count;    }    count = xmlOutputBufferWriteString(writer->out, "<!ELEMENT ");    if (count < 0)        return -1;    sum += count;    count = xmlOutputBufferWriteString(writer->out, (const char *) name);    if (count < 0)        return -1;    sum += count;    return sum;}/** * xmlTextWriterEndDTDElement: * @writer:  the xmlTextWriterPtr * * End an xml DTD element. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterEndDTDElement(xmlTextWriterPtr writer){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL)        return -1;    sum = 0;    lk = xmlListFront(writer->nodes);    if (lk == 0)        return -1;    p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);    if (p == 0)        return -1;    switch (p->state) {        case XML_TEXTWRITER_DTD_ELEM:        case XML_TEXTWRITER_DTD_ELEM_TEXT:            count = xmlOutputBufferWriteString(writer->out, ">");            if (count < 0)                return -1;            sum += count;            break;        default:            return -1;    }    if (writer->indent) {        count = xmlOutputBufferWriteString(writer->out, "\n");        if (count < 0)            return -1;        sum += count;    }    xmlListPopFront(writer->nodes);    return sum;}/** * xmlTextWriterWriteFormatDTDElement: * @writer:  the xmlTextWriterPtr * @name:  the name of the DTD element * @format:  format string (see printf) * @...:  extra parameters for the format * * Write a formatted DTD element. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */int XMLCDECLxmlTextWriterWriteFormatDTDElement(xmlTextWriterPtr writer,                                   const xmlChar * name,                                   const char *format, ...){    int rc;    va_list ap;    va_start(ap, format);    rc = xmlTextWriterWriteVFormatDTDElement(writer, name, format, ap);    va_end(ap);    return rc;}/** * xmlTextWriterWriteVFormatDTDElement: * @writer:  the xmlTextWriterPtr * @name:  the name of the DTD element * @format:  format string (see printf) * @argptr:  pointer to the first member of the variable argument list. * * Write a formatted DTD element. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteVFormatDTDElement(xmlTextWriterPtr writer,                                    const xmlChar * name,                                    const char *format, va_list argptr){    int rc;    xmlChar *buf;    if (writer == NULL)        return -1;    buf = xmlTextWriterVSprintf(format, argptr);    if (buf == NULL)        return -1;    rc = xmlTextWriterWriteDTDElement(writer, name, buf);    xmlFree(buf);    return rc;}/** * xmlTextWriterWriteDTDElement: * @writer:  the xmlTextWriterPtr * @name:  the name of the DTD element * @content:  content of the element * * Write a DTD element. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteDTDElement(xmlTextWriterPtr writer,                             const xmlChar * name, const xmlChar * content){    int count;    int sum;    if (content == NULL)        return -1;    sum = 0;    count = xmlTextWriterStartDTDElement(writer, name);    if (count == -1)        return -1;    sum += count;    count = xmlTextWriterWriteString(writer, content);    if (count == -1)        return -1;    sum += count;    count = xmlTextWriterEndDTDElement(writer);    if (count == -1)        return -1;    sum += count;    return sum;}/** * xmlTextWriterStartDTDAttlist: * @writer:  the xmlTextWriterPtr * @name:  the name of the DTD ATTLIST * * Start an xml DTD ATTLIST. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterStartDTDAttlist(xmlTextWriterPtr writer, const xmlChar * name){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL || name == NULL || *name == '\0')        return -1;    sum = 0;    lk = xmlListFront(writer->nodes);    if (lk == 0) {        return -1;    }    p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);    if (p != 0) {        switch (p->state) {            case XML_TEXTWRITER_DTD:                count = xmlOutputBufferWriteString(writer->out, " [");                if (count < 0)                    return -1;                sum += count;                if (writer->indent) {                    count = xmlOutputBufferWriteString(writer->out, "\n");                    if (count < 0)                        return -1;                    sum += count;                }                p->state = XML_TEXTWRITER_DTD_TEXT;                /* fallthrough */            case XML_TEXTWRITER_DTD_TEXT:            case XML_TEXTWRITER_NONE:                break;            default:                return -1;        }    }    p = (xmlTextWriterStackEntry *)        xmlMalloc(sizeof(xmlTextWriterStackEntry));    if (p == 0) {        xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                        "xmlTextWriterStartDTDAttlist : out of memory!\n");        return -1;    }    p->name = xmlStrdup(name);    if (p->name == 0) {        xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                        "xmlTextWriterStartDTDAttlist : out of memory!\n");        xmlFree(p);        return -1;    }    p->state = XML_TEXTWRITER_DTD_ATTL;    xmlListPushFront(writer->nodes, p);    if (writer->indent) {        count = xmlTextWriterWriteIndent(writer);        if (count < 0)            return -1;        sum += count;    }    count = xmlOutputBufferWriteString(writer->out, "<!ATTLIST ");    if (count < 0)        return -1;    sum += count;    count = xmlOutputBufferWriteString(writer->out, (const char *) name);    if (count < 0)        return -1;    sum += count;    return sum;}/** * xmlTextWriterEndDTDAttlist: * @writer:  the xmlTextWriterPtr * * End an xml DTD attribute list. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterEndDTDAttlist(xmlTextWriterPtr writer){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL)        return -1;    sum = 0;    lk = xmlListFront(writer->nodes);    if (lk == 0)        return -1;    p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);    if (p == 0)        return -1;    switch (p->state) {        case XML_TEXTWRITER_DTD_ATTL:        case XML_TEXTWRITER_DTD_ATTL_TEXT:            count = xmlOutputBufferWriteString(writer->out, ">");            if (count < 0)                return -1;            sum += count;            break;        default:            return -1;    }    if (writer->indent) {        count = xmlOutputBufferWriteString(writer->out, "\n");        if (count < 0)            return -1;        sum += count;    }    xmlListPopFront(writer->nodes);    return sum;}/** * xmlTextWriterWriteFormatDTDAttlist: * @writer:  the xmlTextWriterPtr * @name:  the name of the DTD ATTLIST * @format:  format string (see printf) * @...:  extra parameters for the format * * Write a formatted DTD ATTLIST. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */int XMLCDECLxmlTextWriterWriteFormatDTDAttlist(xmlTextWriterPtr writer,                                   const xmlChar * name,                                   const char *format, ...){    int rc;    va_list ap;    va_start(ap, format);    rc = xmlTextWriterWriteVFormatDTDAttlist(writer, name, format, ap);    va_end(ap);    return rc;}/** * xmlTextWriterWriteVFormatDTDAttlist: * @writer:  the xmlTextWriterPtr * @name:  the name of the DTD ATTLIST * @format:  format string (see printf) * @argptr:  pointer to the first member of the variable argument list. * * Write a formatted DTD ATTLIST. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteVFormatDTDAttlist(xmlTextWriterPtr writer,                                    const xmlChar * name,                                    const char *format, va_list argptr){    int rc;    xmlChar *buf;    if (writer == NULL)        return -1;    buf = xmlTextWriterVSprintf(format, argptr);    if (buf == NULL)        return -1;    rc = xmlTextWriterWriteDTDAttlist(writer, name, buf);    xmlFree(buf);    return rc;}/** * xmlTextWriterWriteDTDAttlist: * @writer:  the xmlTextWriterPtr * @name:  the name of the DTD ATTLIST * @content:  content of the ATTLIST * * Write a DTD ATTLIST. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteDTDAttlist(xmlTextWriterPtr writer,                             const xmlChar * name, const xmlChar * content){    int count;    int sum;    if (content == NULL)        return -1;    sum = 0;    count = xmlTextWriterStartDTDAttlist(writer, name);    if (count == -1)        return -1;    sum += count;    count = xmlTextWriterWriteString(writer, content);    if (count == -1)        return -1;    sum += count;    count = xmlTextWriterEndDTDAttlist(writer);    if (count == -1)        return -1;    sum += count;    return sum;}/** * xmlTextWriterStartDTDEntity: * @writer:  the xmlTextWriterPtr * @pe:  TRUE if this is a parameter entity, FALSE if not * @name:  the name of the DTD ATTLIST * * Start an xml DTD ATTLIST. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterStartDTDEntity(xmlTextWriterPtr writer,                            int pe, const xmlChar * name){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL || name == NULL || *name == '\0')        return -1;    sum = 0;    lk = xmlListFront(writer->nodes);    if (lk != 0) {        p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);        if (p != 0) {            switch (p->state) {                case XML_TEXTWRITER_DTD:                    count = xmlOutputBufferWriteString(writer->out, " [");                    if (count < 0)                        return -1;                    sum += count;                    if (writer->indent) {                        count =                            xmlOutputBufferWriteString(writer->out, "\n");                        if (count < 0)                            return -1;                        sum += count;                    }                    p->state = XML_TEXTWRITER_DTD_TEXT;                    /* fallthrough */                case XML_TEXTWRITER_DTD_TEXT:                case XML_TEXTWRITER_NONE:                    break;                default:                    return -1;            }        }    }    p = (xmlTextWriterStackEntry *)        xmlMalloc(sizeof(xmlTextWriterStackEntry));    if (p == 0) {        xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                        "xmlTextWriterStartDTDElement : out of memory!\n");        return -1;    }    p->name = xmlStrdup(name);    if (p->name == 0) {        xmlWriterErrMsg(writer, XML_ERR_NO_MEMORY,                        "xmlTextWriterStartDTDElement : out of memory!\n");        xmlFree(p);        return -1;    }    if (pe != 0)        p->state = XML_TEXTWRITER_DTD_PENT;    else        p->state = XML_TEXTWRITER_DTD_ENTY;    xmlListPushFront(writer->nodes, p);    if (writer->indent) {        count = xmlTextWriterWriteIndent(writer);        if (count < 0)            return -1;        sum += count;    }    count = xmlOutputBufferWriteString(writer->out, "<!ENTITY ");    if (count < 0)        return -1;    sum += count;    if (pe != 0) {        count = xmlOutputBufferWriteString(writer->out, "% ");        if (count < 0)            return -1;        sum += count;    }    count = xmlOutputBufferWriteString(writer->out, (const char *) name);    if (count < 0)        return -1;    sum += count;    return sum;}/** * xmlTextWriterEndDTDEntity: * @writer:  the xmlTextWriterPtr * * End an xml DTD entity. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterEndDTDEntity(xmlTextWriterPtr writer){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL)        return -1;    sum = 0;    lk = xmlListFront(writer->nodes);    if (lk == 0)        return -1;    p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);    if (p == 0)        return -1;    switch (p->state) {        case XML_TEXTWRITER_DTD_ENTY_TEXT:            count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);            if (count < 0)                return -1;            sum += count;        case XML_TEXTWRITER_DTD_ENTY:        case XML_TEXTWRITER_DTD_PENT:            count = xmlOutputBufferWriteString(writer->out, ">");            if (count < 0)                return -1;            sum += count;            break;        default:            return -1;    }    if (writer->indent) {        count = xmlOutputBufferWriteString(writer->out, "\n");        if (count < 0)            return -1;        sum += count;    }    xmlListPopFront(writer->nodes);    return sum;}/** * xmlTextWriterWriteFormatDTDInternalEntity: * @writer:  the xmlTextWriterPtr * @pe:  TRUE if this is a parameter entity, FALSE if not * @name:  the name of the DTD entity * @format:  format string (see printf) * @...:  extra parameters for the format * * Write a formatted DTD internal entity. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */int XMLCDECLxmlTextWriterWriteFormatDTDInternalEntity(xmlTextWriterPtr writer,                                          int pe,                                          const xmlChar * name,                                          const char *format, ...){    int rc;    va_list ap;    va_start(ap, format);    rc = xmlTextWriterWriteVFormatDTDInternalEntity(writer, pe, name,                                                    format, ap);    va_end(ap);    return rc;}/** * xmlTextWriterWriteVFormatDTDInternalEntity: * @writer:  the xmlTextWriterPtr * @pe:  TRUE if this is a parameter entity, FALSE if not * @name:  the name of the DTD entity * @format:  format string (see printf) * @argptr:  pointer to the first member of the variable argument list. * * Write a formatted DTD internal entity. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteVFormatDTDInternalEntity(xmlTextWriterPtr writer,                                           int pe,                                           const xmlChar * name,                                           const char *format,                                           va_list argptr){    int rc;    xmlChar *buf;    if (writer == NULL)        return -1;    buf = xmlTextWriterVSprintf(format, argptr);    if (buf == NULL)        return -1;    rc = xmlTextWriterWriteDTDInternalEntity(writer, pe, name, buf);    xmlFree(buf);    return rc;}/** * xmlTextWriterWriteDTDEntity: * @writer:  the xmlTextWriterPtr * @pe:  TRUE if this is a parameter entity, FALSE if not * @name:  the name of the DTD entity * @pubid:  the public identifier, which is an alternative to the system identifier * @sysid:  the system identifier, which is the URI of the DTD * @ndataid:  the xml notation name. * @content:  content of the entity * * Write a DTD entity. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteDTDEntity(xmlTextWriterPtr writer,                            int pe,                            const xmlChar * name,                            const xmlChar * pubid,                            const xmlChar * sysid,                            const xmlChar * ndataid,                            const xmlChar * content){    if ((content == NULL) && (pubid == NULL) && (sysid == NULL))        return -1;    if ((pe != 0) && (ndataid != NULL))        return -1;    if ((pubid == NULL) && (sysid == NULL))        return xmlTextWriterWriteDTDInternalEntity(writer, pe, name,                                                   content);    return xmlTextWriterWriteDTDExternalEntity(writer, pe, name, pubid,                                               sysid, ndataid);}/** * xmlTextWriterWriteDTDInternalEntity: * @writer:  the xmlTextWriterPtr * @pe:  TRUE if this is a parameter entity, FALSE if not * @name:  the name of the DTD entity * @content:  content of the entity * * Write a DTD internal entity. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteDTDInternalEntity(xmlTextWriterPtr writer,                                    int pe,                                    const xmlChar * name,                                    const xmlChar * content){    int count;    int sum;    if ((name == NULL) || (*name == '\0') || (content == NULL))        return -1;    sum = 0;    count = xmlTextWriterStartDTDEntity(writer, pe, name);    if (count == -1)        return -1;    sum += count;    count = xmlTextWriterWriteString(writer, content);    if (count == -1)        return -1;    sum += count;    count = xmlTextWriterEndDTDEntity(writer);    if (count == -1)        return -1;    sum += count;    return sum;}/** * xmlTextWriterWriteDTDExternalEntity: * @writer:  the xmlTextWriterPtr * @pe:  TRUE if this is a parameter entity, FALSE if not * @name:  the name of the DTD entity * @pubid:  the public identifier, which is an alternative to the system identifier * @sysid:  the system identifier, which is the URI of the DTD * @ndataid:  the xml notation name. * * Write a DTD external entity. The entity must have been started with xmlTextWriterStartDTDEntity * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteDTDExternalEntity(xmlTextWriterPtr writer,                                    int pe,                                    const xmlChar * name,                                    const xmlChar * pubid,                                    const xmlChar * sysid,                                    const xmlChar * ndataid){    int count;    int sum;    if (((pubid == NULL) && (sysid == NULL)))        return -1;    if ((pe != 0) && (ndataid != NULL))        return -1;    sum = 0;    count = xmlTextWriterStartDTDEntity(writer, pe, name);    if (count == -1)        return -1;    sum += count;    count =        xmlTextWriterWriteDTDExternalEntityContents(writer, pubid, sysid,                                                    ndataid);    if (count < 0)        return -1;    sum += count;    count = xmlTextWriterEndDTDEntity(writer);    if (count == -1)        return -1;    sum += count;    return sum;}/** * xmlTextWriterWriteDTDExternalEntityContents: * @writer:  the xmlTextWriterPtr * @pubid:  the public identifier, which is an alternative to the system identifier * @sysid:  the system identifier, which is the URI of the DTD * @ndataid:  the xml notation name. * * Write the contents of a DTD external entity. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteDTDExternalEntityContents(xmlTextWriterPtr writer,                                            const xmlChar * pubid,                                            const xmlChar * sysid,                                            const xmlChar * ndataid){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL) {        xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                        "xmlTextWriterWriteDTDExternalEntityContents: xmlTextWriterPtr invalid!\n");        return -1;    }    sum = 0;    lk = xmlListFront(writer->nodes);    if (lk == 0) {        xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                        "xmlTextWriterWriteDTDExternalEntityContents: you must call xmlTextWriterStartDTDEntity before the call to this function!\n");        return -1;    }    p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);    if (p == 0)        return -1;    switch (p->state) {        case XML_TEXTWRITER_DTD_ENTY:            break;        case XML_TEXTWRITER_DTD_PENT:            if (ndataid != NULL) {                xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                                "xmlTextWriterWriteDTDExternalEntityContents: notation not allowed with parameter entities!\n");                return -1;            }            break;        default:            xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                            "xmlTextWriterWriteDTDExternalEntityContents: you must call xmlTextWriterStartDTDEntity before the call to this function!\n");            return -1;    }    if (pubid != 0) {        if (sysid == 0) {            xmlWriterErrMsg(writer, XML_ERR_INTERNAL_ERROR,                            "xmlTextWriterWriteDTDExternalEntityContents: system identifier needed!\n");            return -1;        }        count = xmlOutputBufferWriteString(writer->out, " PUBLIC ");        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);        if (count < 0)            return -1;        sum += count;        count =            xmlOutputBufferWriteString(writer->out, (const char *) pubid);        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);        if (count < 0)            return -1;        sum += count;    }    if (sysid != 0) {        if (pubid == 0) {            count = xmlOutputBufferWriteString(writer->out, " SYSTEM");            if (count < 0)                return -1;            sum += count;        }        count = xmlOutputBufferWriteString(writer->out, " ");        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);        if (count < 0)            return -1;        sum += count;        count =            xmlOutputBufferWriteString(writer->out, (const char *) sysid);        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);        if (count < 0)            return -1;        sum += count;    }    if (ndataid != NULL) {        count = xmlOutputBufferWriteString(writer->out, " NDATA ");        if (count < 0)            return -1;        sum += count;        count =            xmlOutputBufferWriteString(writer->out,                                       (const char *) ndataid);        if (count < 0)            return -1;        sum += count;    }    return sum;}/** * xmlTextWriterWriteDTDNotation: * @writer:  the xmlTextWriterPtr * @name:  the name of the xml notation * @pubid:  the public identifier, which is an alternative to the system identifier * @sysid:  the system identifier, which is the URI of the DTD * * Write a DTD entity. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterWriteDTDNotation(xmlTextWriterPtr writer,                              const xmlChar * name,                              const xmlChar * pubid, const xmlChar * sysid){    int count;    int sum;    xmlLinkPtr lk;    xmlTextWriterStackEntry *p;    if (writer == NULL || name == NULL || *name == '\0')        return -1;    sum = 0;    lk = xmlListFront(writer->nodes);    if (lk == 0) {        return -1;    }    p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);    if (p != 0) {        switch (p->state) {            case XML_TEXTWRITER_DTD:                count = xmlOutputBufferWriteString(writer->out, " [");                if (count < 0)                    return -1;                sum += count;                if (writer->indent) {                    count = xmlOutputBufferWriteString(writer->out, "\n");                    if (count < 0)                        return -1;                    sum += count;                }                p->state = XML_TEXTWRITER_DTD_TEXT;                /* fallthrough */            case XML_TEXTWRITER_DTD_TEXT:                break;            default:                return -1;        }    }    if (writer->indent) {        count = xmlTextWriterWriteIndent(writer);        if (count < 0)            return -1;        sum += count;    }    count = xmlOutputBufferWriteString(writer->out, "<!NOTATION ");    if (count < 0)        return -1;    sum += count;    count = xmlOutputBufferWriteString(writer->out, (const char *) name);    if (count < 0)        return -1;    sum += count;    if (pubid != 0) {        count = xmlOutputBufferWriteString(writer->out, " PUBLIC ");        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);        if (count < 0)            return -1;        sum += count;        count =            xmlOutputBufferWriteString(writer->out, (const char *) pubid);        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);        if (count < 0)            return -1;        sum += count;    }    if (sysid != 0) {        if (pubid == 0) {            count = xmlOutputBufferWriteString(writer->out, " SYSTEM");            if (count < 0)                return -1;            sum += count;        }        count = xmlOutputBufferWriteString(writer->out, " ");        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);        if (count < 0)            return -1;        sum += count;        count =            xmlOutputBufferWriteString(writer->out, (const char *) sysid);        if (count < 0)            return -1;        sum += count;        count = xmlOutputBufferWrite(writer->out, 1, &writer->qchar);        if (count < 0)            return -1;        sum += count;    }    count = xmlOutputBufferWriteString(writer->out, ">");    if (count < 0)        return -1;    sum += count;    return sum;}/** * xmlTextWriterFlush: * @writer:  the xmlTextWriterPtr * * Flush the output buffer. * * Returns the bytes written (may be 0 because of buffering) or -1 in case of error */intxmlTextWriterFlush(xmlTextWriterPtr writer){    int count;    if (writer == NULL)        return -1;    if (writer->out == NULL)        count = 0;    else        count = xmlOutputBufferFlush(writer->out);    return count;}/** * misc *//** * xmlFreeTextWriterStackEntry: * @lk:  the xmlLinkPtr * * Free callback for the xmlList. */static voidxmlFreeTextWriterStackEntry(xmlLinkPtr lk){    xmlTextWriterStackEntry *p;    p = (xmlTextWriterStackEntry *) xmlLinkGetData(lk);    if (p == 0)        return;    if (p->name != 0)        xmlFree(p->name);    xmlFree(p);}/** * xmlCmpTextWriterStackEntry: * @data0:  the first data * @data1:  the second data * * Compare callback for the xmlList. * * Returns -1, 0, 1 */static intxmlCmpTextWriterStackEntry(const void *data0, const void *data1){    xmlTextWriterStackEntry *p0;    xmlTextWriterStackEntry *p1;    if (data0 == data1)        return 0;    if (data0 == 0)        return -1;    if (data1 == 0)        return 1;    p0 = (xmlTextWriterStackEntry *) data0;    p1 = (xmlTextWriterStackEntry *) data1;    return xmlStrcmp(p0->name, p1->name);}/** * misc *//** * xmlTextWriterOutputNSDecl: * @writer:  the xmlTextWriterPtr * * Output the current namespace declarations. */static intxmlTextWriterOutputNSDecl(xmlTextWriterPtr writer){    xmlLinkPtr lk;    xmlTextWriterNsStackEntry *np;    int count;    int sum;    sum = 0;    while (!xmlListEmpty(writer->nsstack)) {        xmlChar *namespaceURI = NULL;        xmlChar *prefix = NULL;        lk = xmlListFront(writer->nsstack);        np = (xmlTextWriterNsStackEntry *) xmlLinkGetData(lk);        if (np != 0) {            namespaceURI = xmlStrdup(np->uri);            prefix = xmlStrdup(np->prefix);        }        xmlListPopFront(writer->nsstack);        if (np != 0) {            count = xmlTextWriterWriteAttribute(writer, prefix, namespaceURI);            xmlFree(namespaceURI);            xmlFree(prefix);            if (count < 0) {                xmlListDelete(writer->nsstack);                writer->nsstack = NULL;                return -1;            }            sum += count;        }    }    return sum;}/** * xmlFreeTextWriterNsStackEntry: * @lk:  the xmlLinkPtr * * Free callback for the xmlList. */static voidxmlFreeTextWriterNsStackEntry(xmlLinkPtr lk){    xmlTextWriterNsStackEntry *p;    p = (xmlTextWriterNsStackEntry *) xmlLinkGetData(lk);    if (p == 0)        return;    if (p->prefix != 0)        xmlFree(p->prefix);    if (p->uri != 0)        xmlFree(p->uri);    xmlFree(p);}/** * xmlCmpTextWriterNsStackEntry: * @data0:  the first data * @data1:  the second data * * Compare callback for the xmlList. * * Returns -1, 0, 1 */static intxmlCmpTextWriterNsStackEntry(const void *data0, const void *data1){    xmlTextWriterNsStackEntry *p0;    xmlTextWriterNsStackEntry *p1;    int rc;    if (data0 == data1)        return 0;    if (data0 == 0)        return -1;    if (data1 == 0)        return 1;    p0 = (xmlTextWriterNsStackEntry *) data0;    p1 = (xmlTextWriterNsStackEntry *) data1;    rc = xmlStrcmp(p0->prefix, p1->prefix);    if ((rc != 0) || (p0->elem != p1->elem))        rc = -1;    return rc;}/** * xmlTextWriterWriteDocCallback: * @context:  the xmlBufferPtr * @str:  the data to write * @len:  the length of the data * * Write callback for the xmlOutputBuffer with target xmlBuffer * * Returns -1, 0, 1 */static intxmlTextWriterWriteDocCallback(void *context, const xmlChar * str, int len){    xmlParserCtxtPtr ctxt = (xmlParserCtxtPtr) context;    int rc;    if ((rc = xmlParseChunk(ctxt, (const char *) str, len, 0)) != 0) {        xmlWriterErrMsgInt(NULL, XML_ERR_INTERNAL_ERROR,                        "xmlTextWriterWriteDocCallback : XML error %d !\n",                        rc);        return -1;    }    return len;}/** * xmlTextWriterCloseDocCallback: * @context:  the xmlBufferPtr * * Close callback for the xmlOutputBuffer with target xmlBuffer * * Returns -1, 0, 1 */static intxmlTextWriterCloseDocCallback(void *context){    xmlParserCtxtPtr ctxt = (xmlParserCtxtPtr) context;    int rc;    if ((rc = xmlParseChunk(ctxt, NULL, 0, 1)) != 0) {        xmlWriterErrMsgInt(NULL, XML_ERR_INTERNAL_ERROR,                        "xmlTextWriterWriteDocCallback : XML error %d !\n",                        rc);        return -1;    }    return 0;}/** * xmlTextWriterVSprintf: * @format:  see printf * @argptr:  pointer to the first member of the variable argument list. * * Utility function for formatted output * * Returns a new xmlChar buffer with the data or NULL on error. This buffer must be freed. */static xmlChar *xmlTextWriterVSprintf(const char *format, va_list argptr){    int size;    int count;    xmlChar *buf;    va_list locarg;    size = BUFSIZ;    buf = (xmlChar *) xmlMalloc(size);    if (buf == NULL) {        xmlWriterErrMsg(NULL, XML_ERR_NO_MEMORY,                        "xmlTextWriterVSprintf : out of memory!\n");        return NULL;    }    VA_COPY(locarg, argptr);    while (((count = vsnprintf((char *) buf, size, format, locarg)) < 0)           || (count == size - 1) || (count == size) || (count > size)) {	va_end(locarg);        xmlFree(buf);        size += BUFSIZ;        buf = (xmlChar *) xmlMalloc(size);        if (buf == NULL) {            xmlWriterErrMsg(NULL, XML_ERR_NO_MEMORY,                            "xmlTextWriterVSprintf : out of memory!\n");            return NULL;        }	VA_COPY(locarg, argptr);    }    va_end(locarg);    return buf;}/** * xmlTextWriterStartDocumentCallback: * @ctx: the user data (XML parser context) * * called at the start of document processing. */static voidxmlTextWriterStartDocumentCallback(void *ctx){    xmlParserCtxtPtr ctxt = (xmlParserCtxtPtr) ctx;    xmlDocPtr doc;    if (ctxt->html) {#ifdef LIBXML_HTML_ENABLED        if (ctxt->myDoc == NULL)            ctxt->myDoc = htmlNewDocNoDtD(NULL, NULL);        if (ctxt->myDoc == NULL) {            if ((ctxt->sax != NULL) && (ctxt->sax->error != NULL))                ctxt->sax->error(ctxt->userData,                                 "SAX.startDocument(): out of memory\n");            ctxt->errNo = XML_ERR_NO_MEMORY;            ctxt->instate = XML_PARSER_EOF;            ctxt->disableSAX = 1;            return;        }#else        xmlWriterErrMsg(NULL, XML_ERR_INTERNAL_ERROR,                        "libxml2 built without HTML support\n");        ctxt->errNo = XML_ERR_INTERNAL_ERROR;        ctxt->instate = XML_PARSER_EOF;        ctxt->disableSAX = 1;        return;#endif    } else {        doc = ctxt->myDoc;        if (doc == NULL)            doc = ctxt->myDoc = xmlNewDoc(ctxt->version);        if (doc != NULL) {            if (doc->children == NULL) {                if (ctxt->encoding != NULL)                    doc->encoding = xmlStrdup(ctxt->encoding);                else                    doc->encoding = NULL;                doc->standalone = ctxt->standalone;            }        } else {            if ((ctxt->sax != NULL) && (ctxt->sax->error != NULL))                ctxt->sax->error(ctxt->userData,                                 "SAX.startDocument(): out of memory\n");            ctxt->errNo = XML_ERR_NO_MEMORY;            ctxt->instate = XML_PARSER_EOF;            ctxt->disableSAX = 1;            return;        }    }    if ((ctxt->myDoc != NULL) && (ctxt->myDoc->URL == NULL) &&        (ctxt->input != NULL) && (ctxt->input->filename != NULL)) {        ctxt->myDoc->URL =            xmlCanonicPath((const xmlChar *) ctxt->input->filename);        if (ctxt->myDoc->URL == NULL)            ctxt->myDoc->URL =                xmlStrdup((const xmlChar *) ctxt->input->filename);    }}/** * xmlTextWriterSetIndent: * @writer:  the xmlTextWriterPtr * @indent:  do indentation? * * Set indentation output. indent = 0 do not indentation. indent > 0 do indentation. * * Returns -1 on error or 0 otherwise. */intxmlTextWriterSetIndent(xmlTextWriterPtr writer, int indent){    if ((writer == NULL) || (indent < 0))        return -1;    writer->indent = indent;    writer->doindent = 1;    return 0;}/** * xmlTextWriterSetIndentString: * @writer:  the xmlTextWriterPtr * @str:  the xmlChar string * * Set string indentation. * * Returns -1 on error or 0 otherwise. */intxmlTextWriterSetIndentString(xmlTextWriterPtr writer, const xmlChar * str){    if ((writer == NULL) || (!str))        return -1;    if (writer->ichar != NULL)        xmlFree(writer->ichar);    writer->ichar = xmlStrdup(str);    if (!writer->ichar)        return -1;    else        return 0;}/** * xmlTextWriterWriteIndent: * @writer:  the xmlTextWriterPtr * * Write indent string. * * Returns -1 on error or the number of strings written. */static intxmlTextWriterWriteIndent(xmlTextWriterPtr writer){    int lksize;    int i;    int ret;    lksize = xmlListSize(writer->nodes);    if (lksize < 1)        return (-1);            /* list is empty */    for (i = 0; i < (lksize - 1); i++) {        ret = xmlOutputBufferWriteString(writer->out,                                         (const char *) writer->ichar);        if (ret == -1)            return (-1);    }    return (lksize - 1);}/** * xmlTextWriterHandleStateDependencies: * @writer:  the xmlTextWriterPtr * @p:  the xmlTextWriterStackEntry * * Write state dependent strings. * * Returns -1 on error or the number of characters written. */static intxmlTextWriterHandleStateDependencies(xmlTextWriterPtr writer,                                     xmlTextWriterStackEntry * p){    int count;    int sum;    char extra[3];    if (writer == NULL)        return -1;    if (p == NULL)        return 0;    sum = 0;    extra[0] = extra[1] = extra[2] = '\0';    if (p != 0) {        sum = 0;        switch (p->state) {            case XML_TEXTWRITER_NAME:                /* Output namespace declarations */                count = xmlTextWriterOutputNSDecl(writer);                if (count < 0)                    return -1;                sum += count;                extra[0] = '>';                p->state = XML_TEXTWRITER_TEXT;                break;            case XML_TEXTWRITER_PI:                extra[0] = ' ';                p->state = XML_TEXTWRITER_PI_TEXT;                break;            case XML_TEXTWRITER_DTD:                extra[0] = ' ';                extra[1] = '[';                p->state = XML_TEXTWRITER_DTD_TEXT;                break;            case XML_TEXTWRITER_DTD_ELEM:                extra[0] = ' ';                p->state = XML_TEXTWRITER_DTD_ELEM_TEXT;                break;            case XML_TEXTWRITER_DTD_ATTL:                extra[0] = ' ';                p->state = XML_TEXTWRITER_DTD_ATTL_TEXT;                break;            case XML_TEXTWRITER_DTD_ENTY:            case XML_TEXTWRITER_DTD_PENT:                extra[0] = ' ';                extra[1] = writer->qchar;                p->state = XML_TEXTWRITER_DTD_ENTY_TEXT;                break;            default:                break;        }    }    if (*extra != '\0') {        count = xmlOutputBufferWriteString(writer->out, extra);        if (count < 0)            return -1;        sum += count;    }    return sum;}#define bottom_xmlwriter#include "elfgcchack.h"#endif
 |