| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821 |
- /*-----------------------------------------------------------------------------
- * Name: CV_CoreInstr.c
- * Purpose: CMSIS CORE validation tests implementation
- *-----------------------------------------------------------------------------
- * Copyright (c) 2017 - 2021 Arm Limited. All rights reserved.
- *----------------------------------------------------------------------------*/
- #include "CV_Framework.h"
- #include "cmsis_cv.h"
- #if defined(__CORTEX_M)
- #elif defined(__CORTEX_A)
- #include "irq_ctrl.h"
- #else
- #error __CORTEX_M or __CORTEX_A must be defined!
- #endif
- /*-----------------------------------------------------------------------------
- * Test implementation
- *----------------------------------------------------------------------------*/
- /*-----------------------------------------------------------------------------
- * Test cases
- *----------------------------------------------------------------------------*/
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_NOP
- \details
- - Check if __NOP instrinsic is available
- - No real assertion is deployed, just a compile time check.
- */
- void TC_CoreInstr_NOP (void) {
- __NOP();
- ASSERT_TRUE(1U == 1U);
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_SEV
- \details
- - Check if __SEV instrinsic is available
- - No real assertion is deployed, just a compile time check.
- */
- void TC_CoreInstr_SEV (void) {
- __SEV();
- ASSERT_TRUE(1U == 1U);
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_BKPT
- \details
- - Check if __BKPT instrinsic is available
- - No real assertion is deployed, just a compile time check.
- */
- void TC_CoreInstr_BKPT (void) {
- __BKPT(0xABU);
- ASSERT_TRUE(1U == 1U);
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_ISB
- \details
- - Check if __ISB instrinsic is available
- - No real assertion is deployed, just a compile time check.
- */
- void TC_CoreInstr_ISB (void) {
- __ISB();
- ASSERT_TRUE(1U == 1U);
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_DSB
- \details
- - Check if __DSB instrinsic is available
- - No real assertion is deployed, just a compile time check.
- */
- void TC_CoreInstr_DSB (void) {
- __DSB();
- ASSERT_TRUE(1U == 1U);
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_DMB
- \details
- - Check if __DNB instrinsic is available
- - No real assertion is deployed, just a compile time check.
- */
- void TC_CoreInstr_DMB (void) {
- __DMB();
- ASSERT_TRUE(1U == 1U);
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_WFI
- \details
- - Check if __WFI instrinsic is available
- - No real assertion is deployed, just a compile time check.
- */
- void TC_CoreInstr_WFI (void) {
- __WFI();
- ASSERT_TRUE(1U == 1U);
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_WFE
- \details
- - Check if __WFE instrinsic is available
- - No real assertion is deployed, just a compile time check.
- */
- void TC_CoreInstr_WFE (void) {
- __WFE();
- ASSERT_TRUE(1U == 1U);
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_REV
- \details
- - Check if __REV instrinsic swaps all bytes in a word.
- */
- void TC_CoreInstr_REV (void) {
- volatile uint32_t op1_u32;
- volatile uint32_t res_u32;
- op1_u32 = 0x47110815U;
- res_u32 = __REV(op1_u32);
- ASSERT_TRUE(res_u32 == 0x15081147U);
- op1_u32 = 0x80000000U;
- res_u32 = __REV(op1_u32);
- ASSERT_TRUE(res_u32 == 0x00000080U);
- op1_u32 = 0x00000080U;
- res_u32 = __REV(op1_u32);
- ASSERT_TRUE(res_u32 == 0x80000000U);
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_REV16
- \details
- - Check if __REV16 instrinsic swaps the bytes in both halfwords independendly.
- */
- void TC_CoreInstr_REV16(void) {
- volatile uint32_t op1_u32;
- volatile uint32_t res_u32;
- op1_u32 = 0x47110815U;
- res_u32 = __REV16(op1_u32);
- ASSERT_TRUE(res_u32 == 0x11471508U);
- op1_u32 = 0x00001234U;
- res_u32 = __REV16(op1_u32);
- ASSERT_TRUE(res_u32 == 0x00003412U);
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_REVSH
- \details
- - Check if __REVSH instrinsic swaps bytes in a signed halfword keeping the sign.
- */
- void TC_CoreInstr_REVSH(void) {
- volatile int16_t value = 0U;
- int16_t result = 0U;
- value = 0x4711;
- result = __REVSH(value);
- ASSERT_TRUE(result == 0x1147);
- value = (int16_t)0x8000;
- result = __REVSH(value);
- ASSERT_TRUE(result == 0x0080);
- value = 0x0080;
- result = __REVSH(value);
- ASSERT_TRUE(result == (int16_t)0x8000);
- value = -0x1234;
- result = __REVSH(value);
- ASSERT_TRUE(result == (int16_t)0xcced);
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_RBIT
- \details
- - Check if __RBIT instrinsic revserses the bit order of arbitrary words.
- */
- void TC_CoreInstr_RBIT (void) {
- volatile uint32_t value = 0U;
- uint32_t result = 0U;
- value = 0xAAAAAAAAU;
- result = __RBIT(value);
- ASSERT_TRUE(result == 0x55555555U);
- value = 0x55555555U;
- result = __RBIT(value);
- ASSERT_TRUE(result == 0xAAAAAAAAU);
- value = 0x00000001U;
- result = __RBIT(value);
- ASSERT_TRUE(result == 0x80000000U);
- value = 0x80000000U;
- result = __RBIT(value);
- ASSERT_TRUE(result == 0x00000001U);
- value = 0xDEADBEEFU;
- result = __RBIT(value);
- ASSERT_TRUE(result == 0xF77DB57BU);
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_ROR
- \details
- - Check if __ROR instrinsic moves all bits as expected.
- */
- void TC_CoreInstr_ROR(void) {
- volatile uint32_t value = 0U;
- uint32_t result = 0U;
- value = 0x00000001U;
- result = __ROR(value, 1U);
- ASSERT_TRUE(result == 0x80000000U);
- value = 0x80000000U;
- result = __ROR(value, 1U);
- ASSERT_TRUE(result == 0x40000000U);
- value = 0x40000000U;
- result = __ROR(value, 30U);
- ASSERT_TRUE(result == 0x00000001U);
- value = 0x00000001U;
- result = __ROR(value, 32U);
- ASSERT_TRUE(result == 0x00000001U);
- value = 0x08154711U;
- result = __ROR(value, 8U);
- ASSERT_TRUE(result == 0x11081547U);
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_CLZ
- \details
- - Check if __CLZ instrinsic counts leading zeros.
- */
- void TC_CoreInstr_CLZ (void) {
- volatile uint32_t value = 0U;
- uint32_t result = 0U;
- value = 0x00000000U;
- result = __CLZ(value);
- ASSERT_TRUE(result == 32);
- value = 0x00000001U;
- result = __CLZ(value);
- ASSERT_TRUE(result == 31);
- value = 0x40000000U;
- result = __CLZ(value);
- ASSERT_TRUE(result == 1);
- value = 0x80000000U;
- result = __CLZ(value);
- ASSERT_TRUE(result == 0);
- value = 0xFFFFFFFFU;
- result = __CLZ(value);
- ASSERT_TRUE(result == 0);
- value = 0x80000001U;
- result = __CLZ(value);
- ASSERT_TRUE(result == 0);
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_SSAT
- \details
- - Check if __SSAT instrinsic saturates signed integer values.
- */
- void TC_CoreInstr_SSAT (void) {
- volatile int32_t value = 0;
- int32_t result = 0;
- value = INT32_MAX;
- result = __SSAT(value, 32U);
- ASSERT_TRUE(result == INT32_MAX);
- value = INT32_MAX;
- result = __SSAT(value, 16U);
- ASSERT_TRUE(result == INT16_MAX);
- value = INT32_MAX;
- result = __SSAT(value, 8U);
- ASSERT_TRUE(result == INT8_MAX);
- value = INT32_MAX;
- result = __SSAT(value, 1U);
- ASSERT_TRUE(result == 0);
- value = INT32_MIN;
- result = __SSAT(value, 32U);
- ASSERT_TRUE(result == INT32_MIN);
- value = INT32_MIN;
- result = __SSAT(value, 16U);
- ASSERT_TRUE(result == INT16_MIN);
- value = INT32_MIN;
- result = __SSAT(value, 8U);
- ASSERT_TRUE(result == INT8_MIN);
- value = INT32_MIN;
- result = __SSAT(value, 1U);
- ASSERT_TRUE(result == -1);
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_USAT
- \details
- - Check if __USAT instrinsic saturates unsigned integer values.
- */
- void TC_CoreInstr_USAT (void) {
- volatile int32_t value = 0U;
- uint32_t result = 0U;
- value = INT32_MAX;
- result = __USAT(value, 31U);
- ASSERT_TRUE(result == (UINT32_MAX >> 1U));
- value = INT32_MAX;
- result = __USAT(value, 16U);
- ASSERT_TRUE(result == UINT16_MAX);
- value = INT32_MAX;
- result = __USAT(value, 8U);
- ASSERT_TRUE(result == UINT8_MAX);
- value = INT32_MAX;
- result = __USAT(value, 0U);
- ASSERT_TRUE(result == 0U);
- value = INT32_MIN;
- result = __USAT(value, 31U);
- ASSERT_TRUE(result == 0U);
- value = INT32_MIN;
- result = __USAT(value, 16U);
- ASSERT_TRUE(result == 0U);
- value = INT32_MIN;
- result = __USAT(value, 8U);
- ASSERT_TRUE(result == 0U);
- value = INT32_MIN;
- result = __USAT(value, 0U);
- ASSERT_TRUE(result == 0U);
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- /**
- \brief Test case: TC_CoreInstr_RRX
- \details
- - Check if __USAT instrinsic saturates unsigned integer values.
- */
- void TC_CoreInstr_RRX (void) {
- #if ((defined (__ARM_ARCH_7M__ ) && (__ARM_ARCH_7M__ == 1)) || \
- (defined (__ARM_ARCH_7EM__ ) && (__ARM_ARCH_7EM__ == 1)) || \
- (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) || \
- (defined (__ARM_ARCH_8_1M_MAIN__ ) && (__ARM_ARCH_8_1M_MAIN__ == 1)) )
- volatile uint32_t value = 0U;
- volatile uint32_t result = 0U;
- volatile xPSR_Type xPSR;
- value = 0x80000002;
- xPSR.w = __get_xPSR();
- result = __RRX(value);
- ASSERT_TRUE(result == (0x40000001 | (uint32_t)(xPSR.b.C << 31)));
- #endif
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- #if ((defined (__ARM_ARCH_7M__ ) && (__ARM_ARCH_7M__ == 1)) || \
- (defined (__ARM_ARCH_7EM__ ) && (__ARM_ARCH_7EM__ == 1)) || \
- (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) || \
- (defined (__ARM_ARCH_8M_BASE__ ) && (__ARM_ARCH_8M_BASE__ == 1)) || \
- (defined (__ARM_ARCH_8_1M_MAIN__ ) && (__ARM_ARCH_8_1M_MAIN__ == 1)) || \
- (defined(__CORTEX_A) ) )
- /// Exclusive byte value
- static volatile uint8_t TC_CoreInstr_LoadStoreExclusive_byte = 0x47U;
- /// Exclusive halfword value
- static volatile uint16_t TC_CoreInstr_LoadStoreExclusive_hword = 0x0815U;
- /// Exclusive word value
- static volatile uint32_t TC_CoreInstr_LoadStoreExclusive_word = 0x08154711U;
- /**
- \brief Interrupt function for TC_CoreInstr_LoadStoreExclusive
- \details
- The interrupt manipulates all the global data
- which disrupts the exclusive sequences in the test
- */
- static void TC_CoreInstr_LoadStoreExclusive_IRQHandler(void) {
- const uint8_t b = __LDREXB(&TC_CoreInstr_LoadStoreExclusive_byte);
- __STREXB((uint8_t)~b, &TC_CoreInstr_LoadStoreExclusive_byte);
- const uint16_t hw = __LDREXH(&TC_CoreInstr_LoadStoreExclusive_hword);
- __STREXH((uint16_t)~hw, &TC_CoreInstr_LoadStoreExclusive_hword);
- const uint32_t w = __LDREXW(&TC_CoreInstr_LoadStoreExclusive_word);
- __STREXW((uint32_t)~w, &TC_CoreInstr_LoadStoreExclusive_word);
- }
- /**
- \brief Helper function for TC_CoreInstr_LoadStoreExclusive to enable test interrupt.
- \details
- This helper function implements interrupt enabling according to target
- architecture, i.e. Cortex-A or Cortex-M.
- */
- static void TC_CoreInstr_LoadStoreExclusive_IRQEnable(void) {
- #if defined(__CORTEX_M)
- TST_IRQHandler = TC_CoreInstr_LoadStoreExclusive_IRQHandler;
- NVIC_EnableIRQ(Interrupt0_IRQn);
- #elif defined(__CORTEX_A)
- IRQ_SetHandler(SGI0_IRQn, TC_CoreInstr_LoadStoreExclusive_IRQHandler);
- IRQ_Enable(SGI0_IRQn);
- #else
- #error __CORTEX_M or __CORTEX_A must be defined!
- #endif
- __enable_irq();
- }
- /**
- \brief Helper function for TC_CoreInstr_LoadStoreExclusive to set test interrupt pending.
- \details
- This helper function implements set pending the test interrupt according to target
- architecture, i.e. Cortex-A or Cortex-M.
- */
- static void TC_CoreInstr_LoadStoreExclusive_IRQPend(void) {
- #if defined(__CORTEX_M)
- NVIC_SetPendingIRQ(Interrupt0_IRQn);
- #elif defined(__CORTEX_A)
- IRQ_SetPending(SGI0_IRQn);
- #else
- #error __CORTEX_M or __CORTEX_A must be defined!
- #endif
- for(uint32_t i = 10U; i > 0U; --i) {}
- }
- /**
- \brief Helper function for TC_CoreInstr_LoadStoreExclusive to disable test interrupt.
- \details
- This helper function implements interrupt disabling according to target
- architecture, i.e. Cortex-A or Cortex-M.
- */
- static void TC_CoreInstr_LoadStoreExclusive_IRQDisable(void) {
- __disable_irq();
- #if defined(__CORTEX_M)
- NVIC_DisableIRQ(Interrupt0_IRQn);
- TST_IRQHandler = NULL;
- #elif defined(__CORTEX_A)
- IRQ_Disable(SGI0_IRQn);
- IRQ_SetHandler(SGI0_IRQn, NULL);
- #else
- #error __CORTEX_M or __CORTEX_A must be defined!
- #endif
- }
- #endif
- /**
- \brief Test case: TC_CoreInstr_LoadStoreExclusive
- \details
- Checks exclusive load and store instructions:
- - LDREXB, LDREXH, LDREXW
- - STREXB, STREXH, STREXW
- - CLREX
- */
- void TC_CoreInstr_LoadStoreExclusive (void) {
- #if ((defined (__ARM_ARCH_7M__ ) && (__ARM_ARCH_7M__ == 1)) || \
- (defined (__ARM_ARCH_7EM__ ) && (__ARM_ARCH_7EM__ == 1)) || \
- (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) || \
- (defined (__ARM_ARCH_8M_BASE__ ) && (__ARM_ARCH_8M_BASE__ == 1)) || \
- (defined (__ARM_ARCH_8_1M_MAIN__ ) && (__ARM_ARCH_8_1M_MAIN__ == 1)) || \
- (defined(__CORTEX_A) ) )
- uint8_t u8, u8Inv;
- uint16_t u16, u16Inv;
- uint32_t u32, u32Inv;
- uint32_t result;
- /* 1. Test exclusives without interruption */
- u8 = __LDREXB(&TC_CoreInstr_LoadStoreExclusive_byte);
- ASSERT_TRUE(u8 == TC_CoreInstr_LoadStoreExclusive_byte);
- result = __STREXB(u8+1U, &TC_CoreInstr_LoadStoreExclusive_byte);
- ASSERT_TRUE(result == 0U);
- ASSERT_TRUE(TC_CoreInstr_LoadStoreExclusive_byte == u8+1U);
- u16 = __LDREXH(&TC_CoreInstr_LoadStoreExclusive_hword);
- ASSERT_TRUE(u16 == TC_CoreInstr_LoadStoreExclusive_hword);
- result = __STREXH(u16+1U, &TC_CoreInstr_LoadStoreExclusive_hword);
- ASSERT_TRUE(result == 0U);
- ASSERT_TRUE(TC_CoreInstr_LoadStoreExclusive_hword == u16+1U);
- u32 = __LDREXW(&TC_CoreInstr_LoadStoreExclusive_word);
- ASSERT_TRUE(u32 == TC_CoreInstr_LoadStoreExclusive_word);
- result = __STREXW(u32+1U, &TC_CoreInstr_LoadStoreExclusive_word);
- ASSERT_TRUE(result == 0U);
- ASSERT_TRUE(TC_CoreInstr_LoadStoreExclusive_word == u32+1U);
- /* 2. Test exclusives with clear */
- u8 = __LDREXB(&TC_CoreInstr_LoadStoreExclusive_byte);
- ASSERT_TRUE(u8 == TC_CoreInstr_LoadStoreExclusive_byte);
- __CLREX();
- result = __STREXB(u8+1U, &TC_CoreInstr_LoadStoreExclusive_byte);
- ASSERT_TRUE(result == 1U);
- ASSERT_TRUE(TC_CoreInstr_LoadStoreExclusive_byte == u8);
- u16 = __LDREXH(&TC_CoreInstr_LoadStoreExclusive_hword);
- ASSERT_TRUE(u16 == TC_CoreInstr_LoadStoreExclusive_hword);
- __CLREX();
- result = __STREXH(u16+1U, &TC_CoreInstr_LoadStoreExclusive_hword);
- ASSERT_TRUE(result == 1U);
- ASSERT_TRUE(TC_CoreInstr_LoadStoreExclusive_hword == u16);
- u32 = __LDREXW(&TC_CoreInstr_LoadStoreExclusive_word);
- ASSERT_TRUE(u32 == TC_CoreInstr_LoadStoreExclusive_word);
- __CLREX();
- result = __STREXW(u32+1U, &TC_CoreInstr_LoadStoreExclusive_word);
- ASSERT_TRUE(result == 1U);
- ASSERT_TRUE(TC_CoreInstr_LoadStoreExclusive_word == u32);
- /* 3. Test exclusives with interruption */
- TC_CoreInstr_LoadStoreExclusive_IRQEnable();
- u8 = __LDREXB(&TC_CoreInstr_LoadStoreExclusive_byte);
- ASSERT_TRUE(u8 == TC_CoreInstr_LoadStoreExclusive_byte);
- TC_CoreInstr_LoadStoreExclusive_IRQPend();
- result = __STREXB(u8+1U, &TC_CoreInstr_LoadStoreExclusive_byte);
- ASSERT_TRUE(result == 1U);
- u8Inv = (uint8_t)~u8;
- ASSERT_TRUE(u8Inv == TC_CoreInstr_LoadStoreExclusive_byte);
- u16 = __LDREXH(&TC_CoreInstr_LoadStoreExclusive_hword);
- ASSERT_TRUE(u16 == TC_CoreInstr_LoadStoreExclusive_hword);
- TC_CoreInstr_LoadStoreExclusive_IRQPend();
- result = __STREXH(u16+1U, &TC_CoreInstr_LoadStoreExclusive_hword);
- ASSERT_TRUE(result == 1U);
- u16Inv = (uint16_t)~u16;
- ASSERT_TRUE(u16Inv == TC_CoreInstr_LoadStoreExclusive_hword);
- u32 = __LDREXW(&TC_CoreInstr_LoadStoreExclusive_word);
- ASSERT_TRUE(u32 == TC_CoreInstr_LoadStoreExclusive_word);
- TC_CoreInstr_LoadStoreExclusive_IRQPend();
- result = __STREXW(u32+1U, &TC_CoreInstr_LoadStoreExclusive_word);
- ASSERT_TRUE(result == 1U);
- u32Inv = (uint32_t)~u32;
- ASSERT_TRUE(u32Inv == TC_CoreInstr_LoadStoreExclusive_word);
- TC_CoreInstr_LoadStoreExclusive_IRQDisable();
- #endif
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- #if ((defined (__ARM_ARCH_7M__ ) && (__ARM_ARCH_7M__ == 1)) || \
- (defined (__ARM_ARCH_7EM__ ) && (__ARM_ARCH_7EM__ == 1)) || \
- (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) || \
- (defined (__ARM_ARCH_8_1M_MAIN__ ) && (__ARM_ARCH_8_1M_MAIN__ == 1)) )
- /// byte value unprivileged access
- static volatile uint8_t TC_CoreInstr_LoadStoreUnpriv_byte = 0x47U;
- /// halfword value unprivileged access
- static volatile uint16_t TC_CoreInstr_LoadStoreUnpriv_hword = 0x0815U;
- /// word value unprivileged access
- static volatile uint32_t TC_CoreInstr_LoadStoreUnpriv_word = 0x08154711U;
- #endif
- /**
- \brief Test case: TC_CoreInstr_LoadStoreUnpriv
- \details
- Checks load/store unprivileged instructions:
- - LDRBT, LDRHT, LDRT
- - STRBT, STRHT, STRT
- */
- void TC_CoreInstr_LoadStoreUnpriv (void) {
- #if ((defined (__ARM_ARCH_7M__ ) && (__ARM_ARCH_7M__ == 1)) || \
- (defined (__ARM_ARCH_7EM__ ) && (__ARM_ARCH_7EM__ == 1)) || \
- (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) || \
- (defined (__ARM_ARCH_8_1M_MAIN__ ) && (__ARM_ARCH_8_1M_MAIN__ == 1)) )
- uint8_t u8 = 0U;
- uint16_t u16 = 0U;
- uint32_t u32 = 0U;
- /* 1. Test without interruption */
- u8 = __LDRBT(&TC_CoreInstr_LoadStoreUnpriv_byte);
- ASSERT_TRUE(u8 == TC_CoreInstr_LoadStoreUnpriv_byte);
- __STRBT(u8+1U, &TC_CoreInstr_LoadStoreUnpriv_byte);
- ASSERT_TRUE(TC_CoreInstr_LoadStoreUnpriv_byte == u8+1U);
- u16 = __LDRHT(&TC_CoreInstr_LoadStoreUnpriv_hword);
- ASSERT_TRUE(u16 == TC_CoreInstr_LoadStoreUnpriv_hword);
- __STRHT(u16+1U, &TC_CoreInstr_LoadStoreUnpriv_hword);
- ASSERT_TRUE(TC_CoreInstr_LoadStoreUnpriv_hword == u16+1U);
- u32 = __LDRT(&TC_CoreInstr_LoadStoreUnpriv_word);
- ASSERT_TRUE(u32 == TC_CoreInstr_LoadStoreUnpriv_word);
- __STRT(u32+1U, &TC_CoreInstr_LoadStoreUnpriv_word);
- ASSERT_TRUE(TC_CoreInstr_LoadStoreUnpriv_word == u32+1U);
- #endif
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- #if ((defined (__ARM_ARCH_8_1M_MAIN__ ) && (__ARM_ARCH_8_1M_MAIN__ == 1)) || \
- (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) || \
- (defined (__ARM_ARCH_8M_BASE__ ) && (__ARM_ARCH_8M_BASE__ == 1)) )
- /// byte value unprivileged access
- static volatile uint8_t TC_CoreInstr_LoadStoreAcquire_byte = 0x47U;
- /// halfword value unprivileged access
- static volatile uint16_t TC_CoreInstr_LoadStoreAcquire_hword = 0x0815U;
- /// word value unprivileged access
- static volatile uint32_t TC_CoreInstr_LoadStoreAcquire_word = 0x08154711U;
- #endif
- /**
- \brief Test case: TC_CoreInstr_LoadStoreAquire
- \details
- Checks Load-Acquire and Store-Release instructions:
- - LDAB, LDAH, LDA
- - STLB, STLH, STL
- */
- void TC_CoreInstr_LoadStoreAcquire (void) {
- #if ((defined (__ARM_ARCH_8_1M_MAIN__ ) && (__ARM_ARCH_8_1M_MAIN__ == 1)) || \
- (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) || \
- (defined (__ARM_ARCH_8M_BASE__ ) && (__ARM_ARCH_8M_BASE__ == 1)) )
- uint8_t u8 = 0U;
- uint16_t u16 = 0U;
- uint32_t u32 = 0U;
- /* 1. Test without interruption */
- u8 = __LDAB(&TC_CoreInstr_LoadStoreAcquire_byte);
- ASSERT_TRUE(u8 == TC_CoreInstr_LoadStoreAcquire_byte);
- __STLB(u8+1U, &TC_CoreInstr_LoadStoreAcquire_byte);
- ASSERT_TRUE(TC_CoreInstr_LoadStoreAcquire_byte == u8+1U);
- u16 = __LDAH(&TC_CoreInstr_LoadStoreAcquire_hword);
- ASSERT_TRUE(u16 == TC_CoreInstr_LoadStoreAcquire_hword);
- __STLH(u16+1U, &TC_CoreInstr_LoadStoreAcquire_hword);
- ASSERT_TRUE(TC_CoreInstr_LoadStoreAcquire_hword == u16+1U);
- u32 = __LDA(&TC_CoreInstr_LoadStoreAcquire_word);
- ASSERT_TRUE(u32 == TC_CoreInstr_LoadStoreAcquire_word);
- __STL(u32+1U, &TC_CoreInstr_LoadStoreAcquire_word);
- ASSERT_TRUE(TC_CoreInstr_LoadStoreAcquire_word == u32+1U);
- #endif
- }
- /*=======0=========1=========2=========3=========4=========5=========6=========7=========8=========9=========0=========1====*/
- #if ((defined (__ARM_ARCH_8_1M_MAIN__ ) && (__ARM_ARCH_8_1M_MAIN__ == 1)) || \
- (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) || \
- (defined (__ARM_ARCH_8M_BASE__ ) && (__ARM_ARCH_8M_BASE__ == 1)) )
- /// byte value unprivileged access
- static volatile uint8_t TC_CoreInstr_LoadStoreAcquireExclusive_byte = 0x47U;
- /// halfword value unprivileged access
- static volatile uint16_t TC_CoreInstr_LoadStoreAcquireExclusive_hword = 0x0815U;
- /// word value unprivileged access
- static volatile uint32_t TC_CoreInstr_LoadStoreAcquireExclusive_word = 0x08154711U;
- #endif
- /**
- \brief Test case: TC_CoreInstr_LoadStoreAquire
- \details
- Checks Load-Acquire and Store-Release exclusive instructions:
- - LDAEXB, LDAEXH, LDAEX
- - STLEXB, STLEXH, STLEX
- */
- void TC_CoreInstr_LoadStoreAcquireExclusive (void) {
- #if ((defined (__ARM_ARCH_8_1M_MAIN__ ) && (__ARM_ARCH_8_1M_MAIN__ == 1)) || \
- (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) || \
- (defined (__ARM_ARCH_8M_BASE__ ) && (__ARM_ARCH_8M_BASE__ == 1)) )
- uint8_t u8 = 0U;
- uint16_t u16 = 0U;
- uint32_t u32 = 0U;
- uint32_t result = 0U;
- /* 1. Test without interruption */
- u8 = __LDAEXB(&TC_CoreInstr_LoadStoreAcquireExclusive_byte);
- ASSERT_TRUE(u8 == TC_CoreInstr_LoadStoreAcquireExclusive_byte);
- result = __STLEXB(u8+1U, &TC_CoreInstr_LoadStoreAcquireExclusive_byte);
- ASSERT_TRUE(result == 0U);
- ASSERT_TRUE(TC_CoreInstr_LoadStoreAcquireExclusive_byte == u8+1U);
- u16 = __LDAEXH(&TC_CoreInstr_LoadStoreAcquireExclusive_hword);
- ASSERT_TRUE(u16 == TC_CoreInstr_LoadStoreAcquireExclusive_hword);
- result = __STLEXH(u16+1U, &TC_CoreInstr_LoadStoreAcquireExclusive_hword);
- ASSERT_TRUE(result == 0U);
- ASSERT_TRUE(TC_CoreInstr_LoadStoreAcquireExclusive_hword == u16+1U);
- u32 = __LDAEX(&TC_CoreInstr_LoadStoreAcquireExclusive_word);
- ASSERT_TRUE(u32 == TC_CoreInstr_LoadStoreAcquireExclusive_word);
- result = __STLEX(u32+1U, &TC_CoreInstr_LoadStoreAcquireExclusive_word);
- ASSERT_TRUE(result == 0U);
- ASSERT_TRUE(TC_CoreInstr_LoadStoreAcquireExclusive_word == u32+1U);
- #endif
- }
- /**
- \brief Test case: TC_CoreInstr_UnalignedUint16
- \details
- Checks macro functions to access unaligned uint16_t values:
- - __UNALIGNED_UINT16_READ
- - __UNALIGNED_UINT16_WRITE
- */
- void TC_CoreInstr_UnalignedUint16(void) {
- uint8_t buffer[3] = { 0U, 0U, 0U };
- uint16_t val;
-
- for(int i=0; i<2; i++) {
- __UNALIGNED_UINT16_WRITE(&(buffer[i]), 0x4711U);
- ASSERT_TRUE(buffer[i] == 0x11U);
- ASSERT_TRUE(buffer[i+1] == 0x47U);
- ASSERT_TRUE(buffer[(i+2)%3] == 0x00U);
-
- buffer[i] = 0x12U;
- buffer[i+1] = 0x46U;
-
- val = __UNALIGNED_UINT16_READ(&(buffer[i]));
- ASSERT_TRUE(val == 0x4612U);
-
- buffer[i] = 0x00U;
- buffer[i+1] = 0x00U;
- }
- }
- /**
- \brief Test case: TC_CoreInstr_UnalignedUint32
- \details
- Checks macro functions to access unaligned uint32_t values:
- - __UNALIGNED_UINT32_READ
- - __UNALIGNED_UINT32_WRITE
- */
- void TC_CoreInstr_UnalignedUint32(void) {
- uint8_t buffer[7] = { 0U, 0U, 0U, 0U, 0U, 0U, 0U };
- uint32_t val;
-
- for(int i=0; i<4; i++) {
- __UNALIGNED_UINT32_WRITE(&(buffer[i]), 0x08154711UL);
- ASSERT_TRUE(buffer[i+0] == 0x11U);
- ASSERT_TRUE(buffer[i+1] == 0x47U);
- ASSERT_TRUE(buffer[i+2] == 0x15U);
- ASSERT_TRUE(buffer[i+3] == 0x08U);
- ASSERT_TRUE(buffer[(i+4)%7] == 0x00U);
- ASSERT_TRUE(buffer[(i+5)%7] == 0x00U);
- ASSERT_TRUE(buffer[(i+6)%7] == 0x00U);
-
- buffer[i+0] = 0x12U;
- buffer[i+1] = 0x46U;
- buffer[i+2] = 0x14U;
- buffer[i+3] = 0x09U;
-
- val = __UNALIGNED_UINT32_READ(&(buffer[i]));
- ASSERT_TRUE(val == 0x09144612UL);
-
- buffer[i+0] = 0x00U;
- buffer[i+1] = 0x00U;
- buffer[i+2] = 0x00U;
- buffer[i+3] = 0x00U;
- }
- }
|