diff --git a/Zend/zend.c b/Zend/zend.c index 01ce306312756..ada509181ceb0 100644 --- a/Zend/zend.c +++ b/Zend/zend.c @@ -823,6 +823,10 @@ static void executor_globals_ctor(zend_executor_globals *executor_globals) /* {{ executor_globals->pid = 0; executor_globals->oldact = (struct sigaction){0}; #endif + memset(executor_globals->strtod_state.freelist, 0, + sizeof(executor_globals->strtod_state.freelist)); + executor_globals->strtod_state.p5s = NULL; + executor_globals->strtod_state.result = NULL; } /* }}} */ @@ -918,7 +922,6 @@ void zend_startup(zend_utility_functions *utility_functions) /* {{{ */ #endif zend_startup_hrtime(); - zend_startup_strtod(); zend_startup_extensions_mechanism(); /* Set up utility functions and values */ diff --git a/Zend/zend_globals.h b/Zend/zend_globals.h index 8900a5f416f53..e126d61b34abf 100644 --- a/Zend/zend_globals.h +++ b/Zend/zend_globals.h @@ -41,6 +41,7 @@ #include "zend_arena.h" #include "zend_call_stack.h" #include "zend_max_execution_timer.h" +#include "zend_strtod.h" /* Define ZTS if you want a thread-safe Zend */ /*#undef ZTS*/ @@ -304,6 +305,8 @@ struct _zend_executor_globals { struct sigaction oldact; #endif + zend_strtod_state strtod_state; + void *reserved[ZEND_MAX_RESERVED_RESOURCES]; }; diff --git a/Zend/zend_strtod.c b/Zend/zend_strtod.c index 8a59196285080..6a358bb1128eb 100644 --- a/Zend/zend_strtod.c +++ b/Zend/zend_strtod.c @@ -189,6 +189,7 @@ #include #include #include "zend_strtod_int.h" +#include "zend_globals.h" #ifndef Long #define Long int32_t @@ -197,6 +198,16 @@ #define ULong uint32_t #endif +#undef Bigint +#undef freelist +#undef p5s +#undef dtoa_result + +#define Bigint _zend_strtod_bigint +#define freelist (EG(strtod_state).freelist) +#define p5s (EG(strtod_state).p5s) +#define dtoa_result (EG(strtod_state).result) + #ifdef DEBUG static void Bug(const char *message) { fprintf(stderr, "%s\n", message); @@ -224,6 +235,7 @@ extern void *MALLOC(size_t); #endif #else #define MALLOC malloc +#define FREE free #endif #ifndef Omit_Private_Memory @@ -522,7 +534,7 @@ BCinfo { int dp0, dp1, dplen, dsign, e0, inexact, nd, nd0, rounding, scale, uflc #define FREE_DTOA_LOCK(n) /*nothing*/ #endif -#define Kmax 7 +#define Kmax ZEND_STRTOD_K_MAX struct Bigint { @@ -533,37 +545,23 @@ Bigint { typedef struct Bigint Bigint; +#ifndef Bigint static Bigint *freelist[Kmax+1]; +#endif static void destroy_freelist(void); static void free_p5s(void); -#ifdef ZTS +#ifdef MULTIPLE_THREADS static MUTEX_T dtoa_mutex; static MUTEX_T pow5mult_mutex; #endif /* ZTS */ -ZEND_API int zend_startup_strtod(void) /* {{{ */ -{ -#ifdef ZTS - dtoa_mutex = tsrm_mutex_alloc(); - pow5mult_mutex = tsrm_mutex_alloc(); -#endif - return 1; -} -/* }}} */ ZEND_API int zend_shutdown_strtod(void) /* {{{ */ { destroy_freelist(); free_p5s(); -#ifdef ZTS - tsrm_mutex_free(dtoa_mutex); - dtoa_mutex = NULL; - - tsrm_mutex_free(pow5mult_mutex); - pow5mult_mutex = NULL; -#endif return 1; } /* }}} */ @@ -627,11 +625,7 @@ Bfree { if (v) { if (v->k > Kmax) -#ifdef FREE FREE((void*)v); -#else - free((void*)v); -#endif else { ACQUIRE_DTOA_LOCK(0); v->next = freelist[v->k]; @@ -947,7 +941,9 @@ mult return c; } +#ifndef p5s static Bigint *p5s; +#endif static Bigint * pow5mult @@ -3602,7 +3598,7 @@ zend_strtod return sign ? -dval(&rv) : dval(&rv); } -#ifndef MULTIPLE_THREADS +#if !defined(MULTIPLE_THREADS) && !defined(dtoa_result) ZEND_TLS char *dtoa_result; #endif @@ -4616,7 +4612,7 @@ static void destroy_freelist(void) Bigint **listp = &freelist[i]; while ((tmp = *listp) != NULL) { *listp = tmp->next; - free(tmp); + FREE(tmp); } freelist[i] = NULL; } @@ -4631,7 +4627,8 @@ static void free_p5s(void) listp = &p5s; while ((tmp = *listp) != NULL) { *listp = tmp->next; - free(tmp); + FREE(tmp); } + p5s = NULL; FREE_DTOA_LOCK(1) } diff --git a/Zend/zend_strtod.h b/Zend/zend_strtod.h index b049e56e370c5..4e0d85a7d2166 100644 --- a/Zend/zend_strtod.h +++ b/Zend/zend_strtod.h @@ -23,6 +23,13 @@ #include BEGIN_EXTERN_C() +#define ZEND_STRTOD_K_MAX 7 +typedef struct _zend_strtod_bigint zend_strtod_bigint; +typedef struct _zend_strtod_state { + zend_strtod_bigint *freelist[ZEND_STRTOD_K_MAX+1]; + zend_strtod_bigint *p5s; + char *result; +} zend_strtod_state; ZEND_API void zend_freedtoa(char *s); ZEND_API char *zend_dtoa(double _d, int mode, int ndigits, int *decpt, bool *sign, char **rve); ZEND_API char *zend_gcvt(double value, int ndigit, char dec_point, char exponent, char *buf); @@ -30,7 +37,6 @@ ZEND_API double zend_strtod(const char *s00, const char **se); ZEND_API double zend_hex_strtod(const char *str, const char **endptr); ZEND_API double zend_oct_strtod(const char *str, const char **endptr); ZEND_API double zend_bin_strtod(const char *str, const char **endptr); -ZEND_API int zend_startup_strtod(void); ZEND_API int zend_shutdown_strtod(void); END_EXTERN_C() diff --git a/Zend/zend_strtod_int.h b/Zend/zend_strtod_int.h index f528b4753eabb..79b993f7dbd9f 100644 --- a/Zend/zend_strtod_int.h +++ b/Zend/zend_strtod_int.h @@ -104,24 +104,4 @@ #endif #endif -#ifdef ZTS -#define MULTIPLE_THREADS 1 - -#define ACQUIRE_DTOA_LOCK(x) \ - if (0 == x) { \ - tsrm_mutex_lock(dtoa_mutex); \ - } else if (1 == x) { \ - tsrm_mutex_lock(pow5mult_mutex); \ - } - -#define FREE_DTOA_LOCK(x) \ - if (0 == x) { \ - tsrm_mutex_unlock(dtoa_mutex); \ - } else if (1 == x) { \ - tsrm_mutex_unlock(pow5mult_mutex); \ - } - - -#endif - #endif /* ZEND_STRTOD_INT_H */