Blame catalog.c

Packit Service a31ea6
/**
Packit Service a31ea6
 * catalog.c: set of generic Catalog related routines
Packit Service a31ea6
 *
Packit Service a31ea6
 * Reference:  SGML Open Technical Resolution TR9401:1997.
Packit Service a31ea6
 *             http://www.jclark.com/sp/catalog.htm
Packit Service a31ea6
 *
Packit Service a31ea6
 *             XML Catalogs Working Draft 06 August 2001
Packit Service a31ea6
 *             http://www.oasis-open.org/committees/entity/spec-2001-08-06.html
Packit Service a31ea6
 *
Packit Service a31ea6
 * See Copyright for the status of this software.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Daniel.Veillard@imag.fr
Packit Service a31ea6
 */
Packit Service a31ea6
Packit Service a31ea6
#define IN_LIBXML
Packit Service a31ea6
#include "libxml.h"
Packit Service a31ea6
Packit Service a31ea6
#ifdef LIBXML_CATALOG_ENABLED
Packit Service a31ea6
#ifdef HAVE_SYS_TYPES_H
Packit Service a31ea6
#include <sys/types.h>
Packit Service a31ea6
#endif
Packit Service a31ea6
#ifdef HAVE_SYS_STAT_H
Packit Service a31ea6
#include <sys/stat.h>
Packit Service a31ea6
#endif
Packit Service a31ea6
#ifdef HAVE_UNISTD_H
Packit Service a31ea6
#include <unistd.h>
Packit Service a31ea6
#endif
Packit Service a31ea6
#ifdef HAVE_FCNTL_H
Packit Service a31ea6
#include <fcntl.h>
Packit Service a31ea6
#endif
Packit Service a31ea6
#ifdef HAVE_STDLIB_H
Packit Service a31ea6
#include <stdlib.h>
Packit Service a31ea6
#endif
Packit Service a31ea6
#include <string.h>
Packit Service a31ea6
#include <libxml/xmlmemory.h>
Packit Service a31ea6
#include <libxml/hash.h>
Packit Service a31ea6
#include <libxml/uri.h>
Packit Service a31ea6
#include <libxml/parserInternals.h>
Packit Service a31ea6
#include <libxml/catalog.h>
Packit Service a31ea6
#include <libxml/xmlerror.h>
Packit Service a31ea6
#include <libxml/threads.h>
Packit Service a31ea6
#include <libxml/globals.h>
Packit Service a31ea6
Packit Service a31ea6
#include "buf.h"
Packit Service a31ea6
Packit Service a31ea6
#define MAX_DELEGATE	50
Packit Service a31ea6
#define MAX_CATAL_DEPTH	50
Packit Service a31ea6
Packit Service a31ea6
#ifdef _WIN32
Packit Service a31ea6
# define PATH_SEPARATOR ';'
Packit Service a31ea6
#else
Packit Service a31ea6
# define PATH_SEPARATOR ':'
Packit Service a31ea6
#endif
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * TODO:
Packit Service a31ea6
 *
Packit Service a31ea6
 * macro to flag unimplemented blocks
Packit Service a31ea6
 * XML_CATALOG_PREFER user env to select between system/public prefered
Packit Service a31ea6
 * option. C.f. Richard Tobin <richard@cogsci.ed.ac.uk>
Packit Service a31ea6
 *> Just FYI, I am using an environment variable XML_CATALOG_PREFER with
Packit Service a31ea6
 *> values "system" and "public".  I have made the default be "system" to
Packit Service a31ea6
 *> match yours.
Packit Service a31ea6
 */
Packit Service a31ea6
#define TODO								\
Packit Service a31ea6
    xmlGenericError(xmlGenericErrorContext,				\
Packit Service a31ea6
	    "Unimplemented block at %s:%d\n",				\
Packit Service a31ea6
            __FILE__, __LINE__);
Packit Service a31ea6
Packit Service a31ea6
#define XML_URN_PUBID "urn:publicid:"
Packit Service a31ea6
#define XML_CATAL_BREAK ((xmlChar *) -1)
Packit Service a31ea6
#ifndef XML_XML_DEFAULT_CATALOG
Packit Service a31ea6
#define XML_XML_DEFAULT_CATALOG "file:///etc/xml/catalog"
Packit Service a31ea6
#endif
Packit Service a31ea6
#ifndef XML_SGML_DEFAULT_CATALOG
Packit Service a31ea6
#define XML_SGML_DEFAULT_CATALOG "file:///etc/sgml/catalog"
Packit Service a31ea6
#endif
Packit Service a31ea6
Packit Service a31ea6
#if defined(_WIN32) && defined(_MSC_VER)
Packit Service a31ea6
#undef XML_XML_DEFAULT_CATALOG
Packit Service a31ea6
static char XML_XML_DEFAULT_CATALOG[256] = "file:///etc/xml/catalog";
Packit Service a31ea6
#if defined(_WIN32_WCE)
Packit Service a31ea6
/* Windows CE don't have a A variant */
Packit Service a31ea6
#define GetModuleHandleA GetModuleHandle
Packit Service a31ea6
#define GetModuleFileNameA GetModuleFileName
Packit Service a31ea6
#else
Packit Service a31ea6
#if !defined(_WINDOWS_)
Packit Service a31ea6
void* __stdcall GetModuleHandleA(const char*);
Packit Service a31ea6
unsigned long __stdcall GetModuleFileNameA(void*, char*, unsigned long);
Packit Service a31ea6
#endif
Packit Service a31ea6
#endif
Packit Service a31ea6
#endif
Packit Service a31ea6
Packit Service a31ea6
static xmlChar *xmlCatalogNormalizePublic(const xmlChar *pubID);
Packit Service a31ea6
static int xmlExpandCatalog(xmlCatalogPtr catal, const char *filename);
Packit Service a31ea6
Packit Service a31ea6
/************************************************************************
Packit Service a31ea6
 *									*
Packit Service a31ea6
 *			Types, all private				*
Packit Service a31ea6
 *									*
Packit Service a31ea6
 ************************************************************************/
Packit Service a31ea6
Packit Service a31ea6
typedef enum {
Packit Service a31ea6
    XML_CATA_REMOVED = -1,
Packit Service a31ea6
    XML_CATA_NONE = 0,
Packit Service a31ea6
    XML_CATA_CATALOG,
Packit Service a31ea6
    XML_CATA_BROKEN_CATALOG,
Packit Service a31ea6
    XML_CATA_NEXT_CATALOG,
Packit Service a31ea6
    XML_CATA_GROUP,
Packit Service a31ea6
    XML_CATA_PUBLIC,
Packit Service a31ea6
    XML_CATA_SYSTEM,
Packit Service a31ea6
    XML_CATA_REWRITE_SYSTEM,
Packit Service a31ea6
    XML_CATA_DELEGATE_PUBLIC,
Packit Service a31ea6
    XML_CATA_DELEGATE_SYSTEM,
Packit Service a31ea6
    XML_CATA_URI,
Packit Service a31ea6
    XML_CATA_REWRITE_URI,
Packit Service a31ea6
    XML_CATA_DELEGATE_URI,
Packit Service a31ea6
    SGML_CATA_SYSTEM,
Packit Service a31ea6
    SGML_CATA_PUBLIC,
Packit Service a31ea6
    SGML_CATA_ENTITY,
Packit Service a31ea6
    SGML_CATA_PENTITY,
Packit Service a31ea6
    SGML_CATA_DOCTYPE,
Packit Service a31ea6
    SGML_CATA_LINKTYPE,
Packit Service a31ea6
    SGML_CATA_NOTATION,
Packit Service a31ea6
    SGML_CATA_DELEGATE,
Packit Service a31ea6
    SGML_CATA_BASE,
Packit Service a31ea6
    SGML_CATA_CATALOG,
Packit Service a31ea6
    SGML_CATA_DOCUMENT,
Packit Service a31ea6
    SGML_CATA_SGMLDECL
Packit Service a31ea6
} xmlCatalogEntryType;
Packit Service a31ea6
Packit Service a31ea6
typedef struct _xmlCatalogEntry xmlCatalogEntry;
Packit Service a31ea6
typedef xmlCatalogEntry *xmlCatalogEntryPtr;
Packit Service a31ea6
struct _xmlCatalogEntry {
Packit Service a31ea6
    struct _xmlCatalogEntry *next;
Packit Service a31ea6
    struct _xmlCatalogEntry *parent;
Packit Service a31ea6
    struct _xmlCatalogEntry *children;
Packit Service a31ea6
    xmlCatalogEntryType type;
Packit Service a31ea6
    xmlChar *name;
Packit Service a31ea6
    xmlChar *value;
Packit Service a31ea6
    xmlChar *URL;  /* The expanded URL using the base */
Packit Service a31ea6
    xmlCatalogPrefer prefer;
Packit Service a31ea6
    int dealloc;
Packit Service a31ea6
    int depth;
Packit Service a31ea6
    struct _xmlCatalogEntry *group;
Packit Service a31ea6
};
Packit Service a31ea6
Packit Service a31ea6
typedef enum {
Packit Service a31ea6
    XML_XML_CATALOG_TYPE = 1,
Packit Service a31ea6
    XML_SGML_CATALOG_TYPE
Packit Service a31ea6
} xmlCatalogType;
Packit Service a31ea6
Packit Service a31ea6
#define XML_MAX_SGML_CATA_DEPTH 10
Packit Service a31ea6
struct _xmlCatalog {
Packit Service a31ea6
    xmlCatalogType type;	/* either XML or SGML */
Packit Service a31ea6
Packit Service a31ea6
    /*
Packit Service a31ea6
     * SGML Catalogs are stored as a simple hash table of catalog entries
Packit Service a31ea6
     * Catalog stack to check against overflows when building the
Packit Service a31ea6
     * SGML catalog
Packit Service a31ea6
     */
Packit Service a31ea6
    char *catalTab[XML_MAX_SGML_CATA_DEPTH];	/* stack of catals */
Packit Service a31ea6
    int          catalNr;	/* Number of current catal streams */
Packit Service a31ea6
    int          catalMax;	/* Max number of catal streams */
Packit Service a31ea6
    xmlHashTablePtr sgml;
Packit Service a31ea6
Packit Service a31ea6
    /*
Packit Service a31ea6
     * XML Catalogs are stored as a tree of Catalog entries
Packit Service a31ea6
     */
Packit Service a31ea6
    xmlCatalogPrefer prefer;
Packit Service a31ea6
    xmlCatalogEntryPtr xml;
Packit Service a31ea6
};
Packit Service a31ea6
Packit Service a31ea6
/************************************************************************
Packit Service a31ea6
 *									*
Packit Service a31ea6
 *			Global variables				*
Packit Service a31ea6
 *									*
Packit Service a31ea6
 ************************************************************************/
Packit Service a31ea6
Packit Service a31ea6
/*
Packit Service a31ea6
 * Those are preferences
Packit Service a31ea6
 */
Packit Service a31ea6
static int xmlDebugCatalogs = 0;   /* used for debugging */
Packit Service a31ea6
static xmlCatalogAllow xmlCatalogDefaultAllow = XML_CATA_ALLOW_ALL;
Packit Service a31ea6
static xmlCatalogPrefer xmlCatalogDefaultPrefer = XML_CATA_PREFER_PUBLIC;
Packit Service a31ea6
Packit Service a31ea6
/*
Packit Service a31ea6
 * Hash table containing all the trees of XML catalogs parsed by
Packit Service a31ea6
 * the application.
Packit Service a31ea6
 */
Packit Service a31ea6
static xmlHashTablePtr xmlCatalogXMLFiles = NULL;
Packit Service a31ea6
Packit Service a31ea6
/*
Packit Service a31ea6
 * The default catalog in use by the application
Packit Service a31ea6
 */
Packit Service a31ea6
static xmlCatalogPtr xmlDefaultCatalog = NULL;
Packit Service a31ea6
Packit Service a31ea6
/*
Packit Service a31ea6
 * A mutex for modifying the shared global catalog(s)
Packit Service a31ea6
 * xmlDefaultCatalog tree.
Packit Service a31ea6
 * It also protects xmlCatalogXMLFiles
Packit Service a31ea6
 * The core of this readers/writer scheme is in xmlFetchXMLCatalogFile()
Packit Service a31ea6
 */
Packit Service a31ea6
static xmlRMutexPtr xmlCatalogMutex = NULL;
Packit Service a31ea6
Packit Service a31ea6
/*
Packit Service a31ea6
 * Whether the catalog support was initialized.
Packit Service a31ea6
 */
Packit Service a31ea6
static int xmlCatalogInitialized = 0;
Packit Service a31ea6
Packit Service a31ea6
/************************************************************************
Packit Service a31ea6
 *									*
Packit Service a31ea6
 *			Catalog error handlers				*
Packit Service a31ea6
 *									*
Packit Service a31ea6
 ************************************************************************/
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogErrMemory:
Packit Service a31ea6
 * @extra:  extra informations
Packit Service a31ea6
 *
Packit Service a31ea6
 * Handle an out of memory condition
Packit Service a31ea6
 */
Packit Service a31ea6
static void
Packit Service a31ea6
xmlCatalogErrMemory(const char *extra)
Packit Service a31ea6
{
Packit Service a31ea6
    __xmlRaiseError(NULL, NULL, NULL, NULL, NULL, XML_FROM_CATALOG,
Packit Service a31ea6
                    XML_ERR_NO_MEMORY, XML_ERR_ERROR, NULL, 0,
Packit Service a31ea6
		    extra, NULL, NULL, 0, 0,
Packit Service a31ea6
		    "Memory allocation failed : %s\n", extra);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogErr:
Packit Service a31ea6
 * @catal: the Catalog entry
Packit Service a31ea6
 * @node: the context node
Packit Service a31ea6
 * @msg:  the error message
Packit Service a31ea6
 * @extra:  extra informations
Packit Service a31ea6
 *
Packit Service a31ea6
 * Handle a catalog error
Packit Service a31ea6
 */
Packit Service a31ea6
static void LIBXML_ATTR_FORMAT(4,0)
Packit Service a31ea6
xmlCatalogErr(xmlCatalogEntryPtr catal, xmlNodePtr node, int error,
Packit Service a31ea6
               const char *msg, const xmlChar *str1, const xmlChar *str2,
Packit Service a31ea6
	       const xmlChar *str3)
Packit Service a31ea6
{
Packit Service a31ea6
    __xmlRaiseError(NULL, NULL, NULL, catal, node, XML_FROM_CATALOG,
Packit Service a31ea6
                    error, XML_ERR_ERROR, NULL, 0,
Packit Service a31ea6
		    (const char *) str1, (const char *) str2,
Packit Service a31ea6
		    (const char *) str3, 0, 0,
Packit Service a31ea6
		    msg, str1, str2, str3);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
Packit Service a31ea6
/************************************************************************
Packit Service a31ea6
 *									*
Packit Service a31ea6
 *			Allocation and Freeing				*
Packit Service a31ea6
 *									*
Packit Service a31ea6
 ************************************************************************/
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlNewCatalogEntry:
Packit Service a31ea6
 * @type:  type of entry
Packit Service a31ea6
 * @name:  name of the entry
Packit Service a31ea6
 * @value:  value of the entry
Packit Service a31ea6
 * @prefer:  the PUBLIC vs. SYSTEM current preference value
Packit Service a31ea6
 * @group:  for members of a group, the group entry
Packit Service a31ea6
 *
Packit Service a31ea6
 * create a new Catalog entry, this type is shared both by XML and
Packit Service a31ea6
 * SGML catalogs, but the acceptable types values differs.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the xmlCatalogEntryPtr or NULL in case of error
Packit Service a31ea6
 */
Packit Service a31ea6
static xmlCatalogEntryPtr
Packit Service a31ea6
xmlNewCatalogEntry(xmlCatalogEntryType type, const xmlChar *name,
Packit Service a31ea6
	   const xmlChar *value, const xmlChar *URL, xmlCatalogPrefer prefer,
Packit Service a31ea6
	   xmlCatalogEntryPtr group) {
Packit Service a31ea6
    xmlCatalogEntryPtr ret;
Packit Service a31ea6
    xmlChar *normid = NULL;
Packit Service a31ea6
Packit Service a31ea6
    ret = (xmlCatalogEntryPtr) xmlMalloc(sizeof(xmlCatalogEntry));
Packit Service a31ea6
    if (ret == NULL) {
Packit Service a31ea6
        xmlCatalogErrMemory("allocating catalog entry");
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
    ret->next = NULL;
Packit Service a31ea6
    ret->parent = NULL;
Packit Service a31ea6
    ret->children = NULL;
Packit Service a31ea6
    ret->type = type;
Packit Service a31ea6
    if (type == XML_CATA_PUBLIC || type == XML_CATA_DELEGATE_PUBLIC) {
Packit Service a31ea6
        normid = xmlCatalogNormalizePublic(name);
Packit Service a31ea6
        if (normid != NULL)
Packit Service a31ea6
            name = (*normid != 0 ? normid : NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
    if (name != NULL)
Packit Service a31ea6
	ret->name = xmlStrdup(name);
Packit Service a31ea6
    else
Packit Service a31ea6
	ret->name = NULL;
Packit Service a31ea6
    if (normid != NULL)
Packit Service a31ea6
        xmlFree(normid);
Packit Service a31ea6
    if (value != NULL)
Packit Service a31ea6
	ret->value = xmlStrdup(value);
Packit Service a31ea6
    else
Packit Service a31ea6
	ret->value = NULL;
Packit Service a31ea6
    if (URL == NULL)
Packit Service a31ea6
	URL = value;
Packit Service a31ea6
    if (URL != NULL)
Packit Service a31ea6
	ret->URL = xmlStrdup(URL);
Packit Service a31ea6
    else
Packit Service a31ea6
	ret->URL = NULL;
Packit Service a31ea6
    ret->prefer = prefer;
Packit Service a31ea6
    ret->dealloc = 0;
Packit Service a31ea6
    ret->depth = 0;
Packit Service a31ea6
    ret->group = group;
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
static void
Packit Service a31ea6
xmlFreeCatalogEntryList(xmlCatalogEntryPtr ret);
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlFreeCatalogEntry:
Packit Service a31ea6
 * @ret:  a Catalog entry
Packit Service a31ea6
 *
Packit Service a31ea6
 * Free the memory allocated to a Catalog entry
Packit Service a31ea6
 */
Packit Service a31ea6
static void
Packit Service a31ea6
xmlFreeCatalogEntry(xmlCatalogEntryPtr ret) {
Packit Service a31ea6
    if (ret == NULL)
Packit Service a31ea6
	return;
Packit Service a31ea6
    /*
Packit Service a31ea6
     * Entries stored in the file hash must be deallocated
Packit Service a31ea6
     * only by the file hash cleaner !
Packit Service a31ea6
     */
Packit Service a31ea6
    if (ret->dealloc == 1)
Packit Service a31ea6
	return;
Packit Service a31ea6
Packit Service a31ea6
    if (xmlDebugCatalogs) {
Packit Service a31ea6
	if (ret->name != NULL)
Packit Service a31ea6
	    xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		    "Free catalog entry %s\n", ret->name);
Packit Service a31ea6
	else if (ret->value != NULL)
Packit Service a31ea6
	    xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		    "Free catalog entry %s\n", ret->value);
Packit Service a31ea6
	else
Packit Service a31ea6
	    xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		    "Free catalog entry\n");
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    if (ret->name != NULL)
Packit Service a31ea6
	xmlFree(ret->name);
Packit Service a31ea6
    if (ret->value != NULL)
Packit Service a31ea6
	xmlFree(ret->value);
Packit Service a31ea6
    if (ret->URL != NULL)
Packit Service a31ea6
	xmlFree(ret->URL);
Packit Service a31ea6
    xmlFree(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlFreeCatalogEntryList:
Packit Service a31ea6
 * @ret:  a Catalog entry list
Packit Service a31ea6
 *
Packit Service a31ea6
 * Free the memory allocated to a full chained list of Catalog entries
Packit Service a31ea6
 */
Packit Service a31ea6
static void
Packit Service a31ea6
xmlFreeCatalogEntryList(xmlCatalogEntryPtr ret) {
Packit Service a31ea6
    xmlCatalogEntryPtr next;
Packit Service a31ea6
Packit Service a31ea6
    while (ret != NULL) {
Packit Service a31ea6
	next = ret->next;
Packit Service a31ea6
	xmlFreeCatalogEntry(ret);
Packit Service a31ea6
	ret = next;
Packit Service a31ea6
    }
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlFreeCatalogHashEntryList:
Packit Service a31ea6
 * @ret:  a Catalog entry list
Packit Service a31ea6
 *
Packit Service a31ea6
 * Free the memory allocated to list of Catalog entries from the
Packit Service a31ea6
 * catalog file hash.
Packit Service a31ea6
 */
Packit Service a31ea6
static void
Packit Service a31ea6
xmlFreeCatalogHashEntryList(xmlCatalogEntryPtr catal) {
Packit Service a31ea6
    xmlCatalogEntryPtr children, next;
Packit Service a31ea6
Packit Service a31ea6
    if (catal == NULL)
Packit Service a31ea6
	return;
Packit Service a31ea6
Packit Service a31ea6
    children = catal->children;
Packit Service a31ea6
    while (children != NULL) {
Packit Service a31ea6
	next = children->next;
Packit Service a31ea6
	children->dealloc = 0;
Packit Service a31ea6
	children->children = NULL;
Packit Service a31ea6
	xmlFreeCatalogEntry(children);
Packit Service a31ea6
	children = next;
Packit Service a31ea6
    }
Packit Service a31ea6
    catal->dealloc = 0;
Packit Service a31ea6
    xmlFreeCatalogEntry(catal);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCreateNewCatalog:
Packit Service a31ea6
 * @type:  type of catalog
Packit Service a31ea6
 * @prefer:  the PUBLIC vs. SYSTEM current preference value
Packit Service a31ea6
 *
Packit Service a31ea6
 * create a new Catalog, this type is shared both by XML and
Packit Service a31ea6
 * SGML catalogs, but the acceptable types values differs.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the xmlCatalogPtr or NULL in case of error
Packit Service a31ea6
 */
Packit Service a31ea6
static xmlCatalogPtr
Packit Service a31ea6
xmlCreateNewCatalog(xmlCatalogType type, xmlCatalogPrefer prefer) {
Packit Service a31ea6
    xmlCatalogPtr ret;
Packit Service a31ea6
Packit Service a31ea6
    ret = (xmlCatalogPtr) xmlMalloc(sizeof(xmlCatalog));
Packit Service a31ea6
    if (ret == NULL) {
Packit Service a31ea6
        xmlCatalogErrMemory("allocating catalog");
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
    memset(ret, 0, sizeof(xmlCatalog));
Packit Service a31ea6
    ret->type = type;
Packit Service a31ea6
    ret->catalNr = 0;
Packit Service a31ea6
    ret->catalMax = XML_MAX_SGML_CATA_DEPTH;
Packit Service a31ea6
    ret->prefer = prefer;
Packit Service a31ea6
    if (ret->type == XML_SGML_CATALOG_TYPE)
Packit Service a31ea6
	ret->sgml = xmlHashCreate(10);
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlFreeCatalog:
Packit Service a31ea6
 * @catal:  a Catalog
Packit Service a31ea6
 *
Packit Service a31ea6
 * Free the memory allocated to a Catalog
Packit Service a31ea6
 */
Packit Service a31ea6
void
Packit Service a31ea6
xmlFreeCatalog(xmlCatalogPtr catal) {
Packit Service a31ea6
    if (catal == NULL)
Packit Service a31ea6
	return;
Packit Service a31ea6
    if (catal->xml != NULL)
Packit Service a31ea6
	xmlFreeCatalogEntryList(catal->xml);
Packit Service a31ea6
    if (catal->sgml != NULL)
Packit Service a31ea6
	xmlHashFree(catal->sgml,
Packit Service a31ea6
		(xmlHashDeallocator) xmlFreeCatalogEntry);
Packit Service a31ea6
    xmlFree(catal);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/************************************************************************
Packit Service a31ea6
 *									*
Packit Service a31ea6
 *			Serializing Catalogs				*
Packit Service a31ea6
 *									*
Packit Service a31ea6
 ************************************************************************/
Packit Service a31ea6
Packit Service a31ea6
#ifdef LIBXML_OUTPUT_ENABLED
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogDumpEntry:
Packit Service a31ea6
 * @entry:  the catalog entry
Packit Service a31ea6
 * @out:  the file.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Serialize an SGML Catalog entry
Packit Service a31ea6
 */
Packit Service a31ea6
static void
Packit Service a31ea6
xmlCatalogDumpEntry(xmlCatalogEntryPtr entry, FILE *out) {
Packit Service a31ea6
    if ((entry == NULL) || (out == NULL))
Packit Service a31ea6
	return;
Packit Service a31ea6
    switch (entry->type) {
Packit Service a31ea6
	case SGML_CATA_ENTITY:
Packit Service a31ea6
	    fprintf(out, "ENTITY "); break;
Packit Service a31ea6
	case SGML_CATA_PENTITY:
Packit Service a31ea6
	    fprintf(out, "ENTITY %%"); break;
Packit Service a31ea6
	case SGML_CATA_DOCTYPE:
Packit Service a31ea6
	    fprintf(out, "DOCTYPE "); break;
Packit Service a31ea6
	case SGML_CATA_LINKTYPE:
Packit Service a31ea6
	    fprintf(out, "LINKTYPE "); break;
Packit Service a31ea6
	case SGML_CATA_NOTATION:
Packit Service a31ea6
	    fprintf(out, "NOTATION "); break;
Packit Service a31ea6
	case SGML_CATA_PUBLIC:
Packit Service a31ea6
	    fprintf(out, "PUBLIC "); break;
Packit Service a31ea6
	case SGML_CATA_SYSTEM:
Packit Service a31ea6
	    fprintf(out, "SYSTEM "); break;
Packit Service a31ea6
	case SGML_CATA_DELEGATE:
Packit Service a31ea6
	    fprintf(out, "DELEGATE "); break;
Packit Service a31ea6
	case SGML_CATA_BASE:
Packit Service a31ea6
	    fprintf(out, "BASE "); break;
Packit Service a31ea6
	case SGML_CATA_CATALOG:
Packit Service a31ea6
	    fprintf(out, "CATALOG "); break;
Packit Service a31ea6
	case SGML_CATA_DOCUMENT:
Packit Service a31ea6
	    fprintf(out, "DOCUMENT "); break;
Packit Service a31ea6
	case SGML_CATA_SGMLDECL:
Packit Service a31ea6
	    fprintf(out, "SGMLDECL "); break;
Packit Service a31ea6
	default:
Packit Service a31ea6
	    return;
Packit Service a31ea6
    }
Packit Service a31ea6
    switch (entry->type) {
Packit Service a31ea6
	case SGML_CATA_ENTITY:
Packit Service a31ea6
	case SGML_CATA_PENTITY:
Packit Service a31ea6
	case SGML_CATA_DOCTYPE:
Packit Service a31ea6
	case SGML_CATA_LINKTYPE:
Packit Service a31ea6
	case SGML_CATA_NOTATION:
Packit Service a31ea6
	    fprintf(out, "%s", (const char *) entry->name); break;
Packit Service a31ea6
	case SGML_CATA_PUBLIC:
Packit Service a31ea6
	case SGML_CATA_SYSTEM:
Packit Service a31ea6
	case SGML_CATA_SGMLDECL:
Packit Service a31ea6
	case SGML_CATA_DOCUMENT:
Packit Service a31ea6
	case SGML_CATA_CATALOG:
Packit Service a31ea6
	case SGML_CATA_BASE:
Packit Service a31ea6
	case SGML_CATA_DELEGATE:
Packit Service a31ea6
	    fprintf(out, "\"%s\"", entry->name); break;
Packit Service a31ea6
	default:
Packit Service a31ea6
	    break;
Packit Service a31ea6
    }
Packit Service a31ea6
    switch (entry->type) {
Packit Service a31ea6
	case SGML_CATA_ENTITY:
Packit Service a31ea6
	case SGML_CATA_PENTITY:
Packit Service a31ea6
	case SGML_CATA_DOCTYPE:
Packit Service a31ea6
	case SGML_CATA_LINKTYPE:
Packit Service a31ea6
	case SGML_CATA_NOTATION:
Packit Service a31ea6
	case SGML_CATA_PUBLIC:
Packit Service a31ea6
	case SGML_CATA_SYSTEM:
Packit Service a31ea6
	case SGML_CATA_DELEGATE:
Packit Service a31ea6
	    fprintf(out, " \"%s\"", entry->value); break;
Packit Service a31ea6
	default:
Packit Service a31ea6
	    break;
Packit Service a31ea6
    }
Packit Service a31ea6
    fprintf(out, "\n");
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlDumpXMLCatalogNode:
Packit Service a31ea6
 * @catal:  top catalog entry
Packit Service a31ea6
 * @catalog: pointer to the xml tree
Packit Service a31ea6
 * @doc: the containing document
Packit Service a31ea6
 * @ns: the current namespace
Packit Service a31ea6
 * @cgroup: group node for group members
Packit Service a31ea6
 *
Packit Service a31ea6
 * Serializes a Catalog entry, called by xmlDumpXMLCatalog and recursively
Packit Service a31ea6
 * for group entries
Packit Service a31ea6
 */
Packit Service a31ea6
static void xmlDumpXMLCatalogNode(xmlCatalogEntryPtr catal, xmlNodePtr catalog,
Packit Service a31ea6
		    xmlDocPtr doc, xmlNsPtr ns, xmlCatalogEntryPtr cgroup) {
Packit Service a31ea6
    xmlNodePtr node;
Packit Service a31ea6
    xmlCatalogEntryPtr cur;
Packit Service a31ea6
    /*
Packit Service a31ea6
     * add all the catalog entries
Packit Service a31ea6
     */
Packit Service a31ea6
    cur = catal;
Packit Service a31ea6
    while (cur != NULL) {
Packit Service a31ea6
        if (cur->group == cgroup) {
Packit Service a31ea6
	    switch (cur->type) {
Packit Service a31ea6
	        case XML_CATA_REMOVED:
Packit Service a31ea6
		    break;
Packit Service a31ea6
	        case XML_CATA_BROKEN_CATALOG:
Packit Service a31ea6
	        case XML_CATA_CATALOG:
Packit Service a31ea6
		    if (cur == catal) {
Packit Service a31ea6
			cur = cur->children;
Packit Service a31ea6
		        continue;
Packit Service a31ea6
		    }
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case XML_CATA_NEXT_CATALOG:
Packit Service a31ea6
		    node = xmlNewDocNode(doc, ns, BAD_CAST "nextCatalog", NULL);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "catalog", cur->value);
Packit Service a31ea6
		    xmlAddChild(catalog, node);
Packit Service a31ea6
                    break;
Packit Service a31ea6
		case XML_CATA_NONE:
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case XML_CATA_GROUP:
Packit Service a31ea6
		    node = xmlNewDocNode(doc, ns, BAD_CAST "group", NULL);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "id", cur->name);
Packit Service a31ea6
		    if (cur->value != NULL) {
Packit Service a31ea6
		        xmlNsPtr xns;
Packit Service a31ea6
			xns = xmlSearchNsByHref(doc, node, XML_XML_NAMESPACE);
Packit Service a31ea6
			if (xns != NULL)
Packit Service a31ea6
			    xmlSetNsProp(node, xns, BAD_CAST "base",
Packit Service a31ea6
					 cur->value);
Packit Service a31ea6
		    }
Packit Service a31ea6
		    switch (cur->prefer) {
Packit Service a31ea6
			case XML_CATA_PREFER_NONE:
Packit Service a31ea6
		            break;
Packit Service a31ea6
			case XML_CATA_PREFER_PUBLIC:
Packit Service a31ea6
		            xmlSetProp(node, BAD_CAST "prefer", BAD_CAST "public");
Packit Service a31ea6
			    break;
Packit Service a31ea6
			case XML_CATA_PREFER_SYSTEM:
Packit Service a31ea6
		            xmlSetProp(node, BAD_CAST "prefer", BAD_CAST "system");
Packit Service a31ea6
			    break;
Packit Service a31ea6
		    }
Packit Service a31ea6
		    xmlDumpXMLCatalogNode(cur->next, node, doc, ns, cur);
Packit Service a31ea6
		    xmlAddChild(catalog, node);
Packit Service a31ea6
	            break;
Packit Service a31ea6
		case XML_CATA_PUBLIC:
Packit Service a31ea6
		    node = xmlNewDocNode(doc, ns, BAD_CAST "public", NULL);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "publicId", cur->name);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "uri", cur->value);
Packit Service a31ea6
		    xmlAddChild(catalog, node);
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case XML_CATA_SYSTEM:
Packit Service a31ea6
		    node = xmlNewDocNode(doc, ns, BAD_CAST "system", NULL);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "systemId", cur->name);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "uri", cur->value);
Packit Service a31ea6
		    xmlAddChild(catalog, node);
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case XML_CATA_REWRITE_SYSTEM:
Packit Service a31ea6
		    node = xmlNewDocNode(doc, ns, BAD_CAST "rewriteSystem", NULL);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "systemIdStartString", cur->name);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "rewritePrefix", cur->value);
Packit Service a31ea6
		    xmlAddChild(catalog, node);
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case XML_CATA_DELEGATE_PUBLIC:
Packit Service a31ea6
		    node = xmlNewDocNode(doc, ns, BAD_CAST "delegatePublic", NULL);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "publicIdStartString", cur->name);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "catalog", cur->value);
Packit Service a31ea6
		    xmlAddChild(catalog, node);
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case XML_CATA_DELEGATE_SYSTEM:
Packit Service a31ea6
		    node = xmlNewDocNode(doc, ns, BAD_CAST "delegateSystem", NULL);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "systemIdStartString", cur->name);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "catalog", cur->value);
Packit Service a31ea6
		    xmlAddChild(catalog, node);
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case XML_CATA_URI:
Packit Service a31ea6
		    node = xmlNewDocNode(doc, ns, BAD_CAST "uri", NULL);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "name", cur->name);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "uri", cur->value);
Packit Service a31ea6
		    xmlAddChild(catalog, node);
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case XML_CATA_REWRITE_URI:
Packit Service a31ea6
		    node = xmlNewDocNode(doc, ns, BAD_CAST "rewriteURI", NULL);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "uriStartString", cur->name);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "rewritePrefix", cur->value);
Packit Service a31ea6
		    xmlAddChild(catalog, node);
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case XML_CATA_DELEGATE_URI:
Packit Service a31ea6
		    node = xmlNewDocNode(doc, ns, BAD_CAST "delegateURI", NULL);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "uriStartString", cur->name);
Packit Service a31ea6
		    xmlSetProp(node, BAD_CAST "catalog", cur->value);
Packit Service a31ea6
		    xmlAddChild(catalog, node);
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case SGML_CATA_SYSTEM:
Packit Service a31ea6
		case SGML_CATA_PUBLIC:
Packit Service a31ea6
		case SGML_CATA_ENTITY:
Packit Service a31ea6
		case SGML_CATA_PENTITY:
Packit Service a31ea6
		case SGML_CATA_DOCTYPE:
Packit Service a31ea6
		case SGML_CATA_LINKTYPE:
Packit Service a31ea6
		case SGML_CATA_NOTATION:
Packit Service a31ea6
		case SGML_CATA_DELEGATE:
Packit Service a31ea6
		case SGML_CATA_BASE:
Packit Service a31ea6
		case SGML_CATA_CATALOG:
Packit Service a31ea6
		case SGML_CATA_DOCUMENT:
Packit Service a31ea6
		case SGML_CATA_SGMLDECL:
Packit Service a31ea6
		    break;
Packit Service a31ea6
	    }
Packit Service a31ea6
        }
Packit Service a31ea6
	cur = cur->next;
Packit Service a31ea6
    }
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
static int
Packit Service a31ea6
xmlDumpXMLCatalog(FILE *out, xmlCatalogEntryPtr catal) {
Packit Service a31ea6
    int ret;
Packit Service a31ea6
    xmlDocPtr doc;
Packit Service a31ea6
    xmlNsPtr ns;
Packit Service a31ea6
    xmlDtdPtr dtd;
Packit Service a31ea6
    xmlNodePtr catalog;
Packit Service a31ea6
    xmlOutputBufferPtr buf;
Packit Service a31ea6
Packit Service a31ea6
    /*
Packit Service a31ea6
     * Rebuild a catalog
Packit Service a31ea6
     */
Packit Service a31ea6
    doc = xmlNewDoc(NULL);
Packit Service a31ea6
    if (doc == NULL)
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
    dtd = xmlNewDtd(doc, BAD_CAST "catalog",
Packit Service a31ea6
	       BAD_CAST "-//OASIS//DTD Entity Resolution XML Catalog V1.0//EN",
Packit Service a31ea6
BAD_CAST "http://www.oasis-open.org/committees/entity/release/1.0/catalog.dtd");
Packit Service a31ea6
Packit Service a31ea6
    xmlAddChild((xmlNodePtr) doc, (xmlNodePtr) dtd);
Packit Service a31ea6
Packit Service a31ea6
    ns = xmlNewNs(NULL, XML_CATALOGS_NAMESPACE, NULL);
Packit Service a31ea6
    if (ns == NULL) {
Packit Service a31ea6
	xmlFreeDoc(doc);
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
    }
Packit Service a31ea6
    catalog = xmlNewDocNode(doc, ns, BAD_CAST "catalog", NULL);
Packit Service a31ea6
    if (catalog == NULL) {
Packit Service a31ea6
	xmlFreeNs(ns);
Packit Service a31ea6
	xmlFreeDoc(doc);
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
    }
Packit Service a31ea6
    catalog->nsDef = ns;
Packit Service a31ea6
    xmlAddChild((xmlNodePtr) doc, catalog);
Packit Service a31ea6
Packit Service a31ea6
    xmlDumpXMLCatalogNode(catal, catalog, doc, ns, NULL);
Packit Service a31ea6
Packit Service a31ea6
    /*
Packit Service a31ea6
     * reserialize it
Packit Service a31ea6
     */
Packit Service a31ea6
    buf = xmlOutputBufferCreateFile(out, NULL);
Packit Service a31ea6
    if (buf == NULL) {
Packit Service a31ea6
	xmlFreeDoc(doc);
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
    }
Packit Service a31ea6
    ret = xmlSaveFormatFileTo(buf, doc, NULL, 1);
Packit Service a31ea6
Packit Service a31ea6
    /*
Packit Service a31ea6
     * Free it
Packit Service a31ea6
     */
Packit Service a31ea6
    xmlFreeDoc(doc);
Packit Service a31ea6
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
#endif /* LIBXML_OUTPUT_ENABLED */
Packit Service a31ea6
Packit Service a31ea6
/************************************************************************
Packit Service a31ea6
 *									*
Packit Service a31ea6
 *			Converting SGML Catalogs to XML			*
Packit Service a31ea6
 *									*
Packit Service a31ea6
 ************************************************************************/
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogConvertEntry:
Packit Service a31ea6
 * @entry:  the entry
Packit Service a31ea6
 * @catal:  pointer to the catalog being converted
Packit Service a31ea6
 *
Packit Service a31ea6
 * Convert one entry from the catalog
Packit Service a31ea6
 */
Packit Service a31ea6
static void
Packit Service a31ea6
xmlCatalogConvertEntry(xmlCatalogEntryPtr entry, xmlCatalogPtr catal) {
Packit Service a31ea6
    if ((entry == NULL) || (catal == NULL) || (catal->sgml == NULL) ||
Packit Service a31ea6
	(catal->xml == NULL))
Packit Service a31ea6
	return;
Packit Service a31ea6
    switch (entry->type) {
Packit Service a31ea6
	case SGML_CATA_ENTITY:
Packit Service a31ea6
	    entry->type = XML_CATA_PUBLIC;
Packit Service a31ea6
	    break;
Packit Service a31ea6
	case SGML_CATA_PENTITY:
Packit Service a31ea6
	    entry->type = XML_CATA_PUBLIC;
Packit Service a31ea6
	    break;
Packit Service a31ea6
	case SGML_CATA_DOCTYPE:
Packit Service a31ea6
	    entry->type = XML_CATA_PUBLIC;
Packit Service a31ea6
	    break;
Packit Service a31ea6
	case SGML_CATA_LINKTYPE:
Packit Service a31ea6
	    entry->type = XML_CATA_PUBLIC;
Packit Service a31ea6
	    break;
Packit Service a31ea6
	case SGML_CATA_NOTATION:
Packit Service a31ea6
	    entry->type = XML_CATA_PUBLIC;
Packit Service a31ea6
	    break;
Packit Service a31ea6
	case SGML_CATA_PUBLIC:
Packit Service a31ea6
	    entry->type = XML_CATA_PUBLIC;
Packit Service a31ea6
	    break;
Packit Service a31ea6
	case SGML_CATA_SYSTEM:
Packit Service a31ea6
	    entry->type = XML_CATA_SYSTEM;
Packit Service a31ea6
	    break;
Packit Service a31ea6
	case SGML_CATA_DELEGATE:
Packit Service a31ea6
	    entry->type = XML_CATA_DELEGATE_PUBLIC;
Packit Service a31ea6
	    break;
Packit Service a31ea6
	case SGML_CATA_CATALOG:
Packit Service a31ea6
	    entry->type = XML_CATA_CATALOG;
Packit Service a31ea6
	    break;
Packit Service a31ea6
	default:
Packit Service a31ea6
	    xmlHashRemoveEntry(catal->sgml, entry->name,
Packit Service a31ea6
		               (xmlHashDeallocator) xmlFreeCatalogEntry);
Packit Service a31ea6
	    return;
Packit Service a31ea6
    }
Packit Service a31ea6
    /*
Packit Service a31ea6
     * Conversion successful, remove from the SGML catalog
Packit Service a31ea6
     * and add it to the default XML one
Packit Service a31ea6
     */
Packit Service a31ea6
    xmlHashRemoveEntry(catal->sgml, entry->name, NULL);
Packit Service a31ea6
    entry->parent = catal->xml;
Packit Service a31ea6
    entry->next = NULL;
Packit Service a31ea6
    if (catal->xml->children == NULL)
Packit Service a31ea6
	catal->xml->children = entry;
Packit Service a31ea6
    else {
Packit Service a31ea6
	xmlCatalogEntryPtr prev;
Packit Service a31ea6
Packit Service a31ea6
	prev = catal->xml->children;
Packit Service a31ea6
	while (prev->next != NULL)
Packit Service a31ea6
	    prev = prev->next;
Packit Service a31ea6
	prev->next = entry;
Packit Service a31ea6
    }
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlConvertSGMLCatalog:
Packit Service a31ea6
 * @catal: the catalog
Packit Service a31ea6
 *
Packit Service a31ea6
 * Convert all the SGML catalog entries as XML ones
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the number of entries converted if successful, -1 otherwise
Packit Service a31ea6
 */
Packit Service a31ea6
int
Packit Service a31ea6
xmlConvertSGMLCatalog(xmlCatalogPtr catal) {
Packit Service a31ea6
Packit Service a31ea6
    if ((catal == NULL) || (catal->type != XML_SGML_CATALOG_TYPE))
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
Packit Service a31ea6
    if (xmlDebugCatalogs) {
Packit Service a31ea6
	xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		"Converting SGML catalog to XML\n");
Packit Service a31ea6
    }
Packit Service a31ea6
    xmlHashScan(catal->sgml,
Packit Service a31ea6
		(xmlHashScanner) xmlCatalogConvertEntry,
Packit Service a31ea6
		&catal);
Packit Service a31ea6
    return(0);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/************************************************************************
Packit Service a31ea6
 *									*
Packit Service a31ea6
 *			Helper function					*
Packit Service a31ea6
 *									*
Packit Service a31ea6
 ************************************************************************/
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogUnWrapURN:
Packit Service a31ea6
 * @urn:  an "urn:publicid:" to unwrap
Packit Service a31ea6
 *
Packit Service a31ea6
 * Expand the URN into the equivalent Public Identifier
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the new identifier or NULL, the string must be deallocated
Packit Service a31ea6
 *         by the caller.
Packit Service a31ea6
 */
Packit Service a31ea6
static xmlChar *
Packit Service a31ea6
xmlCatalogUnWrapURN(const xmlChar *urn) {
Packit Service a31ea6
    xmlChar result[2000];
Packit Service a31ea6
    unsigned int i = 0;
Packit Service a31ea6
Packit Service a31ea6
    if (xmlStrncmp(urn, BAD_CAST XML_URN_PUBID, sizeof(XML_URN_PUBID) - 1))
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    urn += sizeof(XML_URN_PUBID) - 1;
Packit Service a31ea6
Packit Service a31ea6
    while (*urn != 0) {
Packit Service a31ea6
	if (i > sizeof(result) - 4)
Packit Service a31ea6
	    break;
Packit Service a31ea6
	if (*urn == '+') {
Packit Service a31ea6
	    result[i++] = ' ';
Packit Service a31ea6
	    urn++;
Packit Service a31ea6
	} else if (*urn == ':') {
Packit Service a31ea6
	    result[i++] = '/';
Packit Service a31ea6
	    result[i++] = '/';
Packit Service a31ea6
	    urn++;
Packit Service a31ea6
	} else if (*urn == ';') {
Packit Service a31ea6
	    result[i++] = ':';
Packit Service a31ea6
	    result[i++] = ':';
Packit Service a31ea6
	    urn++;
Packit Service a31ea6
	} else if (*urn == '%') {
Packit Service a31ea6
	    if ((urn[1] == '2') && (urn[2] == 'B'))
Packit Service a31ea6
		result[i++] = '+';
Packit Service a31ea6
	    else if ((urn[1] == '3') && (urn[2] == 'A'))
Packit Service a31ea6
		result[i++] = ':';
Packit Service a31ea6
	    else if ((urn[1] == '2') && (urn[2] == 'F'))
Packit Service a31ea6
		result[i++] = '/';
Packit Service a31ea6
	    else if ((urn[1] == '3') && (urn[2] == 'B'))
Packit Service a31ea6
		result[i++] = ';';
Packit Service a31ea6
	    else if ((urn[1] == '2') && (urn[2] == '7'))
Packit Service a31ea6
		result[i++] = '\'';
Packit Service a31ea6
	    else if ((urn[1] == '3') && (urn[2] == 'F'))
Packit Service a31ea6
		result[i++] = '?';
Packit Service a31ea6
	    else if ((urn[1] == '2') && (urn[2] == '3'))
Packit Service a31ea6
		result[i++] = '#';
Packit Service a31ea6
	    else if ((urn[1] == '2') && (urn[2] == '5'))
Packit Service a31ea6
		result[i++] = '%';
Packit Service a31ea6
	    else {
Packit Service a31ea6
		result[i++] = *urn;
Packit Service a31ea6
		urn++;
Packit Service a31ea6
		continue;
Packit Service a31ea6
	    }
Packit Service a31ea6
	    urn += 3;
Packit Service a31ea6
	} else {
Packit Service a31ea6
	    result[i++] = *urn;
Packit Service a31ea6
	    urn++;
Packit Service a31ea6
	}
Packit Service a31ea6
    }
Packit Service a31ea6
    result[i] = 0;
Packit Service a31ea6
Packit Service a31ea6
    return(xmlStrdup(result));
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlParseCatalogFile:
Packit Service a31ea6
 * @filename:  the filename
Packit Service a31ea6
 *
Packit Service a31ea6
 * parse an XML file and build a tree. It's like xmlParseFile()
Packit Service a31ea6
 * except it bypass all catalog lookups.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the resulting document tree or NULL in case of error
Packit Service a31ea6
 */
Packit Service a31ea6
Packit Service a31ea6
xmlDocPtr
Packit Service a31ea6
xmlParseCatalogFile(const char *filename) {
Packit Service a31ea6
    xmlDocPtr ret;
Packit Service a31ea6
    xmlParserCtxtPtr ctxt;
Packit Service a31ea6
    char *directory = NULL;
Packit Service a31ea6
    xmlParserInputPtr inputStream;
Packit Service a31ea6
    xmlParserInputBufferPtr buf;
Packit Service a31ea6
Packit Service a31ea6
    ctxt = xmlNewParserCtxt();
Packit Service a31ea6
    if (ctxt == NULL) {
Packit Service a31ea6
#ifdef LIBXML_SAX1_ENABLED
Packit Service a31ea6
	if (xmlDefaultSAXHandler.error != NULL) {
Packit Service a31ea6
	    xmlDefaultSAXHandler.error(NULL, "out of memory\n");
Packit Service a31ea6
	}
Packit Service a31ea6
#endif
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    buf = xmlParserInputBufferCreateFilename(filename, XML_CHAR_ENCODING_NONE);
Packit Service a31ea6
    if (buf == NULL) {
Packit Service a31ea6
	xmlFreeParserCtxt(ctxt);
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    inputStream = xmlNewInputStream(ctxt);
Packit Service a31ea6
    if (inputStream == NULL) {
Packit Service a31ea6
	xmlFreeParserCtxt(ctxt);
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    inputStream->filename = (char *) xmlCanonicPath((const xmlChar *)filename);
Packit Service a31ea6
    inputStream->buf = buf;
Packit Service a31ea6
    xmlBufResetInput(buf->buffer, inputStream);
Packit Service a31ea6
Packit Service a31ea6
    inputPush(ctxt, inputStream);
Packit Service a31ea6
    if ((ctxt->directory == NULL) && (directory == NULL))
Packit Service a31ea6
        directory = xmlParserGetDirectory(filename);
Packit Service a31ea6
    if ((ctxt->directory == NULL) && (directory != NULL))
Packit Service a31ea6
        ctxt->directory = directory;
Packit Service a31ea6
    ctxt->valid = 0;
Packit Service a31ea6
    ctxt->validate = 0;
Packit Service a31ea6
    ctxt->loadsubset = 0;
Packit Service a31ea6
    ctxt->pedantic = 0;
Packit Service a31ea6
    ctxt->dictNames = 1;
Packit Service a31ea6
Packit Service a31ea6
    xmlParseDocument(ctxt);
Packit Service a31ea6
Packit Service a31ea6
    if (ctxt->wellFormed)
Packit Service a31ea6
	ret = ctxt->myDoc;
Packit Service a31ea6
    else {
Packit Service a31ea6
        ret = NULL;
Packit Service a31ea6
        xmlFreeDoc(ctxt->myDoc);
Packit Service a31ea6
        ctxt->myDoc = NULL;
Packit Service a31ea6
    }
Packit Service a31ea6
    xmlFreeParserCtxt(ctxt);
Packit Service a31ea6
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlLoadFileContent:
Packit Service a31ea6
 * @filename:  a file path
Packit Service a31ea6
 *
Packit Service a31ea6
 * Load a file content into memory.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns a pointer to the 0 terminated string or NULL in case of error
Packit Service a31ea6
 */
Packit Service a31ea6
static xmlChar *
Packit Service a31ea6
xmlLoadFileContent(const char *filename)
Packit Service a31ea6
{
Packit Service a31ea6
#ifdef HAVE_STAT
Packit Service a31ea6
    int fd;
Packit Service a31ea6
#else
Packit Service a31ea6
    FILE *fd;
Packit Service a31ea6
#endif
Packit Service a31ea6
    int len;
Packit Service a31ea6
    long size;
Packit Service a31ea6
Packit Service a31ea6
#ifdef HAVE_STAT
Packit Service a31ea6
    struct stat info;
Packit Service a31ea6
#endif
Packit Service a31ea6
    xmlChar *content;
Packit Service a31ea6
Packit Service a31ea6
    if (filename == NULL)
Packit Service a31ea6
        return (NULL);
Packit Service a31ea6
Packit Service a31ea6
#ifdef HAVE_STAT
Packit Service a31ea6
    if (stat(filename, &info) < 0)
Packit Service a31ea6
        return (NULL);
Packit Service a31ea6
#endif
Packit Service a31ea6
Packit Service a31ea6
#ifdef HAVE_STAT
Packit Service a31ea6
    if ((fd = open(filename, O_RDONLY)) < 0)
Packit Service a31ea6
#else
Packit Service a31ea6
    if ((fd = fopen(filename, "rb")) == NULL)
Packit Service a31ea6
#endif
Packit Service a31ea6
    {
Packit Service a31ea6
        return (NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
#ifdef HAVE_STAT
Packit Service a31ea6
    size = info.st_size;
Packit Service a31ea6
#else
Packit Service a31ea6
    if (fseek(fd, 0, SEEK_END) || (size = ftell(fd)) == EOF || fseek(fd, 0, SEEK_SET)) {        /* File operations denied? ok, just close and return failure */
Packit Service a31ea6
        fclose(fd);
Packit Service a31ea6
        return (NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
#endif
Packit Service a31ea6
    content = (xmlChar*)xmlMallocAtomic(size + 10);
Packit Service a31ea6
    if (content == NULL) {
Packit Service a31ea6
        xmlCatalogErrMemory("allocating catalog data");
Packit Service a31ea6
#ifdef HAVE_STAT
Packit Service a31ea6
	close(fd);
Packit Service a31ea6
#else
Packit Service a31ea6
	fclose(fd);
Packit Service a31ea6
#endif
Packit Service a31ea6
        return (NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
#ifdef HAVE_STAT
Packit Service a31ea6
    len = read(fd, content, size);
Packit Service a31ea6
    close(fd);
Packit Service a31ea6
#else
Packit Service a31ea6
    len = fread(content, 1, size, fd);
Packit Service a31ea6
    fclose(fd);
Packit Service a31ea6
#endif
Packit Service a31ea6
    if (len < 0) {
Packit Service a31ea6
        xmlFree(content);
Packit Service a31ea6
        return (NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
    content[len] = 0;
Packit Service a31ea6
Packit Service a31ea6
    return(content);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogNormalizePublic:
Packit Service a31ea6
 * @pubID:  the public ID string
Packit Service a31ea6
 *
Packit Service a31ea6
 *  Normalizes the Public Identifier
Packit Service a31ea6
 *
Packit Service a31ea6
 * Implements 6.2. Public Identifier Normalization
Packit Service a31ea6
 * from http://www.oasis-open.org/committees/entity/spec-2001-08-06.html
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the new string or NULL, the string must be deallocated
Packit Service a31ea6
 *         by the caller.
Packit Service a31ea6
 */
Packit Service a31ea6
static xmlChar *
Packit Service a31ea6
xmlCatalogNormalizePublic(const xmlChar *pubID)
Packit Service a31ea6
{
Packit Service a31ea6
    int ok = 1;
Packit Service a31ea6
    int white;
Packit Service a31ea6
    const xmlChar *p;
Packit Service a31ea6
    xmlChar *ret;
Packit Service a31ea6
    xmlChar *q;
Packit Service a31ea6
Packit Service a31ea6
    if (pubID == NULL)
Packit Service a31ea6
        return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    white = 1;
Packit Service a31ea6
    for (p = pubID;*p != 0 && ok;p++) {
Packit Service a31ea6
        if (!xmlIsBlank_ch(*p))
Packit Service a31ea6
            white = 0;
Packit Service a31ea6
        else if (*p == 0x20 && !white)
Packit Service a31ea6
            white = 1;
Packit Service a31ea6
        else
Packit Service a31ea6
            ok = 0;
Packit Service a31ea6
    }
Packit Service a31ea6
    if (ok && !white)	/* is normalized */
Packit Service a31ea6
        return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    ret = xmlStrdup(pubID);
Packit Service a31ea6
    q = ret;
Packit Service a31ea6
    white = 0;
Packit Service a31ea6
    for (p = pubID;*p != 0;p++) {
Packit Service a31ea6
        if (xmlIsBlank_ch(*p)) {
Packit Service a31ea6
            if (q != ret)
Packit Service a31ea6
                white = 1;
Packit Service a31ea6
        } else {
Packit Service a31ea6
            if (white) {
Packit Service a31ea6
                *(q++) = 0x20;
Packit Service a31ea6
                white = 0;
Packit Service a31ea6
            }
Packit Service a31ea6
            *(q++) = *p;
Packit Service a31ea6
        }
Packit Service a31ea6
    }
Packit Service a31ea6
    *q = 0;
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/************************************************************************
Packit Service a31ea6
 *									*
Packit Service a31ea6
 *			The XML Catalog parser				*
Packit Service a31ea6
 *									*
Packit Service a31ea6
 ************************************************************************/
Packit Service a31ea6
Packit Service a31ea6
static xmlCatalogEntryPtr
Packit Service a31ea6
xmlParseXMLCatalogFile(xmlCatalogPrefer prefer, const xmlChar *filename);
Packit Service a31ea6
static void
Packit Service a31ea6
xmlParseXMLCatalogNodeList(xmlNodePtr cur, xmlCatalogPrefer prefer,
Packit Service a31ea6
	                   xmlCatalogEntryPtr parent, xmlCatalogEntryPtr cgroup);
Packit Service a31ea6
static xmlChar *
Packit Service a31ea6
xmlCatalogListXMLResolve(xmlCatalogEntryPtr catal, const xmlChar *pubID,
Packit Service a31ea6
	              const xmlChar *sysID);
Packit Service a31ea6
static xmlChar *
Packit Service a31ea6
xmlCatalogListXMLResolveURI(xmlCatalogEntryPtr catal, const xmlChar *URI);
Packit Service a31ea6
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlGetXMLCatalogEntryType:
Packit Service a31ea6
 * @name:  the name
Packit Service a31ea6
 *
Packit Service a31ea6
 * lookup the internal type associated to an XML catalog entry name
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the type associated with that name
Packit Service a31ea6
 */
Packit Service a31ea6
static xmlCatalogEntryType
Packit Service a31ea6
xmlGetXMLCatalogEntryType(const xmlChar *name) {
Packit Service a31ea6
    xmlCatalogEntryType type = XML_CATA_NONE;
Packit Service a31ea6
    if (xmlStrEqual(name, (const xmlChar *) "system"))
Packit Service a31ea6
	type = XML_CATA_SYSTEM;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "public"))
Packit Service a31ea6
	type = XML_CATA_PUBLIC;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "rewriteSystem"))
Packit Service a31ea6
	type = XML_CATA_REWRITE_SYSTEM;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "delegatePublic"))
Packit Service a31ea6
	type = XML_CATA_DELEGATE_PUBLIC;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "delegateSystem"))
Packit Service a31ea6
	type = XML_CATA_DELEGATE_SYSTEM;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "uri"))
Packit Service a31ea6
	type = XML_CATA_URI;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "rewriteURI"))
Packit Service a31ea6
	type = XML_CATA_REWRITE_URI;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "delegateURI"))
Packit Service a31ea6
	type = XML_CATA_DELEGATE_URI;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "nextCatalog"))
Packit Service a31ea6
	type = XML_CATA_NEXT_CATALOG;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "catalog"))
Packit Service a31ea6
	type = XML_CATA_CATALOG;
Packit Service a31ea6
    return(type);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlParseXMLCatalogOneNode:
Packit Service a31ea6
 * @cur:  the XML node
Packit Service a31ea6
 * @type:  the type of Catalog entry
Packit Service a31ea6
 * @name:  the name of the node
Packit Service a31ea6
 * @attrName:  the attribute holding the value
Packit Service a31ea6
 * @uriAttrName:  the attribute holding the URI-Reference
Packit Service a31ea6
 * @prefer:  the PUBLIC vs. SYSTEM current preference value
Packit Service a31ea6
 * @cgroup:  the group which includes this node
Packit Service a31ea6
 *
Packit Service a31ea6
 * Finishes the examination of an XML tree node of a catalog and build
Packit Service a31ea6
 * a Catalog entry from it.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the new Catalog entry node or NULL in case of error.
Packit Service a31ea6
 */
Packit Service a31ea6
static xmlCatalogEntryPtr
Packit Service a31ea6
xmlParseXMLCatalogOneNode(xmlNodePtr cur, xmlCatalogEntryType type,
Packit Service a31ea6
			  const xmlChar *name, const xmlChar *attrName,
Packit Service a31ea6
			  const xmlChar *uriAttrName, xmlCatalogPrefer prefer,
Packit Service a31ea6
			  xmlCatalogEntryPtr cgroup) {
Packit Service a31ea6
    int ok = 1;
Packit Service a31ea6
    xmlChar *uriValue;
Packit Service a31ea6
    xmlChar *nameValue = NULL;
Packit Service a31ea6
    xmlChar *base = NULL;
Packit Service a31ea6
    xmlChar *URL = NULL;
Packit Service a31ea6
    xmlCatalogEntryPtr ret = NULL;
Packit Service a31ea6
Packit Service a31ea6
    if (attrName != NULL) {
Packit Service a31ea6
	nameValue = xmlGetProp(cur, attrName);
Packit Service a31ea6
	if (nameValue == NULL) {
Packit Service a31ea6
	    xmlCatalogErr(ret, cur, XML_CATALOG_MISSING_ATTR,
Packit Service a31ea6
			  "%s entry lacks '%s'\n", name, attrName, NULL);
Packit Service a31ea6
	    ok = 0;
Packit Service a31ea6
	}
Packit Service a31ea6
    }
Packit Service a31ea6
    uriValue = xmlGetProp(cur, uriAttrName);
Packit Service a31ea6
    if (uriValue == NULL) {
Packit Service a31ea6
	xmlCatalogErr(ret, cur, XML_CATALOG_MISSING_ATTR,
Packit Service a31ea6
		"%s entry lacks '%s'\n", name, uriAttrName, NULL);
Packit Service a31ea6
	ok = 0;
Packit Service a31ea6
    }
Packit Service a31ea6
    if (!ok) {
Packit Service a31ea6
	if (nameValue != NULL)
Packit Service a31ea6
	    xmlFree(nameValue);
Packit Service a31ea6
	if (uriValue != NULL)
Packit Service a31ea6
	    xmlFree(uriValue);
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    base = xmlNodeGetBase(cur->doc, cur);
Packit Service a31ea6
    URL = xmlBuildURI(uriValue, base);
Packit Service a31ea6
    if (URL != NULL) {
Packit Service a31ea6
	if (xmlDebugCatalogs > 1) {
Packit Service a31ea6
	    if (nameValue != NULL)
Packit Service a31ea6
		xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			"Found %s: '%s' '%s'\n", name, nameValue, URL);
Packit Service a31ea6
	    else
Packit Service a31ea6
		xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			"Found %s: '%s'\n", name, URL);
Packit Service a31ea6
	}
Packit Service a31ea6
	ret = xmlNewCatalogEntry(type, nameValue, uriValue, URL, prefer, cgroup);
Packit Service a31ea6
    } else {
Packit Service a31ea6
	xmlCatalogErr(ret, cur, XML_CATALOG_ENTRY_BROKEN,
Packit Service a31ea6
		"%s entry '%s' broken ?: %s\n", name, uriAttrName, uriValue);
Packit Service a31ea6
    }
Packit Service a31ea6
    if (nameValue != NULL)
Packit Service a31ea6
	xmlFree(nameValue);
Packit Service a31ea6
    if (uriValue != NULL)
Packit Service a31ea6
	xmlFree(uriValue);
Packit Service a31ea6
    if (base != NULL)
Packit Service a31ea6
	xmlFree(base);
Packit Service a31ea6
    if (URL != NULL)
Packit Service a31ea6
	xmlFree(URL);
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlParseXMLCatalogNode:
Packit Service a31ea6
 * @cur:  the XML node
Packit Service a31ea6
 * @prefer:  the PUBLIC vs. SYSTEM current preference value
Packit Service a31ea6
 * @parent:  the parent Catalog entry
Packit Service a31ea6
 * @cgroup:  the group which includes this node
Packit Service a31ea6
 *
Packit Service a31ea6
 * Examines an XML tree node of a catalog and build
Packit Service a31ea6
 * a Catalog entry from it adding it to its parent. The examination can
Packit Service a31ea6
 * be recursive.
Packit Service a31ea6
 */
Packit Service a31ea6
static void
Packit Service a31ea6
xmlParseXMLCatalogNode(xmlNodePtr cur, xmlCatalogPrefer prefer,
Packit Service a31ea6
	               xmlCatalogEntryPtr parent, xmlCatalogEntryPtr cgroup)
Packit Service a31ea6
{
Packit Service a31ea6
    xmlChar *base = NULL;
Packit Service a31ea6
    xmlCatalogEntryPtr entry = NULL;
Packit Service a31ea6
Packit Service a31ea6
    if (cur == NULL)
Packit Service a31ea6
        return;
Packit Service a31ea6
    if (xmlStrEqual(cur->name, BAD_CAST "group")) {
Packit Service a31ea6
        xmlChar *prop;
Packit Service a31ea6
	xmlCatalogPrefer pref = XML_CATA_PREFER_NONE;
Packit Service a31ea6
Packit Service a31ea6
        prop = xmlGetProp(cur, BAD_CAST "prefer");
Packit Service a31ea6
        if (prop != NULL) {
Packit Service a31ea6
            if (xmlStrEqual(prop, BAD_CAST "system")) {
Packit Service a31ea6
                prefer = XML_CATA_PREFER_SYSTEM;
Packit Service a31ea6
            } else if (xmlStrEqual(prop, BAD_CAST "public")) {
Packit Service a31ea6
                prefer = XML_CATA_PREFER_PUBLIC;
Packit Service a31ea6
            } else {
Packit Service a31ea6
		xmlCatalogErr(parent, cur, XML_CATALOG_PREFER_VALUE,
Packit Service a31ea6
                              "Invalid value for prefer: '%s'\n",
Packit Service a31ea6
			      prop, NULL, NULL);
Packit Service a31ea6
            }
Packit Service a31ea6
            xmlFree(prop);
Packit Service a31ea6
	    pref = prefer;
Packit Service a31ea6
        }
Packit Service a31ea6
	prop = xmlGetProp(cur, BAD_CAST "id");
Packit Service a31ea6
	base = xmlGetNsProp(cur, BAD_CAST "base", XML_XML_NAMESPACE);
Packit Service a31ea6
	entry = xmlNewCatalogEntry(XML_CATA_GROUP, prop, base, NULL, pref, cgroup);
Packit Service a31ea6
	xmlFree(prop);
Packit Service a31ea6
    } else if (xmlStrEqual(cur->name, BAD_CAST "public")) {
Packit Service a31ea6
	entry = xmlParseXMLCatalogOneNode(cur, XML_CATA_PUBLIC,
Packit Service a31ea6
		BAD_CAST "public", BAD_CAST "publicId", BAD_CAST "uri", prefer, cgroup);
Packit Service a31ea6
    } else if (xmlStrEqual(cur->name, BAD_CAST "system")) {
Packit Service a31ea6
	entry = xmlParseXMLCatalogOneNode(cur, XML_CATA_SYSTEM,
Packit Service a31ea6
		BAD_CAST "system", BAD_CAST "systemId", BAD_CAST "uri", prefer, cgroup);
Packit Service a31ea6
    } else if (xmlStrEqual(cur->name, BAD_CAST "rewriteSystem")) {
Packit Service a31ea6
	entry = xmlParseXMLCatalogOneNode(cur, XML_CATA_REWRITE_SYSTEM,
Packit Service a31ea6
		BAD_CAST "rewriteSystem", BAD_CAST "systemIdStartString",
Packit Service a31ea6
		BAD_CAST "rewritePrefix", prefer, cgroup);
Packit Service a31ea6
    } else if (xmlStrEqual(cur->name, BAD_CAST "delegatePublic")) {
Packit Service a31ea6
	entry = xmlParseXMLCatalogOneNode(cur, XML_CATA_DELEGATE_PUBLIC,
Packit Service a31ea6
		BAD_CAST "delegatePublic", BAD_CAST "publicIdStartString",
Packit Service a31ea6
		BAD_CAST "catalog", prefer, cgroup);
Packit Service a31ea6
    } else if (xmlStrEqual(cur->name, BAD_CAST "delegateSystem")) {
Packit Service a31ea6
	entry = xmlParseXMLCatalogOneNode(cur, XML_CATA_DELEGATE_SYSTEM,
Packit Service a31ea6
		BAD_CAST "delegateSystem", BAD_CAST "systemIdStartString",
Packit Service a31ea6
		BAD_CAST "catalog", prefer, cgroup);
Packit Service a31ea6
    } else if (xmlStrEqual(cur->name, BAD_CAST "uri")) {
Packit Service a31ea6
	entry = xmlParseXMLCatalogOneNode(cur, XML_CATA_URI,
Packit Service a31ea6
		BAD_CAST "uri", BAD_CAST "name",
Packit Service a31ea6
		BAD_CAST "uri", prefer, cgroup);
Packit Service a31ea6
    } else if (xmlStrEqual(cur->name, BAD_CAST "rewriteURI")) {
Packit Service a31ea6
	entry = xmlParseXMLCatalogOneNode(cur, XML_CATA_REWRITE_URI,
Packit Service a31ea6
		BAD_CAST "rewriteURI", BAD_CAST "uriStartString",
Packit Service a31ea6
		BAD_CAST "rewritePrefix", prefer, cgroup);
Packit Service a31ea6
    } else if (xmlStrEqual(cur->name, BAD_CAST "delegateURI")) {
Packit Service a31ea6
	entry = xmlParseXMLCatalogOneNode(cur, XML_CATA_DELEGATE_URI,
Packit Service a31ea6
		BAD_CAST "delegateURI", BAD_CAST "uriStartString",
Packit Service a31ea6
		BAD_CAST "catalog", prefer, cgroup);
Packit Service a31ea6
    } else if (xmlStrEqual(cur->name, BAD_CAST "nextCatalog")) {
Packit Service a31ea6
	entry = xmlParseXMLCatalogOneNode(cur, XML_CATA_NEXT_CATALOG,
Packit Service a31ea6
		BAD_CAST "nextCatalog", NULL,
Packit Service a31ea6
		BAD_CAST "catalog", prefer, cgroup);
Packit Service a31ea6
    }
Packit Service a31ea6
    if (entry != NULL) {
Packit Service a31ea6
        if (parent != NULL) {
Packit Service a31ea6
	    entry->parent = parent;
Packit Service a31ea6
	    if (parent->children == NULL)
Packit Service a31ea6
		parent->children = entry;
Packit Service a31ea6
	    else {
Packit Service a31ea6
		xmlCatalogEntryPtr prev;
Packit Service a31ea6
Packit Service a31ea6
		prev = parent->children;
Packit Service a31ea6
		while (prev->next != NULL)
Packit Service a31ea6
		    prev = prev->next;
Packit Service a31ea6
		prev->next = entry;
Packit Service a31ea6
	    }
Packit Service a31ea6
	}
Packit Service a31ea6
	if (entry->type == XML_CATA_GROUP) {
Packit Service a31ea6
	    /*
Packit Service a31ea6
	     * Recurse to propagate prefer to the subtree
Packit Service a31ea6
	     * (xml:base handling is automated)
Packit Service a31ea6
	     */
Packit Service a31ea6
            xmlParseXMLCatalogNodeList(cur->children, prefer, parent, entry);
Packit Service a31ea6
	}
Packit Service a31ea6
    }
Packit Service a31ea6
    if (base != NULL)
Packit Service a31ea6
	xmlFree(base);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlParseXMLCatalogNodeList:
Packit Service a31ea6
 * @cur:  the XML node list of siblings
Packit Service a31ea6
 * @prefer:  the PUBLIC vs. SYSTEM current preference value
Packit Service a31ea6
 * @parent:  the parent Catalog entry
Packit Service a31ea6
 * @cgroup:  the group which includes this list
Packit Service a31ea6
 *
Packit Service a31ea6
 * Examines a list of XML sibling nodes of a catalog and build
Packit Service a31ea6
 * a list of Catalog entry from it adding it to the parent.
Packit Service a31ea6
 * The examination will recurse to examine node subtrees.
Packit Service a31ea6
 */
Packit Service a31ea6
static void
Packit Service a31ea6
xmlParseXMLCatalogNodeList(xmlNodePtr cur, xmlCatalogPrefer prefer,
Packit Service a31ea6
	                   xmlCatalogEntryPtr parent, xmlCatalogEntryPtr cgroup) {
Packit Service a31ea6
    while (cur != NULL) {
Packit Service a31ea6
	if ((cur->ns != NULL) && (cur->ns->href != NULL) &&
Packit Service a31ea6
	    (xmlStrEqual(cur->ns->href, XML_CATALOGS_NAMESPACE))) {
Packit Service a31ea6
	    xmlParseXMLCatalogNode(cur, prefer, parent, cgroup);
Packit Service a31ea6
	}
Packit Service a31ea6
	cur = cur->next;
Packit Service a31ea6
    }
Packit Service a31ea6
    /* TODO: sort the list according to REWRITE lengths and prefer value */
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlParseXMLCatalogFile:
Packit Service a31ea6
 * @prefer:  the PUBLIC vs. SYSTEM current preference value
Packit Service a31ea6
 * @filename:  the filename for the catalog
Packit Service a31ea6
 *
Packit Service a31ea6
 * Parses the catalog file to extract the XML tree and then analyze the
Packit Service a31ea6
 * tree to build a list of Catalog entries corresponding to this catalog
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the resulting Catalog entries list
Packit Service a31ea6
 */
Packit Service a31ea6
static xmlCatalogEntryPtr
Packit Service a31ea6
xmlParseXMLCatalogFile(xmlCatalogPrefer prefer, const xmlChar *filename) {
Packit Service a31ea6
    xmlDocPtr doc;
Packit Service a31ea6
    xmlNodePtr cur;
Packit Service a31ea6
    xmlChar *prop;
Packit Service a31ea6
    xmlCatalogEntryPtr parent = NULL;
Packit Service a31ea6
Packit Service a31ea6
    if (filename == NULL)
Packit Service a31ea6
        return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    doc = xmlParseCatalogFile((const char *) filename);
Packit Service a31ea6
    if (doc == NULL) {
Packit Service a31ea6
	if (xmlDebugCatalogs)
Packit Service a31ea6
	    xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		    "Failed to parse catalog %s\n", filename);
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    if (xmlDebugCatalogs)
Packit Service a31ea6
	xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		"%d Parsing catalog %s\n", xmlGetThreadId(), filename);
Packit Service a31ea6
Packit Service a31ea6
    cur = xmlDocGetRootElement(doc);
Packit Service a31ea6
    if ((cur != NULL) && (xmlStrEqual(cur->name, BAD_CAST "catalog")) &&
Packit Service a31ea6
	(cur->ns != NULL) && (cur->ns->href != NULL) &&
Packit Service a31ea6
	(xmlStrEqual(cur->ns->href, XML_CATALOGS_NAMESPACE))) {
Packit Service a31ea6
Packit Service a31ea6
	parent = xmlNewCatalogEntry(XML_CATA_CATALOG, NULL,
Packit Service a31ea6
				    (const xmlChar *)filename, NULL, prefer, NULL);
Packit Service a31ea6
        if (parent == NULL) {
Packit Service a31ea6
	    xmlFreeDoc(doc);
Packit Service a31ea6
	    return(NULL);
Packit Service a31ea6
	}
Packit Service a31ea6
Packit Service a31ea6
	prop = xmlGetProp(cur, BAD_CAST "prefer");
Packit Service a31ea6
	if (prop != NULL) {
Packit Service a31ea6
	    if (xmlStrEqual(prop, BAD_CAST "system")) {
Packit Service a31ea6
		prefer = XML_CATA_PREFER_SYSTEM;
Packit Service a31ea6
	    } else if (xmlStrEqual(prop, BAD_CAST "public")) {
Packit Service a31ea6
		prefer = XML_CATA_PREFER_PUBLIC;
Packit Service a31ea6
	    } else {
Packit Service a31ea6
		xmlCatalogErr(NULL, cur, XML_CATALOG_PREFER_VALUE,
Packit Service a31ea6
			      "Invalid value for prefer: '%s'\n",
Packit Service a31ea6
			      prop, NULL, NULL);
Packit Service a31ea6
	    }
Packit Service a31ea6
	    xmlFree(prop);
Packit Service a31ea6
	}
Packit Service a31ea6
	cur = cur->children;
Packit Service a31ea6
	xmlParseXMLCatalogNodeList(cur, prefer, parent, NULL);
Packit Service a31ea6
    } else {
Packit Service a31ea6
	xmlCatalogErr(NULL, (xmlNodePtr) doc, XML_CATALOG_NOT_CATALOG,
Packit Service a31ea6
		      "File %s is not an XML Catalog\n",
Packit Service a31ea6
		      filename, NULL, NULL);
Packit Service a31ea6
	xmlFreeDoc(doc);
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
    xmlFreeDoc(doc);
Packit Service a31ea6
    return(parent);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlFetchXMLCatalogFile:
Packit Service a31ea6
 * @catal:  an existing but incomplete catalog entry
Packit Service a31ea6
 *
Packit Service a31ea6
 * Fetch and parse the subcatalog referenced by an entry
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns 0 in case of success, -1 otherwise
Packit Service a31ea6
 */
Packit Service a31ea6
static int
Packit Service a31ea6
xmlFetchXMLCatalogFile(xmlCatalogEntryPtr catal) {
Packit Service a31ea6
    xmlCatalogEntryPtr doc;
Packit Service a31ea6
Packit Service a31ea6
    if (catal == NULL)
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
    if (catal->URL == NULL)
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
Packit Service a31ea6
    /*
Packit Service a31ea6
     * lock the whole catalog for modification
Packit Service a31ea6
     */
Packit Service a31ea6
    xmlRMutexLock(xmlCatalogMutex);
Packit Service a31ea6
    if (catal->children != NULL) {
Packit Service a31ea6
	/* Okay someone else did it in the meantime */
Packit Service a31ea6
	xmlRMutexUnlock(xmlCatalogMutex);
Packit Service a31ea6
	return(0);
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    if (xmlCatalogXMLFiles != NULL) {
Packit Service a31ea6
	doc = (xmlCatalogEntryPtr)
Packit Service a31ea6
	    xmlHashLookup(xmlCatalogXMLFiles, catal->URL);
Packit Service a31ea6
	if (doc != NULL) {
Packit Service a31ea6
	    if (xmlDebugCatalogs)
Packit Service a31ea6
		xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		    "Found %s in file hash\n", catal->URL);
Packit Service a31ea6
Packit Service a31ea6
	    if (catal->type == XML_CATA_CATALOG)
Packit Service a31ea6
		catal->children = doc->children;
Packit Service a31ea6
	    else
Packit Service a31ea6
		catal->children = doc;
Packit Service a31ea6
	    catal->dealloc = 0;
Packit Service a31ea6
	    xmlRMutexUnlock(xmlCatalogMutex);
Packit Service a31ea6
	    return(0);
Packit Service a31ea6
	}
Packit Service a31ea6
	if (xmlDebugCatalogs)
Packit Service a31ea6
	    xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		"%s not found in file hash\n", catal->URL);
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    /*
Packit Service a31ea6
     * Fetch and parse. Note that xmlParseXMLCatalogFile does not
Packit Service a31ea6
     * use the existing catalog, there is no recursion allowed at
Packit Service a31ea6
     * that level.
Packit Service a31ea6
     */
Packit Service a31ea6
    doc = xmlParseXMLCatalogFile(catal->prefer, catal->URL);
Packit Service a31ea6
    if (doc == NULL) {
Packit Service a31ea6
	catal->type = XML_CATA_BROKEN_CATALOG;
Packit Service a31ea6
	xmlRMutexUnlock(xmlCatalogMutex);
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    if (catal->type == XML_CATA_CATALOG)
Packit Service a31ea6
	catal->children = doc->children;
Packit Service a31ea6
    else
Packit Service a31ea6
	catal->children = doc;
Packit Service a31ea6
Packit Service a31ea6
    doc->dealloc = 1;
Packit Service a31ea6
Packit Service a31ea6
    if (xmlCatalogXMLFiles == NULL)
Packit Service a31ea6
	xmlCatalogXMLFiles = xmlHashCreate(10);
Packit Service a31ea6
    if (xmlCatalogXMLFiles != NULL) {
Packit Service a31ea6
	if (xmlDebugCatalogs)
Packit Service a31ea6
	    xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		"%s added to file hash\n", catal->URL);
Packit Service a31ea6
	xmlHashAddEntry(xmlCatalogXMLFiles, catal->URL, doc);
Packit Service a31ea6
    }
Packit Service a31ea6
    xmlRMutexUnlock(xmlCatalogMutex);
Packit Service a31ea6
    return(0);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/************************************************************************
Packit Service a31ea6
 *									*
Packit Service a31ea6
 *			XML Catalog handling				*
Packit Service a31ea6
 *									*
Packit Service a31ea6
 ************************************************************************/
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlAddXMLCatalog:
Packit Service a31ea6
 * @catal:  top of an XML catalog
Packit Service a31ea6
 * @type:  the type of record to add to the catalog
Packit Service a31ea6
 * @orig:  the system, public or prefix to match (or NULL)
Packit Service a31ea6
 * @replace:  the replacement value for the match
Packit Service a31ea6
 *
Packit Service a31ea6
 * Add an entry in the XML catalog, it may overwrite existing but
Packit Service a31ea6
 * different entries.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns 0 if successful, -1 otherwise
Packit Service a31ea6
 */
Packit Service a31ea6
static int
Packit Service a31ea6
xmlAddXMLCatalog(xmlCatalogEntryPtr catal, const xmlChar *type,
Packit Service a31ea6
	      const xmlChar *orig, const xmlChar *replace) {
Packit Service a31ea6
    xmlCatalogEntryPtr cur;
Packit Service a31ea6
    xmlCatalogEntryType typ;
Packit Service a31ea6
    int doregister = 0;
Packit Service a31ea6
Packit Service a31ea6
    if ((catal == NULL) ||
Packit Service a31ea6
	((catal->type != XML_CATA_CATALOG) &&
Packit Service a31ea6
	 (catal->type != XML_CATA_BROKEN_CATALOG)))
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
    if (catal->children == NULL) {
Packit Service a31ea6
	xmlFetchXMLCatalogFile(catal);
Packit Service a31ea6
    }
Packit Service a31ea6
    if (catal->children == NULL)
Packit Service a31ea6
	doregister = 1;
Packit Service a31ea6
Packit Service a31ea6
    typ = xmlGetXMLCatalogEntryType(type);
Packit Service a31ea6
    if (typ == XML_CATA_NONE) {
Packit Service a31ea6
	if (xmlDebugCatalogs)
Packit Service a31ea6
	    xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		    "Failed to add unknown element %s to catalog\n", type);
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    cur = catal->children;
Packit Service a31ea6
    /*
Packit Service a31ea6
     * Might be a simple "update in place"
Packit Service a31ea6
     */
Packit Service a31ea6
    if (cur != NULL) {
Packit Service a31ea6
	while (cur != NULL) {
Packit Service a31ea6
	    if ((orig != NULL) && (cur->type == typ) &&
Packit Service a31ea6
		(xmlStrEqual(orig, cur->name))) {
Packit Service a31ea6
		if (xmlDebugCatalogs)
Packit Service a31ea6
		    xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			    "Updating element %s to catalog\n", type);
Packit Service a31ea6
		if (cur->value != NULL)
Packit Service a31ea6
		    xmlFree(cur->value);
Packit Service a31ea6
		if (cur->URL != NULL)
Packit Service a31ea6
		    xmlFree(cur->URL);
Packit Service a31ea6
		cur->value = xmlStrdup(replace);
Packit Service a31ea6
		cur->URL = xmlStrdup(replace);
Packit Service a31ea6
		return(0);
Packit Service a31ea6
	    }
Packit Service a31ea6
	    if (cur->next == NULL)
Packit Service a31ea6
		break;
Packit Service a31ea6
	    cur = cur->next;
Packit Service a31ea6
	}
Packit Service a31ea6
    }
Packit Service a31ea6
    if (xmlDebugCatalogs)
Packit Service a31ea6
	xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		"Adding element %s to catalog\n", type);
Packit Service a31ea6
    if (cur == NULL)
Packit Service a31ea6
	catal->children = xmlNewCatalogEntry(typ, orig, replace,
Packit Service a31ea6
		                             NULL, catal->prefer, NULL);
Packit Service a31ea6
    else
Packit Service a31ea6
	cur->next = xmlNewCatalogEntry(typ, orig, replace,
Packit Service a31ea6
		                       NULL, catal->prefer, NULL);
Packit Service a31ea6
    if (doregister) {
Packit Service a31ea6
        catal->type = XML_CATA_CATALOG;
Packit Service a31ea6
	cur = (xmlCatalogEntryPtr)xmlHashLookup(xmlCatalogXMLFiles, catal->URL);
Packit Service a31ea6
	if (cur != NULL)
Packit Service a31ea6
	    cur->children = catal->children;
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    return(0);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlDelXMLCatalog:
Packit Service a31ea6
 * @catal:  top of an XML catalog
Packit Service a31ea6
 * @value:  the value to remove from the catalog
Packit Service a31ea6
 *
Packit Service a31ea6
 * Remove entries in the XML catalog where the value or the URI
Packit Service a31ea6
 * is equal to @value
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the number of entries removed if successful, -1 otherwise
Packit Service a31ea6
 */
Packit Service a31ea6
static int
Packit Service a31ea6
xmlDelXMLCatalog(xmlCatalogEntryPtr catal, const xmlChar *value) {
Packit Service a31ea6
    xmlCatalogEntryPtr cur;
Packit Service a31ea6
    int ret = 0;
Packit Service a31ea6
Packit Service a31ea6
    if ((catal == NULL) ||
Packit Service a31ea6
	((catal->type != XML_CATA_CATALOG) &&
Packit Service a31ea6
	 (catal->type != XML_CATA_BROKEN_CATALOG)))
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
    if (value == NULL)
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
    if (catal->children == NULL) {
Packit Service a31ea6
	xmlFetchXMLCatalogFile(catal);
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    /*
Packit Service a31ea6
     * Scan the children
Packit Service a31ea6
     */
Packit Service a31ea6
    cur = catal->children;
Packit Service a31ea6
    while (cur != NULL) {
Packit Service a31ea6
	if (((cur->name != NULL) && (xmlStrEqual(value, cur->name))) ||
Packit Service a31ea6
	    (xmlStrEqual(value, cur->value))) {
Packit Service a31ea6
	    if (xmlDebugCatalogs) {
Packit Service a31ea6
		if (cur->name != NULL)
Packit Service a31ea6
		    xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			    "Removing element %s from catalog\n", cur->name);
Packit Service a31ea6
		else
Packit Service a31ea6
		    xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			    "Removing element %s from catalog\n", cur->value);
Packit Service a31ea6
	    }
Packit Service a31ea6
	    cur->type = XML_CATA_REMOVED;
Packit Service a31ea6
	}
Packit Service a31ea6
	cur = cur->next;
Packit Service a31ea6
    }
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogXMLResolve:
Packit Service a31ea6
 * @catal:  a catalog list
Packit Service a31ea6
 * @pubID:  the public ID string
Packit Service a31ea6
 * @sysID:  the system ID string
Packit Service a31ea6
 *
Packit Service a31ea6
 * Do a complete resolution lookup of an External Identifier for a
Packit Service a31ea6
 * list of catalog entries.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Implements (or tries to) 7.1. External Identifier Resolution
Packit Service a31ea6
 * from http://www.oasis-open.org/committees/entity/spec-2001-08-06.html
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the URI of the resource or NULL if not found
Packit Service a31ea6
 */
Packit Service a31ea6
static xmlChar *
Packit Service a31ea6
xmlCatalogXMLResolve(xmlCatalogEntryPtr catal, const xmlChar *pubID,
Packit Service a31ea6
	              const xmlChar *sysID) {
Packit Service a31ea6
    xmlChar *ret = NULL;
Packit Service a31ea6
    xmlCatalogEntryPtr cur;
Packit Service a31ea6
    int haveDelegate = 0;
Packit Service a31ea6
    int haveNext = 0;
Packit Service a31ea6
Packit Service a31ea6
    /*
Packit Service a31ea6
     * protection against loops
Packit Service a31ea6
     */
Packit Service a31ea6
    if (catal->depth > MAX_CATAL_DEPTH) {
Packit Service a31ea6
	xmlCatalogErr(catal, NULL, XML_CATALOG_RECURSION,
Packit Service a31ea6
		      "Detected recursion in catalog %s\n",
Packit Service a31ea6
		      catal->name, NULL, NULL);
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
    catal->depth++;
Packit Service a31ea6
Packit Service a31ea6
    /*
Packit Service a31ea6
     * First tries steps 2/ 3/ 4/ if a system ID is provided.
Packit Service a31ea6
     */
Packit Service a31ea6
    if (sysID != NULL) {
Packit Service a31ea6
	xmlCatalogEntryPtr rewrite = NULL;
Packit Service a31ea6
	int lenrewrite = 0, len;
Packit Service a31ea6
	cur = catal;
Packit Service a31ea6
	haveDelegate = 0;
Packit Service a31ea6
	while (cur != NULL) {
Packit Service a31ea6
	    switch (cur->type) {
Packit Service a31ea6
		case XML_CATA_SYSTEM:
Packit Service a31ea6
		    if (xmlStrEqual(sysID, cur->name)) {
Packit Service a31ea6
			if (xmlDebugCatalogs)
Packit Service a31ea6
			    xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
				    "Found system match %s, using %s\n",
Packit Service a31ea6
				            cur->name, cur->URL);
Packit Service a31ea6
			catal->depth--;
Packit Service a31ea6
			return(xmlStrdup(cur->URL));
Packit Service a31ea6
		    }
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case XML_CATA_REWRITE_SYSTEM:
Packit Service a31ea6
		    len = xmlStrlen(cur->name);
Packit Service a31ea6
		    if ((len > lenrewrite) &&
Packit Service a31ea6
			(!xmlStrncmp(sysID, cur->name, len))) {
Packit Service a31ea6
			lenrewrite = len;
Packit Service a31ea6
			rewrite = cur;
Packit Service a31ea6
		    }
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case XML_CATA_DELEGATE_SYSTEM:
Packit Service a31ea6
		    if (!xmlStrncmp(sysID, cur->name, xmlStrlen(cur->name)))
Packit Service a31ea6
			haveDelegate++;
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case XML_CATA_NEXT_CATALOG:
Packit Service a31ea6
		    haveNext++;
Packit Service a31ea6
		    break;
Packit Service a31ea6
		default:
Packit Service a31ea6
		    break;
Packit Service a31ea6
	    }
Packit Service a31ea6
	    cur = cur->next;
Packit Service a31ea6
	}
Packit Service a31ea6
	if (rewrite != NULL) {
Packit Service a31ea6
	    if (xmlDebugCatalogs)
Packit Service a31ea6
		xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			"Using rewriting rule %s\n", rewrite->name);
Packit Service a31ea6
	    ret = xmlStrdup(rewrite->URL);
Packit Service a31ea6
	    if (ret != NULL)
Packit Service a31ea6
		ret = xmlStrcat(ret, &sysID[lenrewrite]);
Packit Service a31ea6
	    catal->depth--;
Packit Service a31ea6
	    return(ret);
Packit Service a31ea6
	}
Packit Service a31ea6
	if (haveDelegate) {
Packit Service a31ea6
	    const xmlChar *delegates[MAX_DELEGATE];
Packit Service a31ea6
	    int nbList = 0, i;
Packit Service a31ea6
Packit Service a31ea6
	    /*
Packit Service a31ea6
	     * Assume the entries have been sorted by decreasing substring
Packit Service a31ea6
	     * matches when the list was produced.
Packit Service a31ea6
	     */
Packit Service a31ea6
	    cur = catal;
Packit Service a31ea6
	    while (cur != NULL) {
Packit Service a31ea6
		if ((cur->type == XML_CATA_DELEGATE_SYSTEM) &&
Packit Service a31ea6
		    (!xmlStrncmp(sysID, cur->name, xmlStrlen(cur->name)))) {
Packit Service a31ea6
		    for (i = 0;i < nbList;i++)
Packit Service a31ea6
			if (xmlStrEqual(cur->URL, delegates[i]))
Packit Service a31ea6
			    break;
Packit Service a31ea6
		    if (i < nbList) {
Packit Service a31ea6
			cur = cur->next;
Packit Service a31ea6
			continue;
Packit Service a31ea6
		    }
Packit Service a31ea6
		    if (nbList < MAX_DELEGATE)
Packit Service a31ea6
			delegates[nbList++] = cur->URL;
Packit Service a31ea6
Packit Service a31ea6
		    if (cur->children == NULL) {
Packit Service a31ea6
			xmlFetchXMLCatalogFile(cur);
Packit Service a31ea6
		    }
Packit Service a31ea6
		    if (cur->children != NULL) {
Packit Service a31ea6
			if (xmlDebugCatalogs)
Packit Service a31ea6
			    xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
				    "Trying system delegate %s\n", cur->URL);
Packit Service a31ea6
			ret = xmlCatalogListXMLResolve(
Packit Service a31ea6
				cur->children, NULL, sysID);
Packit Service a31ea6
			if (ret != NULL) {
Packit Service a31ea6
			    catal->depth--;
Packit Service a31ea6
			    return(ret);
Packit Service a31ea6
			}
Packit Service a31ea6
		    }
Packit Service a31ea6
		}
Packit Service a31ea6
		cur = cur->next;
Packit Service a31ea6
	    }
Packit Service a31ea6
	    /*
Packit Service a31ea6
	     * Apply the cut algorithm explained in 4/
Packit Service a31ea6
	     */
Packit Service a31ea6
	    catal->depth--;
Packit Service a31ea6
	    return(XML_CATAL_BREAK);
Packit Service a31ea6
	}
Packit Service a31ea6
    }
Packit Service a31ea6
    /*
Packit Service a31ea6
     * Then tries 5/ 6/ if a public ID is provided
Packit Service a31ea6
     */
Packit Service a31ea6
    if (pubID != NULL) {
Packit Service a31ea6
	cur = catal;
Packit Service a31ea6
	haveDelegate = 0;
Packit Service a31ea6
	while (cur != NULL) {
Packit Service a31ea6
	    switch (cur->type) {
Packit Service a31ea6
		case XML_CATA_PUBLIC:
Packit Service a31ea6
		    if (xmlStrEqual(pubID, cur->name)) {
Packit Service a31ea6
			if (xmlDebugCatalogs)
Packit Service a31ea6
			    xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
				    "Found public match %s\n", cur->name);
Packit Service a31ea6
			catal->depth--;
Packit Service a31ea6
			return(xmlStrdup(cur->URL));
Packit Service a31ea6
		    }
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case XML_CATA_DELEGATE_PUBLIC:
Packit Service a31ea6
		    if (!xmlStrncmp(pubID, cur->name, xmlStrlen(cur->name)) &&
Packit Service a31ea6
			(cur->prefer == XML_CATA_PREFER_PUBLIC))
Packit Service a31ea6
			haveDelegate++;
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case XML_CATA_NEXT_CATALOG:
Packit Service a31ea6
		    if (sysID == NULL)
Packit Service a31ea6
			haveNext++;
Packit Service a31ea6
		    break;
Packit Service a31ea6
		default:
Packit Service a31ea6
		    break;
Packit Service a31ea6
	    }
Packit Service a31ea6
	    cur = cur->next;
Packit Service a31ea6
	}
Packit Service a31ea6
	if (haveDelegate) {
Packit Service a31ea6
	    const xmlChar *delegates[MAX_DELEGATE];
Packit Service a31ea6
	    int nbList = 0, i;
Packit Service a31ea6
Packit Service a31ea6
	    /*
Packit Service a31ea6
	     * Assume the entries have been sorted by decreasing substring
Packit Service a31ea6
	     * matches when the list was produced.
Packit Service a31ea6
	     */
Packit Service a31ea6
	    cur = catal;
Packit Service a31ea6
	    while (cur != NULL) {
Packit Service a31ea6
		if ((cur->type == XML_CATA_DELEGATE_PUBLIC) &&
Packit Service a31ea6
		    (cur->prefer == XML_CATA_PREFER_PUBLIC) &&
Packit Service a31ea6
		    (!xmlStrncmp(pubID, cur->name, xmlStrlen(cur->name)))) {
Packit Service a31ea6
Packit Service a31ea6
		    for (i = 0;i < nbList;i++)
Packit Service a31ea6
			if (xmlStrEqual(cur->URL, delegates[i]))
Packit Service a31ea6
			    break;
Packit Service a31ea6
		    if (i < nbList) {
Packit Service a31ea6
			cur = cur->next;
Packit Service a31ea6
			continue;
Packit Service a31ea6
		    }
Packit Service a31ea6
		    if (nbList < MAX_DELEGATE)
Packit Service a31ea6
			delegates[nbList++] = cur->URL;
Packit Service a31ea6
Packit Service a31ea6
		    if (cur->children == NULL) {
Packit Service a31ea6
			xmlFetchXMLCatalogFile(cur);
Packit Service a31ea6
		    }
Packit Service a31ea6
		    if (cur->children != NULL) {
Packit Service a31ea6
			if (xmlDebugCatalogs)
Packit Service a31ea6
			    xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
				    "Trying public delegate %s\n", cur->URL);
Packit Service a31ea6
			ret = xmlCatalogListXMLResolve(
Packit Service a31ea6
				cur->children, pubID, NULL);
Packit Service a31ea6
			if (ret != NULL) {
Packit Service a31ea6
			    catal->depth--;
Packit Service a31ea6
			    return(ret);
Packit Service a31ea6
			}
Packit Service a31ea6
		    }
Packit Service a31ea6
		}
Packit Service a31ea6
		cur = cur->next;
Packit Service a31ea6
	    }
Packit Service a31ea6
	    /*
Packit Service a31ea6
	     * Apply the cut algorithm explained in 4/
Packit Service a31ea6
	     */
Packit Service a31ea6
	    catal->depth--;
Packit Service a31ea6
	    return(XML_CATAL_BREAK);
Packit Service a31ea6
	}
Packit Service a31ea6
    }
Packit Service a31ea6
    if (haveNext) {
Packit Service a31ea6
	cur = catal;
Packit Service a31ea6
	while (cur != NULL) {
Packit Service a31ea6
	    if (cur->type == XML_CATA_NEXT_CATALOG) {
Packit Service a31ea6
		if (cur->children == NULL) {
Packit Service a31ea6
		    xmlFetchXMLCatalogFile(cur);
Packit Service a31ea6
		}
Packit Service a31ea6
		if (cur->children != NULL) {
Packit Service a31ea6
		    ret = xmlCatalogListXMLResolve(cur->children, pubID, sysID);
Packit Service a31ea6
		    if (ret != NULL) {
Packit Service a31ea6
			catal->depth--;
Packit Service a31ea6
			return(ret);
Packit Service a31ea6
		    } else if (catal->depth > MAX_CATAL_DEPTH) {
Packit Service a31ea6
		        return(NULL);
Packit Service a31ea6
		    }
Packit Service a31ea6
		}
Packit Service a31ea6
	    }
Packit Service a31ea6
	    cur = cur->next;
Packit Service a31ea6
	}
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    catal->depth--;
Packit Service a31ea6
    return(NULL);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogXMLResolveURI:
Packit Service a31ea6
 * @catal:  a catalog list
Packit Service a31ea6
 * @URI:  the URI
Packit Service a31ea6
 * @sysID:  the system ID string
Packit Service a31ea6
 *
Packit Service a31ea6
 * Do a complete resolution lookup of an External Identifier for a
Packit Service a31ea6
 * list of catalog entries.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Implements (or tries to) 7.2.2. URI Resolution
Packit Service a31ea6
 * from http://www.oasis-open.org/committees/entity/spec-2001-08-06.html
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the URI of the resource or NULL if not found
Packit Service a31ea6
 */
Packit Service a31ea6
static xmlChar *
Packit Service a31ea6
xmlCatalogXMLResolveURI(xmlCatalogEntryPtr catal, const xmlChar *URI) {
Packit Service a31ea6
    xmlChar *ret = NULL;
Packit Service a31ea6
    xmlCatalogEntryPtr cur;
Packit Service a31ea6
    int haveDelegate = 0;
Packit Service a31ea6
    int haveNext = 0;
Packit Service a31ea6
    xmlCatalogEntryPtr rewrite = NULL;
Packit Service a31ea6
    int lenrewrite = 0, len;
Packit Service a31ea6
Packit Service a31ea6
    if (catal == NULL)
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    if (URI == NULL)
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    if (catal->depth > MAX_CATAL_DEPTH) {
Packit Service a31ea6
	xmlCatalogErr(catal, NULL, XML_CATALOG_RECURSION,
Packit Service a31ea6
		      "Detected recursion in catalog %s\n",
Packit Service a31ea6
		      catal->name, NULL, NULL);
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    /*
Packit Service a31ea6
     * First tries steps 2/ 3/ 4/ if a system ID is provided.
Packit Service a31ea6
     */
Packit Service a31ea6
    cur = catal;
Packit Service a31ea6
    haveDelegate = 0;
Packit Service a31ea6
    while (cur != NULL) {
Packit Service a31ea6
	switch (cur->type) {
Packit Service a31ea6
	    case XML_CATA_URI:
Packit Service a31ea6
		if (xmlStrEqual(URI, cur->name)) {
Packit Service a31ea6
		    if (xmlDebugCatalogs)
Packit Service a31ea6
			xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
				"Found URI match %s\n", cur->name);
Packit Service a31ea6
		    return(xmlStrdup(cur->URL));
Packit Service a31ea6
		}
Packit Service a31ea6
		break;
Packit Service a31ea6
	    case XML_CATA_REWRITE_URI:
Packit Service a31ea6
		len = xmlStrlen(cur->name);
Packit Service a31ea6
		if ((len > lenrewrite) &&
Packit Service a31ea6
		    (!xmlStrncmp(URI, cur->name, len))) {
Packit Service a31ea6
		    lenrewrite = len;
Packit Service a31ea6
		    rewrite = cur;
Packit Service a31ea6
		}
Packit Service a31ea6
		break;
Packit Service a31ea6
	    case XML_CATA_DELEGATE_URI:
Packit Service a31ea6
		if (!xmlStrncmp(URI, cur->name, xmlStrlen(cur->name)))
Packit Service a31ea6
		    haveDelegate++;
Packit Service a31ea6
		break;
Packit Service a31ea6
	    case XML_CATA_NEXT_CATALOG:
Packit Service a31ea6
		haveNext++;
Packit Service a31ea6
		break;
Packit Service a31ea6
	    default:
Packit Service a31ea6
		break;
Packit Service a31ea6
	}
Packit Service a31ea6
	cur = cur->next;
Packit Service a31ea6
    }
Packit Service a31ea6
    if (rewrite != NULL) {
Packit Service a31ea6
	if (xmlDebugCatalogs)
Packit Service a31ea6
	    xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		    "Using rewriting rule %s\n", rewrite->name);
Packit Service a31ea6
	ret = xmlStrdup(rewrite->URL);
Packit Service a31ea6
	if (ret != NULL)
Packit Service a31ea6
	    ret = xmlStrcat(ret, &URI[lenrewrite]);
Packit Service a31ea6
	return(ret);
Packit Service a31ea6
    }
Packit Service a31ea6
    if (haveDelegate) {
Packit Service a31ea6
	const xmlChar *delegates[MAX_DELEGATE];
Packit Service a31ea6
	int nbList = 0, i;
Packit Service a31ea6
Packit Service a31ea6
	/*
Packit Service a31ea6
	 * Assume the entries have been sorted by decreasing substring
Packit Service a31ea6
	 * matches when the list was produced.
Packit Service a31ea6
	 */
Packit Service a31ea6
	cur = catal;
Packit Service a31ea6
	while (cur != NULL) {
Packit Service a31ea6
	    if (((cur->type == XML_CATA_DELEGATE_SYSTEM) ||
Packit Service a31ea6
	         (cur->type == XML_CATA_DELEGATE_URI)) &&
Packit Service a31ea6
		(!xmlStrncmp(URI, cur->name, xmlStrlen(cur->name)))) {
Packit Service a31ea6
		for (i = 0;i < nbList;i++)
Packit Service a31ea6
		    if (xmlStrEqual(cur->URL, delegates[i]))
Packit Service a31ea6
			break;
Packit Service a31ea6
		if (i < nbList) {
Packit Service a31ea6
		    cur = cur->next;
Packit Service a31ea6
		    continue;
Packit Service a31ea6
		}
Packit Service a31ea6
		if (nbList < MAX_DELEGATE)
Packit Service a31ea6
		    delegates[nbList++] = cur->URL;
Packit Service a31ea6
Packit Service a31ea6
		if (cur->children == NULL) {
Packit Service a31ea6
		    xmlFetchXMLCatalogFile(cur);
Packit Service a31ea6
		}
Packit Service a31ea6
		if (cur->children != NULL) {
Packit Service a31ea6
		    if (xmlDebugCatalogs)
Packit Service a31ea6
			xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
				"Trying URI delegate %s\n", cur->URL);
Packit Service a31ea6
		    ret = xmlCatalogListXMLResolveURI(
Packit Service a31ea6
			    cur->children, URI);
Packit Service a31ea6
		    if (ret != NULL)
Packit Service a31ea6
			return(ret);
Packit Service a31ea6
		}
Packit Service a31ea6
	    }
Packit Service a31ea6
	    cur = cur->next;
Packit Service a31ea6
	}
Packit Service a31ea6
	/*
Packit Service a31ea6
	 * Apply the cut algorithm explained in 4/
Packit Service a31ea6
	 */
Packit Service a31ea6
	return(XML_CATAL_BREAK);
Packit Service a31ea6
    }
Packit Service a31ea6
    if (haveNext) {
Packit Service a31ea6
	cur = catal;
Packit Service a31ea6
	while (cur != NULL) {
Packit Service a31ea6
	    if (cur->type == XML_CATA_NEXT_CATALOG) {
Packit Service a31ea6
		if (cur->children == NULL) {
Packit Service a31ea6
		    xmlFetchXMLCatalogFile(cur);
Packit Service a31ea6
		}
Packit Service a31ea6
		if (cur->children != NULL) {
Packit Service a31ea6
		    ret = xmlCatalogListXMLResolveURI(cur->children, URI);
Packit Service a31ea6
		    if (ret != NULL)
Packit Service a31ea6
			return(ret);
Packit Service a31ea6
		}
Packit Service a31ea6
	    }
Packit Service a31ea6
	    cur = cur->next;
Packit Service a31ea6
	}
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    return(NULL);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogListXMLResolve:
Packit Service a31ea6
 * @catal:  a catalog list
Packit Service a31ea6
 * @pubID:  the public ID string
Packit Service a31ea6
 * @sysID:  the system ID string
Packit Service a31ea6
 *
Packit Service a31ea6
 * Do a complete resolution lookup of an External Identifier for a
Packit Service a31ea6
 * list of catalogs
Packit Service a31ea6
 *
Packit Service a31ea6
 * Implements (or tries to) 7.1. External Identifier Resolution
Packit Service a31ea6
 * from http://www.oasis-open.org/committees/entity/spec-2001-08-06.html
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the URI of the resource or NULL if not found
Packit Service a31ea6
 */
Packit Service a31ea6
static xmlChar *
Packit Service a31ea6
xmlCatalogListXMLResolve(xmlCatalogEntryPtr catal, const xmlChar *pubID,
Packit Service a31ea6
	              const xmlChar *sysID) {
Packit Service a31ea6
    xmlChar *ret = NULL;
Packit Service a31ea6
    xmlChar *urnID = NULL;
Packit Service a31ea6
    xmlChar *normid;
Packit Service a31ea6
Packit Service a31ea6
    if (catal == NULL)
Packit Service a31ea6
        return(NULL);
Packit Service a31ea6
    if ((pubID == NULL) && (sysID == NULL))
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    normid = xmlCatalogNormalizePublic(pubID);
Packit Service a31ea6
    if (normid != NULL)
Packit Service a31ea6
        pubID = (*normid != 0 ? normid : NULL);
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlStrncmp(pubID, BAD_CAST XML_URN_PUBID, sizeof(XML_URN_PUBID) - 1)) {
Packit Service a31ea6
	urnID = xmlCatalogUnWrapURN(pubID);
Packit Service a31ea6
	if (xmlDebugCatalogs) {
Packit Service a31ea6
	    if (urnID == NULL)
Packit Service a31ea6
		xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			"Public URN ID %s expanded to NULL\n", pubID);
Packit Service a31ea6
	    else
Packit Service a31ea6
		xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			"Public URN ID expanded to %s\n", urnID);
Packit Service a31ea6
	}
Packit Service a31ea6
	ret = xmlCatalogListXMLResolve(catal, urnID, sysID);
Packit Service a31ea6
	if (urnID != NULL)
Packit Service a31ea6
	    xmlFree(urnID);
Packit Service a31ea6
	if (normid != NULL)
Packit Service a31ea6
	    xmlFree(normid);
Packit Service a31ea6
	return(ret);
Packit Service a31ea6
    }
Packit Service a31ea6
    if (!xmlStrncmp(sysID, BAD_CAST XML_URN_PUBID, sizeof(XML_URN_PUBID) - 1)) {
Packit Service a31ea6
	urnID = xmlCatalogUnWrapURN(sysID);
Packit Service a31ea6
	if (xmlDebugCatalogs) {
Packit Service a31ea6
	    if (urnID == NULL)
Packit Service a31ea6
		xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			"System URN ID %s expanded to NULL\n", sysID);
Packit Service a31ea6
	    else
Packit Service a31ea6
		xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			"System URN ID expanded to %s\n", urnID);
Packit Service a31ea6
	}
Packit Service a31ea6
	if (pubID == NULL)
Packit Service a31ea6
	    ret = xmlCatalogListXMLResolve(catal, urnID, NULL);
Packit Service a31ea6
	else if (xmlStrEqual(pubID, urnID))
Packit Service a31ea6
	    ret = xmlCatalogListXMLResolve(catal, pubID, NULL);
Packit Service a31ea6
	else {
Packit Service a31ea6
	    ret = xmlCatalogListXMLResolve(catal, pubID, urnID);
Packit Service a31ea6
	}
Packit Service a31ea6
	if (urnID != NULL)
Packit Service a31ea6
	    xmlFree(urnID);
Packit Service a31ea6
	if (normid != NULL)
Packit Service a31ea6
	    xmlFree(normid);
Packit Service a31ea6
	return(ret);
Packit Service a31ea6
    }
Packit Service a31ea6
    while (catal != NULL) {
Packit Service a31ea6
	if (catal->type == XML_CATA_CATALOG) {
Packit Service a31ea6
	    if (catal->children == NULL) {
Packit Service a31ea6
		xmlFetchXMLCatalogFile(catal);
Packit Service a31ea6
	    }
Packit Service a31ea6
	    if (catal->children != NULL) {
Packit Service a31ea6
		ret = xmlCatalogXMLResolve(catal->children, pubID, sysID);
Packit Service a31ea6
		if (ret != NULL) {
Packit Service a31ea6
		    break;
Packit Service a31ea6
                } else if ((catal->children != NULL) &&
Packit Service a31ea6
		           (catal->children->depth > MAX_CATAL_DEPTH)) {
Packit Service a31ea6
	            ret = NULL;
Packit Service a31ea6
		    break;
Packit Service a31ea6
	        }
Packit Service a31ea6
	    }
Packit Service a31ea6
	}
Packit Service a31ea6
	catal = catal->next;
Packit Service a31ea6
    }
Packit Service a31ea6
    if (normid != NULL)
Packit Service a31ea6
	xmlFree(normid);
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogListXMLResolveURI:
Packit Service a31ea6
 * @catal:  a catalog list
Packit Service a31ea6
 * @URI:  the URI
Packit Service a31ea6
 *
Packit Service a31ea6
 * Do a complete resolution lookup of an URI for a list of catalogs
Packit Service a31ea6
 *
Packit Service a31ea6
 * Implements (or tries to) 7.2. URI Resolution
Packit Service a31ea6
 * from http://www.oasis-open.org/committees/entity/spec-2001-08-06.html
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the URI of the resource or NULL if not found
Packit Service a31ea6
 */
Packit Service a31ea6
static xmlChar *
Packit Service a31ea6
xmlCatalogListXMLResolveURI(xmlCatalogEntryPtr catal, const xmlChar *URI) {
Packit Service a31ea6
    xmlChar *ret = NULL;
Packit Service a31ea6
    xmlChar *urnID = NULL;
Packit Service a31ea6
Packit Service a31ea6
    if (catal == NULL)
Packit Service a31ea6
        return(NULL);
Packit Service a31ea6
    if (URI == NULL)
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlStrncmp(URI, BAD_CAST XML_URN_PUBID, sizeof(XML_URN_PUBID) - 1)) {
Packit Service a31ea6
	urnID = xmlCatalogUnWrapURN(URI);
Packit Service a31ea6
	if (xmlDebugCatalogs) {
Packit Service a31ea6
	    if (urnID == NULL)
Packit Service a31ea6
		xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			"URN ID %s expanded to NULL\n", URI);
Packit Service a31ea6
	    else
Packit Service a31ea6
		xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			"URN ID expanded to %s\n", urnID);
Packit Service a31ea6
	}
Packit Service a31ea6
	ret = xmlCatalogListXMLResolve(catal, urnID, NULL);
Packit Service a31ea6
	if (urnID != NULL)
Packit Service a31ea6
	    xmlFree(urnID);
Packit Service a31ea6
	return(ret);
Packit Service a31ea6
    }
Packit Service a31ea6
    while (catal != NULL) {
Packit Service a31ea6
	if (catal->type == XML_CATA_CATALOG) {
Packit Service a31ea6
	    if (catal->children == NULL) {
Packit Service a31ea6
		xmlFetchXMLCatalogFile(catal);
Packit Service a31ea6
	    }
Packit Service a31ea6
	    if (catal->children != NULL) {
Packit Service a31ea6
		ret = xmlCatalogXMLResolveURI(catal->children, URI);
Packit Service a31ea6
		if (ret != NULL)
Packit Service a31ea6
		    return(ret);
Packit Service a31ea6
	    }
Packit Service a31ea6
	}
Packit Service a31ea6
	catal = catal->next;
Packit Service a31ea6
    }
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/************************************************************************
Packit Service a31ea6
 *									*
Packit Service a31ea6
 *			The SGML Catalog parser				*
Packit Service a31ea6
 *									*
Packit Service a31ea6
 ************************************************************************/
Packit Service a31ea6
Packit Service a31ea6
Packit Service a31ea6
#define RAW *cur
Packit Service a31ea6
#define NEXT cur++;
Packit Service a31ea6
#define SKIP(x) cur += x;
Packit Service a31ea6
Packit Service a31ea6
#define SKIP_BLANKS while (IS_BLANK_CH(*cur)) NEXT;
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlParseSGMLCatalogComment:
Packit Service a31ea6
 * @cur:  the current character
Packit Service a31ea6
 *
Packit Service a31ea6
 * Skip a comment in an SGML catalog
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns new current character
Packit Service a31ea6
 */
Packit Service a31ea6
static const xmlChar *
Packit Service a31ea6
xmlParseSGMLCatalogComment(const xmlChar *cur) {
Packit Service a31ea6
    if ((cur[0] != '-') || (cur[1] != '-'))
Packit Service a31ea6
	return(cur);
Packit Service a31ea6
    SKIP(2);
Packit Service a31ea6
    while ((cur[0] != 0) && ((cur[0] != '-') || ((cur[1] != '-'))))
Packit Service a31ea6
	NEXT;
Packit Service a31ea6
    if (cur[0] == 0) {
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
    return(cur + 2);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlParseSGMLCatalogPubid:
Packit Service a31ea6
 * @cur:  the current character
Packit Service a31ea6
 * @id:  the return location
Packit Service a31ea6
 *
Packit Service a31ea6
 * Parse an SGML catalog ID
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns new current character and store the value in @id
Packit Service a31ea6
 */
Packit Service a31ea6
static const xmlChar *
Packit Service a31ea6
xmlParseSGMLCatalogPubid(const xmlChar *cur, xmlChar **id) {
Packit Service a31ea6
    xmlChar *buf = NULL, *tmp;
Packit Service a31ea6
    int len = 0;
Packit Service a31ea6
    int size = 50;
Packit Service a31ea6
    xmlChar stop;
Packit Service a31ea6
    int count = 0;
Packit Service a31ea6
Packit Service a31ea6
    *id = NULL;
Packit Service a31ea6
Packit Service a31ea6
    if (RAW == '"') {
Packit Service a31ea6
        NEXT;
Packit Service a31ea6
	stop = '"';
Packit Service a31ea6
    } else if (RAW == '\'') {
Packit Service a31ea6
        NEXT;
Packit Service a31ea6
	stop = '\'';
Packit Service a31ea6
    } else {
Packit Service a31ea6
	stop = ' ';
Packit Service a31ea6
    }
Packit Service a31ea6
    buf = (xmlChar *) xmlMallocAtomic(size * sizeof(xmlChar));
Packit Service a31ea6
    if (buf == NULL) {
Packit Service a31ea6
        xmlCatalogErrMemory("allocating public ID");
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
    while (IS_PUBIDCHAR_CH(*cur) || (*cur == '?')) {
Packit Service a31ea6
	if ((*cur == stop) && (stop != ' '))
Packit Service a31ea6
	    break;
Packit Service a31ea6
	if ((stop == ' ') && (IS_BLANK_CH(*cur)))
Packit Service a31ea6
	    break;
Packit Service a31ea6
	if (len + 1 >= size) {
Packit Service a31ea6
	    size *= 2;
Packit Service a31ea6
	    tmp = (xmlChar *) xmlRealloc(buf, size * sizeof(xmlChar));
Packit Service a31ea6
	    if (tmp == NULL) {
Packit Service a31ea6
		xmlCatalogErrMemory("allocating public ID");
Packit Service a31ea6
		xmlFree(buf);
Packit Service a31ea6
		return(NULL);
Packit Service a31ea6
	    }
Packit Service a31ea6
	    buf = tmp;
Packit Service a31ea6
	}
Packit Service a31ea6
	buf[len++] = *cur;
Packit Service a31ea6
	count++;
Packit Service a31ea6
	NEXT;
Packit Service a31ea6
    }
Packit Service a31ea6
    buf[len] = 0;
Packit Service a31ea6
    if (stop == ' ') {
Packit Service a31ea6
	if (!IS_BLANK_CH(*cur)) {
Packit Service a31ea6
	    xmlFree(buf);
Packit Service a31ea6
	    return(NULL);
Packit Service a31ea6
	}
Packit Service a31ea6
    } else {
Packit Service a31ea6
	if (*cur != stop) {
Packit Service a31ea6
	    xmlFree(buf);
Packit Service a31ea6
	    return(NULL);
Packit Service a31ea6
	}
Packit Service a31ea6
	NEXT;
Packit Service a31ea6
    }
Packit Service a31ea6
    *id = buf;
Packit Service a31ea6
    return(cur);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlParseSGMLCatalogName:
Packit Service a31ea6
 * @cur:  the current character
Packit Service a31ea6
 * @name:  the return location
Packit Service a31ea6
 *
Packit Service a31ea6
 * Parse an SGML catalog name
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns new current character and store the value in @name
Packit Service a31ea6
 */
Packit Service a31ea6
static const xmlChar *
Packit Service a31ea6
xmlParseSGMLCatalogName(const xmlChar *cur, xmlChar **name) {
Packit Service a31ea6
    xmlChar buf[XML_MAX_NAMELEN + 5];
Packit Service a31ea6
    int len = 0;
Packit Service a31ea6
    int c;
Packit Service a31ea6
Packit Service a31ea6
    *name = NULL;
Packit Service a31ea6
Packit Service a31ea6
    /*
Packit Service a31ea6
     * Handler for more complex cases
Packit Service a31ea6
     */
Packit Service a31ea6
    c = *cur;
Packit Service a31ea6
    if ((!IS_LETTER(c) && (c != '_') && (c != ':'))) {
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    while (((IS_LETTER(c)) || (IS_DIGIT(c)) ||
Packit Service a31ea6
            (c == '.') || (c == '-') ||
Packit Service a31ea6
	    (c == '_') || (c == ':'))) {
Packit Service a31ea6
	buf[len++] = c;
Packit Service a31ea6
	cur++;
Packit Service a31ea6
	c = *cur;
Packit Service a31ea6
	if (len >= XML_MAX_NAMELEN)
Packit Service a31ea6
	    return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
    *name = xmlStrndup(buf, len);
Packit Service a31ea6
    return(cur);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlGetSGMLCatalogEntryType:
Packit Service a31ea6
 * @name:  the entry name
Packit Service a31ea6
 *
Packit Service a31ea6
 * Get the Catalog entry type for a given SGML Catalog name
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns Catalog entry type
Packit Service a31ea6
 */
Packit Service a31ea6
static xmlCatalogEntryType
Packit Service a31ea6
xmlGetSGMLCatalogEntryType(const xmlChar *name) {
Packit Service a31ea6
    xmlCatalogEntryType type = XML_CATA_NONE;
Packit Service a31ea6
    if (xmlStrEqual(name, (const xmlChar *) "SYSTEM"))
Packit Service a31ea6
	type = SGML_CATA_SYSTEM;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "PUBLIC"))
Packit Service a31ea6
	type = SGML_CATA_PUBLIC;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "DELEGATE"))
Packit Service a31ea6
	type = SGML_CATA_DELEGATE;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "ENTITY"))
Packit Service a31ea6
	type = SGML_CATA_ENTITY;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "DOCTYPE"))
Packit Service a31ea6
	type = SGML_CATA_DOCTYPE;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "LINKTYPE"))
Packit Service a31ea6
	type = SGML_CATA_LINKTYPE;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "NOTATION"))
Packit Service a31ea6
	type = SGML_CATA_NOTATION;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "SGMLDECL"))
Packit Service a31ea6
	type = SGML_CATA_SGMLDECL;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "DOCUMENT"))
Packit Service a31ea6
	type = SGML_CATA_DOCUMENT;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "CATALOG"))
Packit Service a31ea6
	type = SGML_CATA_CATALOG;
Packit Service a31ea6
    else if (xmlStrEqual(name, (const xmlChar *) "BASE"))
Packit Service a31ea6
	type = SGML_CATA_BASE;
Packit Service a31ea6
    return(type);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlParseSGMLCatalog:
Packit Service a31ea6
 * @catal:  the SGML Catalog
Packit Service a31ea6
 * @value:  the content of the SGML Catalog serialization
Packit Service a31ea6
 * @file:  the filepath for the catalog
Packit Service a31ea6
 * @super:  should this be handled as a Super Catalog in which case
Packit Service a31ea6
 *          parsing is not recursive
Packit Service a31ea6
 *
Packit Service a31ea6
 * Parse an SGML catalog content and fill up the @catal hash table with
Packit Service a31ea6
 * the new entries found.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns 0 in case of success, -1 in case of error.
Packit Service a31ea6
 */
Packit Service a31ea6
static int
Packit Service a31ea6
xmlParseSGMLCatalog(xmlCatalogPtr catal, const xmlChar *value,
Packit Service a31ea6
	            const char *file, int super) {
Packit Service a31ea6
    const xmlChar *cur = value;
Packit Service a31ea6
    xmlChar *base = NULL;
Packit Service a31ea6
    int res;
Packit Service a31ea6
Packit Service a31ea6
    if ((cur == NULL) || (file == NULL))
Packit Service a31ea6
        return(-1);
Packit Service a31ea6
    base = xmlStrdup((const xmlChar *) file);
Packit Service a31ea6
Packit Service a31ea6
    while ((cur != NULL) && (cur[0] != 0)) {
Packit Service a31ea6
	SKIP_BLANKS;
Packit Service a31ea6
	if (cur[0] == 0)
Packit Service a31ea6
	    break;
Packit Service a31ea6
	if ((cur[0] == '-') && (cur[1] == '-')) {
Packit Service a31ea6
	    cur = xmlParseSGMLCatalogComment(cur);
Packit Service a31ea6
	    if (cur == NULL) {
Packit Service a31ea6
		/* error */
Packit Service a31ea6
		break;
Packit Service a31ea6
	    }
Packit Service a31ea6
	} else {
Packit Service a31ea6
	    xmlChar *sysid = NULL;
Packit Service a31ea6
	    xmlChar *name = NULL;
Packit Service a31ea6
	    xmlCatalogEntryType type = XML_CATA_NONE;
Packit Service a31ea6
Packit Service a31ea6
	    cur = xmlParseSGMLCatalogName(cur, &name);
Packit Service a31ea6
	    if (name == NULL) {
Packit Service a31ea6
		/* error */
Packit Service a31ea6
		break;
Packit Service a31ea6
	    }
Packit Service a31ea6
	    if (!IS_BLANK_CH(*cur)) {
Packit Service a31ea6
		/* error */
Packit Service a31ea6
		break;
Packit Service a31ea6
	    }
Packit Service a31ea6
	    SKIP_BLANKS;
Packit Service a31ea6
	    if (xmlStrEqual(name, (const xmlChar *) "SYSTEM"))
Packit Service a31ea6
                type = SGML_CATA_SYSTEM;
Packit Service a31ea6
	    else if (xmlStrEqual(name, (const xmlChar *) "PUBLIC"))
Packit Service a31ea6
                type = SGML_CATA_PUBLIC;
Packit Service a31ea6
	    else if (xmlStrEqual(name, (const xmlChar *) "DELEGATE"))
Packit Service a31ea6
                type = SGML_CATA_DELEGATE;
Packit Service a31ea6
	    else if (xmlStrEqual(name, (const xmlChar *) "ENTITY"))
Packit Service a31ea6
                type = SGML_CATA_ENTITY;
Packit Service a31ea6
	    else if (xmlStrEqual(name, (const xmlChar *) "DOCTYPE"))
Packit Service a31ea6
                type = SGML_CATA_DOCTYPE;
Packit Service a31ea6
	    else if (xmlStrEqual(name, (const xmlChar *) "LINKTYPE"))
Packit Service a31ea6
                type = SGML_CATA_LINKTYPE;
Packit Service a31ea6
	    else if (xmlStrEqual(name, (const xmlChar *) "NOTATION"))
Packit Service a31ea6
                type = SGML_CATA_NOTATION;
Packit Service a31ea6
	    else if (xmlStrEqual(name, (const xmlChar *) "SGMLDECL"))
Packit Service a31ea6
                type = SGML_CATA_SGMLDECL;
Packit Service a31ea6
	    else if (xmlStrEqual(name, (const xmlChar *) "DOCUMENT"))
Packit Service a31ea6
                type = SGML_CATA_DOCUMENT;
Packit Service a31ea6
	    else if (xmlStrEqual(name, (const xmlChar *) "CATALOG"))
Packit Service a31ea6
                type = SGML_CATA_CATALOG;
Packit Service a31ea6
	    else if (xmlStrEqual(name, (const xmlChar *) "BASE"))
Packit Service a31ea6
                type = SGML_CATA_BASE;
Packit Service a31ea6
	    else if (xmlStrEqual(name, (const xmlChar *) "OVERRIDE")) {
Packit Service a31ea6
		xmlFree(name);
Packit Service a31ea6
		cur = xmlParseSGMLCatalogName(cur, &name);
Packit Service a31ea6
		if (name == NULL) {
Packit Service a31ea6
		    /* error */
Packit Service a31ea6
		    break;
Packit Service a31ea6
		}
Packit Service a31ea6
		xmlFree(name);
Packit Service a31ea6
		continue;
Packit Service a31ea6
	    }
Packit Service a31ea6
	    xmlFree(name);
Packit Service a31ea6
	    name = NULL;
Packit Service a31ea6
Packit Service a31ea6
	    switch(type) {
Packit Service a31ea6
		case SGML_CATA_ENTITY:
Packit Service a31ea6
		    if (*cur == '%')
Packit Service a31ea6
			type = SGML_CATA_PENTITY;
Packit Service a31ea6
                    /* Falls through. */
Packit Service a31ea6
		case SGML_CATA_PENTITY:
Packit Service a31ea6
		case SGML_CATA_DOCTYPE:
Packit Service a31ea6
		case SGML_CATA_LINKTYPE:
Packit Service a31ea6
		case SGML_CATA_NOTATION:
Packit Service a31ea6
		    cur = xmlParseSGMLCatalogName(cur, &name);
Packit Service a31ea6
		    if (cur == NULL) {
Packit Service a31ea6
			/* error */
Packit Service a31ea6
			break;
Packit Service a31ea6
		    }
Packit Service a31ea6
		    if (!IS_BLANK_CH(*cur)) {
Packit Service a31ea6
			/* error */
Packit Service a31ea6
			break;
Packit Service a31ea6
		    }
Packit Service a31ea6
		    SKIP_BLANKS;
Packit Service a31ea6
		    cur = xmlParseSGMLCatalogPubid(cur, &sysid);
Packit Service a31ea6
		    if (cur == NULL) {
Packit Service a31ea6
			/* error */
Packit Service a31ea6
			break;
Packit Service a31ea6
		    }
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case SGML_CATA_PUBLIC:
Packit Service a31ea6
		case SGML_CATA_SYSTEM:
Packit Service a31ea6
		case SGML_CATA_DELEGATE:
Packit Service a31ea6
		    cur = xmlParseSGMLCatalogPubid(cur, &name);
Packit Service a31ea6
		    if (cur == NULL) {
Packit Service a31ea6
			/* error */
Packit Service a31ea6
			break;
Packit Service a31ea6
		    }
Packit Service a31ea6
		    if (type != SGML_CATA_SYSTEM) {
Packit Service a31ea6
		        xmlChar *normid;
Packit Service a31ea6
Packit Service a31ea6
		        normid = xmlCatalogNormalizePublic(name);
Packit Service a31ea6
		        if (normid != NULL) {
Packit Service a31ea6
		            if (name != NULL)
Packit Service a31ea6
		                xmlFree(name);
Packit Service a31ea6
		            if (*normid != 0)
Packit Service a31ea6
		                name = normid;
Packit Service a31ea6
		            else {
Packit Service a31ea6
		                xmlFree(normid);
Packit Service a31ea6
		                name = NULL;
Packit Service a31ea6
		            }
Packit Service a31ea6
		        }
Packit Service a31ea6
		    }
Packit Service a31ea6
		    if (!IS_BLANK_CH(*cur)) {
Packit Service a31ea6
			/* error */
Packit Service a31ea6
			break;
Packit Service a31ea6
		    }
Packit Service a31ea6
		    SKIP_BLANKS;
Packit Service a31ea6
		    cur = xmlParseSGMLCatalogPubid(cur, &sysid);
Packit Service a31ea6
		    if (cur == NULL) {
Packit Service a31ea6
			/* error */
Packit Service a31ea6
			break;
Packit Service a31ea6
		    }
Packit Service a31ea6
		    break;
Packit Service a31ea6
		case SGML_CATA_BASE:
Packit Service a31ea6
		case SGML_CATA_CATALOG:
Packit Service a31ea6
		case SGML_CATA_DOCUMENT:
Packit Service a31ea6
		case SGML_CATA_SGMLDECL:
Packit Service a31ea6
		    cur = xmlParseSGMLCatalogPubid(cur, &sysid);
Packit Service a31ea6
		    if (cur == NULL) {
Packit Service a31ea6
			/* error */
Packit Service a31ea6
			break;
Packit Service a31ea6
		    }
Packit Service a31ea6
		    break;
Packit Service a31ea6
		default:
Packit Service a31ea6
		    break;
Packit Service a31ea6
	    }
Packit Service a31ea6
	    if (cur == NULL) {
Packit Service a31ea6
		if (name != NULL)
Packit Service a31ea6
		    xmlFree(name);
Packit Service a31ea6
		if (sysid != NULL)
Packit Service a31ea6
		    xmlFree(sysid);
Packit Service a31ea6
		break;
Packit Service a31ea6
	    } else if (type == SGML_CATA_BASE) {
Packit Service a31ea6
		if (base != NULL)
Packit Service a31ea6
		    xmlFree(base);
Packit Service a31ea6
		base = xmlStrdup(sysid);
Packit Service a31ea6
	    } else if ((type == SGML_CATA_PUBLIC) ||
Packit Service a31ea6
		       (type == SGML_CATA_SYSTEM)) {
Packit Service a31ea6
		xmlChar *filename;
Packit Service a31ea6
Packit Service a31ea6
		filename = xmlBuildURI(sysid, base);
Packit Service a31ea6
		if (filename != NULL) {
Packit Service a31ea6
		    xmlCatalogEntryPtr entry;
Packit Service a31ea6
Packit Service a31ea6
		    entry = xmlNewCatalogEntry(type, name, filename,
Packit Service a31ea6
			                       NULL, XML_CATA_PREFER_NONE, NULL);
Packit Service a31ea6
		    res = xmlHashAddEntry(catal->sgml, name, entry);
Packit Service a31ea6
		    if (res < 0) {
Packit Service a31ea6
			xmlFreeCatalogEntry(entry);
Packit Service a31ea6
		    }
Packit Service a31ea6
		    xmlFree(filename);
Packit Service a31ea6
		}
Packit Service a31ea6
Packit Service a31ea6
	    } else if (type == SGML_CATA_CATALOG) {
Packit Service a31ea6
		if (super) {
Packit Service a31ea6
		    xmlCatalogEntryPtr entry;
Packit Service a31ea6
Packit Service a31ea6
		    entry = xmlNewCatalogEntry(type, sysid, NULL, NULL,
Packit Service a31ea6
			                       XML_CATA_PREFER_NONE, NULL);
Packit Service a31ea6
		    res = xmlHashAddEntry(catal->sgml, sysid, entry);
Packit Service a31ea6
		    if (res < 0) {
Packit Service a31ea6
			xmlFreeCatalogEntry(entry);
Packit Service a31ea6
		    }
Packit Service a31ea6
		} else {
Packit Service a31ea6
		    xmlChar *filename;
Packit Service a31ea6
Packit Service a31ea6
		    filename = xmlBuildURI(sysid, base);
Packit Service a31ea6
		    if (filename != NULL) {
Packit Service a31ea6
			xmlExpandCatalog(catal, (const char *)filename);
Packit Service a31ea6
			xmlFree(filename);
Packit Service a31ea6
		    }
Packit Service a31ea6
		}
Packit Service a31ea6
	    }
Packit Service a31ea6
	    /*
Packit Service a31ea6
	     * drop anything else we won't handle it
Packit Service a31ea6
	     */
Packit Service a31ea6
	    if (name != NULL)
Packit Service a31ea6
		xmlFree(name);
Packit Service a31ea6
	    if (sysid != NULL)
Packit Service a31ea6
		xmlFree(sysid);
Packit Service a31ea6
	}
Packit Service a31ea6
    }
Packit Service a31ea6
    if (base != NULL)
Packit Service a31ea6
	xmlFree(base);
Packit Service a31ea6
    if (cur == NULL)
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
    return(0);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/************************************************************************
Packit Service a31ea6
 *									*
Packit Service a31ea6
 *			SGML Catalog handling				*
Packit Service a31ea6
 *									*
Packit Service a31ea6
 ************************************************************************/
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogGetSGMLPublic:
Packit Service a31ea6
 * @catal:  an SGML catalog hash
Packit Service a31ea6
 * @pubID:  the public ID string
Packit Service a31ea6
 *
Packit Service a31ea6
 * Try to lookup the catalog local reference associated to a public ID
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the local resource if found or NULL otherwise.
Packit Service a31ea6
 */
Packit Service a31ea6
static const xmlChar *
Packit Service a31ea6
xmlCatalogGetSGMLPublic(xmlHashTablePtr catal, const xmlChar *pubID) {
Packit Service a31ea6
    xmlCatalogEntryPtr entry;
Packit Service a31ea6
    xmlChar *normid;
Packit Service a31ea6
Packit Service a31ea6
    if (catal == NULL)
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    normid = xmlCatalogNormalizePublic(pubID);
Packit Service a31ea6
    if (normid != NULL)
Packit Service a31ea6
        pubID = (*normid != 0 ? normid : NULL);
Packit Service a31ea6
Packit Service a31ea6
    entry = (xmlCatalogEntryPtr) xmlHashLookup(catal, pubID);
Packit Service a31ea6
    if (entry == NULL) {
Packit Service a31ea6
	if (normid != NULL)
Packit Service a31ea6
	    xmlFree(normid);
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
    if (entry->type == SGML_CATA_PUBLIC) {
Packit Service a31ea6
	if (normid != NULL)
Packit Service a31ea6
	    xmlFree(normid);
Packit Service a31ea6
	return(entry->URL);
Packit Service a31ea6
    }
Packit Service a31ea6
    if (normid != NULL)
Packit Service a31ea6
        xmlFree(normid);
Packit Service a31ea6
    return(NULL);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogGetSGMLSystem:
Packit Service a31ea6
 * @catal:  an SGML catalog hash
Packit Service a31ea6
 * @sysID:  the system ID string
Packit Service a31ea6
 *
Packit Service a31ea6
 * Try to lookup the catalog local reference for a system ID
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the local resource if found or NULL otherwise.
Packit Service a31ea6
 */
Packit Service a31ea6
static const xmlChar *
Packit Service a31ea6
xmlCatalogGetSGMLSystem(xmlHashTablePtr catal, const xmlChar *sysID) {
Packit Service a31ea6
    xmlCatalogEntryPtr entry;
Packit Service a31ea6
Packit Service a31ea6
    if (catal == NULL)
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    entry = (xmlCatalogEntryPtr) xmlHashLookup(catal, sysID);
Packit Service a31ea6
    if (entry == NULL)
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    if (entry->type == SGML_CATA_SYSTEM)
Packit Service a31ea6
	return(entry->URL);
Packit Service a31ea6
    return(NULL);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogSGMLResolve:
Packit Service a31ea6
 * @catal:  the SGML catalog
Packit Service a31ea6
 * @pubID:  the public ID string
Packit Service a31ea6
 * @sysID:  the system ID string
Packit Service a31ea6
 *
Packit Service a31ea6
 * Do a complete resolution lookup of an External Identifier
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the URI of the resource or NULL if not found
Packit Service a31ea6
 */
Packit Service a31ea6
static const xmlChar *
Packit Service a31ea6
xmlCatalogSGMLResolve(xmlCatalogPtr catal, const xmlChar *pubID,
Packit Service a31ea6
	              const xmlChar *sysID) {
Packit Service a31ea6
    const xmlChar *ret = NULL;
Packit Service a31ea6
Packit Service a31ea6
    if (catal->sgml == NULL)
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    if (pubID != NULL)
Packit Service a31ea6
	ret = xmlCatalogGetSGMLPublic(catal->sgml, pubID);
Packit Service a31ea6
    if (ret != NULL)
Packit Service a31ea6
	return(ret);
Packit Service a31ea6
    if (sysID != NULL)
Packit Service a31ea6
	ret = xmlCatalogGetSGMLSystem(catal->sgml, sysID);
Packit Service a31ea6
    if (ret != NULL)
Packit Service a31ea6
	return(ret);
Packit Service a31ea6
    return(NULL);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/************************************************************************
Packit Service a31ea6
 *									*
Packit Service a31ea6
 *			Specific Public interfaces			*
Packit Service a31ea6
 *									*
Packit Service a31ea6
 ************************************************************************/
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlLoadSGMLSuperCatalog:
Packit Service a31ea6
 * @filename:  a file path
Packit Service a31ea6
 *
Packit Service a31ea6
 * Load an SGML super catalog. It won't expand CATALOG or DELEGATE
Packit Service a31ea6
 * references. This is only needed for manipulating SGML Super Catalogs
Packit Service a31ea6
 * like adding and removing CATALOG or DELEGATE entries.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the catalog parsed or NULL in case of error
Packit Service a31ea6
 */
Packit Service a31ea6
xmlCatalogPtr
Packit Service a31ea6
xmlLoadSGMLSuperCatalog(const char *filename)
Packit Service a31ea6
{
Packit Service a31ea6
    xmlChar *content;
Packit Service a31ea6
    xmlCatalogPtr catal;
Packit Service a31ea6
    int ret;
Packit Service a31ea6
Packit Service a31ea6
    content = xmlLoadFileContent(filename);
Packit Service a31ea6
    if (content == NULL)
Packit Service a31ea6
        return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    catal = xmlCreateNewCatalog(XML_SGML_CATALOG_TYPE, xmlCatalogDefaultPrefer);
Packit Service a31ea6
    if (catal == NULL) {
Packit Service a31ea6
	xmlFree(content);
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    ret = xmlParseSGMLCatalog(catal, content, filename, 1);
Packit Service a31ea6
    xmlFree(content);
Packit Service a31ea6
    if (ret < 0) {
Packit Service a31ea6
	xmlFreeCatalog(catal);
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
    return (catal);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlLoadACatalog:
Packit Service a31ea6
 * @filename:  a file path
Packit Service a31ea6
 *
Packit Service a31ea6
 * Load the catalog and build the associated data structures.
Packit Service a31ea6
 * This can be either an XML Catalog or an SGML Catalog
Packit Service a31ea6
 * It will recurse in SGML CATALOG entries. On the other hand XML
Packit Service a31ea6
 * Catalogs are not handled recursively.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the catalog parsed or NULL in case of error
Packit Service a31ea6
 */
Packit Service a31ea6
xmlCatalogPtr
Packit Service a31ea6
xmlLoadACatalog(const char *filename)
Packit Service a31ea6
{
Packit Service a31ea6
    xmlChar *content;
Packit Service a31ea6
    xmlChar *first;
Packit Service a31ea6
    xmlCatalogPtr catal;
Packit Service a31ea6
    int ret;
Packit Service a31ea6
Packit Service a31ea6
    content = xmlLoadFileContent(filename);
Packit Service a31ea6
    if (content == NULL)
Packit Service a31ea6
        return(NULL);
Packit Service a31ea6
Packit Service a31ea6
Packit Service a31ea6
    first = content;
Packit Service a31ea6
Packit Service a31ea6
    while ((*first != 0) && (*first != '-') && (*first != '<') &&
Packit Service a31ea6
	   (!(((*first >= 'A') && (*first <= 'Z')) ||
Packit Service a31ea6
	      ((*first >= 'a') && (*first <= 'z')))))
Packit Service a31ea6
	first++;
Packit Service a31ea6
Packit Service a31ea6
    if (*first != '<') {
Packit Service a31ea6
	catal = xmlCreateNewCatalog(XML_SGML_CATALOG_TYPE, xmlCatalogDefaultPrefer);
Packit Service a31ea6
	if (catal == NULL) {
Packit Service a31ea6
	    xmlFree(content);
Packit Service a31ea6
	    return(NULL);
Packit Service a31ea6
	}
Packit Service a31ea6
        ret = xmlParseSGMLCatalog(catal, content, filename, 0);
Packit Service a31ea6
	if (ret < 0) {
Packit Service a31ea6
	    xmlFreeCatalog(catal);
Packit Service a31ea6
	    xmlFree(content);
Packit Service a31ea6
	    return(NULL);
Packit Service a31ea6
	}
Packit Service a31ea6
    } else {
Packit Service a31ea6
	catal = xmlCreateNewCatalog(XML_XML_CATALOG_TYPE, xmlCatalogDefaultPrefer);
Packit Service a31ea6
	if (catal == NULL) {
Packit Service a31ea6
	    xmlFree(content);
Packit Service a31ea6
	    return(NULL);
Packit Service a31ea6
	}
Packit Service a31ea6
        catal->xml = xmlNewCatalogEntry(XML_CATA_CATALOG, NULL,
Packit Service a31ea6
		       NULL, BAD_CAST filename, xmlCatalogDefaultPrefer, NULL);
Packit Service a31ea6
    }
Packit Service a31ea6
    xmlFree(content);
Packit Service a31ea6
    return (catal);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlExpandCatalog:
Packit Service a31ea6
 * @catal:  a catalog
Packit Service a31ea6
 * @filename:  a file path
Packit Service a31ea6
 *
Packit Service a31ea6
 * Load the catalog and expand the existing catal structure.
Packit Service a31ea6
 * This can be either an XML Catalog or an SGML Catalog
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns 0 in case of success, -1 in case of error
Packit Service a31ea6
 */
Packit Service a31ea6
static int
Packit Service a31ea6
xmlExpandCatalog(xmlCatalogPtr catal, const char *filename)
Packit Service a31ea6
{
Packit Service a31ea6
    int ret;
Packit Service a31ea6
Packit Service a31ea6
    if ((catal == NULL) || (filename == NULL))
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
Packit Service a31ea6
Packit Service a31ea6
    if (catal->type == XML_SGML_CATALOG_TYPE) {
Packit Service a31ea6
	xmlChar *content;
Packit Service a31ea6
Packit Service a31ea6
	content = xmlLoadFileContent(filename);
Packit Service a31ea6
	if (content == NULL)
Packit Service a31ea6
	    return(-1);
Packit Service a31ea6
Packit Service a31ea6
        ret = xmlParseSGMLCatalog(catal, content, filename, 0);
Packit Service a31ea6
	if (ret < 0) {
Packit Service a31ea6
	    xmlFree(content);
Packit Service a31ea6
	    return(-1);
Packit Service a31ea6
	}
Packit Service a31ea6
	xmlFree(content);
Packit Service a31ea6
    } else {
Packit Service a31ea6
	xmlCatalogEntryPtr tmp, cur;
Packit Service a31ea6
	tmp = xmlNewCatalogEntry(XML_CATA_CATALOG, NULL,
Packit Service a31ea6
		       NULL, BAD_CAST filename, xmlCatalogDefaultPrefer, NULL);
Packit Service a31ea6
Packit Service a31ea6
	cur = catal->xml;
Packit Service a31ea6
	if (cur == NULL) {
Packit Service a31ea6
	    catal->xml = tmp;
Packit Service a31ea6
	} else {
Packit Service a31ea6
	    while (cur->next != NULL) cur = cur->next;
Packit Service a31ea6
	    cur->next = tmp;
Packit Service a31ea6
	}
Packit Service a31ea6
    }
Packit Service a31ea6
    return (0);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlACatalogResolveSystem:
Packit Service a31ea6
 * @catal:  a Catalog
Packit Service a31ea6
 * @sysID:  the system ID string
Packit Service a31ea6
 *
Packit Service a31ea6
 * Try to lookup the catalog resource for a system ID
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the resource if found or NULL otherwise, the value returned
Packit Service a31ea6
 *      must be freed by the caller.
Packit Service a31ea6
 */
Packit Service a31ea6
xmlChar *
Packit Service a31ea6
xmlACatalogResolveSystem(xmlCatalogPtr catal, const xmlChar *sysID) {
Packit Service a31ea6
    xmlChar *ret = NULL;
Packit Service a31ea6
Packit Service a31ea6
    if ((sysID == NULL) || (catal == NULL))
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    if (xmlDebugCatalogs)
Packit Service a31ea6
	xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		"Resolve sysID %s\n", sysID);
Packit Service a31ea6
Packit Service a31ea6
    if (catal->type == XML_XML_CATALOG_TYPE) {
Packit Service a31ea6
	ret = xmlCatalogListXMLResolve(catal->xml, NULL, sysID);
Packit Service a31ea6
	if (ret == XML_CATAL_BREAK)
Packit Service a31ea6
	    ret = NULL;
Packit Service a31ea6
    } else {
Packit Service a31ea6
	const xmlChar *sgml;
Packit Service a31ea6
Packit Service a31ea6
	sgml = xmlCatalogGetSGMLSystem(catal->sgml, sysID);
Packit Service a31ea6
	if (sgml != NULL)
Packit Service a31ea6
	    ret = xmlStrdup(sgml);
Packit Service a31ea6
    }
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlACatalogResolvePublic:
Packit Service a31ea6
 * @catal:  a Catalog
Packit Service a31ea6
 * @pubID:  the public ID string
Packit Service a31ea6
 *
Packit Service a31ea6
 * Try to lookup the catalog local reference associated to a public ID in that catalog
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the local resource if found or NULL otherwise, the value returned
Packit Service a31ea6
 *      must be freed by the caller.
Packit Service a31ea6
 */
Packit Service a31ea6
xmlChar *
Packit Service a31ea6
xmlACatalogResolvePublic(xmlCatalogPtr catal, const xmlChar *pubID) {
Packit Service a31ea6
    xmlChar *ret = NULL;
Packit Service a31ea6
Packit Service a31ea6
    if ((pubID == NULL) || (catal == NULL))
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    if (xmlDebugCatalogs)
Packit Service a31ea6
	xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		"Resolve pubID %s\n", pubID);
Packit Service a31ea6
Packit Service a31ea6
    if (catal->type == XML_XML_CATALOG_TYPE) {
Packit Service a31ea6
	ret = xmlCatalogListXMLResolve(catal->xml, pubID, NULL);
Packit Service a31ea6
	if (ret == XML_CATAL_BREAK)
Packit Service a31ea6
	    ret = NULL;
Packit Service a31ea6
    } else {
Packit Service a31ea6
	const xmlChar *sgml;
Packit Service a31ea6
Packit Service a31ea6
	sgml = xmlCatalogGetSGMLPublic(catal->sgml, pubID);
Packit Service a31ea6
	if (sgml != NULL)
Packit Service a31ea6
	    ret = xmlStrdup(sgml);
Packit Service a31ea6
    }
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlACatalogResolve:
Packit Service a31ea6
 * @catal:  a Catalog
Packit Service a31ea6
 * @pubID:  the public ID string
Packit Service a31ea6
 * @sysID:  the system ID string
Packit Service a31ea6
 *
Packit Service a31ea6
 * Do a complete resolution lookup of an External Identifier
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the URI of the resource or NULL if not found, it must be freed
Packit Service a31ea6
 *      by the caller.
Packit Service a31ea6
 */
Packit Service a31ea6
xmlChar *
Packit Service a31ea6
xmlACatalogResolve(xmlCatalogPtr catal, const xmlChar * pubID,
Packit Service a31ea6
                   const xmlChar * sysID)
Packit Service a31ea6
{
Packit Service a31ea6
    xmlChar *ret = NULL;
Packit Service a31ea6
Packit Service a31ea6
    if (((pubID == NULL) && (sysID == NULL)) || (catal == NULL))
Packit Service a31ea6
        return (NULL);
Packit Service a31ea6
Packit Service a31ea6
    if (xmlDebugCatalogs) {
Packit Service a31ea6
         if ((pubID != NULL) && (sysID != NULL)) {
Packit Service a31ea6
             xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
                             "Resolve: pubID %s sysID %s\n", pubID, sysID);
Packit Service a31ea6
         } else if (pubID != NULL) {
Packit Service a31ea6
             xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
                             "Resolve: pubID %s\n", pubID);
Packit Service a31ea6
         } else {
Packit Service a31ea6
             xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
                             "Resolve: sysID %s\n", sysID);
Packit Service a31ea6
         }
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    if (catal->type == XML_XML_CATALOG_TYPE) {
Packit Service a31ea6
        ret = xmlCatalogListXMLResolve(catal->xml, pubID, sysID);
Packit Service a31ea6
	if (ret == XML_CATAL_BREAK)
Packit Service a31ea6
	    ret = NULL;
Packit Service a31ea6
    } else {
Packit Service a31ea6
        const xmlChar *sgml;
Packit Service a31ea6
Packit Service a31ea6
        sgml = xmlCatalogSGMLResolve(catal, pubID, sysID);
Packit Service a31ea6
        if (sgml != NULL)
Packit Service a31ea6
            ret = xmlStrdup(sgml);
Packit Service a31ea6
    }
Packit Service a31ea6
    return (ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlACatalogResolveURI:
Packit Service a31ea6
 * @catal:  a Catalog
Packit Service a31ea6
 * @URI:  the URI
Packit Service a31ea6
 *
Packit Service a31ea6
 * Do a complete resolution lookup of an URI
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the URI of the resource or NULL if not found, it must be freed
Packit Service a31ea6
 *      by the caller.
Packit Service a31ea6
 */
Packit Service a31ea6
xmlChar *
Packit Service a31ea6
xmlACatalogResolveURI(xmlCatalogPtr catal, const xmlChar *URI) {
Packit Service a31ea6
    xmlChar *ret = NULL;
Packit Service a31ea6
Packit Service a31ea6
    if ((URI == NULL) || (catal == NULL))
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    if (xmlDebugCatalogs)
Packit Service a31ea6
	xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		"Resolve URI %s\n", URI);
Packit Service a31ea6
Packit Service a31ea6
    if (catal->type == XML_XML_CATALOG_TYPE) {
Packit Service a31ea6
	ret = xmlCatalogListXMLResolveURI(catal->xml, URI);
Packit Service a31ea6
	if (ret == XML_CATAL_BREAK)
Packit Service a31ea6
	    ret = NULL;
Packit Service a31ea6
    } else {
Packit Service a31ea6
	const xmlChar *sgml;
Packit Service a31ea6
Packit Service a31ea6
	sgml = xmlCatalogSGMLResolve(catal, NULL, URI);
Packit Service a31ea6
	if (sgml != NULL)
Packit Service a31ea6
            ret = xmlStrdup(sgml);
Packit Service a31ea6
    }
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
#ifdef LIBXML_OUTPUT_ENABLED
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlACatalogDump:
Packit Service a31ea6
 * @catal:  a Catalog
Packit Service a31ea6
 * @out:  the file.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Dump the given catalog to the given file.
Packit Service a31ea6
 */
Packit Service a31ea6
void
Packit Service a31ea6
xmlACatalogDump(xmlCatalogPtr catal, FILE *out) {
Packit Service a31ea6
    if ((out == NULL) || (catal == NULL))
Packit Service a31ea6
	return;
Packit Service a31ea6
Packit Service a31ea6
    if (catal->type == XML_XML_CATALOG_TYPE) {
Packit Service a31ea6
	xmlDumpXMLCatalog(out, catal->xml);
Packit Service a31ea6
    } else {
Packit Service a31ea6
	xmlHashScan(catal->sgml,
Packit Service a31ea6
		    (xmlHashScanner) xmlCatalogDumpEntry, out);
Packit Service a31ea6
    }
Packit Service a31ea6
}
Packit Service a31ea6
#endif /* LIBXML_OUTPUT_ENABLED */
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlACatalogAdd:
Packit Service a31ea6
 * @catal:  a Catalog
Packit Service a31ea6
 * @type:  the type of record to add to the catalog
Packit Service a31ea6
 * @orig:  the system, public or prefix to match
Packit Service a31ea6
 * @replace:  the replacement value for the match
Packit Service a31ea6
 *
Packit Service a31ea6
 * Add an entry in the catalog, it may overwrite existing but
Packit Service a31ea6
 * different entries.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns 0 if successful, -1 otherwise
Packit Service a31ea6
 */
Packit Service a31ea6
int
Packit Service a31ea6
xmlACatalogAdd(xmlCatalogPtr catal, const xmlChar * type,
Packit Service a31ea6
              const xmlChar * orig, const xmlChar * replace)
Packit Service a31ea6
{
Packit Service a31ea6
    int res = -1;
Packit Service a31ea6
Packit Service a31ea6
    if (catal == NULL)
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
Packit Service a31ea6
    if (catal->type == XML_XML_CATALOG_TYPE) {
Packit Service a31ea6
        res = xmlAddXMLCatalog(catal->xml, type, orig, replace);
Packit Service a31ea6
    } else {
Packit Service a31ea6
        xmlCatalogEntryType cattype;
Packit Service a31ea6
Packit Service a31ea6
        cattype = xmlGetSGMLCatalogEntryType(type);
Packit Service a31ea6
        if (cattype != XML_CATA_NONE) {
Packit Service a31ea6
            xmlCatalogEntryPtr entry;
Packit Service a31ea6
Packit Service a31ea6
            entry = xmlNewCatalogEntry(cattype, orig, replace, NULL,
Packit Service a31ea6
                                       XML_CATA_PREFER_NONE, NULL);
Packit Service a31ea6
	    if (catal->sgml == NULL)
Packit Service a31ea6
		catal->sgml = xmlHashCreate(10);
Packit Service a31ea6
            res = xmlHashAddEntry(catal->sgml, orig, entry);
Packit Service a31ea6
        }
Packit Service a31ea6
    }
Packit Service a31ea6
    return (res);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlACatalogRemove:
Packit Service a31ea6
 * @catal:  a Catalog
Packit Service a31ea6
 * @value:  the value to remove
Packit Service a31ea6
 *
Packit Service a31ea6
 * Remove an entry from the catalog
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the number of entries removed if successful, -1 otherwise
Packit Service a31ea6
 */
Packit Service a31ea6
int
Packit Service a31ea6
xmlACatalogRemove(xmlCatalogPtr catal, const xmlChar *value) {
Packit Service a31ea6
    int res = -1;
Packit Service a31ea6
Packit Service a31ea6
    if ((catal == NULL) || (value == NULL))
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
Packit Service a31ea6
    if (catal->type == XML_XML_CATALOG_TYPE) {
Packit Service a31ea6
	res = xmlDelXMLCatalog(catal->xml, value);
Packit Service a31ea6
    } else {
Packit Service a31ea6
	res = xmlHashRemoveEntry(catal->sgml, value,
Packit Service a31ea6
		(xmlHashDeallocator) xmlFreeCatalogEntry);
Packit Service a31ea6
	if (res == 0)
Packit Service a31ea6
	    res = 1;
Packit Service a31ea6
    }
Packit Service a31ea6
    return(res);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlNewCatalog:
Packit Service a31ea6
 * @sgml:  should this create an SGML catalog
Packit Service a31ea6
 *
Packit Service a31ea6
 * create a new Catalog.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the xmlCatalogPtr or NULL in case of error
Packit Service a31ea6
 */
Packit Service a31ea6
xmlCatalogPtr
Packit Service a31ea6
xmlNewCatalog(int sgml) {
Packit Service a31ea6
    xmlCatalogPtr catal = NULL;
Packit Service a31ea6
Packit Service a31ea6
    if (sgml) {
Packit Service a31ea6
	catal = xmlCreateNewCatalog(XML_SGML_CATALOG_TYPE,
Packit Service a31ea6
		                    xmlCatalogDefaultPrefer);
Packit Service a31ea6
        if ((catal != NULL) && (catal->sgml == NULL))
Packit Service a31ea6
	    catal->sgml = xmlHashCreate(10);
Packit Service a31ea6
    } else
Packit Service a31ea6
	catal = xmlCreateNewCatalog(XML_XML_CATALOG_TYPE,
Packit Service a31ea6
		                    xmlCatalogDefaultPrefer);
Packit Service a31ea6
    return(catal);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogIsEmpty:
Packit Service a31ea6
 * @catal:  should this create an SGML catalog
Packit Service a31ea6
 *
Packit Service a31ea6
 * Check is a catalog is empty
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns 1 if the catalog is empty, 0 if not, amd -1 in case of error.
Packit Service a31ea6
 */
Packit Service a31ea6
int
Packit Service a31ea6
xmlCatalogIsEmpty(xmlCatalogPtr catal) {
Packit Service a31ea6
    if (catal == NULL)
Packit Service a31ea6
	return(-1);
Packit Service a31ea6
Packit Service a31ea6
    if (catal->type == XML_XML_CATALOG_TYPE) {
Packit Service a31ea6
	if (catal->xml == NULL)
Packit Service a31ea6
	    return(1);
Packit Service a31ea6
	if ((catal->xml->type != XML_CATA_CATALOG) &&
Packit Service a31ea6
	    (catal->xml->type != XML_CATA_BROKEN_CATALOG))
Packit Service a31ea6
	    return(-1);
Packit Service a31ea6
	if (catal->xml->children == NULL)
Packit Service a31ea6
	    return(1);
Packit Service a31ea6
        return(0);
Packit Service a31ea6
    } else {
Packit Service a31ea6
	int res;
Packit Service a31ea6
Packit Service a31ea6
	if (catal->sgml == NULL)
Packit Service a31ea6
	    return(1);
Packit Service a31ea6
	res = xmlHashSize(catal->sgml);
Packit Service a31ea6
	if (res == 0)
Packit Service a31ea6
	    return(1);
Packit Service a31ea6
	if (res < 0)
Packit Service a31ea6
	    return(-1);
Packit Service a31ea6
    }
Packit Service a31ea6
    return(0);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/************************************************************************
Packit Service a31ea6
 *									*
Packit Service a31ea6
 *   Public interfaces manipulating the global shared default catalog	*
Packit Service a31ea6
 *									*
Packit Service a31ea6
 ************************************************************************/
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlInitializeCatalogData:
Packit Service a31ea6
 *
Packit Service a31ea6
 * Do the catalog initialization only of global data, doesn't try to load
Packit Service a31ea6
 * any catalog actually.
Packit Service a31ea6
 * this function is not thread safe, catalog initialization should
Packit Service a31ea6
 * preferably be done once at startup
Packit Service a31ea6
 */
Packit Service a31ea6
static void
Packit Service a31ea6
xmlInitializeCatalogData(void) {
Packit Service a31ea6
    if (xmlCatalogInitialized != 0)
Packit Service a31ea6
	return;
Packit Service a31ea6
Packit Service a31ea6
    if (getenv("XML_DEBUG_CATALOG"))
Packit Service a31ea6
	xmlDebugCatalogs = 1;
Packit Service a31ea6
    xmlCatalogMutex = xmlNewRMutex();
Packit Service a31ea6
Packit Service a31ea6
    xmlCatalogInitialized = 1;
Packit Service a31ea6
}
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlInitializeCatalog:
Packit Service a31ea6
 *
Packit Service a31ea6
 * Do the catalog initialization.
Packit Service a31ea6
 * this function is not thread safe, catalog initialization should
Packit Service a31ea6
 * preferably be done once at startup
Packit Service a31ea6
 */
Packit Service a31ea6
void
Packit Service a31ea6
xmlInitializeCatalog(void) {
Packit Service a31ea6
    if (xmlCatalogInitialized != 0)
Packit Service a31ea6
	return;
Packit Service a31ea6
Packit Service a31ea6
    xmlInitializeCatalogData();
Packit Service a31ea6
    xmlRMutexLock(xmlCatalogMutex);
Packit Service a31ea6
Packit Service a31ea6
    if (getenv("XML_DEBUG_CATALOG"))
Packit Service a31ea6
	xmlDebugCatalogs = 1;
Packit Service a31ea6
Packit Service a31ea6
    if (xmlDefaultCatalog == NULL) {
Packit Service a31ea6
	const char *catalogs;
Packit Service a31ea6
	char *path;
Packit Service a31ea6
	const char *cur, *paths;
Packit Service a31ea6
	xmlCatalogPtr catal;
Packit Service a31ea6
	xmlCatalogEntryPtr *nextent;
Packit Service a31ea6
Packit Service a31ea6
	catalogs = (const char *) getenv("XML_CATALOG_FILES");
Packit Service a31ea6
	if (catalogs == NULL)
Packit Service a31ea6
#if defined(_WIN32) && defined(_MSC_VER)
Packit Service a31ea6
    {
Packit Service a31ea6
		void* hmodule;
Packit Service a31ea6
		hmodule = GetModuleHandleA("libxml2.dll");
Packit Service a31ea6
		if (hmodule == NULL)
Packit Service a31ea6
			hmodule = GetModuleHandleA(NULL);
Packit Service a31ea6
		if (hmodule != NULL) {
Packit Service a31ea6
			char buf[256];
Packit Service a31ea6
			unsigned long len = GetModuleFileNameA(hmodule, buf, 255);
Packit Service a31ea6
			if (len != 0) {
Packit Service a31ea6
				char* p = &(buf[len]);
Packit Service a31ea6
				while (*p != '\\' && p > buf)
Packit Service a31ea6
					p--;
Packit Service a31ea6
				if (p != buf) {
Packit Service a31ea6
					xmlChar* uri;
Packit Service a31ea6
					strncpy(p, "\\..\\etc\\catalog", 255 - (p - buf));
Packit Service a31ea6
					uri = xmlCanonicPath((const xmlChar*)buf);
Packit Service a31ea6
					if (uri != NULL) {
Packit Service a31ea6
						strncpy(XML_XML_DEFAULT_CATALOG, uri, 255);
Packit Service a31ea6
						xmlFree(uri);
Packit Service a31ea6
					}
Packit Service a31ea6
				}
Packit Service a31ea6
			}
Packit Service a31ea6
		}
Packit Service a31ea6
		catalogs = XML_XML_DEFAULT_CATALOG;
Packit Service a31ea6
    }
Packit Service a31ea6
#else
Packit Service a31ea6
	    catalogs = XML_XML_DEFAULT_CATALOG;
Packit Service a31ea6
#endif
Packit Service a31ea6
Packit Service a31ea6
	catal = xmlCreateNewCatalog(XML_XML_CATALOG_TYPE,
Packit Service a31ea6
		xmlCatalogDefaultPrefer);
Packit Service a31ea6
	if (catal != NULL) {
Packit Service a31ea6
	    /* the XML_CATALOG_FILES envvar is allowed to contain a
Packit Service a31ea6
	       space-separated list of entries. */
Packit Service a31ea6
	    cur = catalogs;
Packit Service a31ea6
	    nextent = &catal->xml;
Packit Service a31ea6
	    while (*cur != '\0') {
Packit Service a31ea6
		while (xmlIsBlank_ch(*cur))
Packit Service a31ea6
		    cur++;
Packit Service a31ea6
		if (*cur != 0) {
Packit Service a31ea6
		    paths = cur;
Packit Service a31ea6
		    while ((*cur != 0) && (!xmlIsBlank_ch(*cur)))
Packit Service a31ea6
			cur++;
Packit Service a31ea6
		    path = (char *) xmlStrndup((const xmlChar *)paths, cur - paths);
Packit Service a31ea6
		    if (path != NULL) {
Packit Service a31ea6
			*nextent = xmlNewCatalogEntry(XML_CATA_CATALOG, NULL,
Packit Service a31ea6
				NULL, BAD_CAST path, xmlCatalogDefaultPrefer, NULL);
Packit Service a31ea6
			if (*nextent != NULL)
Packit Service a31ea6
			    nextent = &((*nextent)->next);
Packit Service a31ea6
			xmlFree(path);
Packit Service a31ea6
		    }
Packit Service a31ea6
		}
Packit Service a31ea6
	    }
Packit Service a31ea6
	    xmlDefaultCatalog = catal;
Packit Service a31ea6
	}
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    xmlRMutexUnlock(xmlCatalogMutex);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlLoadCatalog:
Packit Service a31ea6
 * @filename:  a file path
Packit Service a31ea6
 *
Packit Service a31ea6
 * Load the catalog and makes its definitions effective for the default
Packit Service a31ea6
 * external entity loader. It will recurse in SGML CATALOG entries.
Packit Service a31ea6
 * this function is not thread safe, catalog initialization should
Packit Service a31ea6
 * preferably be done once at startup
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns 0 in case of success -1 in case of error
Packit Service a31ea6
 */
Packit Service a31ea6
int
Packit Service a31ea6
xmlLoadCatalog(const char *filename)
Packit Service a31ea6
{
Packit Service a31ea6
    int ret;
Packit Service a31ea6
    xmlCatalogPtr catal;
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlCatalogInitialized)
Packit Service a31ea6
	xmlInitializeCatalogData();
Packit Service a31ea6
Packit Service a31ea6
    xmlRMutexLock(xmlCatalogMutex);
Packit Service a31ea6
Packit Service a31ea6
    if (xmlDefaultCatalog == NULL) {
Packit Service a31ea6
	catal = xmlLoadACatalog(filename);
Packit Service a31ea6
	if (catal == NULL) {
Packit Service a31ea6
	    xmlRMutexUnlock(xmlCatalogMutex);
Packit Service a31ea6
	    return(-1);
Packit Service a31ea6
	}
Packit Service a31ea6
Packit Service a31ea6
	xmlDefaultCatalog = catal;
Packit Service a31ea6
	xmlRMutexUnlock(xmlCatalogMutex);
Packit Service a31ea6
	return(0);
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    ret = xmlExpandCatalog(xmlDefaultCatalog, filename);
Packit Service a31ea6
    xmlRMutexUnlock(xmlCatalogMutex);
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlLoadCatalogs:
Packit Service a31ea6
 * @pathss:  a list of directories separated by a colon or a space.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Load the catalogs and makes their definitions effective for the default
Packit Service a31ea6
 * external entity loader.
Packit Service a31ea6
 * this function is not thread safe, catalog initialization should
Packit Service a31ea6
 * preferably be done once at startup
Packit Service a31ea6
 */
Packit Service a31ea6
void
Packit Service a31ea6
xmlLoadCatalogs(const char *pathss) {
Packit Service a31ea6
    const char *cur;
Packit Service a31ea6
    const char *paths;
Packit Service a31ea6
    xmlChar *path;
Packit Service a31ea6
#ifdef _WIN32
Packit Service a31ea6
    int i, iLen;
Packit Service a31ea6
#endif
Packit Service a31ea6
Packit Service a31ea6
    if (pathss == NULL)
Packit Service a31ea6
	return;
Packit Service a31ea6
Packit Service a31ea6
    cur = pathss;
Packit Service a31ea6
    while (*cur != 0) {
Packit Service a31ea6
	while (xmlIsBlank_ch(*cur)) cur++;
Packit Service a31ea6
	if (*cur != 0) {
Packit Service a31ea6
	    paths = cur;
Packit Service a31ea6
	    while ((*cur != 0) && (*cur != PATH_SEPARATOR) && (!xmlIsBlank_ch(*cur)))
Packit Service a31ea6
		cur++;
Packit Service a31ea6
	    path = xmlStrndup((const xmlChar *)paths, cur - paths);
Packit Service a31ea6
#ifdef _WIN32
Packit Service a31ea6
        iLen = strlen((const char*)path);
Packit Service a31ea6
        for(i = 0; i < iLen; i++) {
Packit Service a31ea6
            if(path[i] == '\\') {
Packit Service a31ea6
                path[i] = '/';
Packit Service a31ea6
            }
Packit Service a31ea6
        }
Packit Service a31ea6
#endif
Packit Service a31ea6
	    if (path != NULL) {
Packit Service a31ea6
		xmlLoadCatalog((const char *) path);
Packit Service a31ea6
		xmlFree(path);
Packit Service a31ea6
	    }
Packit Service a31ea6
	}
Packit Service a31ea6
	while (*cur == PATH_SEPARATOR)
Packit Service a31ea6
	    cur++;
Packit Service a31ea6
    }
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogCleanup:
Packit Service a31ea6
 *
Packit Service a31ea6
 * Free up all the memory associated with catalogs
Packit Service a31ea6
 */
Packit Service a31ea6
void
Packit Service a31ea6
xmlCatalogCleanup(void) {
Packit Service a31ea6
    if (xmlCatalogInitialized == 0)
Packit Service a31ea6
        return;
Packit Service a31ea6
Packit Service a31ea6
    xmlRMutexLock(xmlCatalogMutex);
Packit Service a31ea6
    if (xmlDebugCatalogs)
Packit Service a31ea6
	xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		"Catalogs cleanup\n");
Packit Service a31ea6
    if (xmlCatalogXMLFiles != NULL)
Packit Service a31ea6
	xmlHashFree(xmlCatalogXMLFiles,
Packit Service a31ea6
		    (xmlHashDeallocator)xmlFreeCatalogHashEntryList);
Packit Service a31ea6
    xmlCatalogXMLFiles = NULL;
Packit Service a31ea6
    if (xmlDefaultCatalog != NULL)
Packit Service a31ea6
	xmlFreeCatalog(xmlDefaultCatalog);
Packit Service a31ea6
    xmlDefaultCatalog = NULL;
Packit Service a31ea6
    xmlDebugCatalogs = 0;
Packit Service a31ea6
    xmlCatalogInitialized = 0;
Packit Service a31ea6
    xmlRMutexUnlock(xmlCatalogMutex);
Packit Service a31ea6
    xmlFreeRMutex(xmlCatalogMutex);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogResolveSystem:
Packit Service a31ea6
 * @sysID:  the system ID string
Packit Service a31ea6
 *
Packit Service a31ea6
 * Try to lookup the catalog resource for a system ID
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the resource if found or NULL otherwise, the value returned
Packit Service a31ea6
 *      must be freed by the caller.
Packit Service a31ea6
 */
Packit Service a31ea6
xmlChar *
Packit Service a31ea6
xmlCatalogResolveSystem(const xmlChar *sysID) {
Packit Service a31ea6
    xmlChar *ret;
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlCatalogInitialized)
Packit Service a31ea6
	xmlInitializeCatalog();
Packit Service a31ea6
Packit Service a31ea6
    ret = xmlACatalogResolveSystem(xmlDefaultCatalog, sysID);
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogResolvePublic:
Packit Service a31ea6
 * @pubID:  the public ID string
Packit Service a31ea6
 *
Packit Service a31ea6
 * Try to lookup the catalog reference associated to a public ID
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the resource if found or NULL otherwise, the value returned
Packit Service a31ea6
 *      must be freed by the caller.
Packit Service a31ea6
 */
Packit Service a31ea6
xmlChar *
Packit Service a31ea6
xmlCatalogResolvePublic(const xmlChar *pubID) {
Packit Service a31ea6
    xmlChar *ret;
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlCatalogInitialized)
Packit Service a31ea6
	xmlInitializeCatalog();
Packit Service a31ea6
Packit Service a31ea6
    ret = xmlACatalogResolvePublic(xmlDefaultCatalog, pubID);
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogResolve:
Packit Service a31ea6
 * @pubID:  the public ID string
Packit Service a31ea6
 * @sysID:  the system ID string
Packit Service a31ea6
 *
Packit Service a31ea6
 * Do a complete resolution lookup of an External Identifier
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the URI of the resource or NULL if not found, it must be freed
Packit Service a31ea6
 *      by the caller.
Packit Service a31ea6
 */
Packit Service a31ea6
xmlChar *
Packit Service a31ea6
xmlCatalogResolve(const xmlChar *pubID, const xmlChar *sysID) {
Packit Service a31ea6
    xmlChar *ret;
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlCatalogInitialized)
Packit Service a31ea6
	xmlInitializeCatalog();
Packit Service a31ea6
Packit Service a31ea6
    ret = xmlACatalogResolve(xmlDefaultCatalog, pubID, sysID);
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogResolveURI:
Packit Service a31ea6
 * @URI:  the URI
Packit Service a31ea6
 *
Packit Service a31ea6
 * Do a complete resolution lookup of an URI
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the URI of the resource or NULL if not found, it must be freed
Packit Service a31ea6
 *      by the caller.
Packit Service a31ea6
 */
Packit Service a31ea6
xmlChar *
Packit Service a31ea6
xmlCatalogResolveURI(const xmlChar *URI) {
Packit Service a31ea6
    xmlChar *ret;
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlCatalogInitialized)
Packit Service a31ea6
	xmlInitializeCatalog();
Packit Service a31ea6
Packit Service a31ea6
    ret = xmlACatalogResolveURI(xmlDefaultCatalog, URI);
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
#ifdef LIBXML_OUTPUT_ENABLED
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogDump:
Packit Service a31ea6
 * @out:  the file.
Packit Service a31ea6
 *
Packit Service a31ea6
 * Dump all the global catalog content to the given file.
Packit Service a31ea6
 */
Packit Service a31ea6
void
Packit Service a31ea6
xmlCatalogDump(FILE *out) {
Packit Service a31ea6
    if (out == NULL)
Packit Service a31ea6
	return;
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlCatalogInitialized)
Packit Service a31ea6
	xmlInitializeCatalog();
Packit Service a31ea6
Packit Service a31ea6
    xmlACatalogDump(xmlDefaultCatalog, out);
Packit Service a31ea6
}
Packit Service a31ea6
#endif /* LIBXML_OUTPUT_ENABLED */
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogAdd:
Packit Service a31ea6
 * @type:  the type of record to add to the catalog
Packit Service a31ea6
 * @orig:  the system, public or prefix to match
Packit Service a31ea6
 * @replace:  the replacement value for the match
Packit Service a31ea6
 *
Packit Service a31ea6
 * Add an entry in the catalog, it may overwrite existing but
Packit Service a31ea6
 * different entries.
Packit Service a31ea6
 * If called before any other catalog routine, allows to override the
Packit Service a31ea6
 * default shared catalog put in place by xmlInitializeCatalog();
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns 0 if successful, -1 otherwise
Packit Service a31ea6
 */
Packit Service a31ea6
int
Packit Service a31ea6
xmlCatalogAdd(const xmlChar *type, const xmlChar *orig, const xmlChar *replace) {
Packit Service a31ea6
    int res = -1;
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlCatalogInitialized)
Packit Service a31ea6
	xmlInitializeCatalogData();
Packit Service a31ea6
Packit Service a31ea6
    xmlRMutexLock(xmlCatalogMutex);
Packit Service a31ea6
    /*
Packit Service a31ea6
     * Specific case where one want to override the default catalog
Packit Service a31ea6
     * put in place by xmlInitializeCatalog();
Packit Service a31ea6
     */
Packit Service a31ea6
    if ((xmlDefaultCatalog == NULL) &&
Packit Service a31ea6
	(xmlStrEqual(type, BAD_CAST "catalog"))) {
Packit Service a31ea6
	xmlDefaultCatalog = xmlCreateNewCatalog(XML_XML_CATALOG_TYPE,
Packit Service a31ea6
		                          xmlCatalogDefaultPrefer);
Packit Service a31ea6
	xmlDefaultCatalog->xml = xmlNewCatalogEntry(XML_CATA_CATALOG, NULL,
Packit Service a31ea6
				    orig, NULL,  xmlCatalogDefaultPrefer, NULL);
Packit Service a31ea6
Packit Service a31ea6
	xmlRMutexUnlock(xmlCatalogMutex);
Packit Service a31ea6
	return(0);
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    res = xmlACatalogAdd(xmlDefaultCatalog, type, orig, replace);
Packit Service a31ea6
    xmlRMutexUnlock(xmlCatalogMutex);
Packit Service a31ea6
    return(res);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogRemove:
Packit Service a31ea6
 * @value:  the value to remove
Packit Service a31ea6
 *
Packit Service a31ea6
 * Remove an entry from the catalog
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the number of entries removed if successful, -1 otherwise
Packit Service a31ea6
 */
Packit Service a31ea6
int
Packit Service a31ea6
xmlCatalogRemove(const xmlChar *value) {
Packit Service a31ea6
    int res;
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlCatalogInitialized)
Packit Service a31ea6
	xmlInitializeCatalog();
Packit Service a31ea6
Packit Service a31ea6
    xmlRMutexLock(xmlCatalogMutex);
Packit Service a31ea6
    res = xmlACatalogRemove(xmlDefaultCatalog, value);
Packit Service a31ea6
    xmlRMutexUnlock(xmlCatalogMutex);
Packit Service a31ea6
    return(res);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogConvert:
Packit Service a31ea6
 *
Packit Service a31ea6
 * Convert all the SGML catalog entries as XML ones
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the number of entries converted if successful, -1 otherwise
Packit Service a31ea6
 */
Packit Service a31ea6
int
Packit Service a31ea6
xmlCatalogConvert(void) {
Packit Service a31ea6
    int res = -1;
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlCatalogInitialized)
Packit Service a31ea6
	xmlInitializeCatalog();
Packit Service a31ea6
Packit Service a31ea6
    xmlRMutexLock(xmlCatalogMutex);
Packit Service a31ea6
    res = xmlConvertSGMLCatalog(xmlDefaultCatalog);
Packit Service a31ea6
    xmlRMutexUnlock(xmlCatalogMutex);
Packit Service a31ea6
    return(res);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/************************************************************************
Packit Service a31ea6
 *									*
Packit Service a31ea6
 *	Public interface manipulating the common preferences		*
Packit Service a31ea6
 *									*
Packit Service a31ea6
 ************************************************************************/
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogGetDefaults:
Packit Service a31ea6
 *
Packit Service a31ea6
 * Used to get the user preference w.r.t. to what catalogs should
Packit Service a31ea6
 * be accepted
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the current xmlCatalogAllow value
Packit Service a31ea6
 */
Packit Service a31ea6
xmlCatalogAllow
Packit Service a31ea6
xmlCatalogGetDefaults(void) {
Packit Service a31ea6
    return(xmlCatalogDefaultAllow);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogSetDefaults:
Packit Service a31ea6
 * @allow:  what catalogs should be accepted
Packit Service a31ea6
 *
Packit Service a31ea6
 * Used to set the user preference w.r.t. to what catalogs should
Packit Service a31ea6
 * be accepted
Packit Service a31ea6
 */
Packit Service a31ea6
void
Packit Service a31ea6
xmlCatalogSetDefaults(xmlCatalogAllow allow) {
Packit Service a31ea6
    if (xmlDebugCatalogs) {
Packit Service a31ea6
	switch (allow) {
Packit Service a31ea6
	    case XML_CATA_ALLOW_NONE:
Packit Service a31ea6
		xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			"Disabling catalog usage\n");
Packit Service a31ea6
		break;
Packit Service a31ea6
	    case XML_CATA_ALLOW_GLOBAL:
Packit Service a31ea6
		xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			"Allowing only global catalogs\n");
Packit Service a31ea6
		break;
Packit Service a31ea6
	    case XML_CATA_ALLOW_DOCUMENT:
Packit Service a31ea6
		xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			"Allowing only catalogs from the document\n");
Packit Service a31ea6
		break;
Packit Service a31ea6
	    case XML_CATA_ALLOW_ALL:
Packit Service a31ea6
		xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			"Allowing all catalogs\n");
Packit Service a31ea6
		break;
Packit Service a31ea6
	}
Packit Service a31ea6
    }
Packit Service a31ea6
    xmlCatalogDefaultAllow = allow;
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogSetDefaultPrefer:
Packit Service a31ea6
 * @prefer:  the default preference for delegation
Packit Service a31ea6
 *
Packit Service a31ea6
 * Allows to set the preference between public and system for deletion
Packit Service a31ea6
 * in XML Catalog resolution. C.f. section 4.1.1 of the spec
Packit Service a31ea6
 * Values accepted are XML_CATA_PREFER_PUBLIC or XML_CATA_PREFER_SYSTEM
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the previous value of the default preference for delegation
Packit Service a31ea6
 */
Packit Service a31ea6
xmlCatalogPrefer
Packit Service a31ea6
xmlCatalogSetDefaultPrefer(xmlCatalogPrefer prefer) {
Packit Service a31ea6
    xmlCatalogPrefer ret = xmlCatalogDefaultPrefer;
Packit Service a31ea6
Packit Service a31ea6
    if (prefer == XML_CATA_PREFER_NONE)
Packit Service a31ea6
	return(ret);
Packit Service a31ea6
Packit Service a31ea6
    if (xmlDebugCatalogs) {
Packit Service a31ea6
	switch (prefer) {
Packit Service a31ea6
	    case XML_CATA_PREFER_PUBLIC:
Packit Service a31ea6
		xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			"Setting catalog preference to PUBLIC\n");
Packit Service a31ea6
		break;
Packit Service a31ea6
	    case XML_CATA_PREFER_SYSTEM:
Packit Service a31ea6
		xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
			"Setting catalog preference to SYSTEM\n");
Packit Service a31ea6
		break;
Packit Service a31ea6
	    default:
Packit Service a31ea6
		return(ret);
Packit Service a31ea6
	}
Packit Service a31ea6
    }
Packit Service a31ea6
    xmlCatalogDefaultPrefer = prefer;
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogSetDebug:
Packit Service a31ea6
 * @level:  the debug level of catalogs required
Packit Service a31ea6
 *
Packit Service a31ea6
 * Used to set the debug level for catalog operation, 0 disable
Packit Service a31ea6
 * debugging, 1 enable it
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the previous value of the catalog debugging level
Packit Service a31ea6
 */
Packit Service a31ea6
int
Packit Service a31ea6
xmlCatalogSetDebug(int level) {
Packit Service a31ea6
    int ret = xmlDebugCatalogs;
Packit Service a31ea6
Packit Service a31ea6
    if (level <= 0)
Packit Service a31ea6
        xmlDebugCatalogs = 0;
Packit Service a31ea6
    else
Packit Service a31ea6
	xmlDebugCatalogs = level;
Packit Service a31ea6
    return(ret);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/************************************************************************
Packit Service a31ea6
 *									*
Packit Service a31ea6
 *   Minimal interfaces used for per-document catalogs by the parser	*
Packit Service a31ea6
 *									*
Packit Service a31ea6
 ************************************************************************/
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogFreeLocal:
Packit Service a31ea6
 * @catalogs:  a document's list of catalogs
Packit Service a31ea6
 *
Packit Service a31ea6
 * Free up the memory associated to the catalog list
Packit Service a31ea6
 */
Packit Service a31ea6
void
Packit Service a31ea6
xmlCatalogFreeLocal(void *catalogs) {
Packit Service a31ea6
    xmlCatalogEntryPtr catal;
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlCatalogInitialized)
Packit Service a31ea6
	xmlInitializeCatalog();
Packit Service a31ea6
Packit Service a31ea6
    catal = (xmlCatalogEntryPtr) catalogs;
Packit Service a31ea6
    if (catal != NULL)
Packit Service a31ea6
	xmlFreeCatalogEntryList(catal);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogAddLocal:
Packit Service a31ea6
 * @catalogs:  a document's list of catalogs
Packit Service a31ea6
 * @URL:  the URL to a new local catalog
Packit Service a31ea6
 *
Packit Service a31ea6
 * Add the new entry to the catalog list
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the updated list
Packit Service a31ea6
 */
Packit Service a31ea6
void *
Packit Service a31ea6
xmlCatalogAddLocal(void *catalogs, const xmlChar *URL) {
Packit Service a31ea6
    xmlCatalogEntryPtr catal, add;
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlCatalogInitialized)
Packit Service a31ea6
	xmlInitializeCatalog();
Packit Service a31ea6
Packit Service a31ea6
    if (URL == NULL)
Packit Service a31ea6
	return(catalogs);
Packit Service a31ea6
Packit Service a31ea6
    if (xmlDebugCatalogs)
Packit Service a31ea6
	xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		"Adding document catalog %s\n", URL);
Packit Service a31ea6
Packit Service a31ea6
    add = xmlNewCatalogEntry(XML_CATA_CATALOG, NULL, URL, NULL,
Packit Service a31ea6
	                     xmlCatalogDefaultPrefer, NULL);
Packit Service a31ea6
    if (add == NULL)
Packit Service a31ea6
	return(catalogs);
Packit Service a31ea6
Packit Service a31ea6
    catal = (xmlCatalogEntryPtr) catalogs;
Packit Service a31ea6
    if (catal == NULL)
Packit Service a31ea6
	return((void *) add);
Packit Service a31ea6
Packit Service a31ea6
    while (catal->next != NULL)
Packit Service a31ea6
	catal = catal->next;
Packit Service a31ea6
    catal->next = add;
Packit Service a31ea6
    return(catalogs);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogLocalResolve:
Packit Service a31ea6
 * @catalogs:  a document's list of catalogs
Packit Service a31ea6
 * @pubID:  the public ID string
Packit Service a31ea6
 * @sysID:  the system ID string
Packit Service a31ea6
 *
Packit Service a31ea6
 * Do a complete resolution lookup of an External Identifier using a
Packit Service a31ea6
 * document's private catalog list
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the URI of the resource or NULL if not found, it must be freed
Packit Service a31ea6
 *      by the caller.
Packit Service a31ea6
 */
Packit Service a31ea6
xmlChar *
Packit Service a31ea6
xmlCatalogLocalResolve(void *catalogs, const xmlChar *pubID,
Packit Service a31ea6
	               const xmlChar *sysID) {
Packit Service a31ea6
    xmlCatalogEntryPtr catal;
Packit Service a31ea6
    xmlChar *ret;
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlCatalogInitialized)
Packit Service a31ea6
	xmlInitializeCatalog();
Packit Service a31ea6
Packit Service a31ea6
    if ((pubID == NULL) && (sysID == NULL))
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    if (xmlDebugCatalogs) {
Packit Service a31ea6
        if ((pubID != NULL) && (sysID != NULL)) {
Packit Service a31ea6
            xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
                            "Local Resolve: pubID %s sysID %s\n", pubID, sysID);
Packit Service a31ea6
        } else if (pubID != NULL) {
Packit Service a31ea6
            xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
                            "Local Resolve: pubID %s\n", pubID);
Packit Service a31ea6
        } else {
Packit Service a31ea6
            xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
                            "Local Resolve: sysID %s\n", sysID);
Packit Service a31ea6
        }
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    catal = (xmlCatalogEntryPtr) catalogs;
Packit Service a31ea6
    if (catal == NULL)
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    ret = xmlCatalogListXMLResolve(catal, pubID, sysID);
Packit Service a31ea6
    if ((ret != NULL) && (ret != XML_CATAL_BREAK))
Packit Service a31ea6
	return(ret);
Packit Service a31ea6
    return(NULL);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogLocalResolveURI:
Packit Service a31ea6
 * @catalogs:  a document's list of catalogs
Packit Service a31ea6
 * @URI:  the URI
Packit Service a31ea6
 *
Packit Service a31ea6
 * Do a complete resolution lookup of an URI using a
Packit Service a31ea6
 * document's private catalog list
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the URI of the resource or NULL if not found, it must be freed
Packit Service a31ea6
 *      by the caller.
Packit Service a31ea6
 */
Packit Service a31ea6
xmlChar *
Packit Service a31ea6
xmlCatalogLocalResolveURI(void *catalogs, const xmlChar *URI) {
Packit Service a31ea6
    xmlCatalogEntryPtr catal;
Packit Service a31ea6
    xmlChar *ret;
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlCatalogInitialized)
Packit Service a31ea6
	xmlInitializeCatalog();
Packit Service a31ea6
Packit Service a31ea6
    if (URI == NULL)
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    if (xmlDebugCatalogs)
Packit Service a31ea6
	xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		"Resolve URI %s\n", URI);
Packit Service a31ea6
Packit Service a31ea6
    catal = (xmlCatalogEntryPtr) catalogs;
Packit Service a31ea6
    if (catal == NULL)
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
    ret = xmlCatalogListXMLResolveURI(catal, URI);
Packit Service a31ea6
    if ((ret != NULL) && (ret != XML_CATAL_BREAK))
Packit Service a31ea6
	return(ret);
Packit Service a31ea6
    return(NULL);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/************************************************************************
Packit Service a31ea6
 *									*
Packit Service a31ea6
 *			Deprecated interfaces				*
Packit Service a31ea6
 *									*
Packit Service a31ea6
 ************************************************************************/
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogGetSystem:
Packit Service a31ea6
 * @sysID:  the system ID string
Packit Service a31ea6
 *
Packit Service a31ea6
 * Try to lookup the catalog reference associated to a system ID
Packit Service a31ea6
 * DEPRECATED, use xmlCatalogResolveSystem()
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the resource if found or NULL otherwise.
Packit Service a31ea6
 */
Packit Service a31ea6
const xmlChar *
Packit Service a31ea6
xmlCatalogGetSystem(const xmlChar *sysID) {
Packit Service a31ea6
    xmlChar *ret;
Packit Service a31ea6
    static xmlChar result[1000];
Packit Service a31ea6
    static int msg = 0;
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlCatalogInitialized)
Packit Service a31ea6
	xmlInitializeCatalog();
Packit Service a31ea6
Packit Service a31ea6
    if (msg == 0) {
Packit Service a31ea6
	xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		"Use of deprecated xmlCatalogGetSystem() call\n");
Packit Service a31ea6
	msg++;
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    if (sysID == NULL)
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    /*
Packit Service a31ea6
     * Check first the XML catalogs
Packit Service a31ea6
     */
Packit Service a31ea6
    if (xmlDefaultCatalog != NULL) {
Packit Service a31ea6
	ret = xmlCatalogListXMLResolve(xmlDefaultCatalog->xml, NULL, sysID);
Packit Service a31ea6
	if ((ret != NULL) && (ret != XML_CATAL_BREAK)) {
Packit Service a31ea6
	    snprintf((char *) result, sizeof(result) - 1, "%s", (char *) ret);
Packit Service a31ea6
	    result[sizeof(result) - 1] = 0;
Packit Service a31ea6
	    return(result);
Packit Service a31ea6
	}
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    if (xmlDefaultCatalog != NULL)
Packit Service a31ea6
	return(xmlCatalogGetSGMLSystem(xmlDefaultCatalog->sgml, sysID));
Packit Service a31ea6
    return(NULL);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
/**
Packit Service a31ea6
 * xmlCatalogGetPublic:
Packit Service a31ea6
 * @pubID:  the public ID string
Packit Service a31ea6
 *
Packit Service a31ea6
 * Try to lookup the catalog reference associated to a public ID
Packit Service a31ea6
 * DEPRECATED, use xmlCatalogResolvePublic()
Packit Service a31ea6
 *
Packit Service a31ea6
 * Returns the resource if found or NULL otherwise.
Packit Service a31ea6
 */
Packit Service a31ea6
const xmlChar *
Packit Service a31ea6
xmlCatalogGetPublic(const xmlChar *pubID) {
Packit Service a31ea6
    xmlChar *ret;
Packit Service a31ea6
    static xmlChar result[1000];
Packit Service a31ea6
    static int msg = 0;
Packit Service a31ea6
Packit Service a31ea6
    if (!xmlCatalogInitialized)
Packit Service a31ea6
	xmlInitializeCatalog();
Packit Service a31ea6
Packit Service a31ea6
    if (msg == 0) {
Packit Service a31ea6
	xmlGenericError(xmlGenericErrorContext,
Packit Service a31ea6
		"Use of deprecated xmlCatalogGetPublic() call\n");
Packit Service a31ea6
	msg++;
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    if (pubID == NULL)
Packit Service a31ea6
	return(NULL);
Packit Service a31ea6
Packit Service a31ea6
    /*
Packit Service a31ea6
     * Check first the XML catalogs
Packit Service a31ea6
     */
Packit Service a31ea6
    if (xmlDefaultCatalog != NULL) {
Packit Service a31ea6
	ret = xmlCatalogListXMLResolve(xmlDefaultCatalog->xml, pubID, NULL);
Packit Service a31ea6
	if ((ret != NULL) && (ret != XML_CATAL_BREAK)) {
Packit Service a31ea6
	    snprintf((char *) result, sizeof(result) - 1, "%s", (char *) ret);
Packit Service a31ea6
	    result[sizeof(result) - 1] = 0;
Packit Service a31ea6
	    return(result);
Packit Service a31ea6
	}
Packit Service a31ea6
    }
Packit Service a31ea6
Packit Service a31ea6
    if (xmlDefaultCatalog != NULL)
Packit Service a31ea6
	return(xmlCatalogGetSGMLPublic(xmlDefaultCatalog->sgml, pubID));
Packit Service a31ea6
    return(NULL);
Packit Service a31ea6
}
Packit Service a31ea6
Packit Service a31ea6
#define bottom_catalog
Packit Service a31ea6
#include "elfgcchack.h"
Packit Service a31ea6
#endif /* LIBXML_CATALOG_ENABLED */