00

Committer:
ganlikun
Date:
Sun Jun 12 14:02:44 2022 +0000
Revision:
0:13413ea9a877
00

Who changed what in which revision?

UserRevisionLine numberNew contents of line
ganlikun 0:13413ea9a877 1
ganlikun 0:13413ea9a877 2 /** \addtogroup platform */
ganlikun 0:13413ea9a877 3 /** @{*/
ganlikun 0:13413ea9a877 4 /*
ganlikun 0:13413ea9a877 5 * Copyright (c) 2015-2016, ARM Limited, All Rights Reserved
ganlikun 0:13413ea9a877 6 * SPDX-License-Identifier: Apache-2.0
ganlikun 0:13413ea9a877 7 *
ganlikun 0:13413ea9a877 8 * Licensed under the Apache License, Version 2.0 (the "License"); you may
ganlikun 0:13413ea9a877 9 * not use this file except in compliance with the License.
ganlikun 0:13413ea9a877 10 * You may obtain a copy of the License at
ganlikun 0:13413ea9a877 11 *
ganlikun 0:13413ea9a877 12 * http://www.apache.org/licenses/LICENSE-2.0
ganlikun 0:13413ea9a877 13 *
ganlikun 0:13413ea9a877 14 * Unless required by applicable law or agreed to in writing, software
ganlikun 0:13413ea9a877 15 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
ganlikun 0:13413ea9a877 16 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
ganlikun 0:13413ea9a877 17 * See the License for the specific language governing permissions and
ganlikun 0:13413ea9a877 18 * limitations under the License.
ganlikun 0:13413ea9a877 19 */
ganlikun 0:13413ea9a877 20
ganlikun 0:13413ea9a877 21 #ifndef __MBED_UTIL_CRITICAL_H__
ganlikun 0:13413ea9a877 22 #define __MBED_UTIL_CRITICAL_H__
ganlikun 0:13413ea9a877 23
ganlikun 0:13413ea9a877 24 #include <stdbool.h>
ganlikun 0:13413ea9a877 25 #include <stdint.h>
ganlikun 0:13413ea9a877 26 #include <stddef.h>
ganlikun 0:13413ea9a877 27
ganlikun 0:13413ea9a877 28 #ifdef __cplusplus
ganlikun 0:13413ea9a877 29 extern "C" {
ganlikun 0:13413ea9a877 30 #endif
ganlikun 0:13413ea9a877 31
ganlikun 0:13413ea9a877 32
ganlikun 0:13413ea9a877 33 /** Determine the current interrupts enabled state
ganlikun 0:13413ea9a877 34 *
ganlikun 0:13413ea9a877 35 * This function can be called to determine whether or not interrupts are currently enabled.
ganlikun 0:13413ea9a877 36 * @note
ganlikun 0:13413ea9a877 37 * NOTE:
ganlikun 0:13413ea9a877 38 * This function works for both cortex-A and cortex-M, although the underlyng implementation
ganlikun 0:13413ea9a877 39 * differs.
ganlikun 0:13413ea9a877 40 * @return true if interrupts are enabled, false otherwise
ganlikun 0:13413ea9a877 41 */
ganlikun 0:13413ea9a877 42 bool core_util_are_interrupts_enabled(void);
ganlikun 0:13413ea9a877 43
ganlikun 0:13413ea9a877 44 /** Determine if this code is executing from an interrupt
ganlikun 0:13413ea9a877 45 *
ganlikun 0:13413ea9a877 46 * This function can be called to determine if the code is running on interrupt context.
ganlikun 0:13413ea9a877 47 * @note
ganlikun 0:13413ea9a877 48 * NOTE:
ganlikun 0:13413ea9a877 49 * This function works for both cortex-A and cortex-M, although the underlyng implementation
ganlikun 0:13413ea9a877 50 * differs.
ganlikun 0:13413ea9a877 51 * @return true if in an isr, false otherwise
ganlikun 0:13413ea9a877 52 */
ganlikun 0:13413ea9a877 53 bool core_util_is_isr_active(void);
ganlikun 0:13413ea9a877 54
ganlikun 0:13413ea9a877 55 /** Mark the start of a critical section
ganlikun 0:13413ea9a877 56 *
ganlikun 0:13413ea9a877 57 * This function should be called to mark the start of a critical section of code.
ganlikun 0:13413ea9a877 58 * @note
ganlikun 0:13413ea9a877 59 * NOTES:
ganlikun 0:13413ea9a877 60 * 1) The use of this style of critical section is targetted at C based implementations.
ganlikun 0:13413ea9a877 61 * 2) These critical sections can be nested.
ganlikun 0:13413ea9a877 62 * 3) The interrupt enable state on entry to the first critical section (of a nested set, or single
ganlikun 0:13413ea9a877 63 * section) will be preserved on exit from the section.
ganlikun 0:13413ea9a877 64 * 4) This implementation will currently only work on code running in privileged mode.
ganlikun 0:13413ea9a877 65 */
ganlikun 0:13413ea9a877 66 void core_util_critical_section_enter(void);
ganlikun 0:13413ea9a877 67
ganlikun 0:13413ea9a877 68 /** Mark the end of a critical section
ganlikun 0:13413ea9a877 69 *
ganlikun 0:13413ea9a877 70 * This function should be called to mark the end of a critical section of code.
ganlikun 0:13413ea9a877 71 * @note
ganlikun 0:13413ea9a877 72 * NOTES:
ganlikun 0:13413ea9a877 73 * 1) The use of this style of critical section is targetted at C based implementations.
ganlikun 0:13413ea9a877 74 * 2) These critical sections can be nested.
ganlikun 0:13413ea9a877 75 * 3) The interrupt enable state on entry to the first critical section (of a nested set, or single
ganlikun 0:13413ea9a877 76 * section) will be preserved on exit from the section.
ganlikun 0:13413ea9a877 77 * 4) This implementation will currently only work on code running in privileged mode.
ganlikun 0:13413ea9a877 78 */
ganlikun 0:13413ea9a877 79 void core_util_critical_section_exit(void);
ganlikun 0:13413ea9a877 80
ganlikun 0:13413ea9a877 81 /**
ganlikun 0:13413ea9a877 82 * Atomic compare and set. It compares the contents of a memory location to a
ganlikun 0:13413ea9a877 83 * given value and, only if they are the same, modifies the contents of that
ganlikun 0:13413ea9a877 84 * memory location to a given new value. This is done as a single atomic
ganlikun 0:13413ea9a877 85 * operation. The atomicity guarantees that the new value is calculated based on
ganlikun 0:13413ea9a877 86 * up-to-date information; if the value had been updated by another thread in
ganlikun 0:13413ea9a877 87 * the meantime, the write would fail due to a mismatched expectedCurrentValue.
ganlikun 0:13413ea9a877 88 *
ganlikun 0:13413ea9a877 89 * Refer to https://en.wikipedia.org/wiki/Compare-and-set [which may redirect
ganlikun 0:13413ea9a877 90 * you to the article on compare-and swap].
ganlikun 0:13413ea9a877 91 *
ganlikun 0:13413ea9a877 92 * @param ptr The target memory location.
ganlikun 0:13413ea9a877 93 * @param[in,out] expectedCurrentValue A pointer to some location holding the
ganlikun 0:13413ea9a877 94 * expected current value of the data being set atomically.
ganlikun 0:13413ea9a877 95 * The computed 'desiredValue' should be a function of this current value.
ganlikun 0:13413ea9a877 96 * @note: This is an in-out parameter. In the
ganlikun 0:13413ea9a877 97 * failure case of atomic_cas (where the
ganlikun 0:13413ea9a877 98 * destination isn't set), the pointee of expectedCurrentValue is
ganlikun 0:13413ea9a877 99 * updated with the current value.
ganlikun 0:13413ea9a877 100 * @param[in] desiredValue The new value computed based on '*expectedCurrentValue'.
ganlikun 0:13413ea9a877 101 *
ganlikun 0:13413ea9a877 102 * @return true if the memory location was atomically
ganlikun 0:13413ea9a877 103 * updated with the desired value (after verifying
ganlikun 0:13413ea9a877 104 * that it contained the expectedCurrentValue),
ganlikun 0:13413ea9a877 105 * false otherwise. In the failure case,
ganlikun 0:13413ea9a877 106 * exepctedCurrentValue is updated with the new
ganlikun 0:13413ea9a877 107 * value of the target memory location.
ganlikun 0:13413ea9a877 108 *
ganlikun 0:13413ea9a877 109 * pseudocode:
ganlikun 0:13413ea9a877 110 * function cas(p : pointer to int, old : pointer to int, new : int) returns bool {
ganlikun 0:13413ea9a877 111 * if *p != *old {
ganlikun 0:13413ea9a877 112 * *old = *p
ganlikun 0:13413ea9a877 113 * return false
ganlikun 0:13413ea9a877 114 * }
ganlikun 0:13413ea9a877 115 * *p = new
ganlikun 0:13413ea9a877 116 * return true
ganlikun 0:13413ea9a877 117 * }
ganlikun 0:13413ea9a877 118 *
ganlikun 0:13413ea9a877 119 * @note: In the failure case (where the destination isn't set), the value
ganlikun 0:13413ea9a877 120 * pointed to by expectedCurrentValue is still updated with the current value.
ganlikun 0:13413ea9a877 121 * This property helps writing concise code for the following incr:
ganlikun 0:13413ea9a877 122 *
ganlikun 0:13413ea9a877 123 * function incr(p : pointer to int, a : int) returns int {
ganlikun 0:13413ea9a877 124 * done = false
ganlikun 0:13413ea9a877 125 * value = *p // This fetch operation need not be atomic.
ganlikun 0:13413ea9a877 126 * while not done {
ganlikun 0:13413ea9a877 127 * done = atomic_cas(p, &value, value + a) // *value gets updated automatically until success
ganlikun 0:13413ea9a877 128 * }
ganlikun 0:13413ea9a877 129 * return value + a
ganlikun 0:13413ea9a877 130 * }
ganlikun 0:13413ea9a877 131 */
ganlikun 0:13413ea9a877 132 bool core_util_atomic_cas_u8(uint8_t *ptr, uint8_t *expectedCurrentValue, uint8_t desiredValue);
ganlikun 0:13413ea9a877 133
ganlikun 0:13413ea9a877 134 /**
ganlikun 0:13413ea9a877 135 * Atomic compare and set. It compares the contents of a memory location to a
ganlikun 0:13413ea9a877 136 * given value and, only if they are the same, modifies the contents of that
ganlikun 0:13413ea9a877 137 * memory location to a given new value. This is done as a single atomic
ganlikun 0:13413ea9a877 138 * operation. The atomicity guarantees that the new value is calculated based on
ganlikun 0:13413ea9a877 139 * up-to-date information; if the value had been updated by another thread in
ganlikun 0:13413ea9a877 140 * the meantime, the write would fail due to a mismatched expectedCurrentValue.
ganlikun 0:13413ea9a877 141 *
ganlikun 0:13413ea9a877 142 * Refer to https://en.wikipedia.org/wiki/Compare-and-set [which may redirect
ganlikun 0:13413ea9a877 143 * you to the article on compare-and swap].
ganlikun 0:13413ea9a877 144 *
ganlikun 0:13413ea9a877 145 * @param ptr The target memory location.
ganlikun 0:13413ea9a877 146 * @param[in,out] expectedCurrentValue A pointer to some location holding the
ganlikun 0:13413ea9a877 147 * expected current value of the data being set atomically.
ganlikun 0:13413ea9a877 148 * The computed 'desiredValue' should be a function of this current value.
ganlikun 0:13413ea9a877 149 * @note: This is an in-out parameter. In the
ganlikun 0:13413ea9a877 150 * failure case of atomic_cas (where the
ganlikun 0:13413ea9a877 151 * destination isn't set), the pointee of expectedCurrentValue is
ganlikun 0:13413ea9a877 152 * updated with the current value.
ganlikun 0:13413ea9a877 153 * @param[in] desiredValue The new value computed based on '*expectedCurrentValue'.
ganlikun 0:13413ea9a877 154 *
ganlikun 0:13413ea9a877 155 * @return true if the memory location was atomically
ganlikun 0:13413ea9a877 156 * updated with the desired value (after verifying
ganlikun 0:13413ea9a877 157 * that it contained the expectedCurrentValue),
ganlikun 0:13413ea9a877 158 * false otherwise. In the failure case,
ganlikun 0:13413ea9a877 159 * exepctedCurrentValue is updated with the new
ganlikun 0:13413ea9a877 160 * value of the target memory location.
ganlikun 0:13413ea9a877 161 *
ganlikun 0:13413ea9a877 162 * pseudocode:
ganlikun 0:13413ea9a877 163 * function cas(p : pointer to int, old : pointer to int, new : int) returns bool {
ganlikun 0:13413ea9a877 164 * if *p != *old {
ganlikun 0:13413ea9a877 165 * *old = *p
ganlikun 0:13413ea9a877 166 * return false
ganlikun 0:13413ea9a877 167 * }
ganlikun 0:13413ea9a877 168 * *p = new
ganlikun 0:13413ea9a877 169 * return true
ganlikun 0:13413ea9a877 170 * }
ganlikun 0:13413ea9a877 171 *
ganlikun 0:13413ea9a877 172 * @note: In the failure case (where the destination isn't set), the value
ganlikun 0:13413ea9a877 173 * pointed to by expectedCurrentValue is still updated with the current value.
ganlikun 0:13413ea9a877 174 * This property helps writing concise code for the following incr:
ganlikun 0:13413ea9a877 175 *
ganlikun 0:13413ea9a877 176 * function incr(p : pointer to int, a : int) returns int {
ganlikun 0:13413ea9a877 177 * done = false
ganlikun 0:13413ea9a877 178 * value = *p // This fetch operation need not be atomic.
ganlikun 0:13413ea9a877 179 * while not done {
ganlikun 0:13413ea9a877 180 * done = atomic_cas(p, &value, value + a) // *value gets updated automatically until success
ganlikun 0:13413ea9a877 181 * }
ganlikun 0:13413ea9a877 182 * return value + a
ganlikun 0:13413ea9a877 183 * }
ganlikun 0:13413ea9a877 184 */
ganlikun 0:13413ea9a877 185 bool core_util_atomic_cas_u16(uint16_t *ptr, uint16_t *expectedCurrentValue, uint16_t desiredValue);
ganlikun 0:13413ea9a877 186
ganlikun 0:13413ea9a877 187 /**
ganlikun 0:13413ea9a877 188 * Atomic compare and set. It compares the contents of a memory location to a
ganlikun 0:13413ea9a877 189 * given value and, only if they are the same, modifies the contents of that
ganlikun 0:13413ea9a877 190 * memory location to a given new value. This is done as a single atomic
ganlikun 0:13413ea9a877 191 * operation. The atomicity guarantees that the new value is calculated based on
ganlikun 0:13413ea9a877 192 * up-to-date information; if the value had been updated by another thread in
ganlikun 0:13413ea9a877 193 * the meantime, the write would fail due to a mismatched expectedCurrentValue.
ganlikun 0:13413ea9a877 194 *
ganlikun 0:13413ea9a877 195 * Refer to https://en.wikipedia.org/wiki/Compare-and-set [which may redirect
ganlikun 0:13413ea9a877 196 * you to the article on compare-and swap].
ganlikun 0:13413ea9a877 197 *
ganlikun 0:13413ea9a877 198 * @param ptr The target memory location.
ganlikun 0:13413ea9a877 199 * @param[in,out] expectedCurrentValue A pointer to some location holding the
ganlikun 0:13413ea9a877 200 * expected current value of the data being set atomically.
ganlikun 0:13413ea9a877 201 * The computed 'desiredValue' should be a function of this current value.
ganlikun 0:13413ea9a877 202 * @note: This is an in-out parameter. In the
ganlikun 0:13413ea9a877 203 * failure case of atomic_cas (where the
ganlikun 0:13413ea9a877 204 * destination isn't set), the pointee of expectedCurrentValue is
ganlikun 0:13413ea9a877 205 * updated with the current value.
ganlikun 0:13413ea9a877 206 * @param[in] desiredValue The new value computed based on '*expectedCurrentValue'.
ganlikun 0:13413ea9a877 207 *
ganlikun 0:13413ea9a877 208 * @return true if the memory location was atomically
ganlikun 0:13413ea9a877 209 * updated with the desired value (after verifying
ganlikun 0:13413ea9a877 210 * that it contained the expectedCurrentValue),
ganlikun 0:13413ea9a877 211 * false otherwise. In the failure case,
ganlikun 0:13413ea9a877 212 * exepctedCurrentValue is updated with the new
ganlikun 0:13413ea9a877 213 * value of the target memory location.
ganlikun 0:13413ea9a877 214 *
ganlikun 0:13413ea9a877 215 * pseudocode:
ganlikun 0:13413ea9a877 216 * function cas(p : pointer to int, old : pointer to int, new : int) returns bool {
ganlikun 0:13413ea9a877 217 * if *p != *old {
ganlikun 0:13413ea9a877 218 * *old = *p
ganlikun 0:13413ea9a877 219 * return false
ganlikun 0:13413ea9a877 220 * }
ganlikun 0:13413ea9a877 221 * *p = new
ganlikun 0:13413ea9a877 222 * return true
ganlikun 0:13413ea9a877 223 * }
ganlikun 0:13413ea9a877 224 *
ganlikun 0:13413ea9a877 225 * @note: In the failure case (where the destination isn't set), the value
ganlikun 0:13413ea9a877 226 * pointed to by expectedCurrentValue is still updated with the current value.
ganlikun 0:13413ea9a877 227 * This property helps writing concise code for the following incr:
ganlikun 0:13413ea9a877 228 *
ganlikun 0:13413ea9a877 229 * function incr(p : pointer to int, a : int) returns int {
ganlikun 0:13413ea9a877 230 * done = false
ganlikun 0:13413ea9a877 231 * value = *p // This fetch operation need not be atomic.
ganlikun 0:13413ea9a877 232 * while not done {
ganlikun 0:13413ea9a877 233 * done = atomic_cas(p, &value, value + a) // *value gets updated automatically until success
ganlikun 0:13413ea9a877 234 * }
ganlikun 0:13413ea9a877 235 * return value + a
ganlikun 0:13413ea9a877 236 * }
ganlikun 0:13413ea9a877 237 */
ganlikun 0:13413ea9a877 238 bool core_util_atomic_cas_u32(uint32_t *ptr, uint32_t *expectedCurrentValue, uint32_t desiredValue);
ganlikun 0:13413ea9a877 239
ganlikun 0:13413ea9a877 240 /**
ganlikun 0:13413ea9a877 241 * Atomic compare and set. It compares the contents of a memory location to a
ganlikun 0:13413ea9a877 242 * given value and, only if they are the same, modifies the contents of that
ganlikun 0:13413ea9a877 243 * memory location to a given new value. This is done as a single atomic
ganlikun 0:13413ea9a877 244 * operation. The atomicity guarantees that the new value is calculated based on
ganlikun 0:13413ea9a877 245 * up-to-date information; if the value had been updated by another thread in
ganlikun 0:13413ea9a877 246 * the meantime, the write would fail due to a mismatched expectedCurrentValue.
ganlikun 0:13413ea9a877 247 *
ganlikun 0:13413ea9a877 248 * Refer to https://en.wikipedia.org/wiki/Compare-and-set [which may redirect
ganlikun 0:13413ea9a877 249 * you to the article on compare-and swap].
ganlikun 0:13413ea9a877 250 *
ganlikun 0:13413ea9a877 251 * @param ptr The target memory location.
ganlikun 0:13413ea9a877 252 * @param[in,out] expectedCurrentValue A pointer to some location holding the
ganlikun 0:13413ea9a877 253 * expected current value of the data being set atomically.
ganlikun 0:13413ea9a877 254 * The computed 'desiredValue' should be a function of this current value.
ganlikun 0:13413ea9a877 255 * @note: This is an in-out parameter. In the
ganlikun 0:13413ea9a877 256 * failure case of atomic_cas (where the
ganlikun 0:13413ea9a877 257 * destination isn't set), the pointee of expectedCurrentValue is
ganlikun 0:13413ea9a877 258 * updated with the current value.
ganlikun 0:13413ea9a877 259 * @param[in] desiredValue The new value computed based on '*expectedCurrentValue'.
ganlikun 0:13413ea9a877 260 *
ganlikun 0:13413ea9a877 261 * @return true if the memory location was atomically
ganlikun 0:13413ea9a877 262 * updated with the desired value (after verifying
ganlikun 0:13413ea9a877 263 * that it contained the expectedCurrentValue),
ganlikun 0:13413ea9a877 264 * false otherwise. In the failure case,
ganlikun 0:13413ea9a877 265 * exepctedCurrentValue is updated with the new
ganlikun 0:13413ea9a877 266 * value of the target memory location.
ganlikun 0:13413ea9a877 267 *
ganlikun 0:13413ea9a877 268 * pseudocode:
ganlikun 0:13413ea9a877 269 * function cas(p : pointer to int, old : pointer to int, new : int) returns bool {
ganlikun 0:13413ea9a877 270 * if *p != *old {
ganlikun 0:13413ea9a877 271 * *old = *p
ganlikun 0:13413ea9a877 272 * return false
ganlikun 0:13413ea9a877 273 * }
ganlikun 0:13413ea9a877 274 * *p = new
ganlikun 0:13413ea9a877 275 * return true
ganlikun 0:13413ea9a877 276 * }
ganlikun 0:13413ea9a877 277 *
ganlikun 0:13413ea9a877 278 * @note: In the failure case (where the destination isn't set), the value
ganlikun 0:13413ea9a877 279 * pointed to by expectedCurrentValue is still updated with the current value.
ganlikun 0:13413ea9a877 280 * This property helps writing concise code for the following incr:
ganlikun 0:13413ea9a877 281 *
ganlikun 0:13413ea9a877 282 * function incr(p : pointer to int, a : int) returns int {
ganlikun 0:13413ea9a877 283 * done = false
ganlikun 0:13413ea9a877 284 * value = *p // This fetch operation need not be atomic.
ganlikun 0:13413ea9a877 285 * while not done {
ganlikun 0:13413ea9a877 286 * done = atomic_cas(p, &value, value + a) // *value gets updated automatically until success
ganlikun 0:13413ea9a877 287 * }
ganlikun 0:13413ea9a877 288 * return value + a
ganlikun 0:13413ea9a877 289 * }
ganlikun 0:13413ea9a877 290 */
ganlikun 0:13413ea9a877 291 bool core_util_atomic_cas_ptr(void **ptr, void **expectedCurrentValue, void *desiredValue);
ganlikun 0:13413ea9a877 292
ganlikun 0:13413ea9a877 293 /**
ganlikun 0:13413ea9a877 294 * Atomic increment.
ganlikun 0:13413ea9a877 295 * @param valuePtr Target memory location being incremented.
ganlikun 0:13413ea9a877 296 * @param delta The amount being incremented.
ganlikun 0:13413ea9a877 297 * @return The new incremented value.
ganlikun 0:13413ea9a877 298 */
ganlikun 0:13413ea9a877 299 uint8_t core_util_atomic_incr_u8(uint8_t *valuePtr, uint8_t delta);
ganlikun 0:13413ea9a877 300
ganlikun 0:13413ea9a877 301 /**
ganlikun 0:13413ea9a877 302 * Atomic increment.
ganlikun 0:13413ea9a877 303 * @param valuePtr Target memory location being incremented.
ganlikun 0:13413ea9a877 304 * @param delta The amount being incremented.
ganlikun 0:13413ea9a877 305 * @return The new incremented value.
ganlikun 0:13413ea9a877 306 */
ganlikun 0:13413ea9a877 307 uint16_t core_util_atomic_incr_u16(uint16_t *valuePtr, uint16_t delta);
ganlikun 0:13413ea9a877 308
ganlikun 0:13413ea9a877 309 /**
ganlikun 0:13413ea9a877 310 * Atomic increment.
ganlikun 0:13413ea9a877 311 * @param valuePtr Target memory location being incremented.
ganlikun 0:13413ea9a877 312 * @param delta The amount being incremented.
ganlikun 0:13413ea9a877 313 * @return The new incremented value.
ganlikun 0:13413ea9a877 314 */
ganlikun 0:13413ea9a877 315 uint32_t core_util_atomic_incr_u32(uint32_t *valuePtr, uint32_t delta);
ganlikun 0:13413ea9a877 316
ganlikun 0:13413ea9a877 317 /**
ganlikun 0:13413ea9a877 318 * Atomic increment.
ganlikun 0:13413ea9a877 319 * @param valuePtr Target memory location being incremented.
ganlikun 0:13413ea9a877 320 * @param delta The amount being incremented in bytes.
ganlikun 0:13413ea9a877 321 * @return The new incremented value.
ganlikun 0:13413ea9a877 322 *
ganlikun 0:13413ea9a877 323 * @note The type of the pointer argument is not taken into account
ganlikun 0:13413ea9a877 324 * and the pointer is incremented by bytes.
ganlikun 0:13413ea9a877 325 */
ganlikun 0:13413ea9a877 326 void *core_util_atomic_incr_ptr(void **valuePtr, ptrdiff_t delta);
ganlikun 0:13413ea9a877 327
ganlikun 0:13413ea9a877 328 /**
ganlikun 0:13413ea9a877 329 * Atomic decrement.
ganlikun 0:13413ea9a877 330 * @param valuePtr Target memory location being decremented.
ganlikun 0:13413ea9a877 331 * @param delta The amount being decremented.
ganlikun 0:13413ea9a877 332 * @return The new decremented value.
ganlikun 0:13413ea9a877 333 */
ganlikun 0:13413ea9a877 334 uint8_t core_util_atomic_decr_u8(uint8_t *valuePtr, uint8_t delta);
ganlikun 0:13413ea9a877 335
ganlikun 0:13413ea9a877 336 /**
ganlikun 0:13413ea9a877 337 * Atomic decrement.
ganlikun 0:13413ea9a877 338 * @param valuePtr Target memory location being decremented.
ganlikun 0:13413ea9a877 339 * @param delta The amount being decremented.
ganlikun 0:13413ea9a877 340 * @return The new decremented value.
ganlikun 0:13413ea9a877 341 */
ganlikun 0:13413ea9a877 342 uint16_t core_util_atomic_decr_u16(uint16_t *valuePtr, uint16_t delta);
ganlikun 0:13413ea9a877 343
ganlikun 0:13413ea9a877 344 /**
ganlikun 0:13413ea9a877 345 * Atomic decrement.
ganlikun 0:13413ea9a877 346 * @param valuePtr Target memory location being decremented.
ganlikun 0:13413ea9a877 347 * @param delta The amount being decremented.
ganlikun 0:13413ea9a877 348 * @return The new decremented value.
ganlikun 0:13413ea9a877 349 */
ganlikun 0:13413ea9a877 350 uint32_t core_util_atomic_decr_u32(uint32_t *valuePtr, uint32_t delta);
ganlikun 0:13413ea9a877 351
ganlikun 0:13413ea9a877 352 /**
ganlikun 0:13413ea9a877 353 * Atomic decrement.
ganlikun 0:13413ea9a877 354 * @param valuePtr Target memory location being decremented.
ganlikun 0:13413ea9a877 355 * @param delta The amount being decremented in bytes.
ganlikun 0:13413ea9a877 356 * @return The new decremented value.
ganlikun 0:13413ea9a877 357 *
ganlikun 0:13413ea9a877 358 * @note The type of the pointer argument is not taken into account
ganlikun 0:13413ea9a877 359 * and the pointer is decremented by bytes
ganlikun 0:13413ea9a877 360 */
ganlikun 0:13413ea9a877 361 void *core_util_atomic_decr_ptr(void **valuePtr, ptrdiff_t delta);
ganlikun 0:13413ea9a877 362
ganlikun 0:13413ea9a877 363 #ifdef __cplusplus
ganlikun 0:13413ea9a877 364 } // extern "C"
ganlikun 0:13413ea9a877 365 #endif
ganlikun 0:13413ea9a877 366
ganlikun 0:13413ea9a877 367
ganlikun 0:13413ea9a877 368 #endif // __MBED_UTIL_CRITICAL_H__
ganlikun 0:13413ea9a877 369
ganlikun 0:13413ea9a877 370 /** @}*/
ganlikun 0:13413ea9a877 371