1 /* This test is designed to test thread terminate calls when threads are suspended on
2 a semaphore. */
3
4 #include <stdio.h>
5 #include "tx_api.h"
6
7 static unsigned long thread_0_counter = 0;
8 static TX_THREAD thread_0;
9
10 static unsigned long thread_1_counter = 0;
11 static TX_THREAD thread_1;
12
13 static unsigned long thread_2_counter = 0;
14 static TX_THREAD thread_2;
15
16
17 static TX_SEMAPHORE semaphore_0;
18
19
20 /* Define thread prototypes. */
21
22 static void thread_0_entry(ULONG thread_input);
23 static void thread_1_entry(ULONG thread_input);
24 static void thread_2_entry(ULONG thread_input);
25
26
27 /* Prototype for test control return. */
28
29 void test_control_return(UINT status);
30
31
put_notify(TX_SEMAPHORE * semaphore_ptr)32 static void put_notify(TX_SEMAPHORE *semaphore_ptr)
33 {
34
35 /* Don't need to do anything in here... */
36 }
37
38
39 /* Define what the initial system looks like. */
40
41 #ifdef CTEST
test_application_define(void * first_unused_memory)42 void test_application_define(void *first_unused_memory)
43 #else
44 void threadx_semaphore_thread_terminate_application_define(void *first_unused_memory)
45 #endif
46 {
47
48 UINT status;
49 CHAR *pointer;
50
51
52 /* Put first available memory address into a character pointer. */
53 pointer = (CHAR *) first_unused_memory;
54
55 /* Put system definition stuff in here, e.g. thread creates and other assorted
56 create information. */
57
58 status = tx_thread_create(&thread_0, "thread 0", thread_0_entry, 1,
59 pointer, TEST_STACK_SIZE_PRINTF,
60 16, 16, 100, TX_AUTO_START);
61 pointer = pointer + TEST_STACK_SIZE_PRINTF;
62
63 /* Check for status. */
64 if (status != TX_SUCCESS)
65 {
66
67 printf("Running Semaphore Thread Terminate Test............................. ERROR #1\n");
68 test_control_return(1);
69 }
70
71 status = tx_thread_create(&thread_1, "thread 1", thread_1_entry, 1,
72 pointer, TEST_STACK_SIZE_PRINTF,
73 16, 16, 100, TX_AUTO_START);
74 pointer = pointer + TEST_STACK_SIZE_PRINTF;
75
76 /* Check for status. */
77 if (status != TX_SUCCESS)
78 {
79
80 printf("Running Semaphore Thread Terminate Test............................. ERROR #2\n");
81 test_control_return(1);
82 }
83
84 status = tx_thread_create(&thread_2, "thread 2", thread_2_entry, 1,
85 pointer, TEST_STACK_SIZE_PRINTF,
86 16, 16, 100, TX_AUTO_START);
87 pointer = pointer + TEST_STACK_SIZE_PRINTF;
88
89 /* Check for status. */
90 if (status != TX_SUCCESS)
91 {
92
93 printf("Running Semaphore Thread Terminate Test............................. ERROR #3\n");
94 test_control_return(1);
95 }
96
97 /* Create a semaphore with an initial count of 0. */
98 status = tx_semaphore_create(&semaphore_0, "semaphore 0", 0);
99
100 /* Check for status. */
101 if (status != TX_SUCCESS)
102 {
103
104 printf("Running Semaphore Thread Terminate Test............................. ERROR #4\n");
105 test_control_return(1);
106 }
107
108 /* Setup the semaphore notify callback. */
109 status = tx_semaphore_put_notify(&semaphore_0, put_notify);
110
111 #ifndef TX_DISABLE_NOTIFY_CALLBACKS
112
113 /* Check for status. */
114 if (status != TX_SUCCESS)
115 {
116
117 printf("Running Semaphore Thread Terminate Test............................. ERROR #5\n");
118 test_control_return(1);
119 }
120 #else
121
122 /* Check for status. */
123 if (status != TX_FEATURE_NOT_ENABLED)
124 {
125
126 printf("Running Semaphore Thread Terminate Test............................. ERROR #6\n");
127 test_control_return(1);
128 }
129
130 #endif
131
132 }
133
134
135
136 /* Define the test threads. */
137
thread_0_entry(ULONG thread_input)138 static void thread_0_entry(ULONG thread_input)
139 {
140
141 UINT status;
142
143
144 /* Inform user. */
145 printf("Running Semaphore Thread Terminate Test............................. ");
146
147 /* Increment thread 0 counter. */
148 thread_0_counter++;
149
150 /* Relinquish to let other threads run. */
151 tx_thread_relinquish();
152
153 /* Other threads should now be suspended on the semaphore. */
154 if ((thread_1_counter != 1) || (thread_2_counter != 1))
155 {
156
157 /* Semaphore error. */
158 printf("ERROR #7\n");
159 test_control_return(1);
160 }
161
162 /* Terminate the other threads to make sure the semaphore gets
163 cleaned up. */
164 status = tx_thread_terminate(&thread_1);
165
166 /* Check status and run counters of other threads. */
167 if ((status != TX_SUCCESS) || (thread_1_counter != 1) || (thread_2_counter != 1))
168 {
169
170 /* Semaphore error. */
171 printf("ERROR #8\n");
172 test_control_return(1);
173 }
174
175 /* Terminate the other thread. */
176 status = tx_thread_terminate(&thread_2);
177
178 /* Relinquish just to make sure. */
179 tx_thread_relinquish();
180
181 /* Check status and run counters of other threads. */
182 if ((status != TX_SUCCESS) || (thread_1_counter != 1) || (thread_2_counter != 1))
183 {
184
185 /* Semaphore error. */
186 printf("ERROR #9\n");
187 test_control_return(1);
188 }
189 else
190 {
191
192 /* Successful test. */
193 printf("SUCCESS!\n");
194 test_control_return(0);
195 }
196 }
197
198
thread_1_entry(ULONG thread_input)199 static void thread_1_entry(ULONG thread_input)
200 {
201
202 /* Increment thread run counter. */
203 thread_1_counter++;
204
205 /* Suspend on the semaphore. */
206 tx_semaphore_get(&semaphore_0, 33);
207
208 /* Should never get here! */
209 thread_1_counter++;
210 }
211
212
thread_2_entry(ULONG thread_input)213 static void thread_2_entry(ULONG thread_input)
214 {
215
216 /* Increment thread run counter. */
217 thread_2_counter++;
218
219 /* Suspend on the semaphore. */
220 tx_semaphore_get(&semaphore_0, 44);
221
222 /* Should never get here! */
223 thread_2_counter++;
224 }
225