1 /****************************************************************************** 2 * 3 * Copyright (C) 2014 - 2016 Xilinx, Inc. All rights reserved. 4 * 5 * Permission is hereby granted, free of charge, to any person obtaining a copy 6 * of this software and associated documentation files (the "Software"), to deal 7 * in the Software without restriction, including without limitation the rights 8 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 * copies of the Software, and to permit persons to whom the Software is 10 * furnished to do so, subject to the following conditions: 11 * 12 * The above copyright notice and this permission notice shall be included in 13 * all copies or substantial portions of the Software. 14 * 15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 * THE SOFTWARE. 22 * 23 * 24 * 25 ******************************************************************************/ 26 /*****************************************************************************/ 27 /** 28 * 29 * @file xpseudo_asm_gcc.h 30 * 31 * This header file contains macros for using inline assembler code. It is 32 * written specifically for the GNU compiler. 33 * 34 * <pre> 35 * MODIFICATION HISTORY: 36 * 37 * Ver Who Date Changes 38 * ----- -------- -------- ----------------------------------------------- 39 * 5.00 pkp 05/21/14 First release 40 * 6.0 mus 07/27/16 Consolidated file for a53,a9 and r5 processors 41 * </pre> 42 * 43 ******************************************************************************/ 44 45 #ifndef XPSEUDO_ASM_GCC_H /* prevent circular inclusions */ 46 #define XPSEUDO_ASM_GCC_H /* by using protection macros */ 47 48 /***************************** Include Files ********************************/ 49 #include <rtdef.h> 50 51 #ifdef __cplusplus 52 extern "C" { 53 #endif /* __cplusplus */ 54 55 /************************** Constant Definitions ****************************/ 56 57 /**************************** Type Definitions ******************************/ 58 59 /***************** Macros (Inline Functions) Definitions ********************/ 60 61 /* necessary for pre-processor */ 62 #define stringify(s) tostring(s) 63 #define tostring(s) #s 64 65 #if defined (__aarch64__) 66 /* pseudo assembler instructions */ 67 #define mfcpsr() ({rt_uint32_t rval = 0U; \ 68 asm volatile("mrs %0, DAIF" : "=r" (rval));\ 69 rval;\ 70 }) 71 72 #define mtcpsr(v) __asm__ __volatile__ ("msr DAIF, %0" : : "r" (v)) 73 74 #define cpsiei() //__asm__ __volatile__("cpsie i\n") 75 #define cpsidi() //__asm__ __volatile__("cpsid i\n") 76 77 #define cpsief() //__asm__ __volatile__("cpsie f\n") 78 #define cpsidf() //__asm__ __volatile__("cpsid f\n") 79 80 81 82 #define mtgpr(rn, v) /*__asm__ __volatile__(\ 83 "mov r" stringify(rn) ", %0 \n"\ 84 : : "r" (v)\ 85 )*/ 86 87 #define mfgpr(rn) /*({rt_uint32_t rval; \ 88 __asm__ __volatile__(\ 89 "mov %0,r" stringify(rn) "\n"\ 90 : "=r" (rval)\ 91 );\ 92 rval;\ 93 })*/ 94 95 /* memory synchronization operations */ 96 97 /* Instruction Synchronization Barrier */ 98 #define isb() __asm__ __volatile__ ("isb sy") 99 100 /* Data Synchronization Barrier */ 101 #define dsb() __asm__ __volatile__("dsb sy") 102 103 /* Data Memory Barrier */ 104 #define dmb() __asm__ __volatile__("dmb sy") 105 106 107 /* Memory Operations */ 108 #define ldr(adr) ({u64 rval; \ 109 __asm__ __volatile__(\ 110 "ldr %0,[%1]"\ 111 : "=r" (rval) : "r" (adr)\ 112 );\ 113 rval;\ 114 }) 115 116 #define mfelrel3() ({u64 rval = 0U; \ 117 asm volatile("mrs %0, ELR_EL3" : "=r" (rval));\ 118 rval;\ 119 }) 120 121 #define mtelrel3(v) __asm__ __volatile__ ("msr ELR_EL3, %0" : : "r" (v)) 122 123 #else 124 125 /* pseudo assembler instructions */ 126 #define mfcpsr() ({rt_uint32_t rval = 0U; \ 127 __asm__ __volatile__(\ 128 "mrs %0, cpsr\n"\ 129 : "=r" (rval)\ 130 );\ 131 rval;\ 132 }) 133 134 #define mtcpsr(v) __asm__ __volatile__(\ 135 "msr cpsr,%0\n"\ 136 : : "r" (v)\ 137 ) 138 139 #define cpsiei() __asm__ __volatile__("cpsie i\n") 140 #define cpsidi() __asm__ __volatile__("cpsid i\n") 141 142 #define cpsief() __asm__ __volatile__("cpsie f\n") 143 #define cpsidf() __asm__ __volatile__("cpsid f\n") 144 145 146 147 #define mtgpr(rn, v) __asm__ __volatile__(\ 148 "mov r" stringify(rn) ", %0 \n"\ 149 : : "r" (v)\ 150 ) 151 152 #define mfgpr(rn) ({rt_uint32_t rval; \ 153 __asm__ __volatile__(\ 154 "mov %0,r" stringify(rn) "\n"\ 155 : "=r" (rval)\ 156 );\ 157 rval;\ 158 }) 159 160 /* memory synchronization operations */ 161 162 /* Instruction Synchronization Barrier */ 163 #define isb() __asm__ __volatile__ ("isb" : : : "memory") 164 165 /* Data Synchronization Barrier */ 166 #define dsb() __asm__ __volatile__ ("dsb" : : : "memory") 167 168 /* Data Memory Barrier */ 169 #define dmb() __asm__ __volatile__ ("dmb" : : : "memory") 170 171 172 /* Memory Operations */ 173 #define ldr(adr) ({rt_uint32_t rval; \ 174 __asm__ __volatile__(\ 175 "ldr %0,[%1]"\ 176 : "=r" (rval) : "r" (adr)\ 177 );\ 178 rval;\ 179 }) 180 181 #endif 182 183 #define ldrb(adr) ({rt_uint8_t rval; \ 184 __asm__ __volatile__(\ 185 "ldrb %0,[%1]"\ 186 : "=r" (rval) : "r" (adr)\ 187 );\ 188 rval;\ 189 }) 190 191 #define str(adr, val) __asm__ __volatile__(\ 192 "str %0,[%1]\n"\ 193 : : "r" (val), "r" (adr)\ 194 ) 195 196 #define strb(adr, val) __asm__ __volatile__(\ 197 "strb %0,[%1]\n"\ 198 : : "r" (val), "r" (adr)\ 199 ) 200 201 /* Count leading zeroes (clz) */ 202 #define clz(arg) ({rt_uint8_t rval; \ 203 __asm__ __volatile__(\ 204 "clz %0,%1"\ 205 : "=r" (rval) : "r" (arg)\ 206 );\ 207 rval;\ 208 }) 209 210 #if defined (__aarch64__) 211 #define mtcpdc(reg,val) __asm__ __volatile__("dc " #reg ",%0" : : "r" (val)) 212 #define mtcpic(reg,val) __asm__ __volatile__("ic " #reg ",%0" : : "r" (val)) 213 214 #define mtcpicall(reg) __asm__ __volatile__("ic " #reg) 215 #define mtcptlbi(reg) __asm__ __volatile__("tlbi " #reg) 216 #define mtcpat(reg,val) __asm__ __volatile__("at " #reg ",%0" : : "r" (val)) 217 /* CP15 operations */ 218 #define mfcp(reg) ({u64 rval = 0U;\ 219 __asm__ __volatile__("mrs %0, " #reg : "=r" (rval));\ 220 rval;\ 221 }) 222 223 #define mtcp(reg,val) __asm__ __volatile__("msr " #reg ",%0" : : "r" (val)) 224 225 #else 226 /* CP15 operations */ 227 #define mtcp(rn, v) __asm__ __volatile__(\ 228 "mcr " rn "\n"\ 229 : : "r" (v)\ 230 ); 231 232 #define mfcp(rn) ({rt_uint32_t rval = 0U; \ 233 __asm__ __volatile__(\ 234 "mrc " rn "\n"\ 235 : "=r" (rval)\ 236 );\ 237 rval;\ 238 }) 239 #endif 240 241 /************************** Variable Definitions ****************************/ 242 243 /************************** Function Prototypes *****************************/ 244 245 #ifdef __cplusplus 246 } 247 #endif /* __cplusplus */ 248 249 #endif /* XPSEUDO_ASM_GCC_H */ 250