Skip to content

Commit 24859e9

Browse files
authored
Merge pull request #5789 from maciejbocianski/hal_critical_section_tests
Add tests for critical section HAL API
2 parents fe87499 + 628f521 commit 24859e9

File tree

2 files changed

+135
-0
lines changed

2 files changed

+135
-0
lines changed
Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
/* mbed Microcontroller Library
2+
* Copyright (c) 2018 ARM Limited
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
/** \addtogroup hal_critical_tests
18+
* @{
19+
*/
20+
21+
#ifndef MBED_CRITICAL_SECTION_TEST_H
22+
#define MBED_CRITICAL_SECTION_TEST_H
23+
24+
/** Template for HAL critical section tests
25+
*
26+
* Test critical section
27+
* Given a critical section HAL mechanism
28+
* When before critical section
29+
* Then interrupts are enabled
30+
* When inside critical section
31+
* Then interrupts are disabled
32+
* When after critical section
33+
* Then interrupts are enabled again
34+
*
35+
* Test critical section - nested lock
36+
* Given a critical section HAL mechanism
37+
* When before critical section
38+
* Then interrupts are enabled
39+
* When inside nested critical section
40+
* Then interrupts are disabled
41+
* When after nested critical section
42+
* Then interrupts are enabled again
43+
*
44+
*/
45+
template <int N>
46+
void test_critical_section();
47+
48+
49+
/**@}*/
50+
51+
#endif // MBED_CRITICAL_SECTION_TEST_H
Lines changed: 84 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,84 @@
1+
/* mbed Microcontroller Library
2+
* Copyright (c) 2018 ARM Limited
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
#include "critical_section_test.h"
17+
#include "hal/critical_section_api.h"
18+
#include "utest/utest.h"
19+
#include "unity/unity.h"
20+
#include "greentea-client/test_env.h"
21+
#include "mbed.h"
22+
#include "cmsis.h"
23+
#ifdef TARGET_NRF5 // for all NRF5x targets
24+
#include "nrf_nvic.h" // for __NRF_NVIC_APP_IRQS_0 / __NRF_NVIC_APP_IRQS_1
25+
#endif
26+
27+
using utest::v1::Case;
28+
29+
bool test_are_interrupts_enabled(void)
30+
{
31+
// NRF5x targets don't disable interrupts when in critical section, instead they mask application interrupts this is due to BLE stack
32+
// (BLE to be operational requires some interrupts to be always enabled)
33+
#ifdef TARGET_NRF52_DK
34+
// check if APP interrupts are masked for NRF52_DK board
35+
return (((NVIC->ISER[0] & __NRF_NVIC_APP_IRQS_0) != 0) || ((NVIC->ISER[1] & __NRF_NVIC_APP_IRQS_1) != 0));
36+
#elif TARGET_NRF5
37+
// check if APP interrupts are masked for other NRF5 boards
38+
return ((NVIC->ISER[0] & __NRF_NVIC_APP_IRQS_0) != 0);
39+
#else
40+
#if defined(__CORTEX_A9)
41+
return ((__get_CPSR() & 0x80) == 0);
42+
#else
43+
return ((__get_PRIMASK() & 0x1) == 0);
44+
#endif
45+
#endif
46+
}
47+
48+
49+
template<int N>
50+
void test_critical_section()
51+
{
52+
TEST_ASSERT_FALSE(hal_in_critical_section());
53+
TEST_ASSERT_TRUE(test_are_interrupts_enabled());
54+
55+
for (int i = 0; i < N; i++) {
56+
hal_critical_section_enter();
57+
TEST_ASSERT_TRUE(hal_in_critical_section());
58+
TEST_ASSERT_FALSE(test_are_interrupts_enabled());
59+
}
60+
61+
// assumed to be called once (according API)
62+
hal_critical_section_exit();
63+
64+
TEST_ASSERT_FALSE(hal_in_critical_section());
65+
TEST_ASSERT_TRUE(test_are_interrupts_enabled());
66+
}
67+
68+
Case cases[] = {
69+
Case("Test critical section single lock", test_critical_section<1>),
70+
Case("Test critical section nested lock", test_critical_section<10>)
71+
};
72+
73+
utest::v1::status_t greentea_test_setup(const size_t number_of_cases)
74+
{
75+
GREENTEA_SETUP(10, "timing_drift_auto");
76+
return utest::v1::greentea_test_setup_handler(number_of_cases);
77+
}
78+
79+
utest::v1::Specification specification(greentea_test_setup, cases);
80+
81+
int main()
82+
{
83+
return !utest::v1::Harness::run(specification);
84+
}

0 commit comments

Comments
 (0)