mirror of
https://gitlab.gnome.org/GNOME/libxml2.git
synced 2025-03-23 02:50:08 +03:00
threads: Allocate global RMutexes statically
Avoid memory allocations during initialization.
This commit is contained in:
parent
5d36664fc9
commit
769e5a4a42
48
catalog.c
48
catalog.c
@ -40,6 +40,7 @@
|
||||
#include "private/cata.h"
|
||||
#include "private/buf.h"
|
||||
#include "private/error.h"
|
||||
#include "private/threads.h"
|
||||
|
||||
#define MAX_DELEGATE 50
|
||||
#define MAX_CATAL_DEPTH 50
|
||||
@ -166,7 +167,7 @@ static xmlCatalogPtr xmlDefaultCatalog = NULL;
|
||||
* It also protects xmlCatalogXMLFiles
|
||||
* The core of this readers/writer scheme is in xmlFetchXMLCatalogFile()
|
||||
*/
|
||||
static xmlRMutexPtr xmlCatalogMutex = NULL;
|
||||
static xmlRMutex xmlCatalogMutex;
|
||||
|
||||
/*
|
||||
* Whether the default system catalog was initialized.
|
||||
@ -1384,10 +1385,10 @@ xmlFetchXMLCatalogFile(xmlCatalogEntryPtr catal) {
|
||||
/*
|
||||
* lock the whole catalog for modification
|
||||
*/
|
||||
xmlRMutexLock(xmlCatalogMutex);
|
||||
xmlRMutexLock(&xmlCatalogMutex);
|
||||
if (catal->children != NULL) {
|
||||
/* Okay someone else did it in the meantime */
|
||||
xmlRMutexUnlock(xmlCatalogMutex);
|
||||
xmlRMutexUnlock(&xmlCatalogMutex);
|
||||
return(0);
|
||||
}
|
||||
|
||||
@ -1404,7 +1405,7 @@ xmlFetchXMLCatalogFile(xmlCatalogEntryPtr catal) {
|
||||
else
|
||||
catal->children = doc;
|
||||
catal->dealloc = 0;
|
||||
xmlRMutexUnlock(xmlCatalogMutex);
|
||||
xmlRMutexUnlock(&xmlCatalogMutex);
|
||||
return(0);
|
||||
}
|
||||
if (xmlDebugCatalogs)
|
||||
@ -1420,7 +1421,7 @@ xmlFetchXMLCatalogFile(xmlCatalogEntryPtr catal) {
|
||||
doc = xmlParseXMLCatalogFile(catal->prefer, catal->URL);
|
||||
if (doc == NULL) {
|
||||
catal->type = XML_CATA_BROKEN_CATALOG;
|
||||
xmlRMutexUnlock(xmlCatalogMutex);
|
||||
xmlRMutexUnlock(&xmlCatalogMutex);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
@ -1439,7 +1440,7 @@ xmlFetchXMLCatalogFile(xmlCatalogEntryPtr catal) {
|
||||
"%s added to file hash\n", catal->URL);
|
||||
xmlHashAddEntry(xmlCatalogXMLFiles, catal->URL, doc);
|
||||
}
|
||||
xmlRMutexUnlock(xmlCatalogMutex);
|
||||
xmlRMutexUnlock(&xmlCatalogMutex);
|
||||
return(0);
|
||||
}
|
||||
|
||||
@ -3050,7 +3051,7 @@ void
|
||||
xmlInitCatalogInternal(void) {
|
||||
if (getenv("XML_DEBUG_CATALOG"))
|
||||
xmlDebugCatalogs = 1;
|
||||
xmlCatalogMutex = xmlNewRMutex();
|
||||
xmlInitRMutex(&xmlCatalogMutex);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -3065,7 +3066,7 @@ xmlInitializeCatalog(void) {
|
||||
|
||||
xmlInitParser();
|
||||
|
||||
xmlRMutexLock(xmlCatalogMutex);
|
||||
xmlRMutexLock(&xmlCatalogMutex);
|
||||
|
||||
if (xmlDefaultCatalog == NULL) {
|
||||
const char *catalogs;
|
||||
@ -3106,7 +3107,7 @@ xmlInitializeCatalog(void) {
|
||||
}
|
||||
}
|
||||
|
||||
xmlRMutexUnlock(xmlCatalogMutex);
|
||||
xmlRMutexUnlock(&xmlCatalogMutex);
|
||||
|
||||
xmlCatalogInitialized = 1;
|
||||
}
|
||||
@ -3131,22 +3132,22 @@ xmlLoadCatalog(const char *filename)
|
||||
|
||||
xmlInitParser();
|
||||
|
||||
xmlRMutexLock(xmlCatalogMutex);
|
||||
xmlRMutexLock(&xmlCatalogMutex);
|
||||
|
||||
if (xmlDefaultCatalog == NULL) {
|
||||
catal = xmlLoadACatalog(filename);
|
||||
if (catal == NULL) {
|
||||
xmlRMutexUnlock(xmlCatalogMutex);
|
||||
xmlRMutexUnlock(&xmlCatalogMutex);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
xmlDefaultCatalog = catal;
|
||||
xmlRMutexUnlock(xmlCatalogMutex);
|
||||
xmlRMutexUnlock(&xmlCatalogMutex);
|
||||
return(0);
|
||||
}
|
||||
|
||||
ret = xmlExpandCatalog(xmlDefaultCatalog, filename);
|
||||
xmlRMutexUnlock(xmlCatalogMutex);
|
||||
xmlRMutexUnlock(&xmlCatalogMutex);
|
||||
return(ret);
|
||||
}
|
||||
|
||||
@ -3204,7 +3205,7 @@ xmlLoadCatalogs(const char *pathss) {
|
||||
*/
|
||||
void
|
||||
xmlCatalogCleanup(void) {
|
||||
xmlRMutexLock(xmlCatalogMutex);
|
||||
xmlRMutexLock(&xmlCatalogMutex);
|
||||
if (xmlDebugCatalogs)
|
||||
xmlCatalogPrintDebug(
|
||||
"Catalogs cleanup\n");
|
||||
@ -3216,7 +3217,7 @@ xmlCatalogCleanup(void) {
|
||||
xmlDefaultCatalog = NULL;
|
||||
xmlDebugCatalogs = 0;
|
||||
xmlCatalogInitialized = 0;
|
||||
xmlRMutexUnlock(xmlCatalogMutex);
|
||||
xmlRMutexUnlock(&xmlCatalogMutex);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -3226,8 +3227,7 @@ xmlCatalogCleanup(void) {
|
||||
*/
|
||||
void
|
||||
xmlCleanupCatalogInternal(void) {
|
||||
xmlFreeRMutex(xmlCatalogMutex);
|
||||
xmlCatalogMutex = NULL;
|
||||
xmlCleanupRMutex(&xmlCatalogMutex);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -3350,7 +3350,7 @@ xmlCatalogAdd(const xmlChar *type, const xmlChar *orig, const xmlChar *replace)
|
||||
if (!xmlCatalogInitialized)
|
||||
xmlInitializeCatalog();
|
||||
|
||||
xmlRMutexLock(xmlCatalogMutex);
|
||||
xmlRMutexLock(&xmlCatalogMutex);
|
||||
/*
|
||||
* Specific case where one want to override the default catalog
|
||||
* put in place by xmlInitializeCatalog();
|
||||
@ -3363,12 +3363,12 @@ xmlCatalogAdd(const xmlChar *type, const xmlChar *orig, const xmlChar *replace)
|
||||
xmlDefaultCatalog->xml = xmlNewCatalogEntry(XML_CATA_CATALOG, NULL,
|
||||
orig, NULL, xmlCatalogDefaultPrefer, NULL);
|
||||
}
|
||||
xmlRMutexUnlock(xmlCatalogMutex);
|
||||
xmlRMutexUnlock(&xmlCatalogMutex);
|
||||
return(0);
|
||||
}
|
||||
|
||||
res = xmlACatalogAdd(xmlDefaultCatalog, type, orig, replace);
|
||||
xmlRMutexUnlock(xmlCatalogMutex);
|
||||
xmlRMutexUnlock(&xmlCatalogMutex);
|
||||
return(res);
|
||||
}
|
||||
|
||||
@ -3387,9 +3387,9 @@ xmlCatalogRemove(const xmlChar *value) {
|
||||
if (!xmlCatalogInitialized)
|
||||
xmlInitializeCatalog();
|
||||
|
||||
xmlRMutexLock(xmlCatalogMutex);
|
||||
xmlRMutexLock(&xmlCatalogMutex);
|
||||
res = xmlACatalogRemove(xmlDefaultCatalog, value);
|
||||
xmlRMutexUnlock(xmlCatalogMutex);
|
||||
xmlRMutexUnlock(&xmlCatalogMutex);
|
||||
return(res);
|
||||
}
|
||||
|
||||
@ -3407,9 +3407,9 @@ xmlCatalogConvert(void) {
|
||||
if (!xmlCatalogInitialized)
|
||||
xmlInitializeCatalog();
|
||||
|
||||
xmlRMutexLock(xmlCatalogMutex);
|
||||
xmlRMutexLock(&xmlCatalogMutex);
|
||||
res = xmlConvertSGMLCatalog(xmlDefaultCatalog);
|
||||
xmlRMutexUnlock(xmlCatalogMutex);
|
||||
xmlRMutexUnlock(&xmlCatalogMutex);
|
||||
return(res);
|
||||
}
|
||||
|
||||
|
@ -27,9 +27,31 @@ struct _xmlMutex {
|
||||
#endif
|
||||
};
|
||||
|
||||
/*
|
||||
* xmlRMutex are reentrant mutual exception locks
|
||||
*/
|
||||
struct _xmlRMutex {
|
||||
#ifdef HAVE_POSIX_THREADS
|
||||
pthread_mutex_t lock;
|
||||
unsigned int held;
|
||||
unsigned int waiters;
|
||||
pthread_t tid;
|
||||
pthread_cond_t cv;
|
||||
#elif defined HAVE_WIN32_THREADS
|
||||
CRITICAL_SECTION cs;
|
||||
#else
|
||||
int empty;
|
||||
#endif
|
||||
};
|
||||
|
||||
XML_HIDDEN void
|
||||
xmlInitMutex(xmlMutexPtr mutex);
|
||||
XML_HIDDEN void
|
||||
xmlCleanupMutex(xmlMutexPtr mutex);
|
||||
|
||||
XML_HIDDEN void
|
||||
xmlInitRMutex(xmlRMutexPtr mutex);
|
||||
XML_HIDDEN void
|
||||
xmlCleanupRMutex(xmlRMutexPtr mutex);
|
||||
|
||||
#endif /* XML_THREADS_H_PRIVATE__ */
|
||||
|
79
threads.c
79
threads.c
@ -44,24 +44,7 @@
|
||||
* be hosted on allocated blocks needing them for the allocation ...
|
||||
*/
|
||||
|
||||
/*
|
||||
* xmlRMutex are reentrant mutual exception locks
|
||||
*/
|
||||
struct _xmlRMutex {
|
||||
#ifdef HAVE_POSIX_THREADS
|
||||
pthread_mutex_t lock;
|
||||
unsigned int held;
|
||||
unsigned int waiters;
|
||||
pthread_t tid;
|
||||
pthread_cond_t cv;
|
||||
#elif defined HAVE_WIN32_THREADS
|
||||
CRITICAL_SECTION cs;
|
||||
#else
|
||||
int empty;
|
||||
#endif
|
||||
};
|
||||
|
||||
static xmlRMutexPtr xmlLibraryLock = NULL;
|
||||
static xmlRMutex xmlLibraryLock;
|
||||
|
||||
/**
|
||||
* xmlInitMutex:
|
||||
@ -176,6 +159,20 @@ xmlMutexUnlock(xmlMutexPtr tok)
|
||||
#endif
|
||||
}
|
||||
|
||||
void
|
||||
xmlInitRMutex(xmlRMutexPtr tok) {
|
||||
(void) tok;
|
||||
|
||||
#ifdef HAVE_POSIX_THREADS
|
||||
pthread_mutex_init(&tok->lock, NULL);
|
||||
tok->held = 0;
|
||||
tok->waiters = 0;
|
||||
pthread_cond_init(&tok->cv, NULL);
|
||||
#elif defined HAVE_WIN32_THREADS
|
||||
InitializeCriticalSection(&tok->cs);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* xmlNewRMutex:
|
||||
*
|
||||
@ -194,17 +191,22 @@ xmlNewRMutex(void)
|
||||
tok = malloc(sizeof(xmlRMutex));
|
||||
if (tok == NULL)
|
||||
return (NULL);
|
||||
#ifdef HAVE_POSIX_THREADS
|
||||
pthread_mutex_init(&tok->lock, NULL);
|
||||
tok->held = 0;
|
||||
tok->waiters = 0;
|
||||
pthread_cond_init(&tok->cv, NULL);
|
||||
#elif defined HAVE_WIN32_THREADS
|
||||
InitializeCriticalSection(&tok->cs);
|
||||
#endif
|
||||
xmlInitRMutex(tok);
|
||||
return (tok);
|
||||
}
|
||||
|
||||
void
|
||||
xmlCleanupRMutex(xmlRMutexPtr tok) {
|
||||
(void) tok;
|
||||
|
||||
#ifdef HAVE_POSIX_THREADS
|
||||
pthread_mutex_destroy(&tok->lock);
|
||||
pthread_cond_destroy(&tok->cv);
|
||||
#elif defined HAVE_WIN32_THREADS
|
||||
DeleteCriticalSection(&tok->cs);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* xmlFreeRMutex:
|
||||
* @tok: the reentrant mutex
|
||||
@ -213,16 +215,11 @@ xmlNewRMutex(void)
|
||||
* reentrant mutex.
|
||||
*/
|
||||
void
|
||||
xmlFreeRMutex(xmlRMutexPtr tok ATTRIBUTE_UNUSED)
|
||||
xmlFreeRMutex(xmlRMutexPtr tok)
|
||||
{
|
||||
if (tok == NULL)
|
||||
return;
|
||||
#ifdef HAVE_POSIX_THREADS
|
||||
pthread_mutex_destroy(&tok->lock);
|
||||
pthread_cond_destroy(&tok->cv);
|
||||
#elif defined HAVE_WIN32_THREADS
|
||||
DeleteCriticalSection(&tok->cs);
|
||||
#endif
|
||||
xmlCleanupRMutex(tok);
|
||||
free(tok);
|
||||
}
|
||||
|
||||
@ -328,7 +325,7 @@ xmlGetThreadId(void)
|
||||
void
|
||||
xmlLockLibrary(void)
|
||||
{
|
||||
xmlRMutexLock(xmlLibraryLock);
|
||||
xmlRMutexLock(&xmlLibraryLock);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -340,7 +337,7 @@ xmlLockLibrary(void)
|
||||
void
|
||||
xmlUnlockLibrary(void)
|
||||
{
|
||||
xmlRMutexUnlock(xmlLibraryLock);
|
||||
xmlRMutexUnlock(&xmlLibraryLock);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -367,6 +364,16 @@ xmlCleanupThreads(void)
|
||||
{
|
||||
}
|
||||
|
||||
static void
|
||||
xmlInitThreadsInternal(void) {
|
||||
xmlInitRMutex(&xmlLibraryLock);
|
||||
}
|
||||
|
||||
static void
|
||||
xmlCleanupThreadsInternal(void) {
|
||||
xmlCleanupRMutex(&xmlLibraryLock);
|
||||
}
|
||||
|
||||
/************************************************************************
|
||||
* *
|
||||
* Library wide initialization *
|
||||
@ -390,6 +397,7 @@ xmlInitParserInternal(void) {
|
||||
*/
|
||||
xmlInitRandom(); /* Required by xmlInitGlobalsInternal */
|
||||
xmlInitMemoryInternal();
|
||||
xmlInitThreadsInternal();
|
||||
xmlInitGlobalsInternal();
|
||||
xmlInitDictInternal();
|
||||
xmlInitEncodingInternal();
|
||||
@ -471,6 +479,7 @@ xmlCleanupParser(void) {
|
||||
xmlCleanupDictInternal();
|
||||
xmlCleanupRandom();
|
||||
xmlCleanupGlobalsInternal();
|
||||
xmlCleanupThreadsInternal();
|
||||
|
||||
/*
|
||||
* Must come last. xmlCleanupGlobalsInternal can call xmlFree which
|
||||
|
Loading…
x
Reference in New Issue
Block a user