Skip to content

Commit 044b702

Browse files
jmichalski-antkartben
authored andcommitted
posix: fix pthread thread specific data cleanup
It was never deallocationg pthread_key_data nor it was removing the node with it from list Signed-off-by: Jakub Michalski <[email protected]>
1 parent 3d3ffa2 commit 044b702

File tree

3 files changed

+31
-8
lines changed

3 files changed

+31
-8
lines changed

lib/posix/options/key.c

+1-6
Original file line numberDiff line numberDiff line change
@@ -13,14 +13,9 @@
1313
#include <zephyr/sys/__assert.h>
1414
#include <zephyr/sys/sem.h>
1515

16-
struct pthread_key_data {
17-
sys_snode_t node;
18-
pthread_thread_data thread_data;
19-
};
20-
2116
LOG_MODULE_REGISTER(pthread_key, CONFIG_PTHREAD_KEY_LOG_LEVEL);
2217

23-
static SYS_SEM_DEFINE(pthread_key_lock, 1, 1);
18+
SYS_SEM_DEFINE(pthread_key_lock, 1, 1);
2419

2520
/* This is non-standard (i.e. an implementation detail) */
2621
#define PTHREAD_KEY_INITIALIZER (-1)

lib/posix/options/posix_internal.h

+5
Original file line numberDiff line numberDiff line change
@@ -84,6 +84,11 @@ typedef struct pthread_thread_data {
8484
void *spec_data;
8585
} pthread_thread_data;
8686

87+
struct pthread_key_data {
88+
sys_snode_t node;
89+
pthread_thread_data thread_data;
90+
};
91+
8792
static inline bool is_pthread_obj_initialized(uint32_t obj)
8893
{
8994
return (obj & PTHREAD_OBJ_MASK_INIT) != 0;

lib/posix/options/pthread.c

+25-2
Original file line numberDiff line numberDiff line change
@@ -458,19 +458,42 @@ static void posix_thread_recycle_work_handler(struct k_work *work)
458458
}
459459
static K_WORK_DELAYABLE_DEFINE(posix_thread_recycle_work, posix_thread_recycle_work_handler);
460460

461+
extern struct sys_sem pthread_key_lock;
462+
461463
static void posix_thread_finalize(struct posix_thread *t, void *retval)
462464
{
463-
sys_snode_t *node_l;
465+
sys_snode_t *node_l, *node_s;
464466
pthread_key_obj *key_obj;
465467
pthread_thread_data *thread_spec_data;
468+
sys_snode_t *node_key_data, *node_key_data_s, *node_key_data_prev = NULL;
469+
struct pthread_key_data *key_data;
466470

467-
SYS_SLIST_FOR_EACH_NODE(&t->key_list, node_l) {
471+
SYS_SLIST_FOR_EACH_NODE_SAFE(&t->key_list, node_l, node_s) {
468472
thread_spec_data = (pthread_thread_data *)node_l;
469473
if (thread_spec_data != NULL) {
470474
key_obj = thread_spec_data->key;
471475
if (key_obj->destructor != NULL) {
472476
(key_obj->destructor)(thread_spec_data->spec_data);
473477
}
478+
479+
SYS_SEM_LOCK(&pthread_key_lock) {
480+
SYS_SLIST_FOR_EACH_NODE_SAFE(
481+
&key_obj->key_data_l,
482+
node_key_data,
483+
node_key_data_s) {
484+
key_data = (struct pthread_key_data *)node_key_data;
485+
if (&key_data->thread_data == thread_spec_data) {
486+
sys_slist_remove(
487+
&key_obj->key_data_l,
488+
node_key_data_prev,
489+
node_key_data
490+
);
491+
k_free(key_data);
492+
break;
493+
}
494+
node_key_data_prev = node_key_data;
495+
}
496+
}
474497
}
475498
}
476499

0 commit comments

Comments
 (0)