1 /* 2 * Copyright (C) 2016 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef _CM4F_SYSCALL_DO_H_ 18 #define _CM4F_SYSCALL_DO_H_ 19 20 21 #ifdef __cplusplus 22 extern "C" { 23 #endif 24 25 #ifdef _OS_BUILD_ 26 #error "Syscalls should not be called from OS code" 27 #endif 28 29 30 #include <stdint.h> 31 #include <stdarg.h> 32 33 #if defined(__ICCARM__) 34 35 #pragma swi_number=0 36 __swi uintptr_t cpuSyscallDo(uint32_t syscallNo, uint32_t vl); 37 38 #elif defined(__GNUC__) 39 40 #define cpuSyscallDo(syscallNo, vaListPtr) \ 41 ({ \ 42 register uint32_t _r0 asm("r0") = syscallNo; \ 43 register uint32_t _r1 asm("r1") = (uint32_t)vaListPtr; \ 44 asm volatile ( \ 45 "swi 0 \n" \ 46 :"=r"(_r0), "=r"(_r1) \ 47 :"0"(_r0), "1"(_r1) \ 48 :"memory" \ 49 ); \ 50 _r0; \ 51 }) 52 53 /* these are specific to arm-eabi-32-le-gcc ONLY. YMMV otherwise */ 54 55 #define cpuSyscallDo0P(syscallNo) \ 56 ({ \ 57 register uint32_t _r0 asm("r0") = syscallNo; \ 58 asm volatile ( \ 59 "swi 0 \n" \ 60 :"=r"(_r0) \ 61 :"0"(_r0) \ 62 :"memory" \ 63 ); \ 64 _r0; \ 65 }) 66 67 68 #define cpuSyscallDo1P(syscallNo, p1) \ 69 ({ \ 70 register uint32_t _r0 asm("r0") = syscallNo; \ 71 register uint32_t _r1 asm("r1") = (uint32_t)p1;\ 72 asm volatile ( \ 73 "swi 1 \n" \ 74 :"=r"(_r0), "=r"(_r1) \ 75 :"0"(_r0), "1"(_r1) \ 76 :"memory" \ 77 ); \ 78 _r0; \ 79 }) 80 81 82 83 #define cpuSyscallDo2P(syscallNo, p1, p2) \ 84 ({ \ 85 register uint32_t _r0 asm("r0") = syscallNo; \ 86 register uint32_t _r1 asm("r1") = (uint32_t)p1;\ 87 register uint32_t _r2 asm("r2") = (uint32_t)p2;\ 88 asm volatile ( \ 89 "swi 1 \n" \ 90 :"=r"(_r0), "=r"(_r1), "=r"(_r2) \ 91 :"0"(_r0), "1"(_r1), "2"(_r2) \ 92 :"memory" \ 93 ); \ 94 _r0; \ 95 }) 96 97 #define cpuSyscallDo3P(syscallNo, p1, p2, p3) \ 98 ({ \ 99 register uint32_t _r0 asm("r0") = syscallNo; \ 100 register uint32_t _r1 asm("r1") = (uint32_t)p1;\ 101 register uint32_t _r2 asm("r2") = (uint32_t)p2;\ 102 register uint32_t _r3 asm("r3") = (uint32_t)p3;\ 103 asm volatile ( \ 104 "swi 1 \n" \ 105 :"=r"(_r0), "=r"(_r1), "=r"(_r2), "=r"(_r3)\ 106 :"0"(_r0), "1"(_r1), "2"(_r2), "3"(_r3) \ 107 :"memory" \ 108 ); \ 109 _r0; \ 110 }) 111 112 #define cpuSyscallDo4P(syscallNo, p1, p2, p3, p4) \ 113 ({ \ 114 register uint32_t _r0 asm("r0") = syscallNo; \ 115 register uint32_t _r1 asm("r1") = (uint32_t)p1; \ 116 register uint32_t _r2 asm("r2") = (uint32_t)p2; \ 117 register uint32_t _r3 asm("r3") = (uint32_t)p3; \ 118 register uint32_t _r12 asm("r12") = (uint32_t)p4; \ 119 asm volatile ( \ 120 "swi 1 \n" \ 121 :"=r"(_r0), "=r"(_r1), "=r"(_r2), "=r"(_r3), "=r"(_r12) \ 122 :"0"(_r0), "1"(_r1), "2"(_r2), "3"(_r3), "4"(_r12) \ 123 :"memory" \ 124 ); \ 125 _r0; \ 126 }) 127 128 #endif 129 130 131 #ifdef __cplusplus 132 } 133 #endif 134 135 #endif 136 137