]> begriffs open source - cmsis/blob - CMSIS/Core/Include/cmsis_gcc.h
Doxygen: Fixed Core(M) revision history table to use consistent summary attribute.
[cmsis] / CMSIS / Core / Include / cmsis_gcc.h
1 /**************************************************************************//**
2  * @file     cmsis_gcc.h
3  * @brief    CMSIS compiler GCC header file
4  * @version  V5.0.4
5  * @date     09. April 2018
6  ******************************************************************************/
7 /*
8  * Copyright (c) 2009-2018 Arm Limited. All rights reserved.
9  *
10  * SPDX-License-Identifier: Apache-2.0
11  *
12  * Licensed under the Apache License, Version 2.0 (the License); you may
13  * not use this file except in compliance with the License.
14  * You may obtain a copy of the License at
15  *
16  * www.apache.org/licenses/LICENSE-2.0
17  *
18  * Unless required by applicable law or agreed to in writing, software
19  * distributed under the License is distributed on an AS IS BASIS, WITHOUT
20  * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
21  * See the License for the specific language governing permissions and
22  * limitations under the License.
23  */
24
25 #ifndef __CMSIS_GCC_H
26 #define __CMSIS_GCC_H
27
28 /* ignore some GCC warnings */
29 #pragma GCC diagnostic push
30 #pragma GCC diagnostic ignored "-Wsign-conversion"
31 #pragma GCC diagnostic ignored "-Wconversion"
32 #pragma GCC diagnostic ignored "-Wunused-parameter"
33
34 /* Fallback for __has_builtin */
35 #ifndef __has_builtin
36   #define __has_builtin(x) (0)
37 #endif
38
39 /* CMSIS compiler specific defines */
40 #ifndef   __ASM
41   #define __ASM                                  __asm
42 #endif
43 #ifndef   __INLINE
44   #define __INLINE                               inline
45 #endif
46 #ifndef   __STATIC_INLINE
47   #define __STATIC_INLINE                        static inline
48 #endif
49 #ifndef   __STATIC_FORCEINLINE                 
50   #define __STATIC_FORCEINLINE                   __attribute__((always_inline)) static inline
51 #endif                                           
52 #ifndef   __NO_RETURN
53   #define __NO_RETURN                            __attribute__((__noreturn__))
54 #endif
55 #ifndef   __USED
56   #define __USED                                 __attribute__((used))
57 #endif
58 #ifndef   __WEAK
59   #define __WEAK                                 __attribute__((weak))
60 #endif
61 #ifndef   __PACKED
62   #define __PACKED                               __attribute__((packed, aligned(1)))
63 #endif
64 #ifndef   __PACKED_STRUCT
65   #define __PACKED_STRUCT                        struct __attribute__((packed, aligned(1)))
66 #endif
67 #ifndef   __PACKED_UNION
68   #define __PACKED_UNION                         union __attribute__((packed, aligned(1)))
69 #endif
70 #ifndef   __UNALIGNED_UINT32        /* deprecated */
71   #pragma GCC diagnostic push
72   #pragma GCC diagnostic ignored "-Wpacked"
73   #pragma GCC diagnostic ignored "-Wattributes"
74   struct __attribute__((packed)) T_UINT32 { uint32_t v; };
75   #pragma GCC diagnostic pop
76   #define __UNALIGNED_UINT32(x)                  (((struct T_UINT32 *)(x))->v)
77 #endif
78 #ifndef   __UNALIGNED_UINT16_WRITE
79   #pragma GCC diagnostic push
80   #pragma GCC diagnostic ignored "-Wpacked"
81   #pragma GCC diagnostic ignored "-Wattributes"
82   __PACKED_STRUCT T_UINT16_WRITE { uint16_t v; };
83   #pragma GCC diagnostic pop
84   #define __UNALIGNED_UINT16_WRITE(addr, val)    (void)((((struct T_UINT16_WRITE *)(void *)(addr))->v) = (val))
85 #endif
86 #ifndef   __UNALIGNED_UINT16_READ
87   #pragma GCC diagnostic push
88   #pragma GCC diagnostic ignored "-Wpacked"
89   #pragma GCC diagnostic ignored "-Wattributes"
90   __PACKED_STRUCT T_UINT16_READ { uint16_t v; };
91   #pragma GCC diagnostic pop
92   #define __UNALIGNED_UINT16_READ(addr)          (((const struct T_UINT16_READ *)(const void *)(addr))->v)
93 #endif
94 #ifndef   __UNALIGNED_UINT32_WRITE
95   #pragma GCC diagnostic push
96   #pragma GCC diagnostic ignored "-Wpacked"
97   #pragma GCC diagnostic ignored "-Wattributes"
98   __PACKED_STRUCT T_UINT32_WRITE { uint32_t v; };
99   #pragma GCC diagnostic pop
100   #define __UNALIGNED_UINT32_WRITE(addr, val)    (void)((((struct T_UINT32_WRITE *)(void *)(addr))->v) = (val))
101 #endif
102 #ifndef   __UNALIGNED_UINT32_READ
103   #pragma GCC diagnostic push
104   #pragma GCC diagnostic ignored "-Wpacked"
105   #pragma GCC diagnostic ignored "-Wattributes"
106   __PACKED_STRUCT T_UINT32_READ { uint32_t v; };
107   #pragma GCC diagnostic pop
108   #define __UNALIGNED_UINT32_READ(addr)          (((const struct T_UINT32_READ *)(const void *)(addr))->v)
109 #endif
110 #ifndef   __ALIGNED
111   #define __ALIGNED(x)                           __attribute__((aligned(x)))
112 #endif
113 #ifndef   __RESTRICT
114   #define __RESTRICT                             __restrict
115 #endif
116
117
118 /* ###########################  Core Function Access  ########################### */
119 /** \ingroup  CMSIS_Core_FunctionInterface
120     \defgroup CMSIS_Core_RegAccFunctions CMSIS Core Register Access Functions
121   @{
122  */
123
124 /**
125   \brief   Enable IRQ Interrupts
126   \details Enables IRQ interrupts by clearing the I-bit in the CPSR.
127            Can only be executed in Privileged modes.
128  */
129 __STATIC_FORCEINLINE void __enable_irq(void)
130 {
131   __ASM volatile ("cpsie i" : : : "memory");
132 }
133
134
135 /**
136   \brief   Disable IRQ Interrupts
137   \details Disables IRQ interrupts by setting the I-bit in the CPSR.
138            Can only be executed in Privileged modes.
139  */
140 __STATIC_FORCEINLINE void __disable_irq(void)
141 {
142   __ASM volatile ("cpsid i" : : : "memory");
143 }
144
145
146 /**
147   \brief   Get Control Register
148   \details Returns the content of the Control Register.
149   \return               Control Register value
150  */
151 __STATIC_FORCEINLINE uint32_t __get_CONTROL(void)
152 {
153   uint32_t result;
154
155   __ASM volatile ("MRS %0, control" : "=r" (result) );
156   return(result);
157 }
158
159
160 #if (defined (__ARM_FEATURE_CMSE ) && (__ARM_FEATURE_CMSE == 3))
161 /**
162   \brief   Get Control Register (non-secure)
163   \details Returns the content of the non-secure Control Register when in secure mode.
164   \return               non-secure Control Register value
165  */
166 __STATIC_FORCEINLINE uint32_t __TZ_get_CONTROL_NS(void)
167 {
168   uint32_t result;
169
170   __ASM volatile ("MRS %0, control_ns" : "=r" (result) );
171   return(result);
172 }
173 #endif
174
175
176 /**
177   \brief   Set Control Register
178   \details Writes the given value to the Control Register.
179   \param [in]    control  Control Register value to set
180  */
181 __STATIC_FORCEINLINE void __set_CONTROL(uint32_t control)
182 {
183   __ASM volatile ("MSR control, %0" : : "r" (control) : "memory");
184 }
185
186
187 #if (defined (__ARM_FEATURE_CMSE ) && (__ARM_FEATURE_CMSE == 3))
188 /**
189   \brief   Set Control Register (non-secure)
190   \details Writes the given value to the non-secure Control Register when in secure state.
191   \param [in]    control  Control Register value to set
192  */
193 __STATIC_FORCEINLINE void __TZ_set_CONTROL_NS(uint32_t control)
194 {
195   __ASM volatile ("MSR control_ns, %0" : : "r" (control) : "memory");
196 }
197 #endif
198
199
200 /**
201   \brief   Get IPSR Register
202   \details Returns the content of the IPSR Register.
203   \return               IPSR Register value
204  */
205 __STATIC_FORCEINLINE uint32_t __get_IPSR(void)
206 {
207   uint32_t result;
208
209   __ASM volatile ("MRS %0, ipsr" : "=r" (result) );
210   return(result);
211 }
212
213
214 /**
215   \brief   Get APSR Register
216   \details Returns the content of the APSR Register.
217   \return               APSR Register value
218  */
219 __STATIC_FORCEINLINE uint32_t __get_APSR(void)
220 {
221   uint32_t result;
222
223   __ASM volatile ("MRS %0, apsr" : "=r" (result) );
224   return(result);
225 }
226
227
228 /**
229   \brief   Get xPSR Register
230   \details Returns the content of the xPSR Register.
231   \return               xPSR Register value
232  */
233 __STATIC_FORCEINLINE uint32_t __get_xPSR(void)
234 {
235   uint32_t result;
236
237   __ASM volatile ("MRS %0, xpsr" : "=r" (result) );
238   return(result);
239 }
240
241
242 /**
243   \brief   Get Process Stack Pointer
244   \details Returns the current value of the Process Stack Pointer (PSP).
245   \return               PSP Register value
246  */
247 __STATIC_FORCEINLINE uint32_t __get_PSP(void)
248 {
249   register uint32_t result;
250
251   __ASM volatile ("MRS %0, psp"  : "=r" (result) );
252   return(result);
253 }
254
255
256 #if (defined (__ARM_FEATURE_CMSE ) && (__ARM_FEATURE_CMSE == 3))
257 /**
258   \brief   Get Process Stack Pointer (non-secure)
259   \details Returns the current value of the non-secure Process Stack Pointer (PSP) when in secure state.
260   \return               PSP Register value
261  */
262 __STATIC_FORCEINLINE uint32_t __TZ_get_PSP_NS(void)
263 {
264   register uint32_t result;
265
266   __ASM volatile ("MRS %0, psp_ns"  : "=r" (result) );
267   return(result);
268 }
269 #endif
270
271
272 /**
273   \brief   Set Process Stack Pointer
274   \details Assigns the given value to the Process Stack Pointer (PSP).
275   \param [in]    topOfProcStack  Process Stack Pointer value to set
276  */
277 __STATIC_FORCEINLINE void __set_PSP(uint32_t topOfProcStack)
278 {
279   __ASM volatile ("MSR psp, %0" : : "r" (topOfProcStack) : );
280 }
281
282
283 #if (defined (__ARM_FEATURE_CMSE ) && (__ARM_FEATURE_CMSE == 3))
284 /**
285   \brief   Set Process Stack Pointer (non-secure)
286   \details Assigns the given value to the non-secure Process Stack Pointer (PSP) when in secure state.
287   \param [in]    topOfProcStack  Process Stack Pointer value to set
288  */
289 __STATIC_FORCEINLINE void __TZ_set_PSP_NS(uint32_t topOfProcStack)
290 {
291   __ASM volatile ("MSR psp_ns, %0" : : "r" (topOfProcStack) : );
292 }
293 #endif
294
295
296 /**
297   \brief   Get Main Stack Pointer
298   \details Returns the current value of the Main Stack Pointer (MSP).
299   \return               MSP Register value
300  */
301 __STATIC_FORCEINLINE uint32_t __get_MSP(void)
302 {
303   register uint32_t result;
304
305   __ASM volatile ("MRS %0, msp" : "=r" (result) );
306   return(result);
307 }
308
309
310 #if (defined (__ARM_FEATURE_CMSE ) && (__ARM_FEATURE_CMSE == 3))
311 /**
312   \brief   Get Main Stack Pointer (non-secure)
313   \details Returns the current value of the non-secure Main Stack Pointer (MSP) when in secure state.
314   \return               MSP Register value
315  */
316 __STATIC_FORCEINLINE uint32_t __TZ_get_MSP_NS(void)
317 {
318   register uint32_t result;
319
320   __ASM volatile ("MRS %0, msp_ns" : "=r" (result) );
321   return(result);
322 }
323 #endif
324
325
326 /**
327   \brief   Set Main Stack Pointer
328   \details Assigns the given value to the Main Stack Pointer (MSP).
329   \param [in]    topOfMainStack  Main Stack Pointer value to set
330  */
331 __STATIC_FORCEINLINE void __set_MSP(uint32_t topOfMainStack)
332 {
333   __ASM volatile ("MSR msp, %0" : : "r" (topOfMainStack) : );
334 }
335
336
337 #if (defined (__ARM_FEATURE_CMSE ) && (__ARM_FEATURE_CMSE == 3))
338 /**
339   \brief   Set Main Stack Pointer (non-secure)
340   \details Assigns the given value to the non-secure Main Stack Pointer (MSP) when in secure state.
341   \param [in]    topOfMainStack  Main Stack Pointer value to set
342  */
343 __STATIC_FORCEINLINE void __TZ_set_MSP_NS(uint32_t topOfMainStack)
344 {
345   __ASM volatile ("MSR msp_ns, %0" : : "r" (topOfMainStack) : );
346 }
347 #endif
348
349
350 #if (defined (__ARM_FEATURE_CMSE ) && (__ARM_FEATURE_CMSE == 3))
351 /**
352   \brief   Get Stack Pointer (non-secure)
353   \details Returns the current value of the non-secure Stack Pointer (SP) when in secure state.
354   \return               SP Register value
355  */
356 __STATIC_FORCEINLINE uint32_t __TZ_get_SP_NS(void)
357 {
358   register uint32_t result;
359
360   __ASM volatile ("MRS %0, sp_ns" : "=r" (result) );
361   return(result);
362 }
363
364
365 /**
366   \brief   Set Stack Pointer (non-secure)
367   \details Assigns the given value to the non-secure Stack Pointer (SP) when in secure state.
368   \param [in]    topOfStack  Stack Pointer value to set
369  */
370 __STATIC_FORCEINLINE void __TZ_set_SP_NS(uint32_t topOfStack)
371 {
372   __ASM volatile ("MSR sp_ns, %0" : : "r" (topOfStack) : );
373 }
374 #endif
375
376
377 /**
378   \brief   Get Priority Mask
379   \details Returns the current state of the priority mask bit from the Priority Mask Register.
380   \return               Priority Mask value
381  */
382 __STATIC_FORCEINLINE uint32_t __get_PRIMASK(void)
383 {
384   uint32_t result;
385
386   __ASM volatile ("MRS %0, primask" : "=r" (result) :: "memory");
387   return(result);
388 }
389
390
391 #if (defined (__ARM_FEATURE_CMSE ) && (__ARM_FEATURE_CMSE == 3))
392 /**
393   \brief   Get Priority Mask (non-secure)
394   \details Returns the current state of the non-secure priority mask bit from the Priority Mask Register when in secure state.
395   \return               Priority Mask value
396  */
397 __STATIC_FORCEINLINE uint32_t __TZ_get_PRIMASK_NS(void)
398 {
399   uint32_t result;
400
401   __ASM volatile ("MRS %0, primask_ns" : "=r" (result) :: "memory");
402   return(result);
403 }
404 #endif
405
406
407 /**
408   \brief   Set Priority Mask
409   \details Assigns the given value to the Priority Mask Register.
410   \param [in]    priMask  Priority Mask
411  */
412 __STATIC_FORCEINLINE void __set_PRIMASK(uint32_t priMask)
413 {
414   __ASM volatile ("MSR primask, %0" : : "r" (priMask) : "memory");
415 }
416
417
418 #if (defined (__ARM_FEATURE_CMSE ) && (__ARM_FEATURE_CMSE == 3))
419 /**
420   \brief   Set Priority Mask (non-secure)
421   \details Assigns the given value to the non-secure Priority Mask Register when in secure state.
422   \param [in]    priMask  Priority Mask
423  */
424 __STATIC_FORCEINLINE void __TZ_set_PRIMASK_NS(uint32_t priMask)
425 {
426   __ASM volatile ("MSR primask_ns, %0" : : "r" (priMask) : "memory");
427 }
428 #endif
429
430
431 #if ((defined (__ARM_ARCH_7M__      ) && (__ARM_ARCH_7M__      == 1)) || \
432      (defined (__ARM_ARCH_7EM__     ) && (__ARM_ARCH_7EM__     == 1)) || \
433      (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1))    )
434 /**
435   \brief   Enable FIQ
436   \details Enables FIQ interrupts by clearing the F-bit in the CPSR.
437            Can only be executed in Privileged modes.
438  */
439 __STATIC_FORCEINLINE void __enable_fault_irq(void)
440 {
441   __ASM volatile ("cpsie f" : : : "memory");
442 }
443
444
445 /**
446   \brief   Disable FIQ
447   \details Disables FIQ interrupts by setting the F-bit in the CPSR.
448            Can only be executed in Privileged modes.
449  */
450 __STATIC_FORCEINLINE void __disable_fault_irq(void)
451 {
452   __ASM volatile ("cpsid f" : : : "memory");
453 }
454
455
456 /**
457   \brief   Get Base Priority
458   \details Returns the current value of the Base Priority register.
459   \return               Base Priority register value
460  */
461 __STATIC_FORCEINLINE uint32_t __get_BASEPRI(void)
462 {
463   uint32_t result;
464
465   __ASM volatile ("MRS %0, basepri" : "=r" (result) );
466   return(result);
467 }
468
469
470 #if (defined (__ARM_FEATURE_CMSE ) && (__ARM_FEATURE_CMSE == 3))
471 /**
472   \brief   Get Base Priority (non-secure)
473   \details Returns the current value of the non-secure Base Priority register when in secure state.
474   \return               Base Priority register value
475  */
476 __STATIC_FORCEINLINE uint32_t __TZ_get_BASEPRI_NS(void)
477 {
478   uint32_t result;
479
480   __ASM volatile ("MRS %0, basepri_ns" : "=r" (result) );
481   return(result);
482 }
483 #endif
484
485
486 /**
487   \brief   Set Base Priority
488   \details Assigns the given value to the Base Priority register.
489   \param [in]    basePri  Base Priority value to set
490  */
491 __STATIC_FORCEINLINE void __set_BASEPRI(uint32_t basePri)
492 {
493   __ASM volatile ("MSR basepri, %0" : : "r" (basePri) : "memory");
494 }
495
496
497 #if (defined (__ARM_FEATURE_CMSE ) && (__ARM_FEATURE_CMSE == 3))
498 /**
499   \brief   Set Base Priority (non-secure)
500   \details Assigns the given value to the non-secure Base Priority register when in secure state.
501   \param [in]    basePri  Base Priority value to set
502  */
503 __STATIC_FORCEINLINE void __TZ_set_BASEPRI_NS(uint32_t basePri)
504 {
505   __ASM volatile ("MSR basepri_ns, %0" : : "r" (basePri) : "memory");
506 }
507 #endif
508
509
510 /**
511   \brief   Set Base Priority with condition
512   \details Assigns the given value to the Base Priority register only if BASEPRI masking is disabled,
513            or the new value increases the BASEPRI priority level.
514   \param [in]    basePri  Base Priority value to set
515  */
516 __STATIC_FORCEINLINE void __set_BASEPRI_MAX(uint32_t basePri)
517 {
518   __ASM volatile ("MSR basepri_max, %0" : : "r" (basePri) : "memory");
519 }
520
521
522 /**
523   \brief   Get Fault Mask
524   \details Returns the current value of the Fault Mask register.
525   \return               Fault Mask register value
526  */
527 __STATIC_FORCEINLINE uint32_t __get_FAULTMASK(void)
528 {
529   uint32_t result;
530
531   __ASM volatile ("MRS %0, faultmask" : "=r" (result) );
532   return(result);
533 }
534
535
536 #if (defined (__ARM_FEATURE_CMSE ) && (__ARM_FEATURE_CMSE == 3))
537 /**
538   \brief   Get Fault Mask (non-secure)
539   \details Returns the current value of the non-secure Fault Mask register when in secure state.
540   \return               Fault Mask register value
541  */
542 __STATIC_FORCEINLINE uint32_t __TZ_get_FAULTMASK_NS(void)
543 {
544   uint32_t result;
545
546   __ASM volatile ("MRS %0, faultmask_ns" : "=r" (result) );
547   return(result);
548 }
549 #endif
550
551
552 /**
553   \brief   Set Fault Mask
554   \details Assigns the given value to the Fault Mask register.
555   \param [in]    faultMask  Fault Mask value to set
556  */
557 __STATIC_FORCEINLINE void __set_FAULTMASK(uint32_t faultMask)
558 {
559   __ASM volatile ("MSR faultmask, %0" : : "r" (faultMask) : "memory");
560 }
561
562
563 #if (defined (__ARM_FEATURE_CMSE ) && (__ARM_FEATURE_CMSE == 3))
564 /**
565   \brief   Set Fault Mask (non-secure)
566   \details Assigns the given value to the non-secure Fault Mask register when in secure state.
567   \param [in]    faultMask  Fault Mask value to set
568  */
569 __STATIC_FORCEINLINE void __TZ_set_FAULTMASK_NS(uint32_t faultMask)
570 {
571   __ASM volatile ("MSR faultmask_ns, %0" : : "r" (faultMask) : "memory");
572 }
573 #endif
574
575 #endif /* ((defined (__ARM_ARCH_7M__      ) && (__ARM_ARCH_7M__      == 1)) || \
576            (defined (__ARM_ARCH_7EM__     ) && (__ARM_ARCH_7EM__     == 1)) || \
577            (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1))    ) */
578
579
580 #if ((defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) || \
581      (defined (__ARM_ARCH_8M_BASE__ ) && (__ARM_ARCH_8M_BASE__ == 1))    )
582
583 /**
584   \brief   Get Process Stack Pointer Limit
585   Devices without ARMv8-M Main Extensions (i.e. Cortex-M23) lack the non-secure
586   Stack Pointer Limit register hence zero is returned always in non-secure
587   mode.
588   
589   \details Returns the current value of the Process Stack Pointer Limit (PSPLIM).
590   \return               PSPLIM Register value
591  */
592 __STATIC_FORCEINLINE uint32_t __get_PSPLIM(void)
593 {
594 #if (!(defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) && \
595     (!defined (__ARM_FEATURE_CMSE) || (__ARM_FEATURE_CMSE < 3)))
596     // without main extensions, the non-secure PSPLIM is RAZ/WI
597   return 0U;
598 #else
599   register uint32_t result;
600   __ASM volatile ("MRS %0, psplim"  : "=r" (result) );
601   return result;
602 #endif
603 }
604
605 #if (defined (__ARM_FEATURE_CMSE) && (__ARM_FEATURE_CMSE == 3))
606 /**
607   \brief   Get Process Stack Pointer Limit (non-secure)
608   Devices without ARMv8-M Main Extensions (i.e. Cortex-M23) lack the non-secure
609   Stack Pointer Limit register hence zero is returned always.
610
611   \details Returns the current value of the non-secure Process Stack Pointer Limit (PSPLIM) when in secure state.
612   \return               PSPLIM Register value
613  */
614 __STATIC_FORCEINLINE uint32_t __TZ_get_PSPLIM_NS(void)
615 {
616 #if (!(defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)))
617   // without main extensions, the non-secure PSPLIM is RAZ/WI
618   return 0U;
619 #else
620   register uint32_t result;
621   __ASM volatile ("MRS %0, psplim_ns"  : "=r" (result) );
622   return result;
623 #endif
624 }
625 #endif
626
627
628 /**
629   \brief   Set Process Stack Pointer Limit
630   Devices without ARMv8-M Main Extensions (i.e. Cortex-M23) lack the non-secure
631   Stack Pointer Limit register hence the write is silently ignored in non-secure
632   mode.
633   
634   \details Assigns the given value to the Process Stack Pointer Limit (PSPLIM).
635   \param [in]    ProcStackPtrLimit  Process Stack Pointer Limit value to set
636  */
637 __STATIC_FORCEINLINE void __set_PSPLIM(uint32_t ProcStackPtrLimit)
638 {
639 #if (!(defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) && \
640     (!defined (__ARM_FEATURE_CMSE) || (__ARM_FEATURE_CMSE < 3)))
641   // without main extensions, the non-secure PSPLIM is RAZ/WI
642   (void)ProcStackPtrLimit;
643 #else
644   __ASM volatile ("MSR psplim, %0" : : "r" (ProcStackPtrLimit));
645 #endif
646 }
647
648
649 #if (defined (__ARM_FEATURE_CMSE  ) && (__ARM_FEATURE_CMSE   == 3))
650 /**
651   \brief   Set Process Stack Pointer (non-secure)
652   Devices without ARMv8-M Main Extensions (i.e. Cortex-M23) lack the non-secure
653   Stack Pointer Limit register hence the write is silently ignored.
654
655   \details Assigns the given value to the non-secure Process Stack Pointer Limit (PSPLIM) when in secure state.
656   \param [in]    ProcStackPtrLimit  Process Stack Pointer Limit value to set
657  */
658 __STATIC_FORCEINLINE void __TZ_set_PSPLIM_NS(uint32_t ProcStackPtrLimit)
659 {
660 #if (!(defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)))
661   // without main extensions, the non-secure PSPLIM is RAZ/WI
662   (void)ProcStackPtrLimit;
663 #else
664   __ASM volatile ("MSR psplim_ns, %0\n" : : "r" (ProcStackPtrLimit));
665 #endif
666 }
667 #endif
668
669
670 /**
671   \brief   Get Main Stack Pointer Limit
672   Devices without ARMv8-M Main Extensions (i.e. Cortex-M23) lack the non-secure
673   Stack Pointer Limit register hence zero is returned always in non-secure
674   mode.
675
676   \details Returns the current value of the Main Stack Pointer Limit (MSPLIM).
677   \return               MSPLIM Register value
678  */
679 __STATIC_FORCEINLINE uint32_t __get_MSPLIM(void)
680 {
681 #if (!(defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) && \
682     (!defined (__ARM_FEATURE_CMSE) || (__ARM_FEATURE_CMSE < 3)))
683   // without main extensions, the non-secure MSPLIM is RAZ/WI
684   return 0U;
685 #else
686   register uint32_t result;
687   __ASM volatile ("MRS %0, msplim" : "=r" (result) );
688   return result;
689 #endif
690 }
691
692
693 #if (defined (__ARM_FEATURE_CMSE  ) && (__ARM_FEATURE_CMSE   == 3))
694 /**
695   \brief   Get Main Stack Pointer Limit (non-secure)
696   Devices without ARMv8-M Main Extensions (i.e. Cortex-M23) lack the non-secure
697   Stack Pointer Limit register hence zero is returned always.
698
699   \details Returns the current value of the non-secure Main Stack Pointer Limit(MSPLIM) when in secure state.
700   \return               MSPLIM Register value
701  */
702 __STATIC_FORCEINLINE uint32_t __TZ_get_MSPLIM_NS(void)
703 {
704 #if (!(defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)))
705   // without main extensions, the non-secure MSPLIM is RAZ/WI
706   return 0U;
707 #else
708   register uint32_t result;
709   __ASM volatile ("MRS %0, msplim_ns" : "=r" (result) );
710   return result;
711 #endif
712 }
713 #endif
714
715
716 /**
717   \brief   Set Main Stack Pointer Limit
718   Devices without ARMv8-M Main Extensions (i.e. Cortex-M23) lack the non-secure
719   Stack Pointer Limit register hence the write is silently ignored in non-secure
720   mode.
721
722   \details Assigns the given value to the Main Stack Pointer Limit (MSPLIM).
723   \param [in]    MainStackPtrLimit  Main Stack Pointer Limit value to set
724  */
725 __STATIC_FORCEINLINE void __set_MSPLIM(uint32_t MainStackPtrLimit)
726 {
727 #if (!(defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) && \
728     (!defined (__ARM_FEATURE_CMSE) || (__ARM_FEATURE_CMSE < 3)))
729   // without main extensions, the non-secure MSPLIM is RAZ/WI
730   (void)MainStackPtrLimit;
731 #else
732   __ASM volatile ("MSR msplim, %0" : : "r" (MainStackPtrLimit));
733 #endif
734 }
735
736
737 #if (defined (__ARM_FEATURE_CMSE  ) && (__ARM_FEATURE_CMSE   == 3))
738 /**
739   \brief   Set Main Stack Pointer Limit (non-secure)
740   Devices without ARMv8-M Main Extensions (i.e. Cortex-M23) lack the non-secure
741   Stack Pointer Limit register hence the write is silently ignored.
742
743   \details Assigns the given value to the non-secure Main Stack Pointer Limit (MSPLIM) when in secure state.
744   \param [in]    MainStackPtrLimit  Main Stack Pointer value to set
745  */
746 __STATIC_FORCEINLINE void __TZ_set_MSPLIM_NS(uint32_t MainStackPtrLimit)
747 {
748 #if (!(defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)))
749   // without main extensions, the non-secure MSPLIM is RAZ/WI
750   (void)MainStackPtrLimit;
751 #else
752   __ASM volatile ("MSR msplim_ns, %0" : : "r" (MainStackPtrLimit));
753 #endif
754 }
755 #endif
756
757 #endif /* ((defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) || \
758            (defined (__ARM_ARCH_8M_BASE__ ) && (__ARM_ARCH_8M_BASE__ == 1))    ) */
759
760
761 #if ((defined (__ARM_ARCH_7EM__     ) && (__ARM_ARCH_7EM__     == 1)) || \
762      (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1))    )
763
764 /**
765   \brief   Get FPSCR
766   \details Returns the current value of the Floating Point Status/Control register.
767   \return               Floating Point Status/Control register value
768  */
769 __STATIC_FORCEINLINE uint32_t __get_FPSCR(void)
770 {
771 #if ((defined (__FPU_PRESENT) && (__FPU_PRESENT == 1U)) && \
772      (defined (__FPU_USED   ) && (__FPU_USED    == 1U))     )
773 #if __has_builtin(__builtin_arm_get_fpscr) 
774 // Re-enable using built-in when GCC has been fixed
775 // || (__GNUC__ > 7) || (__GNUC__ == 7 && __GNUC_MINOR__ >= 2)
776   /* see https://gcc.gnu.org/ml/gcc-patches/2017-04/msg00443.html */
777   return __builtin_arm_get_fpscr();
778 #else
779   uint32_t result;
780
781   __ASM volatile ("VMRS %0, fpscr" : "=r" (result) );
782   return(result);
783 #endif
784 #else
785   return(0U);
786 #endif
787 }
788
789
790 /**
791   \brief   Set FPSCR
792   \details Assigns the given value to the Floating Point Status/Control register.
793   \param [in]    fpscr  Floating Point Status/Control value to set
794  */
795 __STATIC_FORCEINLINE void __set_FPSCR(uint32_t fpscr)
796 {
797 #if ((defined (__FPU_PRESENT) && (__FPU_PRESENT == 1U)) && \
798      (defined (__FPU_USED   ) && (__FPU_USED    == 1U))     )
799 #if __has_builtin(__builtin_arm_set_fpscr)
800 // Re-enable using built-in when GCC has been fixed
801 // || (__GNUC__ > 7) || (__GNUC__ == 7 && __GNUC_MINOR__ >= 2)
802   /* see https://gcc.gnu.org/ml/gcc-patches/2017-04/msg00443.html */
803   __builtin_arm_set_fpscr(fpscr);
804 #else
805   __ASM volatile ("VMSR fpscr, %0" : : "r" (fpscr) : "vfpcc", "memory");
806 #endif
807 #else
808   (void)fpscr;
809 #endif
810 }
811
812 #endif /* ((defined (__ARM_ARCH_7EM__     ) && (__ARM_ARCH_7EM__     == 1)) || \
813            (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1))    ) */
814
815
816
817 /*@} end of CMSIS_Core_RegAccFunctions */
818
819
820 /* ##########################  Core Instruction Access  ######################### */
821 /** \defgroup CMSIS_Core_InstructionInterface CMSIS Core Instruction Interface
822   Access to dedicated instructions
823   @{
824 */
825
826 /* Define macros for porting to both thumb1 and thumb2.
827  * For thumb1, use low register (r0-r7), specified by constraint "l"
828  * Otherwise, use general registers, specified by constraint "r" */
829 #if defined (__thumb__) && !defined (__thumb2__)
830 #define __CMSIS_GCC_OUT_REG(r) "=l" (r)
831 #define __CMSIS_GCC_RW_REG(r) "+l" (r)
832 #define __CMSIS_GCC_USE_REG(r) "l" (r)
833 #else
834 #define __CMSIS_GCC_OUT_REG(r) "=r" (r)
835 #define __CMSIS_GCC_RW_REG(r) "+r" (r)
836 #define __CMSIS_GCC_USE_REG(r) "r" (r)
837 #endif
838
839 /**
840   \brief   No Operation
841   \details No Operation does nothing. This instruction can be used for code alignment purposes.
842  */
843 #define __NOP()                             __ASM volatile ("nop")
844
845 /**
846   \brief   Wait For Interrupt
847   \details Wait For Interrupt is a hint instruction that suspends execution until one of a number of events occurs.
848  */
849 #define __WFI()                             __ASM volatile ("wfi")
850
851
852 /**
853   \brief   Wait For Event
854   \details Wait For Event is a hint instruction that permits the processor to enter
855            a low-power state until one of a number of events occurs.
856  */
857 #define __WFE()                             __ASM volatile ("wfe")
858
859
860 /**
861   \brief   Send Event
862   \details Send Event is a hint instruction. It causes an event to be signaled to the CPU.
863  */
864 #define __SEV()                             __ASM volatile ("sev")
865
866
867 /**
868   \brief   Instruction Synchronization Barrier
869   \details Instruction Synchronization Barrier flushes the pipeline in the processor,
870            so that all instructions following the ISB are fetched from cache or memory,
871            after the instruction has been completed.
872  */
873 __STATIC_FORCEINLINE void __ISB(void)
874 {
875   __ASM volatile ("isb 0xF":::"memory");
876 }
877
878
879 /**
880   \brief   Data Synchronization Barrier
881   \details Acts as a special kind of Data Memory Barrier.
882            It completes when all explicit memory accesses before this instruction complete.
883  */
884 __STATIC_FORCEINLINE void __DSB(void)
885 {
886   __ASM volatile ("dsb 0xF":::"memory");
887 }
888
889
890 /**
891   \brief   Data Memory Barrier
892   \details Ensures the apparent order of the explicit memory operations before
893            and after the instruction, without ensuring their completion.
894  */
895 __STATIC_FORCEINLINE void __DMB(void)
896 {
897   __ASM volatile ("dmb 0xF":::"memory");
898 }
899
900
901 /**
902   \brief   Reverse byte order (32 bit)
903   \details Reverses the byte order in unsigned integer value. For example, 0x12345678 becomes 0x78563412.
904   \param [in]    value  Value to reverse
905   \return               Reversed value
906  */
907 __STATIC_FORCEINLINE uint32_t __REV(uint32_t value)
908 {
909 #if (__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ >= 5)
910   return __builtin_bswap32(value);
911 #else
912   uint32_t result;
913
914   __ASM volatile ("rev %0, %1" : __CMSIS_GCC_OUT_REG (result) : __CMSIS_GCC_USE_REG (value) );
915   return result;
916 #endif
917 }
918
919
920 /**
921   \brief   Reverse byte order (16 bit)
922   \details Reverses the byte order within each halfword of a word. For example, 0x12345678 becomes 0x34127856.
923   \param [in]    value  Value to reverse
924   \return               Reversed value
925  */
926 __STATIC_FORCEINLINE uint32_t __REV16(uint32_t value)
927 {
928   uint32_t result;
929
930   __ASM volatile ("rev16 %0, %1" : __CMSIS_GCC_OUT_REG (result) : __CMSIS_GCC_USE_REG (value) );
931   return result;
932 }
933
934
935 /**
936   \brief   Reverse byte order (16 bit)
937   \details Reverses the byte order in a 16-bit value and returns the signed 16-bit result. For example, 0x0080 becomes 0x8000.
938   \param [in]    value  Value to reverse
939   \return               Reversed value
940  */
941 __STATIC_FORCEINLINE int16_t __REVSH(int16_t value)
942 {
943 #if (__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ >= 8)
944   return (int16_t)__builtin_bswap16(value);
945 #else
946   int16_t result;
947
948   __ASM volatile ("revsh %0, %1" : __CMSIS_GCC_OUT_REG (result) : __CMSIS_GCC_USE_REG (value) );
949   return result;
950 #endif
951 }
952
953
954 /**
955   \brief   Rotate Right in unsigned value (32 bit)
956   \details Rotate Right (immediate) provides the value of the contents of a register rotated by a variable number of bits.
957   \param [in]    op1  Value to rotate
958   \param [in]    op2  Number of Bits to rotate
959   \return               Rotated value
960  */
961 __STATIC_FORCEINLINE uint32_t __ROR(uint32_t op1, uint32_t op2)
962 {
963   op2 %= 32U;
964   if (op2 == 0U)
965   {
966     return op1;
967   }
968   return (op1 >> op2) | (op1 << (32U - op2));
969 }
970
971
972 /**
973   \brief   Breakpoint
974   \details Causes the processor to enter Debug state.
975            Debug tools can use this to investigate system state when the instruction at a particular address is reached.
976   \param [in]    value  is ignored by the processor.
977                  If required, a debugger can use it to store additional information about the breakpoint.
978  */
979 #define __BKPT(value)                       __ASM volatile ("bkpt "#value)
980
981
982 /**
983   \brief   Reverse bit order of value
984   \details Reverses the bit order of the given value.
985   \param [in]    value  Value to reverse
986   \return               Reversed value
987  */
988 __STATIC_FORCEINLINE uint32_t __RBIT(uint32_t value)
989 {
990   uint32_t result;
991
992 #if ((defined (__ARM_ARCH_7M__      ) && (__ARM_ARCH_7M__      == 1)) || \
993      (defined (__ARM_ARCH_7EM__     ) && (__ARM_ARCH_7EM__     == 1)) || \
994      (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1))    )
995    __ASM volatile ("rbit %0, %1" : "=r" (result) : "r" (value) );
996 #else
997   uint32_t s = (4U /*sizeof(v)*/ * 8U) - 1U; /* extra shift needed at end */
998
999   result = value;                      /* r will be reversed bits of v; first get LSB of v */
1000   for (value >>= 1U; value != 0U; value >>= 1U)
1001   {
1002     result <<= 1U;
1003     result |= value & 1U;
1004     s--;
1005   }
1006   result <<= s;                        /* shift when v's highest bits are zero */
1007 #endif
1008   return result;
1009 }
1010
1011
1012 /**
1013   \brief   Count leading zeros
1014   \details Counts the number of leading zeros of a data value.
1015   \param [in]  value  Value to count the leading zeros
1016   \return             number of leading zeros in value
1017  */
1018 #define __CLZ             (uint8_t)__builtin_clz
1019
1020
1021 #if ((defined (__ARM_ARCH_7M__      ) && (__ARM_ARCH_7M__      == 1)) || \
1022      (defined (__ARM_ARCH_7EM__     ) && (__ARM_ARCH_7EM__     == 1)) || \
1023      (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) || \
1024      (defined (__ARM_ARCH_8M_BASE__ ) && (__ARM_ARCH_8M_BASE__ == 1))    )
1025 /**
1026   \brief   LDR Exclusive (8 bit)
1027   \details Executes a exclusive LDR instruction for 8 bit value.
1028   \param [in]    ptr  Pointer to data
1029   \return             value of type uint8_t at (*ptr)
1030  */
1031 __STATIC_FORCEINLINE uint8_t __LDREXB(volatile uint8_t *addr)
1032 {
1033     uint32_t result;
1034
1035 #if (__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ >= 8)
1036    __ASM volatile ("ldrexb %0, %1" : "=r" (result) : "Q" (*addr) );
1037 #else
1038     /* Prior to GCC 4.8, "Q" will be expanded to [rx, #0] which is not
1039        accepted by assembler. So has to use following less efficient pattern.
1040     */
1041    __ASM volatile ("ldrexb %0, [%1]" : "=r" (result) : "r" (addr) : "memory" );
1042 #endif
1043    return ((uint8_t) result);    /* Add explicit type cast here */
1044 }
1045
1046
1047 /**
1048   \brief   LDR Exclusive (16 bit)
1049   \details Executes a exclusive LDR instruction for 16 bit values.
1050   \param [in]    ptr  Pointer to data
1051   \return        value of type uint16_t at (*ptr)
1052  */
1053 __STATIC_FORCEINLINE uint16_t __LDREXH(volatile uint16_t *addr)
1054 {
1055     uint32_t result;
1056
1057 #if (__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ >= 8)
1058    __ASM volatile ("ldrexh %0, %1" : "=r" (result) : "Q" (*addr) );
1059 #else
1060     /* Prior to GCC 4.8, "Q" will be expanded to [rx, #0] which is not
1061        accepted by assembler. So has to use following less efficient pattern.
1062     */
1063    __ASM volatile ("ldrexh %0, [%1]" : "=r" (result) : "r" (addr) : "memory" );
1064 #endif
1065    return ((uint16_t) result);    /* Add explicit type cast here */
1066 }
1067
1068
1069 /**
1070   \brief   LDR Exclusive (32 bit)
1071   \details Executes a exclusive LDR instruction for 32 bit values.
1072   \param [in]    ptr  Pointer to data
1073   \return        value of type uint32_t at (*ptr)
1074  */
1075 __STATIC_FORCEINLINE uint32_t __LDREXW(volatile uint32_t *addr)
1076 {
1077     uint32_t result;
1078
1079    __ASM volatile ("ldrex %0, %1" : "=r" (result) : "Q" (*addr) );
1080    return(result);
1081 }
1082
1083
1084 /**
1085   \brief   STR Exclusive (8 bit)
1086   \details Executes a exclusive STR instruction for 8 bit values.
1087   \param [in]  value  Value to store
1088   \param [in]    ptr  Pointer to location
1089   \return          0  Function succeeded
1090   \return          1  Function failed
1091  */
1092 __STATIC_FORCEINLINE uint32_t __STREXB(uint8_t value, volatile uint8_t *addr)
1093 {
1094    uint32_t result;
1095
1096    __ASM volatile ("strexb %0, %2, %1" : "=&r" (result), "=Q" (*addr) : "r" ((uint32_t)value) );
1097    return(result);
1098 }
1099
1100
1101 /**
1102   \brief   STR Exclusive (16 bit)
1103   \details Executes a exclusive STR instruction for 16 bit values.
1104   \param [in]  value  Value to store
1105   \param [in]    ptr  Pointer to location
1106   \return          0  Function succeeded
1107   \return          1  Function failed
1108  */
1109 __STATIC_FORCEINLINE uint32_t __STREXH(uint16_t value, volatile uint16_t *addr)
1110 {
1111    uint32_t result;
1112
1113    __ASM volatile ("strexh %0, %2, %1" : "=&r" (result), "=Q" (*addr) : "r" ((uint32_t)value) );
1114    return(result);
1115 }
1116
1117
1118 /**
1119   \brief   STR Exclusive (32 bit)
1120   \details Executes a exclusive STR instruction for 32 bit values.
1121   \param [in]  value  Value to store
1122   \param [in]    ptr  Pointer to location
1123   \return          0  Function succeeded
1124   \return          1  Function failed
1125  */
1126 __STATIC_FORCEINLINE uint32_t __STREXW(uint32_t value, volatile uint32_t *addr)
1127 {
1128    uint32_t result;
1129
1130    __ASM volatile ("strex %0, %2, %1" : "=&r" (result), "=Q" (*addr) : "r" (value) );
1131    return(result);
1132 }
1133
1134
1135 /**
1136   \brief   Remove the exclusive lock
1137   \details Removes the exclusive lock which is created by LDREX.
1138  */
1139 __STATIC_FORCEINLINE void __CLREX(void)
1140 {
1141   __ASM volatile ("clrex" ::: "memory");
1142 }
1143
1144 #endif /* ((defined (__ARM_ARCH_7M__      ) && (__ARM_ARCH_7M__      == 1)) || \
1145            (defined (__ARM_ARCH_7EM__     ) && (__ARM_ARCH_7EM__     == 1)) || \
1146            (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) || \
1147            (defined (__ARM_ARCH_8M_BASE__ ) && (__ARM_ARCH_8M_BASE__ == 1))    ) */
1148
1149
1150 #if ((defined (__ARM_ARCH_7M__      ) && (__ARM_ARCH_7M__      == 1)) || \
1151      (defined (__ARM_ARCH_7EM__     ) && (__ARM_ARCH_7EM__     == 1)) || \
1152      (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1))    )
1153 /**
1154   \brief   Signed Saturate
1155   \details Saturates a signed value.
1156   \param [in]  ARG1  Value to be saturated
1157   \param [in]  ARG2  Bit position to saturate to (1..32)
1158   \return             Saturated value
1159  */
1160 #define __SSAT(ARG1,ARG2) \
1161 __extension__ \
1162 ({                          \
1163   int32_t __RES, __ARG1 = (ARG1); \
1164   __ASM ("ssat %0, %1, %2" : "=r" (__RES) :  "I" (ARG2), "r" (__ARG1) ); \
1165   __RES; \
1166  })
1167
1168
1169 /**
1170   \brief   Unsigned Saturate
1171   \details Saturates an unsigned value.
1172   \param [in]  ARG1  Value to be saturated
1173   \param [in]  ARG2  Bit position to saturate to (0..31)
1174   \return             Saturated value
1175  */
1176 #define __USAT(ARG1,ARG2) \
1177  __extension__ \
1178 ({                          \
1179   uint32_t __RES, __ARG1 = (ARG1); \
1180   __ASM ("usat %0, %1, %2" : "=r" (__RES) :  "I" (ARG2), "r" (__ARG1) ); \
1181   __RES; \
1182  })
1183
1184
1185 /**
1186   \brief   Rotate Right with Extend (32 bit)
1187   \details Moves each bit of a bitstring right by one bit.
1188            The carry input is shifted in at the left end of the bitstring.
1189   \param [in]    value  Value to rotate
1190   \return               Rotated value
1191  */
1192 __STATIC_FORCEINLINE uint32_t __RRX(uint32_t value)
1193 {
1194   uint32_t result;
1195
1196   __ASM volatile ("rrx %0, %1" : __CMSIS_GCC_OUT_REG (result) : __CMSIS_GCC_USE_REG (value) );
1197   return(result);
1198 }
1199
1200
1201 /**
1202   \brief   LDRT Unprivileged (8 bit)
1203   \details Executes a Unprivileged LDRT instruction for 8 bit value.
1204   \param [in]    ptr  Pointer to data
1205   \return             value of type uint8_t at (*ptr)
1206  */
1207 __STATIC_FORCEINLINE uint8_t __LDRBT(volatile uint8_t *ptr)
1208 {
1209     uint32_t result;
1210
1211 #if (__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ >= 8)
1212    __ASM volatile ("ldrbt %0, %1" : "=r" (result) : "Q" (*ptr) );
1213 #else
1214     /* Prior to GCC 4.8, "Q" will be expanded to [rx, #0] which is not
1215        accepted by assembler. So has to use following less efficient pattern.
1216     */
1217    __ASM volatile ("ldrbt %0, [%1]" : "=r" (result) : "r" (ptr) : "memory" );
1218 #endif
1219    return ((uint8_t) result);    /* Add explicit type cast here */
1220 }
1221
1222
1223 /**
1224   \brief   LDRT Unprivileged (16 bit)
1225   \details Executes a Unprivileged LDRT instruction for 16 bit values.
1226   \param [in]    ptr  Pointer to data
1227   \return        value of type uint16_t at (*ptr)
1228  */
1229 __STATIC_FORCEINLINE uint16_t __LDRHT(volatile uint16_t *ptr)
1230 {
1231     uint32_t result;
1232
1233 #if (__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ >= 8)
1234    __ASM volatile ("ldrht %0, %1" : "=r" (result) : "Q" (*ptr) );
1235 #else
1236     /* Prior to GCC 4.8, "Q" will be expanded to [rx, #0] which is not
1237        accepted by assembler. So has to use following less efficient pattern.
1238     */
1239    __ASM volatile ("ldrht %0, [%1]" : "=r" (result) : "r" (ptr) : "memory" );
1240 #endif
1241    return ((uint16_t) result);    /* Add explicit type cast here */
1242 }
1243
1244
1245 /**
1246   \brief   LDRT Unprivileged (32 bit)
1247   \details Executes a Unprivileged LDRT instruction for 32 bit values.
1248   \param [in]    ptr  Pointer to data
1249   \return        value of type uint32_t at (*ptr)
1250  */
1251 __STATIC_FORCEINLINE uint32_t __LDRT(volatile uint32_t *ptr)
1252 {
1253     uint32_t result;
1254
1255    __ASM volatile ("ldrt %0, %1" : "=r" (result) : "Q" (*ptr) );
1256    return(result);
1257 }
1258
1259
1260 /**
1261   \brief   STRT Unprivileged (8 bit)
1262   \details Executes a Unprivileged STRT instruction for 8 bit values.
1263   \param [in]  value  Value to store
1264   \param [in]    ptr  Pointer to location
1265  */
1266 __STATIC_FORCEINLINE void __STRBT(uint8_t value, volatile uint8_t *ptr)
1267 {
1268    __ASM volatile ("strbt %1, %0" : "=Q" (*ptr) : "r" ((uint32_t)value) );
1269 }
1270
1271
1272 /**
1273   \brief   STRT Unprivileged (16 bit)
1274   \details Executes a Unprivileged STRT instruction for 16 bit values.
1275   \param [in]  value  Value to store
1276   \param [in]    ptr  Pointer to location
1277  */
1278 __STATIC_FORCEINLINE void __STRHT(uint16_t value, volatile uint16_t *ptr)
1279 {
1280    __ASM volatile ("strht %1, %0" : "=Q" (*ptr) : "r" ((uint32_t)value) );
1281 }
1282
1283
1284 /**
1285   \brief   STRT Unprivileged (32 bit)
1286   \details Executes a Unprivileged STRT instruction for 32 bit values.
1287   \param [in]  value  Value to store
1288   \param [in]    ptr  Pointer to location
1289  */
1290 __STATIC_FORCEINLINE void __STRT(uint32_t value, volatile uint32_t *ptr)
1291 {
1292    __ASM volatile ("strt %1, %0" : "=Q" (*ptr) : "r" (value) );
1293 }
1294
1295 #else  /* ((defined (__ARM_ARCH_7M__      ) && (__ARM_ARCH_7M__      == 1)) || \
1296            (defined (__ARM_ARCH_7EM__     ) && (__ARM_ARCH_7EM__     == 1)) || \
1297            (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1))    ) */
1298
1299 /**
1300   \brief   Signed Saturate
1301   \details Saturates a signed value.
1302   \param [in]  value  Value to be saturated
1303   \param [in]    sat  Bit position to saturate to (1..32)
1304   \return             Saturated value
1305  */
1306 __STATIC_FORCEINLINE int32_t __SSAT(int32_t val, uint32_t sat)
1307 {
1308   if ((sat >= 1U) && (sat <= 32U))
1309   {
1310     const int32_t max = (int32_t)((1U << (sat - 1U)) - 1U);
1311     const int32_t min = -1 - max ;
1312     if (val > max)
1313     {
1314       return max;
1315     }
1316     else if (val < min)
1317     {
1318       return min;
1319     }
1320   }
1321   return val;
1322 }
1323
1324 /**
1325   \brief   Unsigned Saturate
1326   \details Saturates an unsigned value.
1327   \param [in]  value  Value to be saturated
1328   \param [in]    sat  Bit position to saturate to (0..31)
1329   \return             Saturated value
1330  */
1331 __STATIC_FORCEINLINE uint32_t __USAT(int32_t val, uint32_t sat)
1332 {
1333   if (sat <= 31U)
1334   {
1335     const uint32_t max = ((1U << sat) - 1U);
1336     if (val > (int32_t)max)
1337     {
1338       return max;
1339     }
1340     else if (val < 0)
1341     {
1342       return 0U;
1343     }
1344   }
1345   return (uint32_t)val;
1346 }
1347
1348 #endif /* ((defined (__ARM_ARCH_7M__      ) && (__ARM_ARCH_7M__      == 1)) || \
1349            (defined (__ARM_ARCH_7EM__     ) && (__ARM_ARCH_7EM__     == 1)) || \
1350            (defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1))    ) */
1351
1352
1353 #if ((defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) || \
1354      (defined (__ARM_ARCH_8M_BASE__ ) && (__ARM_ARCH_8M_BASE__ == 1))    )
1355 /**
1356   \brief   Load-Acquire (8 bit)
1357   \details Executes a LDAB instruction for 8 bit value.
1358   \param [in]    ptr  Pointer to data
1359   \return             value of type uint8_t at (*ptr)
1360  */
1361 __STATIC_FORCEINLINE uint8_t __LDAB(volatile uint8_t *ptr)
1362 {
1363     uint32_t result;
1364
1365    __ASM volatile ("ldab %0, %1" : "=r" (result) : "Q" (*ptr) );
1366    return ((uint8_t) result);
1367 }
1368
1369
1370 /**
1371   \brief   Load-Acquire (16 bit)
1372   \details Executes a LDAH instruction for 16 bit values.
1373   \param [in]    ptr  Pointer to data
1374   \return        value of type uint16_t at (*ptr)
1375  */
1376 __STATIC_FORCEINLINE uint16_t __LDAH(volatile uint16_t *ptr)
1377 {
1378     uint32_t result;
1379
1380    __ASM volatile ("ldah %0, %1" : "=r" (result) : "Q" (*ptr) );
1381    return ((uint16_t) result);
1382 }
1383
1384
1385 /**
1386   \brief   Load-Acquire (32 bit)
1387   \details Executes a LDA instruction for 32 bit values.
1388   \param [in]    ptr  Pointer to data
1389   \return        value of type uint32_t at (*ptr)
1390  */
1391 __STATIC_FORCEINLINE uint32_t __LDA(volatile uint32_t *ptr)
1392 {
1393     uint32_t result;
1394
1395    __ASM volatile ("lda %0, %1" : "=r" (result) : "Q" (*ptr) );
1396    return(result);
1397 }
1398
1399
1400 /**
1401   \brief   Store-Release (8 bit)
1402   \details Executes a STLB instruction for 8 bit values.
1403   \param [in]  value  Value to store
1404   \param [in]    ptr  Pointer to location
1405  */
1406 __STATIC_FORCEINLINE void __STLB(uint8_t value, volatile uint8_t *ptr)
1407 {
1408    __ASM volatile ("stlb %1, %0" : "=Q" (*ptr) : "r" ((uint32_t)value) );
1409 }
1410
1411
1412 /**
1413   \brief   Store-Release (16 bit)
1414   \details Executes a STLH instruction for 16 bit values.
1415   \param [in]  value  Value to store
1416   \param [in]    ptr  Pointer to location
1417  */
1418 __STATIC_FORCEINLINE void __STLH(uint16_t value, volatile uint16_t *ptr)
1419 {
1420    __ASM volatile ("stlh %1, %0" : "=Q" (*ptr) : "r" ((uint32_t)value) );
1421 }
1422
1423
1424 /**
1425   \brief   Store-Release (32 bit)
1426   \details Executes a STL instruction for 32 bit values.
1427   \param [in]  value  Value to store
1428   \param [in]    ptr  Pointer to location
1429  */
1430 __STATIC_FORCEINLINE void __STL(uint32_t value, volatile uint32_t *ptr)
1431 {
1432    __ASM volatile ("stl %1, %0" : "=Q" (*ptr) : "r" ((uint32_t)value) );
1433 }
1434
1435
1436 /**
1437   \brief   Load-Acquire Exclusive (8 bit)
1438   \details Executes a LDAB exclusive instruction for 8 bit value.
1439   \param [in]    ptr  Pointer to data
1440   \return             value of type uint8_t at (*ptr)
1441  */
1442 __STATIC_FORCEINLINE uint8_t __LDAEXB(volatile uint8_t *ptr)
1443 {
1444     uint32_t result;
1445
1446    __ASM volatile ("ldaexb %0, %1" : "=r" (result) : "Q" (*ptr) );
1447    return ((uint8_t) result);
1448 }
1449
1450
1451 /**
1452   \brief   Load-Acquire Exclusive (16 bit)
1453   \details Executes a LDAH exclusive instruction for 16 bit values.
1454   \param [in]    ptr  Pointer to data
1455   \return        value of type uint16_t at (*ptr)
1456  */
1457 __STATIC_FORCEINLINE uint16_t __LDAEXH(volatile uint16_t *ptr)
1458 {
1459     uint32_t result;
1460
1461    __ASM volatile ("ldaexh %0, %1" : "=r" (result) : "Q" (*ptr) );
1462    return ((uint16_t) result);
1463 }
1464
1465
1466 /**
1467   \brief   Load-Acquire Exclusive (32 bit)
1468   \details Executes a LDA exclusive instruction for 32 bit values.
1469   \param [in]    ptr  Pointer to data
1470   \return        value of type uint32_t at (*ptr)
1471  */
1472 __STATIC_FORCEINLINE uint32_t __LDAEX(volatile uint32_t *ptr)
1473 {
1474     uint32_t result;
1475
1476    __ASM volatile ("ldaex %0, %1" : "=r" (result) : "Q" (*ptr) );
1477    return(result);
1478 }
1479
1480
1481 /**
1482   \brief   Store-Release Exclusive (8 bit)
1483   \details Executes a STLB exclusive instruction for 8 bit values.
1484   \param [in]  value  Value to store
1485   \param [in]    ptr  Pointer to location
1486   \return          0  Function succeeded
1487   \return          1  Function failed
1488  */
1489 __STATIC_FORCEINLINE uint32_t __STLEXB(uint8_t value, volatile uint8_t *ptr)
1490 {
1491    uint32_t result;
1492
1493    __ASM volatile ("stlexb %0, %2, %1" : "=&r" (result), "=Q" (*ptr) : "r" ((uint32_t)value) );
1494    return(result);
1495 }
1496
1497
1498 /**
1499   \brief   Store-Release Exclusive (16 bit)
1500   \details Executes a STLH exclusive instruction for 16 bit values.
1501   \param [in]  value  Value to store
1502   \param [in]    ptr  Pointer to location
1503   \return          0  Function succeeded
1504   \return          1  Function failed
1505  */
1506 __STATIC_FORCEINLINE uint32_t __STLEXH(uint16_t value, volatile uint16_t *ptr)
1507 {
1508    uint32_t result;
1509
1510    __ASM volatile ("stlexh %0, %2, %1" : "=&r" (result), "=Q" (*ptr) : "r" ((uint32_t)value) );
1511    return(result);
1512 }
1513
1514
1515 /**
1516   \brief   Store-Release Exclusive (32 bit)
1517   \details Executes a STL exclusive instruction for 32 bit values.
1518   \param [in]  value  Value to store
1519   \param [in]    ptr  Pointer to location
1520   \return          0  Function succeeded
1521   \return          1  Function failed
1522  */
1523 __STATIC_FORCEINLINE uint32_t __STLEX(uint32_t value, volatile uint32_t *ptr)
1524 {
1525    uint32_t result;
1526
1527    __ASM volatile ("stlex %0, %2, %1" : "=&r" (result), "=Q" (*ptr) : "r" ((uint32_t)value) );
1528    return(result);
1529 }
1530
1531 #endif /* ((defined (__ARM_ARCH_8M_MAIN__ ) && (__ARM_ARCH_8M_MAIN__ == 1)) || \
1532            (defined (__ARM_ARCH_8M_BASE__ ) && (__ARM_ARCH_8M_BASE__ == 1))    ) */
1533
1534 /*@}*/ /* end of group CMSIS_Core_InstructionInterface */
1535
1536
1537 /* ###################  Compiler specific Intrinsics  ########################### */
1538 /** \defgroup CMSIS_SIMD_intrinsics CMSIS SIMD Intrinsics
1539   Access to dedicated SIMD instructions
1540   @{
1541 */
1542
1543 #if (defined (__ARM_FEATURE_DSP) && (__ARM_FEATURE_DSP == 1))
1544
1545 __STATIC_FORCEINLINE uint32_t __SADD8(uint32_t op1, uint32_t op2)
1546 {
1547   uint32_t result;
1548
1549   __ASM volatile ("sadd8 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1550   return(result);
1551 }
1552
1553 __STATIC_FORCEINLINE uint32_t __QADD8(uint32_t op1, uint32_t op2)
1554 {
1555   uint32_t result;
1556
1557   __ASM volatile ("qadd8 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1558   return(result);
1559 }
1560
1561 __STATIC_FORCEINLINE uint32_t __SHADD8(uint32_t op1, uint32_t op2)
1562 {
1563   uint32_t result;
1564
1565   __ASM volatile ("shadd8 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1566   return(result);
1567 }
1568
1569 __STATIC_FORCEINLINE uint32_t __UADD8(uint32_t op1, uint32_t op2)
1570 {
1571   uint32_t result;
1572
1573   __ASM volatile ("uadd8 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1574   return(result);
1575 }
1576
1577 __STATIC_FORCEINLINE uint32_t __UQADD8(uint32_t op1, uint32_t op2)
1578 {
1579   uint32_t result;
1580
1581   __ASM volatile ("uqadd8 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1582   return(result);
1583 }
1584
1585 __STATIC_FORCEINLINE uint32_t __UHADD8(uint32_t op1, uint32_t op2)
1586 {
1587   uint32_t result;
1588
1589   __ASM volatile ("uhadd8 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1590   return(result);
1591 }
1592
1593
1594 __STATIC_FORCEINLINE uint32_t __SSUB8(uint32_t op1, uint32_t op2)
1595 {
1596   uint32_t result;
1597
1598   __ASM volatile ("ssub8 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1599   return(result);
1600 }
1601
1602 __STATIC_FORCEINLINE uint32_t __QSUB8(uint32_t op1, uint32_t op2)
1603 {
1604   uint32_t result;
1605
1606   __ASM volatile ("qsub8 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1607   return(result);
1608 }
1609
1610 __STATIC_FORCEINLINE uint32_t __SHSUB8(uint32_t op1, uint32_t op2)
1611 {
1612   uint32_t result;
1613
1614   __ASM volatile ("shsub8 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1615   return(result);
1616 }
1617
1618 __STATIC_FORCEINLINE uint32_t __USUB8(uint32_t op1, uint32_t op2)
1619 {
1620   uint32_t result;
1621
1622   __ASM volatile ("usub8 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1623   return(result);
1624 }
1625
1626 __STATIC_FORCEINLINE uint32_t __UQSUB8(uint32_t op1, uint32_t op2)
1627 {
1628   uint32_t result;
1629
1630   __ASM volatile ("uqsub8 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1631   return(result);
1632 }
1633
1634 __STATIC_FORCEINLINE uint32_t __UHSUB8(uint32_t op1, uint32_t op2)
1635 {
1636   uint32_t result;
1637
1638   __ASM volatile ("uhsub8 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1639   return(result);
1640 }
1641
1642
1643 __STATIC_FORCEINLINE uint32_t __SADD16(uint32_t op1, uint32_t op2)
1644 {
1645   uint32_t result;
1646
1647   __ASM volatile ("sadd16 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1648   return(result);
1649 }
1650
1651 __STATIC_FORCEINLINE uint32_t __QADD16(uint32_t op1, uint32_t op2)
1652 {
1653   uint32_t result;
1654
1655   __ASM volatile ("qadd16 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1656   return(result);
1657 }
1658
1659 __STATIC_FORCEINLINE uint32_t __SHADD16(uint32_t op1, uint32_t op2)
1660 {
1661   uint32_t result;
1662
1663   __ASM volatile ("shadd16 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1664   return(result);
1665 }
1666
1667 __STATIC_FORCEINLINE uint32_t __UADD16(uint32_t op1, uint32_t op2)
1668 {
1669   uint32_t result;
1670
1671   __ASM volatile ("uadd16 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1672   return(result);
1673 }
1674
1675 __STATIC_FORCEINLINE uint32_t __UQADD16(uint32_t op1, uint32_t op2)
1676 {
1677   uint32_t result;
1678
1679   __ASM volatile ("uqadd16 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1680   return(result);
1681 }
1682
1683 __STATIC_FORCEINLINE uint32_t __UHADD16(uint32_t op1, uint32_t op2)
1684 {
1685   uint32_t result;
1686
1687   __ASM volatile ("uhadd16 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1688   return(result);
1689 }
1690
1691 __STATIC_FORCEINLINE uint32_t __SSUB16(uint32_t op1, uint32_t op2)
1692 {
1693   uint32_t result;
1694
1695   __ASM volatile ("ssub16 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1696   return(result);
1697 }
1698
1699 __STATIC_FORCEINLINE uint32_t __QSUB16(uint32_t op1, uint32_t op2)
1700 {
1701   uint32_t result;
1702
1703   __ASM volatile ("qsub16 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1704   return(result);
1705 }
1706
1707 __STATIC_FORCEINLINE uint32_t __SHSUB16(uint32_t op1, uint32_t op2)
1708 {
1709   uint32_t result;
1710
1711   __ASM volatile ("shsub16 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1712   return(result);
1713 }
1714
1715 __STATIC_FORCEINLINE uint32_t __USUB16(uint32_t op1, uint32_t op2)
1716 {
1717   uint32_t result;
1718
1719   __ASM volatile ("usub16 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1720   return(result);
1721 }
1722
1723 __STATIC_FORCEINLINE uint32_t __UQSUB16(uint32_t op1, uint32_t op2)
1724 {
1725   uint32_t result;
1726
1727   __ASM volatile ("uqsub16 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1728   return(result);
1729 }
1730
1731 __STATIC_FORCEINLINE uint32_t __UHSUB16(uint32_t op1, uint32_t op2)
1732 {
1733   uint32_t result;
1734
1735   __ASM volatile ("uhsub16 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1736   return(result);
1737 }
1738
1739 __STATIC_FORCEINLINE uint32_t __SASX(uint32_t op1, uint32_t op2)
1740 {
1741   uint32_t result;
1742
1743   __ASM volatile ("sasx %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1744   return(result);
1745 }
1746
1747 __STATIC_FORCEINLINE uint32_t __QASX(uint32_t op1, uint32_t op2)
1748 {
1749   uint32_t result;
1750
1751   __ASM volatile ("qasx %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1752   return(result);
1753 }
1754
1755 __STATIC_FORCEINLINE uint32_t __SHASX(uint32_t op1, uint32_t op2)
1756 {
1757   uint32_t result;
1758
1759   __ASM volatile ("shasx %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1760   return(result);
1761 }
1762
1763 __STATIC_FORCEINLINE uint32_t __UASX(uint32_t op1, uint32_t op2)
1764 {
1765   uint32_t result;
1766
1767   __ASM volatile ("uasx %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1768   return(result);
1769 }
1770
1771 __STATIC_FORCEINLINE uint32_t __UQASX(uint32_t op1, uint32_t op2)
1772 {
1773   uint32_t result;
1774
1775   __ASM volatile ("uqasx %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1776   return(result);
1777 }
1778
1779 __STATIC_FORCEINLINE uint32_t __UHASX(uint32_t op1, uint32_t op2)
1780 {
1781   uint32_t result;
1782
1783   __ASM volatile ("uhasx %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1784   return(result);
1785 }
1786
1787 __STATIC_FORCEINLINE uint32_t __SSAX(uint32_t op1, uint32_t op2)
1788 {
1789   uint32_t result;
1790
1791   __ASM volatile ("ssax %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1792   return(result);
1793 }
1794
1795 __STATIC_FORCEINLINE uint32_t __QSAX(uint32_t op1, uint32_t op2)
1796 {
1797   uint32_t result;
1798
1799   __ASM volatile ("qsax %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1800   return(result);
1801 }
1802
1803 __STATIC_FORCEINLINE uint32_t __SHSAX(uint32_t op1, uint32_t op2)
1804 {
1805   uint32_t result;
1806
1807   __ASM volatile ("shsax %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1808   return(result);
1809 }
1810
1811 __STATIC_FORCEINLINE uint32_t __USAX(uint32_t op1, uint32_t op2)
1812 {
1813   uint32_t result;
1814
1815   __ASM volatile ("usax %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1816   return(result);
1817 }
1818
1819 __STATIC_FORCEINLINE uint32_t __UQSAX(uint32_t op1, uint32_t op2)
1820 {
1821   uint32_t result;
1822
1823   __ASM volatile ("uqsax %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1824   return(result);
1825 }
1826
1827 __STATIC_FORCEINLINE uint32_t __UHSAX(uint32_t op1, uint32_t op2)
1828 {
1829   uint32_t result;
1830
1831   __ASM volatile ("uhsax %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1832   return(result);
1833 }
1834
1835 __STATIC_FORCEINLINE uint32_t __USAD8(uint32_t op1, uint32_t op2)
1836 {
1837   uint32_t result;
1838
1839   __ASM volatile ("usad8 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1840   return(result);
1841 }
1842
1843 __STATIC_FORCEINLINE uint32_t __USADA8(uint32_t op1, uint32_t op2, uint32_t op3)
1844 {
1845   uint32_t result;
1846
1847   __ASM volatile ("usada8 %0, %1, %2, %3" : "=r" (result) : "r" (op1), "r" (op2), "r" (op3) );
1848   return(result);
1849 }
1850
1851 #define __SSAT16(ARG1,ARG2) \
1852 ({                          \
1853   int32_t __RES, __ARG1 = (ARG1); \
1854   __ASM ("ssat16 %0, %1, %2" : "=r" (__RES) :  "I" (ARG2), "r" (__ARG1) ); \
1855   __RES; \
1856  })
1857
1858 #define __USAT16(ARG1,ARG2) \
1859 ({                          \
1860   uint32_t __RES, __ARG1 = (ARG1); \
1861   __ASM ("usat16 %0, %1, %2" : "=r" (__RES) :  "I" (ARG2), "r" (__ARG1) ); \
1862   __RES; \
1863  })
1864
1865 __STATIC_FORCEINLINE uint32_t __UXTB16(uint32_t op1)
1866 {
1867   uint32_t result;
1868
1869   __ASM volatile ("uxtb16 %0, %1" : "=r" (result) : "r" (op1));
1870   return(result);
1871 }
1872
1873 __STATIC_FORCEINLINE uint32_t __UXTAB16(uint32_t op1, uint32_t op2)
1874 {
1875   uint32_t result;
1876
1877   __ASM volatile ("uxtab16 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1878   return(result);
1879 }
1880
1881 __STATIC_FORCEINLINE uint32_t __SXTB16(uint32_t op1)
1882 {
1883   uint32_t result;
1884
1885   __ASM volatile ("sxtb16 %0, %1" : "=r" (result) : "r" (op1));
1886   return(result);
1887 }
1888
1889 __STATIC_FORCEINLINE uint32_t __SXTAB16(uint32_t op1, uint32_t op2)
1890 {
1891   uint32_t result;
1892
1893   __ASM volatile ("sxtab16 %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1894   return(result);
1895 }
1896
1897 __STATIC_FORCEINLINE uint32_t __SMUAD  (uint32_t op1, uint32_t op2)
1898 {
1899   uint32_t result;
1900
1901   __ASM volatile ("smuad %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1902   return(result);
1903 }
1904
1905 __STATIC_FORCEINLINE uint32_t __SMUADX (uint32_t op1, uint32_t op2)
1906 {
1907   uint32_t result;
1908
1909   __ASM volatile ("smuadx %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1910   return(result);
1911 }
1912
1913 __STATIC_FORCEINLINE uint32_t __SMLAD (uint32_t op1, uint32_t op2, uint32_t op3)
1914 {
1915   uint32_t result;
1916
1917   __ASM volatile ("smlad %0, %1, %2, %3" : "=r" (result) : "r" (op1), "r" (op2), "r" (op3) );
1918   return(result);
1919 }
1920
1921 __STATIC_FORCEINLINE uint32_t __SMLADX (uint32_t op1, uint32_t op2, uint32_t op3)
1922 {
1923   uint32_t result;
1924
1925   __ASM volatile ("smladx %0, %1, %2, %3" : "=r" (result) : "r" (op1), "r" (op2), "r" (op3) );
1926   return(result);
1927 }
1928
1929 __STATIC_FORCEINLINE uint64_t __SMLALD (uint32_t op1, uint32_t op2, uint64_t acc)
1930 {
1931   union llreg_u{
1932     uint32_t w32[2];
1933     uint64_t w64;
1934   } llr;
1935   llr.w64 = acc;
1936
1937 #ifndef __ARMEB__   /* Little endian */
1938   __ASM volatile ("smlald %0, %1, %2, %3" : "=r" (llr.w32[0]), "=r" (llr.w32[1]): "r" (op1), "r" (op2) , "0" (llr.w32[0]), "1" (llr.w32[1]) );
1939 #else               /* Big endian */
1940   __ASM volatile ("smlald %0, %1, %2, %3" : "=r" (llr.w32[1]), "=r" (llr.w32[0]): "r" (op1), "r" (op2) , "0" (llr.w32[1]), "1" (llr.w32[0]) );
1941 #endif
1942
1943   return(llr.w64);
1944 }
1945
1946 __STATIC_FORCEINLINE uint64_t __SMLALDX (uint32_t op1, uint32_t op2, uint64_t acc)
1947 {
1948   union llreg_u{
1949     uint32_t w32[2];
1950     uint64_t w64;
1951   } llr;
1952   llr.w64 = acc;
1953
1954 #ifndef __ARMEB__   /* Little endian */
1955   __ASM volatile ("smlaldx %0, %1, %2, %3" : "=r" (llr.w32[0]), "=r" (llr.w32[1]): "r" (op1), "r" (op2) , "0" (llr.w32[0]), "1" (llr.w32[1]) );
1956 #else               /* Big endian */
1957   __ASM volatile ("smlaldx %0, %1, %2, %3" : "=r" (llr.w32[1]), "=r" (llr.w32[0]): "r" (op1), "r" (op2) , "0" (llr.w32[1]), "1" (llr.w32[0]) );
1958 #endif
1959
1960   return(llr.w64);
1961 }
1962
1963 __STATIC_FORCEINLINE uint32_t __SMUSD  (uint32_t op1, uint32_t op2)
1964 {
1965   uint32_t result;
1966
1967   __ASM volatile ("smusd %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1968   return(result);
1969 }
1970
1971 __STATIC_FORCEINLINE uint32_t __SMUSDX (uint32_t op1, uint32_t op2)
1972 {
1973   uint32_t result;
1974
1975   __ASM volatile ("smusdx %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
1976   return(result);
1977 }
1978
1979 __STATIC_FORCEINLINE uint32_t __SMLSD (uint32_t op1, uint32_t op2, uint32_t op3)
1980 {
1981   uint32_t result;
1982
1983   __ASM volatile ("smlsd %0, %1, %2, %3" : "=r" (result) : "r" (op1), "r" (op2), "r" (op3) );
1984   return(result);
1985 }
1986
1987 __STATIC_FORCEINLINE uint32_t __SMLSDX (uint32_t op1, uint32_t op2, uint32_t op3)
1988 {
1989   uint32_t result;
1990
1991   __ASM volatile ("smlsdx %0, %1, %2, %3" : "=r" (result) : "r" (op1), "r" (op2), "r" (op3) );
1992   return(result);
1993 }
1994
1995 __STATIC_FORCEINLINE uint64_t __SMLSLD (uint32_t op1, uint32_t op2, uint64_t acc)
1996 {
1997   union llreg_u{
1998     uint32_t w32[2];
1999     uint64_t w64;
2000   } llr;
2001   llr.w64 = acc;
2002
2003 #ifndef __ARMEB__   /* Little endian */
2004   __ASM volatile ("smlsld %0, %1, %2, %3" : "=r" (llr.w32[0]), "=r" (llr.w32[1]): "r" (op1), "r" (op2) , "0" (llr.w32[0]), "1" (llr.w32[1]) );
2005 #else               /* Big endian */
2006   __ASM volatile ("smlsld %0, %1, %2, %3" : "=r" (llr.w32[1]), "=r" (llr.w32[0]): "r" (op1), "r" (op2) , "0" (llr.w32[1]), "1" (llr.w32[0]) );
2007 #endif
2008
2009   return(llr.w64);
2010 }
2011
2012 __STATIC_FORCEINLINE uint64_t __SMLSLDX (uint32_t op1, uint32_t op2, uint64_t acc)
2013 {
2014   union llreg_u{
2015     uint32_t w32[2];
2016     uint64_t w64;
2017   } llr;
2018   llr.w64 = acc;
2019
2020 #ifndef __ARMEB__   /* Little endian */
2021   __ASM volatile ("smlsldx %0, %1, %2, %3" : "=r" (llr.w32[0]), "=r" (llr.w32[1]): "r" (op1), "r" (op2) , "0" (llr.w32[0]), "1" (llr.w32[1]) );
2022 #else               /* Big endian */
2023   __ASM volatile ("smlsldx %0, %1, %2, %3" : "=r" (llr.w32[1]), "=r" (llr.w32[0]): "r" (op1), "r" (op2) , "0" (llr.w32[1]), "1" (llr.w32[0]) );
2024 #endif
2025
2026   return(llr.w64);
2027 }
2028
2029 __STATIC_FORCEINLINE uint32_t __SEL  (uint32_t op1, uint32_t op2)
2030 {
2031   uint32_t result;
2032
2033   __ASM volatile ("sel %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
2034   return(result);
2035 }
2036
2037 __STATIC_FORCEINLINE  int32_t __QADD( int32_t op1,  int32_t op2)
2038 {
2039   int32_t result;
2040
2041   __ASM volatile ("qadd %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
2042   return(result);
2043 }
2044
2045 __STATIC_FORCEINLINE  int32_t __QSUB( int32_t op1,  int32_t op2)
2046 {
2047   int32_t result;
2048
2049   __ASM volatile ("qsub %0, %1, %2" : "=r" (result) : "r" (op1), "r" (op2) );
2050   return(result);
2051 }
2052
2053 #if 0
2054 #define __PKHBT(ARG1,ARG2,ARG3) \
2055 ({                          \
2056   uint32_t __RES, __ARG1 = (ARG1), __ARG2 = (ARG2); \
2057   __ASM ("pkhbt %0, %1, %2, lsl %3" : "=r" (__RES) :  "r" (__ARG1), "r" (__ARG2), "I" (ARG3)  ); \
2058   __RES; \
2059  })
2060
2061 #define __PKHTB(ARG1,ARG2,ARG3) \
2062 ({                          \
2063   uint32_t __RES, __ARG1 = (ARG1), __ARG2 = (ARG2); \
2064   if (ARG3 == 0) \
2065     __ASM ("pkhtb %0, %1, %2" : "=r" (__RES) :  "r" (__ARG1), "r" (__ARG2)  ); \
2066   else \
2067     __ASM ("pkhtb %0, %1, %2, asr %3" : "=r" (__RES) :  "r" (__ARG1), "r" (__ARG2), "I" (ARG3)  ); \
2068   __RES; \
2069  })
2070 #endif
2071
2072 #define __PKHBT(ARG1,ARG2,ARG3)          ( ((((uint32_t)(ARG1))          ) & 0x0000FFFFUL) |  \
2073                                            ((((uint32_t)(ARG2)) << (ARG3)) & 0xFFFF0000UL)  )
2074
2075 #define __PKHTB(ARG1,ARG2,ARG3)          ( ((((uint32_t)(ARG1))          ) & 0xFFFF0000UL) |  \
2076                                            ((((uint32_t)(ARG2)) >> (ARG3)) & 0x0000FFFFUL)  )
2077
2078 __STATIC_FORCEINLINE int32_t __SMMLA (int32_t op1, int32_t op2, int32_t op3)
2079 {
2080  int32_t result;
2081
2082  __ASM volatile ("smmla %0, %1, %2, %3" : "=r" (result): "r"  (op1), "r" (op2), "r" (op3) );
2083  return(result);
2084 }
2085
2086 #endif /* (__ARM_FEATURE_DSP == 1) */
2087 /*@} end of group CMSIS_SIMD_intrinsics */
2088
2089
2090 #pragma GCC diagnostic pop
2091
2092 #endif /* __CMSIS_GCC_H */