10161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/* 20161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * testrecurse.c: C program to run libxml2 regression tests checking entities 30161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * recursions 40161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 50161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * To compile on Unixes: 60161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * cc -o testrecurse `xml2-config --cflags` testrecurse.c `xml2-config --libs` -lpthread 70161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 80161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * See Copyright for the status of this software. 90161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 100161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * daniel@veillard.com 110161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard */ 120161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 130161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#include "libxml.h" 140161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#include <stdio.h> 150161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 160161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#if !defined(_WIN32) || defined(__CYGWIN__) 170161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#include <unistd.h> 180161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#endif 190161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#include <string.h> 200161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#include <sys/types.h> 210161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#include <sys/stat.h> 220161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#include <fcntl.h> 230161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 240161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#include <libxml/parser.h> 250161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#include <libxml/tree.h> 260161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#include <libxml/uri.h> 270161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#ifdef LIBXML_READER_ENABLED 280161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#include <libxml/xmlreader.h> 290161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#endif 300161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 310161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/* 320161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * O_BINARY is just for Windows compatibility - if it isn't defined 330161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * on this system, avoid any compilation error 340161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard */ 350161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#ifdef O_BINARY 360161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#define RD_FLAGS O_RDONLY | O_BINARY 370161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#else 380161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#define RD_FLAGS O_RDONLY 390161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#endif 400161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 410161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardtypedef int (*functest) (const char *filename, const char *result, 420161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const char *error, int options); 430161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 440161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardtypedef struct testDesc testDesc; 450161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardtypedef testDesc *testDescPtr; 460161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstruct testDesc { 470161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const char *desc; /* descripton of the test */ 480161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard functest func; /* function implementing the test */ 490161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const char *in; /* glob to path for input files */ 500161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const char *out; /* output directory */ 510161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const char *suffix;/* suffix for output files */ 520161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const char *err; /* suffix for error output files */ 530161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int options; /* parser options for the test */ 540161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard}; 550161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 560161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int checkTestFile(const char *filename); 570161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 580161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 590161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#if defined(_WIN32) && !defined(__CYGWIN__) 600161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 610161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#include <windows.h> 620161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#include <io.h> 630161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 640161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardtypedef struct 650161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard{ 660161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard size_t gl_pathc; /* Count of paths matched so far */ 670161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard char **gl_pathv; /* List of matched pathnames. */ 680161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard size_t gl_offs; /* Slots to reserve in 'gl_pathv'. */ 690161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} glob_t; 700161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 710161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#define GLOB_DOOFFS 0 720161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int glob(const char *pattern, int flags, 730161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int errfunc(const char *epath, int eerrno), 740161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard glob_t *pglob) { 750161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard glob_t *ret; 760161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard WIN32_FIND_DATA FindFileData; 770161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard HANDLE hFind; 780161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard unsigned int nb_paths = 0; 790161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard char directory[500]; 800161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int len; 810161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 820161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((pattern == NULL) || (pglob == NULL)) return(-1); 830161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 840161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard strncpy(directory, pattern, 499); 850161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard for (len = strlen(directory);len >= 0;len--) { 860161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (directory[len] == '/') { 870161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard len++; 880161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard directory[len] = 0; 890161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 900161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 910161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 920161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (len <= 0) 930161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard len = 0; 940161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 950161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 960161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret = pglob; 970161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard memset(ret, 0, sizeof(glob_t)); 980161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 990161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard hFind = FindFirstFileA(pattern, &FindFileData); 1000161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (hFind == INVALID_HANDLE_VALUE) 1010161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(0); 1020161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard nb_paths = 20; 1030161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret->gl_pathv = (char **) malloc(nb_paths * sizeof(char *)); 1040161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (ret->gl_pathv == NULL) { 1050161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard FindClose(hFind); 1060161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(-1); 1070161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 1080161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard strncpy(directory + len, FindFileData.cFileName, 499 - len); 1090161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret->gl_pathv[ret->gl_pathc] = strdup(directory); 1100161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (ret->gl_pathv[ret->gl_pathc] == NULL) 1110161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard goto done; 1120161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret->gl_pathc++; 1130161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard while(FindNextFileA(hFind, &FindFileData)) { 1140161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (FindFileData.cFileName[0] == '.') 1150161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard continue; 1160161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (ret->gl_pathc + 2 > nb_paths) { 1170161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard char **tmp = realloc(ret->gl_pathv, nb_paths * 2 * sizeof(char *)); 1180161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (tmp == NULL) 1190161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 1200161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret->gl_pathv = tmp; 1210161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard nb_paths *= 2; 1220161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 1230161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard strncpy(directory + len, FindFileData.cFileName, 499 - len); 1240161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret->gl_pathv[ret->gl_pathc] = strdup(directory); 1250161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (ret->gl_pathv[ret->gl_pathc] == NULL) 1260161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 1270161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret->gl_pathc++; 1280161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 1290161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret->gl_pathv[ret->gl_pathc] = NULL; 1300161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 1310161e638c697890020c410dbedec9bb516d0fe49Daniel Veillarddone: 1320161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard FindClose(hFind); 1330161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(0); 1340161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 1350161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 1360161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 1370161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 1380161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic void globfree(glob_t *pglob) { 1390161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard unsigned int i; 1400161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (pglob == NULL) 1410161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return; 1420161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 1430161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard for (i = 0;i < pglob->gl_pathc;i++) { 1440161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (pglob->gl_pathv[i] != NULL) 1450161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard free(pglob->gl_pathv[i]); 1460161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 1470161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 14822030ef8888579b9ae8d8a63367e31b201eef4b5Daniel Veillard 1490161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#else 1500161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#include <glob.h> 1510161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#endif 1520161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 1530161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/************************************************************************ 1540161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * * 1550161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Huge document generator * 1560161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * * 1570161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ************************************************************************/ 1580161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 1590161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#include <libxml/xmlIO.h> 1600161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 1610161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 1620161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic const char *start = "<!DOCTYPE foo [\ 1630161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard<!ENTITY f 'some internal data'> \ 1640161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard<!ENTITY e '&f;&f;'> \ 1650161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard<!ENTITY d '&e;&e;'> \ 1660161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard]> \ 1670161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard<foo>"; 1680161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 1690161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic const char *segment = " <bar>&e; &f; &d;</bar>\n"; 1700161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic const char *finish = "</foo>"; 1710161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 1720161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int curseg = 0; 1730161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic const char *current; 1740161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int rlen; 1750161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 1760161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/** 1770161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * hugeMatch: 1780161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * @URI: an URI to test 1790161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 1800161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Check for an huge: query 1810161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 1820161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Returns 1 if yes and 0 if another Input module should be used 1830161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard */ 1840161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int 1850161e638c697890020c410dbedec9bb516d0fe49Daniel VeillardhugeMatch(const char * URI) { 1860161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((URI != NULL) && (!strncmp(URI, "huge:", 4))) 1870161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(1); 1880161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(0); 1890161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 1900161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 1910161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/** 1920161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * hugeOpen: 1930161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * @URI: an URI to test 1940161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 1950161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Return a pointer to the huge: query handler, in this example simply 1960161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * the current pointer... 1970161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 1980161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Returns an Input context or NULL in case or error 1990161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard */ 2000161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic void * 2010161e638c697890020c410dbedec9bb516d0fe49Daniel VeillardhugeOpen(const char * URI) { 2020161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((URI == NULL) || (strncmp(URI, "huge:", 4))) 2030161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(NULL); 2040161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard rlen = strlen(start); 2050161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard current = start; 2060161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return((void *) current); 2070161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 2080161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 2090161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/** 2100161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * hugeClose: 2110161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * @context: the read context 2120161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 2130161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Close the huge: query handler 2140161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 2150161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Returns 0 or -1 in case of error 2160161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard */ 2170161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int 2180161e638c697890020c410dbedec9bb516d0fe49Daniel VeillardhugeClose(void * context) { 2190161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (context == NULL) return(-1); 2200161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(0); 2210161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 2220161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 2230161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#define MAX_NODES 1000000 2240161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 2250161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/** 2260161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * hugeRead: 2270161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * @context: the read context 2280161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * @buffer: where to store data 2290161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * @len: number of bytes to read 2300161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 2310161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Implement an huge: query read. 2320161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 2330161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Returns the number of bytes read or -1 in case of error 2340161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard */ 2350161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int 2360161e638c697890020c410dbedec9bb516d0fe49Daniel VeillardhugeRead(void *context, char *buffer, int len) 2370161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard{ 2380161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((context == NULL) || (buffer == NULL) || (len < 0)) 2390161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return (-1); 2400161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 2410161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (len >= rlen) { 2420161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (curseg >= MAX_NODES + 1) { 2430161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard rlen = 0; 2440161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(0); 2450161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 2460161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard len = rlen; 2470161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard rlen = 0; 2480161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard memcpy(buffer, current, len); 2490161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard curseg ++; 2500161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (curseg == MAX_NODES) { 2510161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard fprintf(stderr, "\n"); 2520161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard rlen = strlen(finish); 2530161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard current = finish; 2540161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } else { 2550161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (curseg % (MAX_NODES / 10) == 0) 2560161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard fprintf(stderr, "."); 2570161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard rlen = strlen(segment); 2580161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard current = segment; 2590161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 2600161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } else { 2610161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard memcpy(buffer, current, len); 2620161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard rlen -= len; 2630161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard current += len; 2640161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 2650161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return (len); 2660161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 2670161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 2680161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/************************************************************************ 2690161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * * 2700161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Libxml2 specific routines * 2710161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * * 2720161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ************************************************************************/ 2730161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 2740161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int nb_tests = 0; 2750161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int nb_errors = 0; 2760161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int nb_leaks = 0; 2770161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int extraMemoryFromResolver = 0; 2780161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 2790161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int 2800161e638c697890020c410dbedec9bb516d0fe49Daniel VeillardfatalError(void) { 2810161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard fprintf(stderr, "Exitting tests on fatal error\n"); 2820161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard exit(1); 2830161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 2840161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 2850161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/* 2860161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * We need to trap calls to the resolver to not account memory for the catalog 2870161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * which is shared to the current running test. We also don't want to have 2880161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * network downloads modifying tests. 2890161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard */ 2900161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic xmlParserInputPtr 2910161e638c697890020c410dbedec9bb516d0fe49Daniel VeillardtestExternalEntityLoader(const char *URL, const char *ID, 2920161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlParserCtxtPtr ctxt) { 2930161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlParserInputPtr ret; 2940161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 2950161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (checkTestFile(URL)) { 2960161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret = xmlNoNetExternalEntityLoader(URL, ID, ctxt); 2970161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } else { 2980161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int memused = xmlMemUsed(); 2990161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret = xmlNoNetExternalEntityLoader(URL, ID, ctxt); 3000161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard extraMemoryFromResolver += xmlMemUsed() - memused; 3010161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 3020161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 3030161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(ret); 3040161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 3050161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 3060161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/* 3070161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Trapping the error messages at the generic level to grab the equivalent of 3080161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * stderr messages on CLI tools. 3090161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard */ 3100161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic char testErrors[32769]; 3110161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int testErrorsSize = 0; 3120161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 3130161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic void XMLCDECL 3140161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardchannel(void *ctx ATTRIBUTE_UNUSED, const char *msg, ...) { 3150161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard va_list args; 3160161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int res; 3170161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 3180161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (testErrorsSize >= 32768) 3190161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return; 3200161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard va_start(args, msg); 3210161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard res = vsnprintf(&testErrors[testErrorsSize], 3220161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 32768 - testErrorsSize, 3230161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard msg, args); 3240161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard va_end(args); 3250161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (testErrorsSize + res >= 32768) { 3260161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard /* buffer is full */ 3270161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard testErrorsSize = 32768; 3280161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard testErrors[testErrorsSize] = 0; 3290161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } else { 3300161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard testErrorsSize += res; 3310161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 3320161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard testErrors[testErrorsSize] = 0; 3330161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 3340161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 3350161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/** 3360161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * xmlParserPrintFileContext: 3370161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * @input: an xmlParserInputPtr input 3380161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 3390161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Displays current context within the input content for error tracking 3400161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard */ 3410161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 3420161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic void 3430161e638c697890020c410dbedec9bb516d0fe49Daniel VeillardxmlParserPrintFileContextInternal(xmlParserInputPtr input , 3440161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlGenericErrorFunc chanl, void *data ) { 3450161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const xmlChar *cur, *base; 3460161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard unsigned int n, col; /* GCC warns if signed, because compared with sizeof() */ 3470161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlChar content[81]; /* space for 80 chars + line terminator */ 3480161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlChar *ctnt; 3490161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 3500161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (input == NULL) return; 3510161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard cur = input->cur; 3520161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard base = input->base; 3530161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard /* skip backwards over any end-of-lines */ 3540161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard while ((cur > base) && ((*(cur) == '\n') || (*(cur) == '\r'))) { 3550161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard cur--; 3560161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 3570161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard n = 0; 3580161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard /* search backwards for beginning-of-line (to max buff size) */ 3590161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard while ((n++ < (sizeof(content)-1)) && (cur > base) && 3600161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard (*(cur) != '\n') && (*(cur) != '\r')) 3610161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard cur--; 3620161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((*(cur) == '\n') || (*(cur) == '\r')) cur++; 3630161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard /* calculate the error position in terms of the current position */ 3640161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard col = input->cur - cur; 3650161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard /* search forward for end-of-line (to max buff size) */ 3660161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard n = 0; 3670161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ctnt = content; 3680161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard /* copy selected text to our buffer */ 3690161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard while ((*cur != 0) && (*(cur) != '\n') && 3700161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard (*(cur) != '\r') && (n < sizeof(content)-1)) { 3710161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard *ctnt++ = *cur++; 3720161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard n++; 3730161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 3740161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard *ctnt = 0; 3750161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard /* print out the selected text */ 3760161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard chanl(data ,"%s\n", content); 3770161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard /* create blank line with problem pointer */ 3780161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard n = 0; 3790161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ctnt = content; 3800161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard /* (leave buffer space for pointer + line terminator) */ 3810161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard while ((n<col) && (n++ < sizeof(content)-2) && (*ctnt != 0)) { 3820161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (*(ctnt) != '\t') 3830161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard *(ctnt) = ' '; 3840161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ctnt++; 3850161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 3860161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard *ctnt++ = '^'; 3870161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard *ctnt = 0; 3880161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard chanl(data ,"%s\n", content); 3890161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 3900161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 3910161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic void 3920161e638c697890020c410dbedec9bb516d0fe49Daniel VeillardtestStructuredErrorHandler(void *ctx ATTRIBUTE_UNUSED, xmlErrorPtr err) { 3930161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard char *file = NULL; 3940161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int line = 0; 3950161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int code = -1; 3960161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int domain; 3970161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard void *data = NULL; 3980161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const char *str; 3990161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const xmlChar *name = NULL; 4000161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlNodePtr node; 4010161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlErrorLevel level; 4020161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlParserInputPtr input = NULL; 4030161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlParserInputPtr cur = NULL; 4040161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlParserCtxtPtr ctxt = NULL; 4050161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 4060161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (err == NULL) 4070161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return; 4080161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 4090161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard file = err->file; 4100161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard line = err->line; 4110161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard code = err->code; 4120161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard domain = err->domain; 4130161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard level = err->level; 4140161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard node = err->node; 4150161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((domain == XML_FROM_PARSER) || (domain == XML_FROM_HTML) || 4160161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard (domain == XML_FROM_DTD) || (domain == XML_FROM_NAMESPACE) || 4170161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard (domain == XML_FROM_IO) || (domain == XML_FROM_VALID)) { 4180161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ctxt = err->ctxt; 4190161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 4200161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard str = err->message; 4210161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 4220161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (code == XML_ERR_OK) 4230161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return; 4240161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 4250161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((node != NULL) && (node->type == XML_ELEMENT_NODE)) 4260161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard name = node->name; 4270161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 4280161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard /* 4290161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Maintain the compatibility with the legacy error handling 4300161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard */ 4310161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (ctxt != NULL) { 4320161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard input = ctxt->input; 4330161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((input != NULL) && (input->filename == NULL) && 4340161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard (ctxt->inputNr > 1)) { 4350161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard cur = input; 4360161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard input = ctxt->inputTab[ctxt->inputNr - 2]; 4370161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 4380161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (input != NULL) { 4390161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (input->filename) 4400161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "%s:%d: ", input->filename, input->line); 4410161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard else if ((line != 0) && (domain == XML_FROM_PARSER)) 4420161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "Entity: line %d: ", input->line); 4430161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 4440161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } else { 4450161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (file != NULL) 4460161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "%s:%d: ", file, line); 4470161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard else if ((line != 0) && (domain == XML_FROM_PARSER)) 4480161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "Entity: line %d: ", line); 4490161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 4500161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (name != NULL) { 4510161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "element %s: ", name); 4520161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 4530161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (code == XML_ERR_OK) 4540161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return; 4550161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard switch (domain) { 4560161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_PARSER: 4570161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "parser "); 4580161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 4590161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_NAMESPACE: 4600161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "namespace "); 4610161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 4620161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_DTD: 4630161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_VALID: 4640161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "validity "); 4650161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 4660161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_HTML: 4670161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "HTML parser "); 4680161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 4690161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_MEMORY: 4700161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "memory "); 4710161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 4720161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_OUTPUT: 4730161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "output "); 4740161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 4750161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_IO: 4760161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "I/O "); 4770161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 4780161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_XINCLUDE: 4790161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "XInclude "); 4800161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 4810161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_XPATH: 4820161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "XPath "); 4830161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 4840161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_XPOINTER: 4850161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "parser "); 4860161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 4870161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_REGEXP: 4880161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "regexp "); 4890161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 4900161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_MODULE: 4910161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "module "); 4920161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 4930161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_SCHEMASV: 4940161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "Schemas validity "); 4950161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 4960161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_SCHEMASP: 4970161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "Schemas parser "); 4980161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 4990161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_RELAXNGP: 5000161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "Relax-NG parser "); 5010161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 5020161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_RELAXNGV: 5030161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "Relax-NG validity "); 5040161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 5050161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_CATALOG: 5060161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "Catalog "); 5070161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 5080161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_C14N: 5090161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "C14N "); 5100161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 5110161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_FROM_XSLT: 5120161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "XSLT "); 5130161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 5140161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard default: 5150161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 5160161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 5170161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (code == XML_ERR_OK) 5180161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return; 5190161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard switch (level) { 5200161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_ERR_NONE: 5210161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, ": "); 5220161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 5230161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_ERR_WARNING: 5240161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "warning : "); 5250161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 5260161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_ERR_ERROR: 5270161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "error : "); 5280161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 5290161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard case XML_ERR_FATAL: 5300161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "error : "); 5310161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard break; 5320161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 5330161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (code == XML_ERR_OK) 5340161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return; 5350161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (str != NULL) { 5360161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int len; 5370161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard len = xmlStrlen((const xmlChar *)str); 5380161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((len > 0) && (str[len - 1] != '\n')) 5390161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "%s\n", str); 5400161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard else 5410161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "%s", str); 5420161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } else { 5430161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "%s\n", "out of memory error"); 5440161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 5450161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (code == XML_ERR_OK) 5460161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return; 5470161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 5480161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (ctxt != NULL) { 5490161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlParserPrintFileContextInternal(input, channel, data); 5500161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (cur != NULL) { 5510161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (cur->filename) 5520161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "%s:%d: \n", cur->filename, cur->line); 5530161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard else if ((line != 0) && (domain == XML_FROM_PARSER)) 5540161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "Entity: line %d: \n", cur->line); 5550161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlParserPrintFileContextInternal(cur, channel, data); 5560161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 5570161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 5580161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((domain == XML_FROM_XPATH) && (err->str1 != NULL) && 5590161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard (err->int1 < 100) && 5600161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard (err->int1 < xmlStrlen((const xmlChar *)err->str1))) { 5610161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlChar buf[150]; 5620161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int i; 5630161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 5640161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "%s\n", err->str1); 5650161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard for (i=0;i < err->int1;i++) 5660161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard buf[i] = ' '; 5670161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard buf[i++] = '^'; 5680161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard buf[i] = 0; 5690161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard channel(data, "%s\n", buf); 5700161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 5710161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 5720161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 5730161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic void 5740161e638c697890020c410dbedec9bb516d0fe49Daniel VeillardinitializeLibxml2(void) { 5750161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlGetWarningsDefaultValue = 0; 5760161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlPedanticParserDefault(0); 5770161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 5780161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlMemSetup(xmlMemFree, xmlMemMalloc, xmlMemRealloc, xmlMemoryStrdup); 5790161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlInitParser(); 5800161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlSetExternalEntityLoader(testExternalEntityLoader); 5810161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlSetStructuredErrorFunc(NULL, testStructuredErrorHandler); 5820161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard /* 5830161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * register the new I/O handlers 5840161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard */ 5850161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (xmlRegisterInputCallbacks(hugeMatch, hugeOpen, 5860161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard hugeRead, hugeClose) < 0) { 5870161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard fprintf(stderr, "failed to register Huge handler\n"); 5880161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard exit(1); 5890161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 5900161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 5910161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 5920161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/************************************************************************ 5930161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * * 5940161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * File name and path utilities * 5950161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * * 5960161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ************************************************************************/ 5970161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 5980161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic const char *baseFilename(const char *filename) { 5990161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const char *cur; 6000161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (filename == NULL) 6010161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(NULL); 6020161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard cur = &filename[strlen(filename)]; 6030161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard while ((cur > filename) && (*cur != '/')) 6040161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard cur--; 6050161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (*cur == '/') 6060161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(cur + 1); 6070161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(cur); 6080161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 6090161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 6100161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic char *resultFilename(const char *filename, const char *out, 6110161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const char *suffix) { 6120161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const char *base; 6130161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard char res[500]; 6140161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard char suffixbuff[500]; 6150161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 6160161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/************* 6170161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((filename[0] == 't') && (filename[1] == 'e') && 6180161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard (filename[2] == 's') && (filename[3] == 't') && 6190161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard (filename[4] == '/')) 6200161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard filename = &filename[5]; 6210161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard *************/ 6220161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 6230161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard base = baseFilename(filename); 6240161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (suffix == NULL) 6250161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard suffix = ".tmp"; 6260161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (out == NULL) 6270161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard out = ""; 6280161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 6290161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard strncpy(suffixbuff,suffix,499); 6300161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#ifdef VMS 6310161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if(strstr(base,".") && suffixbuff[0]=='.') 6320161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard suffixbuff[0]='_'; 6330161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#endif 6340161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 6350161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard snprintf(res, 499, "%s%s%s", out, base, suffixbuff); 6360161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard res[499] = 0; 6370161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(strdup(res)); 6380161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 6390161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 6400161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int checkTestFile(const char *filename) { 6410161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard struct stat buf; 6420161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 6430161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (stat(filename, &buf) == -1) 6440161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(0); 6450161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 6460161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#if defined(_WIN32) && !defined(__CYGWIN__) 6470161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (!(buf.st_mode & _S_IFREG)) 6480161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(0); 6490161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#else 6500161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (!S_ISREG(buf.st_mode)) 6510161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(0); 6520161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#endif 6530161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 6540161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(1); 6550161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 6560161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 6570161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 6580161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 6590161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/************************************************************************ 6600161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * * 6610161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Test to detect or not recursive entities * 6620161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * * 6630161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ************************************************************************/ 6640161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/** 6650161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * recursiveDetectTest: 6660161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * @filename: the file to parse 6670161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * @result: the file with expected result 6680161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * @err: the file with error messages: unused 6690161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 6700161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Parse a file loading DTD and replacing entities check it fails for 6710161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * lol cases 6720161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 6730161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Returns 0 in case of success, an error code otherwise 6740161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard */ 6750161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int 6760161e638c697890020c410dbedec9bb516d0fe49Daniel VeillardrecursiveDetectTest(const char *filename, 6770161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const char *result ATTRIBUTE_UNUSED, 6780161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const char *err ATTRIBUTE_UNUSED, 6790161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int options ATTRIBUTE_UNUSED) { 6800161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlDocPtr doc; 6810161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlParserCtxtPtr ctxt; 6820161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int res = 0; 6830161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 6840161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard nb_tests++; 6850161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 6860161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ctxt = xmlNewParserCtxt(); 6870161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard /* 6880161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * base of the test, parse with the old API 6890161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard */ 6900161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard doc = xmlCtxtReadFile(ctxt, filename, NULL, 6910161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard XML_PARSE_NOENT | XML_PARSE_DTDLOAD); 6920161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((doc != NULL) || (ctxt->lastError.code != XML_ERR_ENTITY_LOOP)) { 6930161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard fprintf(stderr, "Failed to detect recursion in %s\n", filename); 6940161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlFreeParserCtxt(ctxt); 6950161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlFreeDoc(doc); 6960161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(1); 6970161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 6980161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlFreeParserCtxt(ctxt); 6990161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 7000161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(res); 7010161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 7020161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 7030161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/** 7040161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * notRecursiveDetectTest: 7050161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * @filename: the file to parse 7060161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * @result: the file with expected result 7070161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * @err: the file with error messages: unused 7080161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 7090161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Parse a file loading DTD and replacing entities check it works for 7100161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * good cases 7110161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 7120161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Returns 0 in case of success, an error code otherwise 7130161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard */ 7140161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int 7150161e638c697890020c410dbedec9bb516d0fe49Daniel VeillardnotRecursiveDetectTest(const char *filename, 7160161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const char *result ATTRIBUTE_UNUSED, 7170161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const char *err ATTRIBUTE_UNUSED, 7180161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int options ATTRIBUTE_UNUSED) { 7190161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlDocPtr doc; 7200161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlParserCtxtPtr ctxt; 7210161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int res = 0; 7220161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 7230161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard nb_tests++; 7240161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 7250161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ctxt = xmlNewParserCtxt(); 7260161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard /* 7270161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * base of the test, parse with the old API 7280161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard */ 7290161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard doc = xmlCtxtReadFile(ctxt, filename, NULL, 7300161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard XML_PARSE_NOENT | XML_PARSE_DTDLOAD); 7310161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (doc == NULL) { 7320161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard fprintf(stderr, "Failed to parse correct file %s\n", filename); 7330161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlFreeParserCtxt(ctxt); 7340161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(1); 7350161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 7360161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlFreeDoc(doc); 7370161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlFreeParserCtxt(ctxt); 7380161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 7390161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(res); 7400161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 7410161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 7420161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#ifdef LIBXML_READER_ENABLED 7430161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/** 7440161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * notRecursiveHugeTest: 7450161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * @filename: the file to parse 7460161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * @result: the file with expected result 7470161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * @err: the file with error messages: unused 7480161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 7490161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Parse a memory generated file 7500161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * good cases 7510161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * 7520161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Returns 0 in case of success, an error code otherwise 7530161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard */ 7540161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int 7550161e638c697890020c410dbedec9bb516d0fe49Daniel VeillardnotRecursiveHugeTest(const char *filename ATTRIBUTE_UNUSED, 7560161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const char *result ATTRIBUTE_UNUSED, 7570161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard const char *err ATTRIBUTE_UNUSED, 7580161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int options ATTRIBUTE_UNUSED) { 7590161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlTextReaderPtr reader; 7600161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int res = 0; 7610161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int ret; 7620161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 7630161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard nb_tests++; 7640161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 7650161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard reader = xmlReaderForFile("huge:test" , NULL, 7660161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard XML_PARSE_NOENT | XML_PARSE_DTDLOAD); 7670161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (reader == NULL) { 7680161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard fprintf(stderr, "Failed to open huge:test\n"); 7690161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(1); 7700161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 7710161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret = xmlTextReaderRead(reader); 7720161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard while (ret == 1) { 7730161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret = xmlTextReaderRead(reader); 7740161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 7750161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (ret != 0) { 7760161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard fprintf(stderr, "Failed to parser huge:test with entities\n"); 7770161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard res = 1; 7780161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 7790161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlFreeTextReader(reader); 7800161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 7810161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(res); 7820161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 7830161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#endif 7840161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 7850161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/************************************************************************ 7860161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * * 7870161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * Tests Descriptions * 7880161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * * 7890161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ************************************************************************/ 7900161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 7910161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic 7920161e638c697890020c410dbedec9bb516d0fe49Daniel VeillardtestDesc testDescriptions[] = { 7930161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard { "Parsing recursive test cases" , 7940161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard recursiveDetectTest, "./test/recurse/lol*.xml", NULL, NULL, NULL, 7950161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 0 }, 7960161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard { "Parsing non-recursive test cases" , 7970161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard notRecursiveDetectTest, "./test/recurse/good*.xml", NULL, NULL, NULL, 7980161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 0 }, 7990161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#ifdef LIBXML_READER_ENABLED 8000161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard { "Parsing non-recursive huge case" , 8010161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard notRecursiveHugeTest, NULL, NULL, NULL, NULL, 8020161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 0 }, 8030161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard#endif 8040161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard {NULL, NULL, NULL, NULL, NULL, NULL, 0} 8050161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard}; 8060161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 8070161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard/************************************************************************ 8080161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * * 8090161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * The main code driving the tests * 8100161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard * * 8110161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ************************************************************************/ 8120161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 8130161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int 8140161e638c697890020c410dbedec9bb516d0fe49Daniel VeillardlaunchTests(testDescPtr tst) { 8150161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int res = 0, err = 0; 8160161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard size_t i; 8170161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard char *result; 8180161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard char *error; 8190161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int mem; 8200161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 8210161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (tst == NULL) return(-1); 8220161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (tst->in != NULL) { 8230161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard glob_t globbuf; 8240161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 8250161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard globbuf.gl_offs = 0; 8260161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard glob(tst->in, GLOB_DOOFFS, NULL, &globbuf); 8270161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard for (i = 0;i < globbuf.gl_pathc;i++) { 8280161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (!checkTestFile(globbuf.gl_pathv[i])) 8290161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard continue; 8300161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (tst->suffix != NULL) { 8310161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard result = resultFilename(globbuf.gl_pathv[i], tst->out, 8320161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard tst->suffix); 8330161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (result == NULL) { 8340161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard fprintf(stderr, "Out of memory !\n"); 8350161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard fatalError(); 8360161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 8370161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } else { 8380161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard result = NULL; 8390161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 8400161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (tst->err != NULL) { 8410161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard error = resultFilename(globbuf.gl_pathv[i], tst->out, 8420161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard tst->err); 8430161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (error == NULL) { 8440161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard fprintf(stderr, "Out of memory !\n"); 8450161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard fatalError(); 8460161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 8470161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } else { 8480161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard error = NULL; 8490161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 8500161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((result) &&(!checkTestFile(result))) { 8510161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard fprintf(stderr, "Missing result file %s\n", result); 8520161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } else if ((error) &&(!checkTestFile(error))) { 8530161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard fprintf(stderr, "Missing error file %s\n", error); 8540161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } else { 8550161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard mem = xmlMemUsed(); 8560161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard extraMemoryFromResolver = 0; 8570161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard testErrorsSize = 0; 8580161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard testErrors[0] = 0; 8590161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard res = tst->func(globbuf.gl_pathv[i], result, error, 8600161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard tst->options | XML_PARSE_COMPACT); 8610161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlResetLastError(); 8620161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (res != 0) { 8630161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard fprintf(stderr, "File %s generated an error\n", 8640161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard globbuf.gl_pathv[i]); 8650161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard nb_errors++; 8660161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard err++; 8670161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 8680161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard else if (xmlMemUsed() != mem) { 8690161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((xmlMemUsed() != mem) && 8700161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard (extraMemoryFromResolver == 0)) { 8710161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard fprintf(stderr, "File %s leaked %d bytes\n", 8720161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard globbuf.gl_pathv[i], xmlMemUsed() - mem); 8730161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard nb_leaks++; 8740161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard err++; 8750161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 8760161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 8770161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard testErrorsSize = 0; 8780161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 8790161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (result) 8800161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard free(result); 8810161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (error) 8820161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard free(error); 8830161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 8840161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard globfree(&globbuf); 8850161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } else { 8860161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard testErrorsSize = 0; 8870161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard testErrors[0] = 0; 8880161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard extraMemoryFromResolver = 0; 8890161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard res = tst->func(NULL, NULL, NULL, tst->options); 8900161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (res != 0) { 8910161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard nb_errors++; 8920161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard err++; 8930161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 8940161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 8950161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(err); 8960161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 8970161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 8980161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int verbose = 0; 8990161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int tests_quiet = 0; 9000161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 9010161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardstatic int 9020161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardruntest(int i) { 9030161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int ret = 0, res; 9040161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int old_errors, old_tests, old_leaks; 9050161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 9060161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard old_errors = nb_errors; 9070161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard old_tests = nb_tests; 9080161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard old_leaks = nb_leaks; 9090161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((tests_quiet == 0) && (testDescriptions[i].desc != NULL)) 9100161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard printf("## %s\n", testDescriptions[i].desc); 9110161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard res = launchTests(&testDescriptions[i]); 9120161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (res != 0) 9130161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret++; 9140161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (verbose) { 9150161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((nb_errors == old_errors) && (nb_leaks == old_leaks)) 9160161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard printf("Ran %d tests, no errors\n", nb_tests - old_tests); 9170161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard else 9180161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard printf("Ran %d tests, %d errors, %d leaks\n", 9190161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard nb_tests - old_tests, 9200161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard nb_errors - old_errors, 9210161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard nb_leaks - old_leaks); 9220161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 9230161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(ret); 9240161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 9250161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 9260161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardint 9270161e638c697890020c410dbedec9bb516d0fe49Daniel Veillardmain(int argc ATTRIBUTE_UNUSED, char **argv ATTRIBUTE_UNUSED) { 9280161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int i, a, ret = 0; 9290161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard int subset = 0; 9300161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 9310161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard initializeLibxml2(); 9320161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 9330161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard for (a = 1; a < argc;a++) { 9340161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (!strcmp(argv[a], "-v")) 9350161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard verbose = 1; 9360161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard else if (!strcmp(argv[a], "-quiet")) 9370161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard tests_quiet = 1; 9380161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard else { 9390161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard for (i = 0; testDescriptions[i].func != NULL; i++) { 9400161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (strstr(testDescriptions[i].desc, argv[a])) { 9410161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret += runtest(i); 9420161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard subset++; 9430161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 9440161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 9450161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 9460161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 9470161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if (subset == 0) { 9480161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard for (i = 0; testDescriptions[i].func != NULL; i++) { 9490161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret += runtest(i); 9500161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 9510161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 9520161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard if ((nb_errors == 0) && (nb_leaks == 0)) { 9530161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret = 0; 9540161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard printf("Total %d tests, no errors\n", 9550161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard nb_tests); 9560161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } else { 9570161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard ret = 1; 9580161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard printf("Total %d tests, %d errors, %d leaks\n", 9590161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard nb_tests, nb_errors, nb_leaks); 9600161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard } 9610161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlCleanupParser(); 9620161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard xmlMemoryDump(); 9630161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard 9640161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard return(ret); 9650161e638c697890020c410dbedec9bb516d0fe49Daniel Veillard} 966