@@ -147,6 +147,78 @@ void test_atomic_add()
147
147
TEST_ASSERT_EQUAL (T (ADD_UNLOCKED_ITERATIONS), data.nonatomic2 );
148
148
}
149
149
150
+ // This should fit into a uint32_t container, and there
151
+ // will be 1 byte of padding to ignore.
152
+ struct small {
153
+ uint8_t a;
154
+ uint8_t b;
155
+ uint8_t c;
156
+ };
157
+
158
+ // An 11-byte weird structure. Should work with critical sections.
159
+ struct large {
160
+ uint8_t a;
161
+ uint8_t b;
162
+ uint8_t c;
163
+ uint8_t dummy[8 ];
164
+ };
165
+
166
+ template <typename A>
167
+ void struct_incrementer_a (A *data)
168
+ {
169
+ for (long i = add_iterations (*data); i > 0 ; i--) {
170
+ typename A::value_type curval = *data, newval;
171
+ do {
172
+ newval = curval;
173
+ newval.a ++;
174
+ } while (!data->compare_exchange_weak (curval, newval));
175
+ }
176
+ }
177
+
178
+ template <typename A>
179
+ void struct_incrementer_b (A *data)
180
+ {
181
+ for (long i = add_iterations (*data); i > 0 ; i--) {
182
+ typename A::value_type curval = *data, newval;
183
+ do {
184
+ newval = curval;
185
+ newval.b ++;
186
+ } while (!data->compare_exchange_weak (curval, newval));
187
+ }
188
+ }
189
+
190
+ template <typename T, size_t N>
191
+ void test_atomic_struct ()
192
+ {
193
+ TEST_ASSERT_EQUAL (N, sizeof (Atomic<T>));
194
+
195
+ T init = { 0 , 0 , 0 };
196
+ Atomic<T> data (init);
197
+
198
+ Thread t1 (osPriorityNormal, THREAD_STACK);
199
+ Thread t2 (osPriorityNormal, THREAD_STACK);
200
+
201
+ TEST_ASSERT_EQUAL (osOK, t1.start (callback (struct_incrementer_a<Atomic<T> >, &data)));
202
+ TEST_ASSERT_EQUAL (osOK, t2.start (callback (struct_incrementer_b<Atomic<T> >, &data)));
203
+
204
+ for (long i = add_iterations (data); i > 0 ; i--) {
205
+ T curval = data, newval;
206
+ do {
207
+ newval = curval;
208
+ newval.c ++;
209
+ } while (!data.compare_exchange_weak (curval, newval));
210
+ }
211
+
212
+ t1.join ();
213
+ t2.join ();
214
+
215
+ T final_val = data;
216
+
217
+ TEST_ASSERT_EQUAL (uint8_t (add_iterations (data)), final_val.a );
218
+ TEST_ASSERT_EQUAL (uint8_t (add_iterations (data)), final_val.b );
219
+ TEST_ASSERT_EQUAL (uint8_t (add_iterations (data)), final_val.c );
220
+ }
221
+
150
222
} // namespace
151
223
152
224
utest::v1::status_t test_setup (const size_t number_of_cases)
@@ -180,7 +252,9 @@ Case cases[] = {
180
252
Case (" Test atomic compare exchange strong 8-bit" , test_atomic_add<uint8_t , strong_incrementer>),
181
253
Case (" Test atomic compare exchange strong 16-bit" , test_atomic_add<uint16_t , strong_incrementer>),
182
254
Case (" Test atomic compare exchange strong 32-bit" , test_atomic_add<uint32_t , strong_incrementer>),
183
- Case (" Test atomic compare exchange strong 64-bit" , test_atomic_add<uint64_t , strong_incrementer>)
255
+ Case (" Test atomic compare exchange strong 64-bit" , test_atomic_add<uint64_t , strong_incrementer>),
256
+ Case (" Test small atomic custom structure" , test_atomic_struct<small, 4 >),
257
+ Case (" Test large atomic custom structure" , test_atomic_struct<large, 11 >)
184
258
};
185
259
186
260
utest::v1::Specification specification (test_setup, cases);
0 commit comments