Skip to content

Commit 33a9d0d

Browse files
committed
Use Thread Local Storage for warray buffer
Signed-off-by: Steffen Jaeckel <[email protected]>
1 parent 334465d commit 33a9d0d

10 files changed

+37
-173
lines changed

demo/test.c

Lines changed: 11 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2502,20 +2502,24 @@ struct thread_info {
25022502
int ret;
25032503
};
25042504

2505-
static void *run_pthread(void *arg)
2505+
static void run(struct thread_info *tinfo)
25062506
{
2507-
struct thread_info *tinfo = arg;
2508-
25092507
tinfo->ret = tinfo->t->fn();
25102508

2509+
if (mp_warray_free() == -2)
2510+
tinfo->ret = EXIT_FAILURE;
2511+
}
2512+
2513+
static void *run_pthread(void *arg)
2514+
{
2515+
run(arg);
2516+
25112517
return arg;
25122518
}
25132519

25142520
static unsigned long run_msvc(void *arg)
25152521
{
2516-
struct thread_info *tinfo = arg;
2517-
2518-
tinfo->ret = tinfo->t->fn();
2522+
run(arg);
25192523

25202524
return 0;
25212525
}
@@ -2609,7 +2613,6 @@ static int unit_tests(int argc, char **argv)
26092613
};
26102614
struct thread_info test_threads[sizeof(test)/sizeof(test[0])], *res;
26112615
unsigned long i, ok, fail, nop;
2612-
size_t n_threads = MP_HAS(MULTI_THREADED) ? sizeof(test) / sizeof(test[0]) : 1;
26132616
uint64_t t;
26142617
int j;
26152618
ok = fail = nop = 0;
@@ -2620,8 +2623,7 @@ static int unit_tests(int argc, char **argv)
26202623
mp_rand_source(s_mp_rand_jenkins);
26212624

26222625
if (MP_HAS(MP_SMALL_STACK_SIZE)) {
2623-
printf("Small-stack enabled with %zu warray buffers\n\n", n_threads);
2624-
DO(mp_warray_init(n_threads, 1));
2626+
printf("Small-stack enabled\n\n");
26252627
}
26262628

26272629
if (MP_HAS(MULTI_THREADED)) {

mp_warray_free.c

Lines changed: 6 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -9,19 +9,13 @@ MP_STATIC_ASSERT(warray_free_sz_does_not_overflow, (sizeof(mp_word) * MP_WARRAY)
99
static int s_warray_free(void)
1010
{
1111
int ret = 0;
12-
size_t n;
13-
for (n = 0; n < s_mp_warray.allocated; ++n) {
14-
if (s_mp_warray.l_used[n].warray) {
15-
ret = -2;
16-
goto ERR_OUT;
17-
}
12+
if (s_mp_warray.w_used)
13+
return -2;
14+
if (s_mp_warray.w_free) {
15+
s_mp_zero_buf(s_mp_warray.w_free, sizeof(mp_word) * MP_WARRAY);
16+
MP_FREE(s_mp_warray.w_free, sizeof(mp_word) * MP_WARRAY);
17+
s_mp_warray.w_free = NULL;
1818
}
19-
for (n = 0; n < s_mp_warray.allocated; ++n) {
20-
MP_FREE(s_mp_warray.l_free[n].warray, sizeof(mp_word) * MP_WARRAY);
21-
s_mp_warray.l_free[n].warray = NULL;
22-
}
23-
s_mp_warray_free(s_mp_warray.usable);
24-
ERR_OUT:
2519
return ret;
2620
}
2721

mp_warray_init.c

Lines changed: 0 additions & 46 deletions
This file was deleted.

s_mp_cmpexch_n.c

Lines changed: 0 additions & 43 deletions
This file was deleted.

s_mp_warray.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,6 @@
33
/* LibTomMath, multiple-precision integer library -- Tom St Denis */
44
/* SPDX-License-Identifier: Unlicense */
55

6-
st_warray s_mp_warray;
6+
mp_thread st_warray s_mp_warray = { 0 };
77

88
#endif

s_mp_warray_free.c

Lines changed: 0 additions & 17 deletions
This file was deleted.

s_mp_warray_get.c

Lines changed: 7 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -5,34 +5,14 @@
55

66
void *s_mp_warray_get(void)
77
{
8-
void *ret = NULL;
9-
size_t n;
10-
if (s_mp_warray.usable == 0) {
11-
if (mp_warray_init(1, false) != MP_OKAY)
12-
return NULL;
8+
if (s_mp_warray.w_used)
9+
return NULL;
10+
if (s_mp_warray.w_free == NULL) {
11+
s_mp_warray.w_free = MP_CALLOC(MP_WARRAY, sizeof(mp_word));
1312
}
14-
for (n = 0; n < s_mp_warray.allocated;) {
15-
if (s_mp_warray.l_free[n].warray == NULL) {
16-
n++;
17-
continue;
18-
}
19-
ret = s_mp_warray.l_free[n].warray;
20-
if (s_mp_cmpexch_n(&s_mp_warray.l_free[n].warray, &ret, NULL)) {
21-
s_mp_warray.l_used[n].warray = ret;
22-
goto LBL_OUT;
23-
}
24-
/* restart from the beginning if we missed a potential slot */
25-
n = 0;
26-
}
27-
ret = NULL;
28-
if (s_mp_warray.allocated + 1 > s_mp_warray.usable)
29-
goto LBL_OUT;
30-
ret = MP_CALLOC(MP_WARRAY, sizeof(mp_word));
31-
if (ret != NULL)
32-
s_mp_warray.l_used[s_mp_warray.allocated++].warray = ret;
33-
34-
LBL_OUT:
35-
return ret;
13+
s_mp_warray.w_used = s_mp_warray.w_free;
14+
s_mp_warray.w_free = NULL;
15+
return s_mp_warray.w_used;
3616
}
3717

3818
#endif

s_mp_warray_put.c

Lines changed: 4 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -5,14 +5,10 @@
55

66
void s_mp_warray_put(void *w)
77
{
8-
size_t n, allocated = s_mp_warray.allocated;
9-
for (n = 0; n < allocated; ++n) {
10-
if (s_mp_warray.l_used[n].warray == w) {
11-
s_mp_warray.l_used[n].warray = NULL;
12-
s_mp_warray.l_free[n].warray = w;
13-
break;
14-
}
15-
}
8+
if (s_mp_warray.w_free || s_mp_warray.w_used != w)
9+
return;
10+
s_mp_warray.w_free = w;
11+
s_mp_warray.w_used = NULL;
1612
}
1713

1814
#endif

tommath.h

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -588,7 +588,6 @@ mp_err mp_fread(mp_int *a, int radix, FILE *stream) MP_WUR;
588588
mp_err mp_fwrite(const mp_int *a, int radix, FILE *stream) MP_WUR;
589589
#endif
590590

591-
mp_err mp_warray_init(size_t n_alloc, bool preallocate);
592591
int mp_warray_free(void);
593592

594593
#define mp_to_binary(M, S, N) mp_to_radix((M), (S), (N), NULL, 2)

tommath_private.h

Lines changed: 8 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -234,8 +234,6 @@ MP_PRIVATE mp_err s_mp_radix_size_overestimate(const mp_int *a, const int radix,
234234
MP_PRIVATE mp_err s_mp_fp_log(const mp_int *a, mp_int *c) MP_WUR;
235235
MP_PRIVATE mp_err s_mp_fp_log_d(const mp_int *a, mp_word *c) MP_WUR;
236236

237-
MP_PRIVATE bool s_mp_cmpexch_n(void **ptr, void **expected, void *desired);
238-
239237
#ifdef MP_SMALL_STACK_SIZE
240238
#define MP_SMALL_STACK_SIZE_C
241239
#define MP_ALLOC_WARRAY(name) *name = s_mp_warray_get()
@@ -247,19 +245,20 @@ MP_PRIVATE bool s_mp_cmpexch_n(void **ptr, void **expected, void *desired);
247245
#define MP_CHECK_WARRAY(name)
248246
#endif
249247

250-
struct warray {
251-
void *warray;
252-
};
248+
#if defined(_MSC_VER)
249+
#define mp_thread __declspec(thread)
250+
#elif defined(__GNUC__)
251+
#define mp_thread __thread
252+
#endif
253+
253254
typedef struct {
254-
struct warray *l_free, *l_used;
255-
size_t allocated, usable;
255+
void *w_free, *w_used;
256256
} st_warray;
257257

258-
extern MP_PRIVATE st_warray s_mp_warray;
258+
extern MP_PRIVATE mp_thread st_warray s_mp_warray;
259259

260260
MP_PRIVATE void *s_mp_warray_get(void);
261261
MP_PRIVATE void s_mp_warray_put(void *w);
262-
MP_PRIVATE void s_mp_warray_free(size_t n);
263262

264263
#define MP_RADIX_MAP_REVERSE_SIZE 80u
265264
extern MP_PRIVATE const char s_mp_radix_map[];

0 commit comments

Comments
 (0)