1 /*
2 * Copyright (c) 2016 Intel Corporation
3 *
4 * SPDX-License-Identifier: Apache-2.0
5 */
6
7 #include <zephyr/ztest.h>
8
9 K_SEM_DEFINE(static_preem_start_sema, 0, 1);
10 K_SEM_DEFINE(preem_start_sema, 0, 1);
11 K_SEM_DEFINE(static_coop_start_sema, 0, 1);
12 K_SEM_DEFINE(coop_start_sema, 0, 1);
13
14 K_SEM_DEFINE(end_sema, 0, 1);
15 /*macro definition*/
16 #define INIT_COOP_PRIO -2
17 #define INIT_COOP_STACK_SIZE (500 + CONFIG_TEST_EXTRA_STACK_SIZE)
18 #define INIT_COOP_P1 ((void *)0xFFFF0000)
19 #define INIT_COOP_P2 ((void *)0xCDEF)
20 #define INIT_COOP_P3_static ((void *)&static_coop_start_sema)
21 #define INIT_COOP_P3 ((void *)&coop_start_sema)
22 #define INIT_COOP_OPTION (K_USER | K_INHERIT_PERMS)
23 #define INIT_COOP_DELAY 2000
24 #define INIT_PREEMPT_PRIO 1
25 #define INIT_PREEMPT_STACK_SIZE (499 + CONFIG_TEST_EXTRA_STACK_SIZE)
26 #define INIT_PREEMPT_P1 ((void *)5)
27 #define INIT_PREEMPT_P2 ((void *)6)
28 #define INIT_PREEMPT_P3_static ((void *)&static_preem_start_sema)
29 #define INIT_PREEMPT_P3 ((void *)&preem_start_sema)
30 #define INIT_PREEMPT_OPTION (K_USER | K_INHERIT_PERMS)
31 #define INIT_PREEMPT_DELAY 0
32
33 static void thread_entry(void *p1, void *p2, void *p3);
34
35 K_THREAD_DEFINE(T_KDEFINE_COOP_THREAD, INIT_COOP_STACK_SIZE,
36 thread_entry, INIT_COOP_P1, INIT_COOP_P2, INIT_COOP_P3_static,
37 INIT_COOP_PRIO, INIT_COOP_OPTION, INIT_COOP_DELAY);
38
39 K_THREAD_DEFINE(T_KDEFINE_PREEMPT_THREAD, INIT_PREEMPT_STACK_SIZE,
40 thread_entry, INIT_PREEMPT_P1, INIT_PREEMPT_P2, INIT_PREEMPT_P3_static,
41 INIT_PREEMPT_PRIO, INIT_PREEMPT_OPTION, INIT_PREEMPT_DELAY);
42
43 K_THREAD_ACCESS_GRANT(T_KDEFINE_COOP_THREAD, &static_preem_start_sema,
44 &preem_start_sema, &static_coop_start_sema, &coop_start_sema, &end_sema);
45 K_THREAD_ACCESS_GRANT(T_KDEFINE_PREEMPT_THREAD, &static_preem_start_sema,
46 &preem_start_sema, &static_coop_start_sema, &coop_start_sema, &end_sema);
47
48 /*local variables*/
49 static K_THREAD_STACK_DEFINE(stack_coop, INIT_COOP_STACK_SIZE);
50 static K_THREAD_STACK_DEFINE(stack_preempt, INIT_PREEMPT_STACK_SIZE);
51 static struct k_thread thread_coop;
52 static struct k_thread thread_preempt;
53 static ZTEST_BMEM uint64_t t_create;
54 static ZTEST_BMEM struct thread_data {
55 int init_prio;
56 int32_t init_delay;
57 void *init_p1;
58 void *init_p2;
59 void *init_p3;
60 } expected;
61
62 /*entry routines*/
thread_entry(void * p1,void * p2,void * p3)63 static void thread_entry(void *p1, void *p2, void *p3)
64 {
65 if (t_create) {
66 uint64_t t_delay = k_uptime_get() - t_create;
67 /**TESTPOINT: check delay start*/
68 zassert_true(t_delay >= expected.init_delay,
69 "k_thread_create delay start failed");
70 }
71
72 k_sem_take(p3, K_FOREVER);
73
74 k_tid_t tid = k_current_get();
75 /**TESTPOINT: check priority and params*/
76 zassert_equal(k_thread_priority_get(tid), expected.init_prio);
77 zassert_equal(p1, expected.init_p1);
78 zassert_equal(p2, expected.init_p2);
79 zassert_equal(p3, expected.init_p3);
80 /*option, stack size, not checked, no public API to get these values*/
81
82 k_sem_give(&end_sema);
83 }
84
85 /**
86 * @addtogroup kernel_thread_tests
87 * @{
88 */
89
90 /**
91 * @brief test preempt thread initialization via K_THREAD_DEFINE
92 *
93 * @see #K_THREAD_DEFINE(x)
94 *
95 * @ingroup kernel_thread_tests
96 */
ZTEST_USER(thread_init,test_kdefine_preempt_thread)97 ZTEST_USER(thread_init, test_kdefine_preempt_thread)
98 {
99 /*static thread created time unknown, skip it*/
100 t_create = 0U;
101 expected.init_p1 = INIT_PREEMPT_P1;
102 expected.init_p2 = INIT_PREEMPT_P2;
103 expected.init_p3 = INIT_PREEMPT_P3_static;
104 expected.init_prio = INIT_PREEMPT_PRIO;
105 expected.init_delay = INIT_PREEMPT_DELAY;
106 k_sem_reset(&end_sema);
107
108 /*signal thread to start*/
109 k_sem_give(&static_preem_start_sema);
110 /*wait for thread to exit*/
111 k_sem_take(&end_sema, K_FOREVER);
112 }
113
114 /**
115 * @brief test coop thread initialization via K_THREAD_DEFINE
116 *
117 * @ingroup kernel_thread_tests
118 *
119 * @see #K_THREAD_DEFINE(x)
120 */
ZTEST_USER(thread_init,test_kdefine_coop_thread)121 ZTEST_USER(thread_init, test_kdefine_coop_thread)
122 {
123 /*static thread creation time unknown, skip it*/
124 t_create = 0U;
125 expected.init_p1 = INIT_COOP_P1;
126 expected.init_p2 = INIT_COOP_P2;
127 expected.init_p3 = INIT_COOP_P3_static;
128 expected.init_prio = INIT_COOP_PRIO;
129 expected.init_delay = INIT_COOP_DELAY;
130 k_sem_reset(&end_sema);
131
132 /*signal thread to start*/
133 k_sem_give(&static_coop_start_sema);
134 /*wait for thread to exit*/
135 k_sem_take(&end_sema, K_FOREVER);
136 }
137
138 /**
139 * @brief test preempt thread initialization via k_thread_create
140 *
141 * @ingroup kernel_thread_tests
142 *
143 * @see k_thread_create()
144 */
ZTEST_USER(thread_init,test_kinit_preempt_thread)145 ZTEST_USER(thread_init, test_kinit_preempt_thread)
146 {
147 /*create preempt thread*/
148 k_tid_t pthread = k_thread_create(&thread_preempt, stack_preempt,
149 INIT_PREEMPT_STACK_SIZE, thread_entry, INIT_PREEMPT_P1,
150 INIT_PREEMPT_P2, INIT_PREEMPT_P3, INIT_PREEMPT_PRIO,
151 INIT_PREEMPT_OPTION,
152 K_MSEC(INIT_PREEMPT_DELAY));
153
154 /*record time stamp of thread creation*/
155 t_create = k_uptime_get();
156 zassert_not_null(pthread, "thread creation failed");
157
158 expected.init_p1 = INIT_PREEMPT_P1;
159 expected.init_p2 = INIT_PREEMPT_P2;
160 expected.init_p3 = INIT_PREEMPT_P3;
161 expected.init_prio = INIT_PREEMPT_PRIO;
162 expected.init_delay = INIT_PREEMPT_DELAY;
163 k_sem_reset(&end_sema);
164
165 /*signal thread to start*/
166 k_sem_give(&preem_start_sema);
167 /*wait for thread to exit*/
168 k_sem_take(&end_sema, K_FOREVER);
169 }
170
171 /**
172 * @brief test coop thread initialization via k_thread_create
173 *
174 * @ingroup kernel_thread_tests
175 *
176 * @see k_thread_create()
177 */
ZTEST(thread_init,test_kinit_coop_thread)178 ZTEST(thread_init, test_kinit_coop_thread)
179 {
180 if (!(IS_ENABLED(CONFIG_USERSPACE))) {
181 ztest_test_skip();
182 }
183
184 /*create coop thread*/
185 k_tid_t pthread = k_thread_create(&thread_coop, stack_coop,
186 INIT_COOP_STACK_SIZE, thread_entry, INIT_COOP_P1,
187 INIT_COOP_P2, INIT_COOP_P3, INIT_COOP_PRIO,
188 INIT_COOP_OPTION, K_MSEC(INIT_COOP_DELAY));
189
190 /*record time stamp of thread creation*/
191 t_create = k_uptime_get();
192 zassert_not_null(pthread, "thread spawn failed");
193
194 expected.init_p1 = INIT_COOP_P1;
195 expected.init_p2 = INIT_COOP_P2;
196 expected.init_p3 = INIT_COOP_P3;
197 expected.init_prio = INIT_COOP_PRIO;
198 expected.init_delay = INIT_COOP_DELAY;
199 k_sem_reset(&end_sema);
200
201 /*signal thread to start*/
202 k_sem_give(&coop_start_sema);
203 /*wait for thread to exit*/
204 k_sem_take(&end_sema, K_FOREVER);
205 }
206
207
208 /**
209 * @}
210 */
211
212 /*test case main entry*/
thread_init_setup(void)213 void *thread_init_setup(void)
214 {
215 k_thread_access_grant(k_current_get(), &thread_preempt, &stack_preempt,
216 &static_preem_start_sema, &preem_start_sema,
217 &static_coop_start_sema, &coop_start_sema, &end_sema);
218 #ifdef CONFIG_USERSPACE
219 k_mem_domain_add_thread(&k_mem_domain_default, T_KDEFINE_COOP_THREAD);
220 k_mem_domain_add_thread(&k_mem_domain_default, T_KDEFINE_PREEMPT_THREAD);
221 #endif
222
223 return NULL;
224 }
225
226 ZTEST_SUITE(thread_init, NULL, thread_init_setup, NULL, NULL, NULL);
227