1 /* SPDX-License-Identifier: GPL-2.0-only */ 2 /* 3 * Copyright (c) Qualcomm Technologies, Inc. and/or its subsidiaries. 4 */ 5 6 #ifndef QCOMTEE_MSG_H 7 #define QCOMTEE_MSG_H 8 9 #include <linux/bitfield.h> 10 11 /** 12 * DOC: ''Qualcomm TEE'' (QTEE) Transport Message 13 * 14 * There are two buffers shared with QTEE: inbound and outbound buffers. 15 * The inbound buffer is used for direct object invocation, and the outbound 16 * buffer is used to make a request from QTEE to the kernel; i.e., a callback 17 * request. 18 * 19 * The unused tail of the outbound buffer is also used for sending and 20 * receiving asynchronous messages. An asynchronous message is independent of 21 * the current object invocation (i.e., contents of the inbound buffer) or 22 * callback request (i.e., the head of the outbound buffer); see 23 * qcomtee_get_async_buffer(). It is used by endpoints (QTEE or kernel) as an 24 * optimization to reduce the number of context switches between the secure and 25 * non-secure worlds. 26 * 27 * For instance, QTEE never sends an explicit callback request to release an 28 * object in the kernel. Instead, it sends asynchronous release messages in the 29 * outbound buffer when QTEE returns from the previous direct object invocation, 30 * or appends asynchronous release messages after the current callback request. 31 * 32 * QTEE supports two types of arguments in a message: buffer and object 33 * arguments. Depending on the direction of data flow, they could be input 34 * buffer (IO) to QTEE, output buffer (OB) from QTEE, input object (IO) to QTEE, 35 * or output object (OO) from QTEE. Object arguments hold object IDs. Buffer 36 * arguments hold (offset, size) pairs into the inbound or outbound buffers. 37 * 38 * QTEE holds an object table for objects it hosts and exposes to the kernel. 39 * An object ID is an index to the object table in QTEE. 40 * 41 * For the direct object invocation message format in the inbound buffer, see 42 * &struct qcomtee_msg_object_invoke. For the callback request message format 43 * in the outbound buffer, see &struct qcomtee_msg_callback. For the message 44 * format for asynchronous messages in the outbound buffer, see 45 * &struct qcomtee_async_msg_hdr. 46 */ 47 48 /** 49 * define QCOMTEE_MSG_OBJECT_NS_BIT - Non-secure bit 50 * 51 * Object ID is a globally unique 32-bit number. IDs referencing objects 52 * in the kernel should have %QCOMTEE_MSG_OBJECT_NS_BIT set. 53 */ 54 #define QCOMTEE_MSG_OBJECT_NS_BIT BIT(31) 55 56 /* Static object IDs recognized by QTEE. */ 57 #define QCOMTEE_MSG_OBJECT_NULL (0U) 58 #define QCOMTEE_MSG_OBJECT_ROOT (1U) 59 60 /* Definitions from QTEE as part of the transport protocol. */ 61 62 /* qcomtee_msg_arg is an argument as recognized by QTEE. */ 63 union qcomtee_msg_arg { 64 struct { 65 u32 offset; 66 u32 size; 67 } b; 68 u32 o; 69 }; 70 71 /* BI and BO payloads in QTEE messages should be at 64-bit boundaries. */ 72 #define qcomtee_msg_offset_align(o) ALIGN((o), sizeof(u64)) 73 74 /* Operations for objects are 32-bit. Transport uses the upper 16 bits. */ 75 #define QCOMTEE_MSG_OBJECT_OP_MASK GENMASK(15, 0) 76 77 /* Reserved Operation IDs sent to QTEE: */ 78 /* QCOMTEE_MSG_OBJECT_OP_RELEASE - Reduces the refcount and releases the object. 79 * QCOMTEE_MSG_OBJECT_OP_RETAIN - Increases the refcount. 80 * 81 * These operation IDs are valid for all objects. 82 */ 83 84 #define QCOMTEE_MSG_OBJECT_OP_RELEASE (QCOMTEE_MSG_OBJECT_OP_MASK - 0) 85 #define QCOMTEE_MSG_OBJECT_OP_RETAIN (QCOMTEE_MSG_OBJECT_OP_MASK - 1) 86 87 /* Subset of operations supported by QTEE root object. */ 88 89 #define QCOMTEE_ROOT_OP_REG_WITH_CREDENTIALS 5 90 #define QCOMTEE_ROOT_OP_NOTIFY_DOMAIN_CHANGE 4 91 #define QCOMTEE_ROOT_OP_ADCI_ACCEPT 8 92 #define QCOMTEE_ROOT_OP_ADCI_SHUTDOWN 9 93 94 /* Subset of operations supported by client_env object. */ 95 96 #define QCOMTEE_CLIENT_ENV_OPEN 0 97 98 /* List of available QTEE service UIDs and subset of operations. */ 99 100 #define QCOMTEE_FEATURE_VER_UID 2033 101 #define QCOMTEE_FEATURE_VER_OP_GET 0 102 /* Get QTEE version number. */ 103 #define QCOMTEE_FEATURE_VER_OP_GET_QTEE_ID 10 104 #define QTEE_VERSION_GET_MAJOR(x) (((x) >> 22) & 0xffU) 105 #define QTEE_VERSION_GET_MINOR(x) (((x) >> 12) & 0xffU) 106 #define QTEE_VERSION_GET_PATCH(x) ((x) >> 0 & 0xfffU) 107 108 /* Response types as returned from qcomtee_object_invoke_ctx_invoke(). */ 109 110 /* The message contains a callback request. */ 111 #define QCOMTEE_RESULT_INBOUND_REQ_NEEDED 3 112 113 /** 114 * struct qcomtee_msg_object_invoke - Direct object invocation message. 115 * @ctx: object ID hosted in QTEE. 116 * @op: operation for the object. 117 * @counts: number of different types of arguments in @args. 118 * @args: array of arguments. 119 * 120 * @counts consists of 4 * 4-bit fields. Bits 0 - 3 represent the number of 121 * input buffers, bits 4 - 7 represent the number of output buffers, 122 * bits 8 - 11 represent the number of input objects, and bits 12 - 15 123 * represent the number of output objects. The remaining bits should be zero. 124 * 125 * 15 12 11 8 7 4 3 0 126 * +----------------+----------------+----------------+----------------+ 127 * | #OO objects | #IO objects | #OB buffers | #IB buffers | 128 * +----------------+----------------+----------------+----------------+ 129 * 130 * The maximum number of arguments of each type is defined by 131 * %QCOMTEE_ARGS_PER_TYPE. 132 */ 133 struct qcomtee_msg_object_invoke { 134 u32 cxt; 135 u32 op; 136 u32 counts; 137 union qcomtee_msg_arg args[]; 138 }; 139 140 /* Bit masks for the four 4-bit nibbles holding the counts. */ 141 #define QCOMTEE_MASK_IB GENMASK(3, 0) 142 #define QCOMTEE_MASK_OB GENMASK(7, 4) 143 #define QCOMTEE_MASK_IO GENMASK(11, 8) 144 #define QCOMTEE_MASK_OO GENMASK(15, 12) 145 146 /** 147 * struct qcomtee_msg_callback - Callback request message. 148 * @result: result of operation @op on the object referenced by @cxt. 149 * @cxt: object ID hosted in the kernel. 150 * @op: operation for the object. 151 * @counts: number of different types of arguments in @args. 152 * @args: array of arguments. 153 * 154 * For details of @counts, see &qcomtee_msg_object_invoke.counts. 155 */ 156 struct qcomtee_msg_callback { 157 u32 result; 158 u32 cxt; 159 u32 op; 160 u32 counts; 161 union qcomtee_msg_arg args[]; 162 }; 163 164 /* Offset in the message for the beginning of the buffer argument's contents. */ 165 #define qcomtee_msg_buffer_args(t, n) \ 166 qcomtee_msg_offset_align(struct_size_t(t, args, n)) 167 /* Pointer to the beginning of a buffer argument's content at an offset. */ 168 #define qcomtee_msg_offset_to_ptr(m, off) ((void *)&((char *)(m))[(off)]) 169 170 /* Some helpers to manage msg.counts. */ 171 172 static inline unsigned int qcomtee_msg_num_ib(u32 counts) 173 { 174 return FIELD_GET(QCOMTEE_MASK_IB, counts); 175 } 176 177 static inline unsigned int qcomtee_msg_num_ob(u32 counts) 178 { 179 return FIELD_GET(QCOMTEE_MASK_OB, counts); 180 } 181 182 static inline unsigned int qcomtee_msg_num_io(u32 counts) 183 { 184 return FIELD_GET(QCOMTEE_MASK_IO, counts); 185 } 186 187 static inline unsigned int qcomtee_msg_num_oo(u32 counts) 188 { 189 return FIELD_GET(QCOMTEE_MASK_OO, counts); 190 } 191 192 static inline unsigned int qcomtee_msg_idx_ib(u32 counts) 193 { 194 return 0; 195 } 196 197 static inline unsigned int qcomtee_msg_idx_ob(u32 counts) 198 { 199 return qcomtee_msg_num_ib(counts); 200 } 201 202 static inline unsigned int qcomtee_msg_idx_io(u32 counts) 203 { 204 return qcomtee_msg_idx_ob(counts) + qcomtee_msg_num_ob(counts); 205 } 206 207 static inline unsigned int qcomtee_msg_idx_oo(u32 counts) 208 { 209 return qcomtee_msg_idx_io(counts) + qcomtee_msg_num_io(counts); 210 } 211 212 #define qcomtee_msg_for_each(i, first, num) \ 213 for ((i) = (first); (i) < (first) + (num); (i)++) 214 215 #define qcomtee_msg_for_each_input_buffer(i, m) \ 216 qcomtee_msg_for_each(i, qcomtee_msg_idx_ib((m)->counts), \ 217 qcomtee_msg_num_ib((m)->counts)) 218 219 #define qcomtee_msg_for_each_output_buffer(i, m) \ 220 qcomtee_msg_for_each(i, qcomtee_msg_idx_ob((m)->counts), \ 221 qcomtee_msg_num_ob((m)->counts)) 222 223 #define qcomtee_msg_for_each_input_object(i, m) \ 224 qcomtee_msg_for_each(i, qcomtee_msg_idx_io((m)->counts), \ 225 qcomtee_msg_num_io((m)->counts)) 226 227 #define qcomtee_msg_for_each_output_object(i, m) \ 228 qcomtee_msg_for_each(i, qcomtee_msg_idx_oo((m)->counts), \ 229 qcomtee_msg_num_oo((m)->counts)) 230 231 /* Sum of arguments in a message. */ 232 #define qcomtee_msg_args(m) \ 233 (qcomtee_msg_idx_oo((m)->counts) + qcomtee_msg_num_oo((m)->counts)) 234 235 static inline void qcomtee_msg_init(struct qcomtee_msg_object_invoke *msg, 236 u32 cxt, u32 op, int in_buffer, 237 int out_buffer, int in_object, 238 int out_object) 239 { 240 u32 counts = 0; 241 242 counts |= (in_buffer & 0xfU); 243 counts |= ((out_buffer - in_buffer) & 0xfU) << 4; 244 counts |= ((in_object - out_buffer) & 0xfU) << 8; 245 counts |= ((out_object - in_object) & 0xfU) << 12; 246 247 msg->cxt = cxt; 248 msg->op = op; 249 msg->counts = counts; 250 } 251 252 /* Generic error codes. */ 253 #define QCOMTEE_MSG_OK 0 /* non-specific success code. */ 254 #define QCOMTEE_MSG_ERROR 1 /* non-specific error. */ 255 #define QCOMTEE_MSG_ERROR_INVALID 2 /* unsupported/unrecognized request. */ 256 #define QCOMTEE_MSG_ERROR_SIZE_IN 3 /* supplied buffer/string too large. */ 257 #define QCOMTEE_MSG_ERROR_SIZE_OUT 4 /* supplied output buffer too small. */ 258 #define QCOMTEE_MSG_ERROR_USERBASE 10 /* start of user-defined error range. */ 259 260 /* Transport layer error codes. */ 261 #define QCOMTEE_MSG_ERROR_DEFUNCT -90 /* object no longer exists. */ 262 #define QCOMTEE_MSG_ERROR_ABORT -91 /* calling thread must exit. */ 263 #define QCOMTEE_MSG_ERROR_BADOBJ -92 /* invalid object context. */ 264 #define QCOMTEE_MSG_ERROR_NOSLOTS -93 /* caller's object table full. */ 265 #define QCOMTEE_MSG_ERROR_MAXARGS -94 /* too many args. */ 266 #define QCOMTEE_MSG_ERROR_MAXDATA -95 /* buffers too large. */ 267 #define QCOMTEE_MSG_ERROR_UNAVAIL -96 /* the request could not be processed. */ 268 #define QCOMTEE_MSG_ERROR_KMEM -97 /* kernel out of memory. */ 269 #define QCOMTEE_MSG_ERROR_REMOTE -98 /* local method sent to remote object. */ 270 #define QCOMTEE_MSG_ERROR_BUSY -99 /* Object is busy. */ 271 #define QCOMTEE_MSG_ERROR_TIMEOUT -103 /* Call Back Object invocation timed out. */ 272 273 static inline void qcomtee_msg_set_result(struct qcomtee_msg_callback *cb_msg, 274 int err) 275 { 276 if (!err) { 277 cb_msg->result = QCOMTEE_MSG_OK; 278 } else if (err < 0) { 279 /* If err < 0, then it is a transport error. */ 280 switch (err) { 281 case -ENOMEM: 282 cb_msg->result = QCOMTEE_MSG_ERROR_KMEM; 283 break; 284 case -ENODEV: 285 cb_msg->result = QCOMTEE_MSG_ERROR_DEFUNCT; 286 break; 287 case -ENOSPC: 288 case -EBUSY: 289 cb_msg->result = QCOMTEE_MSG_ERROR_BUSY; 290 break; 291 case -EBADF: 292 case -EINVAL: 293 cb_msg->result = QCOMTEE_MSG_ERROR_UNAVAIL; 294 break; 295 default: 296 cb_msg->result = QCOMTEE_MSG_ERROR; 297 } 298 } else { 299 /* If err > 0, then it is user defined error, pass it as is. */ 300 cb_msg->result = err; 301 } 302 } 303 304 #endif /* QCOMTEE_MSG_H */ 305