Skip to content

Commit e21e6c1

Browse files
Niranjhana Nnashif
authored andcommitted
tests: posix: improve pthread_key test
In addition to testing all the APIs, this enhancement tests the following two scenarios - when multiple threads use a single key for storage - when a single thread associates its value with multiple keys Signed-off-by: Niranjhana N <niranjhana.n@intel.com>
1 parent 0aa437a commit e21e6c1

File tree

1 file changed

+134
-21
lines changed

1 file changed

+134
-21
lines changed

tests/posix/pthread_key/src/pthread_key.c

Lines changed: 134 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -8,13 +8,15 @@
88
#include <kernel.h>
99
#include <posix/pthread.h>
1010

11+
#define N_THR 2
12+
#define N_KEY 2
1113
#define STACKSZ 1024
1214
#define BUFFSZ 48
1315

14-
K_THREAD_STACK_ARRAY_DEFINE(stacks, 1, STACKSZ);
16+
K_THREAD_STACK_ARRAY_DEFINE(stacks, N_THR, STACKSZ);
1517

16-
pthread_key_t key;
17-
static pthread_once_t key_once;
18+
pthread_key_t key, keys[N_KEY];
19+
static pthread_once_t key_once, keys_once;
1820

1921
void *thread_top(void *p1)
2022
{
@@ -24,8 +26,9 @@ void *thread_top(void *p1)
2426
void *getval;
2527
char *buffer[BUFFSZ];
2628

27-
zassert_true((int)(value = k_malloc(sizeof(buffer))),
28-
"thread could not allocate storage");
29+
value = k_malloc(sizeof(buffer));
30+
31+
zassert_true((int)value, "thread could not allocate storage");
2932

3033
ret = pthread_setspecific(key, (void *)value);
3134

@@ -42,14 +45,44 @@ void *thread_top(void *p1)
4245
zassert_equal(value, getval,
4346
"set and retrieved values are different");
4447

45-
printk("\nset value = %d and retrieved value = %d\n",
48+
printk("set value = %d and retrieved value = %d\n",
4649
(int)value, (int)getval);
4750

48-
ret = pthread_key_delete(key);
51+
return NULL;
52+
}
4953

50-
/* TESTPOINT: Check if key is deleted */
51-
zassert_false(ret, "attempt to delete key failed");
54+
void *thread_func(void *p1)
55+
{
56+
int i, ret = -1;
57+
58+
void *value;
59+
void *getval;
60+
char *buffer[BUFFSZ];
61+
62+
value = k_malloc(sizeof(buffer));
5263

64+
zassert_true((int)value, "thread could not allocate storage");
65+
66+
for (i = 0; i < N_KEY; i++) {
67+
ret = pthread_setspecific(keys[i], (void *)value);
68+
69+
/* TESTPOINT: Check if thread's value is associated with keys */
70+
zassert_false(ret, "pthread_setspecific failed");
71+
}
72+
73+
for (i = 0; i < N_KEY; i++) {
74+
getval = 0;
75+
getval = pthread_getspecific(keys[i]);
76+
77+
/* TESTPOINT: Check if pthread_getspecific returns the same
78+
* value set by pthread_setspecific for each of the keys
79+
*/
80+
zassert_equal(value, getval,
81+
"set and retrieved values are different");
82+
83+
printk("key %d: set value = %d and retrieved value = %d\n",
84+
i, (int)value, (int)getval);
85+
}
5386
return NULL;
5487
}
5588

@@ -61,45 +94,125 @@ static void make_key(void)
6194
zassert_false(ret, "insufficient memory to create key");
6295
}
6396

97+
static void make_keys(void)
98+
{
99+
int i, ret = 0;
100+
101+
for (i = 0; i < N_KEY; i++) {
102+
ret = pthread_key_create(&keys[i], NULL);
103+
zassert_false(ret, "insufficient memory to create keys");
104+
}
105+
}
106+
64107
/**
65108
* @brief Test to demonstrate pthread_key APIs usage
66109
*
67-
* @details The test spawns a thread which uses pthread_once() to
110+
* @details The tests spawn a thread which uses pthread_once() to
68111
* create a key via pthread_key_create() API. It then sets the
69-
* thread-specific value to the key using pthread_set_specific() and
70-
* gets it back using pthread_get_specific and asserts that they
112+
* thread-specific value to the key using pthread_setspecific() and
113+
* gets it back using pthread_getspecific and asserts that they
71114
* are equal. It then deletes the key using pthread_key_delete().
115+
* Both the sub-tests do the above, but one with multiple threads
116+
* using the same key and the other with a single thread using
117+
* multiple keys.
72118
*/
73119

74-
void test_pthread_key(void)
120+
void test_multiple_threads_single_key(void)
75121
{
76-
int ret = -1;
122+
int i, ret = -1;
77123

78-
pthread_attr_t attr;
124+
pthread_attr_t attr[N_THR];
79125
struct sched_param schedparam;
80-
pthread_t newthread;
126+
pthread_t newthread[N_THR];
127+
void *retval;
81128

82129
ret = pthread_once(&key_once, make_key);
83130

84131
/* TESTPOINT: Check if key is created */
85132
zassert_false(ret, "attempt to create key failed");
86133

87-
pthread_attr_init(&attr);
134+
printk("\nDifferent threads set different values to same key:\n");
135+
136+
/* Creating threads with lowest application priority */
137+
for (i = 0; i < N_THR; i++) {
138+
ret = pthread_attr_init(&attr[i]);
139+
if (ret != 0) {
140+
zassert_false(pthread_attr_destroy(&attr[i]),
141+
"Unable to destroy pthread object attr");
142+
zassert_false(pthread_attr_init(&attr[i]),
143+
"Unable to create pthread object attr");
144+
}
145+
146+
schedparam.priority = 2;
147+
pthread_attr_setschedparam(&attr[i], &schedparam);
148+
pthread_attr_setstack(&attr[i], &stacks[i][0], STACKSZ);
149+
150+
ret = pthread_create(&newthread[i], &attr[i], thread_top,
151+
(void *)i);
152+
153+
/* TESTPOINT: Check if threads are created successfully */
154+
zassert_false(ret, "attempt to create threads failed");
155+
}
156+
157+
for (i = 0; i < N_THR; i++) {
158+
printk("thread %d: ", i);
159+
pthread_join(newthread[i], &retval);
160+
}
161+
162+
ret = pthread_key_delete(key);
163+
164+
/* TESTPOINT: Check if key is deleted */
165+
zassert_false(ret, "attempt to delete key failed");
166+
printk("\n");
167+
}
168+
169+
void test_single_thread_multiple_keys(void)
170+
{
171+
int i, ret = -1;
172+
173+
pthread_attr_t attr;
174+
struct sched_param schedparam;
175+
pthread_t newthread;
176+
177+
ret = pthread_once(&keys_once, make_keys);
178+
179+
/* TESTPOINT: Check if keys are created successfully */
180+
zassert_false(ret, "attempt to create keys failed");
181+
182+
printk("\nSingle thread associates its value with different keys:\n");
183+
ret = pthread_attr_init(&attr);
184+
if (ret != 0) {
185+
zassert_false(pthread_attr_destroy(&attr),
186+
"Unable to destroy pthread object attr");
187+
zassert_false(pthread_attr_init(&attr),
188+
"Unable to create pthread object attr");
189+
}
190+
88191
schedparam.priority = 2;
89192
pthread_attr_setschedparam(&attr, &schedparam);
90193
pthread_attr_setstack(&attr, &stacks[0][0], STACKSZ);
91194

92-
ret = pthread_create(&newthread, &attr, thread_top,
195+
ret = pthread_create(&newthread, &attr, thread_func,
93196
(void *)0);
94197

198+
/*TESTPOINT: Check if thread is created successfully */
95199
zassert_false(ret, "attempt to create thread failed");
96200

97201
pthread_join(newthread, NULL);
202+
203+
for (i = 0; i < N_KEY; i++) {
204+
ret = pthread_key_delete(keys[i]);
205+
206+
/* TESTPOINT: Check if keys are deleted */
207+
zassert_false(ret, "attempt to delete keys failed");
208+
}
209+
printk("\n");
98210
}
99211

100212
void test_main(void)
101213
{
102-
ztest_test_suite(test_pthread_keys,
103-
ztest_unit_test(test_pthread_key));
104-
ztest_run_test_suite(test_pthread_keys);
214+
ztest_test_suite(test_pthread_key,
215+
ztest_unit_test(test_multiple_threads_single_key),
216+
ztest_unit_test(test_single_thread_multiple_keys));
217+
ztest_run_test_suite(test_pthread_key);
105218
}

0 commit comments

Comments
 (0)