mirror of
https://gitlab.gnome.org/GNOME/libxml2.git
synced 2025-10-24 13:33:01 +03:00
globals: Introduce xmlCheckThreadLocalStorage
Checks whether (emulated) thread-local storage could be allocated.
This commit is contained in:
25
globals.c
25
globals.c
@@ -806,6 +806,31 @@ xmlNewGlobalState(void)
|
||||
}
|
||||
#endif /* LIBXML_THREAD_ENABLED */
|
||||
|
||||
/**
|
||||
* xmlCheckThreadLocalStorage:
|
||||
*
|
||||
* Check whether thread-local storage could be allocated.
|
||||
*
|
||||
* In multithreaded environments, this function should be called once
|
||||
* in each thread before calling other library functions to make sure
|
||||
* that thread-local storage was allocated properly.
|
||||
*
|
||||
* Returns 0 on success or -1 if a memory allocation failed. A failed
|
||||
* allocation signals a typically fatal and irrecoverable out-of-memory
|
||||
* situation. Don't call any library functions in this case.
|
||||
*
|
||||
* This function never fails for the "main" thread which is the first
|
||||
* thread calling xmlInitParser.
|
||||
*
|
||||
* Available since v2.12.0.
|
||||
*/
|
||||
int
|
||||
xmlCheckThreadLocalStorage(void) {
|
||||
if (IS_MAIN_THREAD)
|
||||
return(0);
|
||||
return((xmlGetGlobalState() == NULL) ? -1 : 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* xmlGetGlobalState:
|
||||
*
|
||||
|
||||
@@ -82,6 +82,7 @@ typedef void (*xmlDeregisterNodeFunc) (xmlNodePtr node);
|
||||
typedef struct _xmlGlobalState xmlGlobalState;
|
||||
typedef xmlGlobalState *xmlGlobalStatePtr;
|
||||
|
||||
XMLPUBFUN int xmlCheckThreadLocalStorage(void);
|
||||
XML_DEPRECATED
|
||||
XMLPUBFUN void xmlInitializeGlobalState(xmlGlobalStatePtr gs);
|
||||
XML_DEPRECATED
|
||||
|
||||
@@ -3,10 +3,11 @@
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
|
||||
#if defined(LIBXML_THREAD_ENABLED) && defined(LIBXML_CATALOG_ENABLED)
|
||||
#include <libxml/globals.h>
|
||||
#include <libxml/threads.h>
|
||||
#include <libxml/parser.h>
|
||||
#include <libxml/threads.h>
|
||||
#include <libxml/globals.h>
|
||||
|
||||
#if defined(LIBXML_THREAD_ENABLED) && defined(LIBXML_CATALOG_ENABLED)
|
||||
#include <libxml/catalog.h>
|
||||
#ifdef HAVE_PTHREAD_H
|
||||
#include <pthread.h>
|
||||
@@ -57,6 +58,12 @@ thread_specific_data(void *private_data)
|
||||
const char *filename = params->filename;
|
||||
int okay = 1;
|
||||
|
||||
if (xmlCheckThreadLocalStorage() != 0) {
|
||||
printf("xmlCheckThreadLocalStorage failed\n");
|
||||
params->okay = 0;
|
||||
return(NULL);
|
||||
}
|
||||
|
||||
if (!strcmp(filename, "test/threads/invalid.xml")) {
|
||||
xmlDoValidityCheckingDefaultValue = 0;
|
||||
xmlGenericErrorContext = stdout;
|
||||
@@ -98,17 +105,39 @@ thread_specific_data(void *private_data)
|
||||
return(NULL);
|
||||
}
|
||||
|
||||
#ifdef HAVE_PTHREAD_H
|
||||
#ifdef _WIN32
|
||||
static DWORD WINAPI
|
||||
win32_thread_specific_data(void *private_data)
|
||||
{
|
||||
thread_specific_data(private_data);
|
||||
return(0);
|
||||
}
|
||||
#endif
|
||||
#endif /* LIBXML_THREADS_ENABLED */
|
||||
|
||||
int
|
||||
main(void)
|
||||
{
|
||||
unsigned int i, repeat;
|
||||
int ret;
|
||||
unsigned int repeat;
|
||||
int status = 0;
|
||||
|
||||
(void) repeat;
|
||||
|
||||
xmlInitParser();
|
||||
|
||||
if (xmlCheckThreadLocalStorage() != 0) {
|
||||
printf("xmlCheckThreadLocalStorage failed for main thread\n");
|
||||
return(1);
|
||||
}
|
||||
|
||||
#if defined(LIBXML_THREAD_ENABLED) && defined(LIBXML_CATALOG_ENABLED)
|
||||
for (repeat = 0;repeat < TEST_REPEAT_COUNT;repeat++) {
|
||||
unsigned int i;
|
||||
int ret;
|
||||
|
||||
xmlLoadCatalog(catalog);
|
||||
|
||||
#ifdef HAVE_PTHREAD_H
|
||||
memset(tid, 0xff, sizeof(*tid)*num_threads);
|
||||
|
||||
for (i = 0; i < num_threads; i++) {
|
||||
@@ -127,35 +156,7 @@ main(void)
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
xmlCatalogCleanup();
|
||||
for (i = 0; i < num_threads; i++)
|
||||
if (threadParams[i].okay == 0)
|
||||
printf("Thread %d handling %s failed\n", i,
|
||||
threadParams[i].filename);
|
||||
}
|
||||
xmlCleanupParser();
|
||||
return (0);
|
||||
}
|
||||
#elif defined(_WIN32)
|
||||
static DWORD WINAPI
|
||||
win32_thread_specific_data(void *private_data)
|
||||
{
|
||||
thread_specific_data(private_data);
|
||||
return(0);
|
||||
}
|
||||
|
||||
int
|
||||
main(void)
|
||||
{
|
||||
unsigned int i, repeat;
|
||||
BOOL ret;
|
||||
|
||||
xmlInitParser();
|
||||
for (repeat = 0;repeat < TEST_REPEAT_COUNT;repeat++)
|
||||
{
|
||||
xmlLoadCatalog(catalog);
|
||||
|
||||
for (i = 0; i < num_threads; i++)
|
||||
{
|
||||
tid[i] = (HANDLE) -1;
|
||||
@@ -187,26 +188,22 @@ main(void)
|
||||
}
|
||||
CloseHandle (tid[i]);
|
||||
}
|
||||
#endif /* pthreads */
|
||||
|
||||
xmlCatalogCleanup();
|
||||
|
||||
for (i = 0; i < num_threads; i++) {
|
||||
if (threadParams[i].okay == 0)
|
||||
if (threadParams[i].okay == 0) {
|
||||
printf("Thread %d handling %s failed\n", i,
|
||||
threadParams[i].filename);
|
||||
status = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif /* LIBXML_THREADS_ENABLED */
|
||||
|
||||
xmlCleanupParser();
|
||||
|
||||
return (0);
|
||||
return (status);
|
||||
}
|
||||
#endif /* pthreads */
|
||||
|
||||
#else /* !LIBXML_THREADS_ENABLED */
|
||||
int
|
||||
main(void)
|
||||
{
|
||||
fprintf(stderr, "libxml was not compiled with thread or catalog support\n");
|
||||
return (0);
|
||||
}
|
||||
#endif
|
||||
|
||||
Reference in New Issue
Block a user