Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Adds a couple of more functions to cortex-M0 atomic operations. #666

Merged
merged 2 commits into from
Oct 13, 2022
Merged
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
65 changes: 61 additions & 4 deletions src/freertos_drivers/common/libatomic.c
Original file line number Diff line number Diff line change
Expand Up @@ -55,19 +55,19 @@ uint16_t __atomic_fetch_sub_2(uint16_t *ptr, uint16_t val, int memorder)
return ret;
}

uint8_t __atomic_exchange_1(uint8_t *ptr, uint8_t val, int memorder)
uint8_t __atomic_fetch_or_1(uint8_t *ptr, uint8_t val, int memorder)
{
ACQ_LOCK();
uint8_t ret = *ptr;
*ptr = val;
*ptr = ret | val;
REL_LOCK();
return ret;
}

uint8_t __atomic_fetch_or_1(uint8_t *ptr, uint8_t val, int memorder)
uint32_t __atomic_fetch_or_4(uint32_t *ptr, uint32_t val, int memorder)
{
ACQ_LOCK();
uint8_t ret = *ptr;
uint32_t ret = *ptr;
*ptr = ret | val;
REL_LOCK();
return ret;
Expand All @@ -82,4 +82,61 @@ uint8_t __atomic_fetch_and_1(uint8_t *ptr, uint8_t val, int memorder)
return ret;
}

uint32_t __atomic_fetch_and_4(uint32_t *ptr, uint32_t val, int memorder)
{
ACQ_LOCK();
uint32_t ret = *ptr;
*ptr = ret & val;
REL_LOCK();
return ret;
}

uint8_t __atomic_exchange_1(uint8_t *ptr, uint8_t val, int memorder)
{
ACQ_LOCK();
uint8_t ret = *ptr;
*ptr = val;
REL_LOCK();
return ret;
}

/// This built-in function implements an atomic compare and exchange
/// operation. This compares the contents of *ptr with the contents of
/// *exp. If equal, the operation is a read-modify-write operation that
/// writes desired into *ptr. If they are not equal, the operation is a read
/// and the current contents of *ptr are written into *expected.
///
/// If desired is written into *ptr then true is returned.
_Bool __atomic_compare_exchange_1(uint8_t *ptr, uint8_t *exp, uint8_t desired,
_Bool weak, int success_memorder, int failure_memorder)
{
ACQ_LOCK();
uint8_t curr = *ptr;
if (curr == *exp)
{
*ptr = desired;
REL_LOCK();
return 1;
}
*exp = curr;
REL_LOCK();
return 0;
}

_Bool __atomic_compare_exchange_4(uint32_t *ptr, uint32_t *exp,
uint32_t desired, _Bool weak, int success_memorder, int failure_memorder)
{
ACQ_LOCK();
uint32_t curr = *ptr;
if (curr == *exp)
{
*ptr = desired;
REL_LOCK();
return 1;
}
*exp = curr;
REL_LOCK();
return 0;
}

#endif // guard for arduino compilation