xref: /optee_os/core/tee/tee_rpmb_fs.c (revision 71cd3ee470bd9d794692f7440ae76dbd5877d8b7)
1 /*
2  * Copyright (c) 2014, STMicroelectronics International N.V.
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions are met:
7  *
8  * 1. Redistributions of source code must retain the above copyright notice,
9  * this list of conditions and the following disclaimer.
10  *
11  * 2. Redistributions in binary form must reproduce the above copyright notice,
12  * this list of conditions and the following disclaimer in the documentation
13  * and/or other materials provided with the distribution.
14  *
15  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
16  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
19  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
20  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
21  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
22  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
23  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
24  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
25  * POSSIBILITY OF SUCH DAMAGE.
26  */
27 
28 #include <assert.h>
29 #include <crypto/crypto.h>
30 #include <kernel/misc.h>
31 #include <kernel/msg_param.h>
32 #include <kernel/mutex.h>
33 #include <kernel/panic.h>
34 #include <kernel/tee_common.h>
35 #include <kernel/tee_common_otp.h>
36 #include <kernel/tee_misc.h>
37 #include <kernel/thread.h>
38 #include <mm/core_memprot.h>
39 #include <mm/mobj.h>
40 #include <mm/tee_mm.h>
41 #include <optee_msg_supplicant.h>
42 #include <stdlib.h>
43 #include <string_ext.h>
44 #include <string.h>
45 #include <sys/queue.h>
46 #include <tee/tee_fs.h>
47 #include <tee/tee_fs_key_manager.h>
48 #include <tee/tee_pobj.h>
49 #include <tee/tee_svc_storage.h>
50 #include <trace.h>
51 #include <util.h>
52 
53 #define RPMB_STORAGE_START_ADDRESS      0
54 #define RPMB_FS_FAT_START_ADDRESS       512
55 #define RPMB_BLOCK_SIZE_SHIFT           8
56 #define RPMB_CID_PRV_OFFSET             9
57 #define RPMB_CID_CRC_OFFSET             15
58 
59 #define RPMB_FS_MAGIC                   0x52504D42
60 #define FS_VERSION                      2
61 #define N_ENTRIES                       8
62 
63 #define FILE_IS_ACTIVE                  (1u << 0)
64 #define FILE_IS_LAST_ENTRY              (1u << 1)
65 
66 #define TEE_RPMB_FS_FILENAME_LENGTH 224
67 
68 /**
69  * FS parameters: Information often used by internal functions.
70  * fat_start_address will be set by rpmb_fs_setup().
71  * rpmb_fs_parameters can be read by any other function.
72  */
73 struct rpmb_fs_parameters {
74 	uint32_t fat_start_address;
75 	uint32_t max_rpmb_address;
76 };
77 
78 /**
79  * File entry for a single file in a RPMB_FS partition.
80  */
81 struct rpmb_fat_entry {
82 	uint32_t start_address;
83 	uint32_t data_size;
84 	uint32_t flags;
85 	uint32_t write_counter;
86 	uint8_t fek[TEE_FS_KM_FEK_SIZE];
87 	char filename[TEE_RPMB_FS_FILENAME_LENGTH];
88 };
89 
90 /**
91  * FAT entry context with reference to a FAT entry and its
92  * location in RPMB.
93  */
94 struct rpmb_file_handle {
95 	struct rpmb_fat_entry fat_entry;
96 	const TEE_UUID *uuid;
97 	char filename[TEE_RPMB_FS_FILENAME_LENGTH];
98 	/* Address for current entry in RPMB */
99 	uint32_t rpmb_fat_address;
100 };
101 
102 /**
103  * RPMB_FS partition data
104  */
105 struct rpmb_fs_partition {
106 	uint32_t rpmb_fs_magic;
107 	uint32_t fs_version;
108 	uint32_t write_counter;
109 	uint32_t fat_start_address;
110 	/* Do not use reserved[] for other purpose than partition data. */
111 	uint8_t reserved[112];
112 };
113 
114 /**
115  * A node in a list of directory entries.
116  */
117 struct tee_rpmb_fs_dirent {
118 	struct tee_fs_dirent entry;
119 	SIMPLEQ_ENTRY(tee_rpmb_fs_dirent) link;
120 };
121 
122 /**
123  * The RPMB directory representation. It contains a queue of
124  * RPMB directory entries: 'next'.
125  * The current pointer points to the last directory entry
126  * returned by readdir().
127  */
128 struct tee_fs_dir {
129 	struct tee_rpmb_fs_dirent *current;
130 	/* */
131 	SIMPLEQ_HEAD(next_head, tee_rpmb_fs_dirent) next;
132 };
133 
134 static struct rpmb_fs_parameters *fs_par;
135 
136 /*
137  * Lower interface to RPMB device
138  */
139 
140 #define RPMB_DATA_OFFSET            (RPMB_STUFF_DATA_SIZE + RPMB_KEY_MAC_SIZE)
141 #define RPMB_MAC_PROTECT_DATA_SIZE  (RPMB_DATA_FRAME_SIZE - RPMB_DATA_OFFSET)
142 
143 #define RPMB_MSG_TYPE_REQ_AUTH_KEY_PROGRAM          0x0001
144 #define RPMB_MSG_TYPE_REQ_WRITE_COUNTER_VAL_READ    0x0002
145 #define RPMB_MSG_TYPE_REQ_AUTH_DATA_WRITE           0x0003
146 #define RPMB_MSG_TYPE_REQ_AUTH_DATA_READ            0x0004
147 #define RPMB_MSG_TYPE_REQ_RESULT_READ               0x0005
148 #define RPMB_MSG_TYPE_RESP_AUTH_KEY_PROGRAM         0x0100
149 #define RPMB_MSG_TYPE_RESP_WRITE_COUNTER_VAL_READ   0x0200
150 #define RPMB_MSG_TYPE_RESP_AUTH_DATA_WRITE          0x0300
151 #define RPMB_MSG_TYPE_RESP_AUTH_DATA_READ           0x0400
152 
153 #define RPMB_STUFF_DATA_SIZE                        196
154 #define RPMB_KEY_MAC_SIZE                           32
155 #define RPMB_DATA_SIZE                              256
156 #define RPMB_NONCE_SIZE                             16
157 #define RPMB_DATA_FRAME_SIZE                        512
158 
159 #define RPMB_RESULT_OK                              0x00
160 #define RPMB_RESULT_GENERAL_FAILURE                 0x01
161 #define RPMB_RESULT_AUTH_FAILURE                    0x02
162 #define RPMB_RESULT_COUNTER_FAILURE                 0x03
163 #define RPMB_RESULT_ADDRESS_FAILURE                 0x04
164 #define RPMB_RESULT_WRITE_FAILURE                   0x05
165 #define RPMB_RESULT_READ_FAILURE                    0x06
166 #define RPMB_RESULT_AUTH_KEY_NOT_PROGRAMMED         0x07
167 #define RPMB_RESULT_MASK                            0x3F
168 #define RPMB_RESULT_WR_CNT_EXPIRED                  0x80
169 
170 /* RPMB internal commands */
171 #define RPMB_CMD_DATA_REQ      0x00
172 #define RPMB_CMD_GET_DEV_INFO  0x01
173 
174 #define RPMB_SIZE_SINGLE (128 * 1024)
175 
176 /* Error codes for get_dev_info request/response. */
177 #define RPMB_CMD_GET_DEV_INFO_RET_OK     0x00
178 #define RPMB_CMD_GET_DEV_INFO_RET_ERROR  0x01
179 
180 struct rpmb_data_frame {
181 	uint8_t stuff_bytes[RPMB_STUFF_DATA_SIZE];
182 	uint8_t key_mac[RPMB_KEY_MAC_SIZE];
183 	uint8_t data[RPMB_DATA_SIZE];
184 	uint8_t nonce[RPMB_NONCE_SIZE];
185 	uint8_t write_counter[4];
186 	uint8_t address[2];
187 	uint8_t block_count[2];
188 	uint8_t op_result[2];
189 	uint8_t msg_type[2];
190 };
191 
192 struct rpmb_req {
193 	uint16_t cmd;
194 	uint16_t dev_id;
195 	uint16_t block_count;
196 	/* variable length of data */
197 	/* uint8_t data[]; REMOVED! */
198 };
199 
200 #define TEE_RPMB_REQ_DATA(req) \
201 		((void *)((struct rpmb_req *)(req) + 1))
202 
203 struct rpmb_raw_data {
204 	uint16_t msg_type;
205 	uint16_t *op_result;
206 	uint16_t *block_count;
207 	uint16_t *blk_idx;
208 	uint32_t *write_counter;
209 	uint8_t *nonce;
210 	uint8_t *key_mac;
211 	uint8_t *data;
212 	/* data length to read or write */
213 	uint32_t len;
214 	/* Byte address offset in the first block involved */
215 	uint8_t byte_offset;
216 };
217 
218 #define RPMB_EMMC_CID_SIZE 16
219 struct rpmb_dev_info {
220 	uint8_t cid[RPMB_EMMC_CID_SIZE];
221 	/* EXT CSD-slice 168 "RPMB Size" */
222 	uint8_t rpmb_size_mult;
223 	/* EXT CSD-slice 222 "Reliable Write Sector Count" */
224 	uint8_t rel_wr_sec_c;
225 	/* Check the ret code and accept the data only if it is OK. */
226 	uint8_t ret_code;
227 };
228 
229 /*
230  * Struct for rpmb context data.
231  *
232  * @key              RPMB key.
233  * @cid              eMMC card ID.
234  * @hash_ctx_size    Hash context size
235  * @wr_cnt           Current write counter.
236  * @max_blk_idx      The highest block index supported by current device.
237  * @rel_wr_blkcnt    Max number of data blocks for each reliable write.
238  * @dev_id           Device ID of the eMMC device.
239  * @wr_cnt_synced    Flag indicating if write counter is synced to RPMB.
240  * @key_derived      Flag indicating if key has been generated.
241  * @key_verified     Flag indicating the key generated is verified ok.
242  * @dev_info_synced  Flag indicating if dev info has been retrieved from RPMB.
243  */
244 struct tee_rpmb_ctx {
245 	uint8_t key[RPMB_KEY_MAC_SIZE];
246 	uint8_t cid[RPMB_EMMC_CID_SIZE];
247 	size_t hash_ctx_size;
248 	uint32_t wr_cnt;
249 	uint16_t max_blk_idx;
250 	uint16_t rel_wr_blkcnt;
251 	uint16_t dev_id;
252 	bool wr_cnt_synced;
253 	bool key_derived;
254 	bool key_verified;
255 	bool dev_info_synced;
256 };
257 
258 static struct tee_rpmb_ctx *rpmb_ctx;
259 
260 /*
261  * Mutex to serialize the operations exported by this file.
262  * It protects rpmb_ctx and prevents overlapping operations on eMMC devices with
263  * different IDs.
264  */
265 static struct mutex rpmb_mutex = MUTEX_INITIALIZER;
266 
267 #ifdef CFG_RPMB_TESTKEY
268 
269 static const uint8_t rpmb_test_key[RPMB_KEY_MAC_SIZE] = {
270 	0xD3, 0xEB, 0x3E, 0xC3, 0x6E, 0x33, 0x4C, 0x9F,
271 	0x98, 0x8C, 0xE2, 0xC0, 0xB8, 0x59, 0x54, 0x61,
272 	0x0D, 0x2B, 0xCF, 0x86, 0x64, 0x84, 0x4D, 0xF2,
273 	0xAB, 0x56, 0xE6, 0xC6, 0x1B, 0xB7, 0x01, 0xE4
274 };
275 
276 static TEE_Result tee_rpmb_key_gen(uint16_t dev_id __unused,
277 				   uint8_t *key, uint32_t len)
278 {
279 	TEE_Result res = TEE_SUCCESS;
280 
281 	if (!key || RPMB_KEY_MAC_SIZE != len) {
282 		res = TEE_ERROR_BAD_PARAMETERS;
283 		goto out;
284 	}
285 
286 	DMSG("RPMB: Using test key");
287 	memcpy(key, rpmb_test_key, RPMB_KEY_MAC_SIZE);
288 
289 out:
290 	return res;
291 }
292 
293 #else /* !CFG_RPMB_TESTKEY */
294 
295 /*
296  * NOTE: We need a common API to get hw unique key and it
297  * should return error when the hw unique is not a valid
298  * one as stated below.
299  * We need to make sure the hw unique we get is valid by:
300  * 1. In case of HUK is used, checking if OTP is hidden (in
301  *    which case only zeros will be returned) or not;
302  * 2. In case of SSK is used, checking if SSK in OTP is
303  *    write_locked (which means a valid key is provisioned)
304  *    or not.
305  *
306  * Maybe tee_get_hw_unique_key() should be exposed as
307  * generic API for getting hw unique key!
308  * We should change the API tee_otp_get_hw_unique_key()
309  * to return error code!
310  */
311 static TEE_Result tee_get_hw_unique_key(struct tee_hw_unique_key *hwkey)
312 {
313 	if (!hwkey)
314 		return TEE_ERROR_BAD_PARAMETERS;
315 
316 	tee_otp_get_hw_unique_key(hwkey);
317 
318 	return TEE_SUCCESS;
319 }
320 
321 static TEE_Result tee_rpmb_key_gen(uint16_t dev_id __unused,
322 				   uint8_t *key, uint32_t len)
323 {
324 	TEE_Result res;
325 	struct tee_hw_unique_key hwkey;
326 	uint8_t message[RPMB_EMMC_CID_SIZE];
327 	uint8_t *ctx = NULL;
328 
329 	if (!key || RPMB_KEY_MAC_SIZE != len) {
330 		res = TEE_ERROR_BAD_PARAMETERS;
331 		goto out;
332 	}
333 
334 	IMSG("RPMB: Using generated key");
335 	res = tee_get_hw_unique_key(&hwkey);
336 	if (res != TEE_SUCCESS)
337 		goto out;
338 
339 	ctx = malloc(rpmb_ctx->hash_ctx_size);
340 	if (!ctx) {
341 		res = TEE_ERROR_OUT_OF_MEMORY;
342 		goto out;
343 	}
344 
345 	/*
346 	 * PRV/CRC would be changed when doing eMMC FFU
347 	 * The following fields should be masked off when deriving RPMB key
348 	 *
349 	 * CID [55: 48]: PRV (Product revision)
350 	 * CID [07: 01]: CRC (CRC7 checksum)
351 	 * CID [00]: not used
352 	 */
353 	memcpy(message, rpmb_ctx->cid, RPMB_EMMC_CID_SIZE);
354 	memset(message + RPMB_CID_PRV_OFFSET, 0, 1);
355 	memset(message + RPMB_CID_CRC_OFFSET, 0, 1);
356 	res = crypto_mac_init(ctx, TEE_ALG_HMAC_SHA256, hwkey.data,
357 			      HW_UNIQUE_KEY_LENGTH);
358 	if (res != TEE_SUCCESS)
359 		goto out;
360 
361 	res = crypto_mac_update(ctx, TEE_ALG_HMAC_SHA256,
362 				    message,
363 				    RPMB_EMMC_CID_SIZE);
364 	if (res != TEE_SUCCESS)
365 		goto out;
366 
367 	res = crypto_mac_final(ctx, TEE_ALG_HMAC_SHA256, key, len);
368 
369 out:
370 	free(ctx);
371 	return res;
372 }
373 
374 #endif /* !CFG_RPMB_TESTKEY */
375 
376 static void u32_to_bytes(uint32_t u32, uint8_t *bytes)
377 {
378 	*bytes = (uint8_t) (u32 >> 24);
379 	*(bytes + 1) = (uint8_t) (u32 >> 16);
380 	*(bytes + 2) = (uint8_t) (u32 >> 8);
381 	*(bytes + 3) = (uint8_t) u32;
382 }
383 
384 static void bytes_to_u32(uint8_t *bytes, uint32_t *u32)
385 {
386 	*u32 = (uint32_t) ((*(bytes) << 24) +
387 			   (*(bytes + 1) << 16) +
388 			   (*(bytes + 2) << 8) + (*(bytes + 3)));
389 }
390 
391 static void u16_to_bytes(uint16_t u16, uint8_t *bytes)
392 {
393 	*bytes = (uint8_t) (u16 >> 8);
394 	*(bytes + 1) = (uint8_t) u16;
395 }
396 
397 static void bytes_to_u16(uint8_t *bytes, uint16_t *u16)
398 {
399 	*u16 = (uint16_t) ((*bytes << 8) + *(bytes + 1));
400 }
401 
402 static TEE_Result tee_rpmb_mac_calc(uint8_t *mac, uint32_t macsize,
403 				    uint8_t *key, uint32_t keysize,
404 				    struct rpmb_data_frame *datafrms,
405 				    uint16_t blkcnt)
406 {
407 	TEE_Result res = TEE_ERROR_GENERIC;
408 	int i;
409 	uint8_t *ctx = NULL;
410 
411 	if (!mac || !key || !datafrms)
412 		return TEE_ERROR_BAD_PARAMETERS;
413 
414 	ctx = malloc(rpmb_ctx->hash_ctx_size);
415 	if (!ctx)
416 		return TEE_ERROR_OUT_OF_MEMORY;
417 
418 	res = crypto_mac_init(ctx, TEE_ALG_HMAC_SHA256, key, keysize);
419 	if (res != TEE_SUCCESS)
420 		goto func_exit;
421 
422 	for (i = 0; i < blkcnt; i++) {
423 		res = crypto_mac_update(ctx, TEE_ALG_HMAC_SHA256,
424 					datafrms[i].data,
425 					RPMB_MAC_PROTECT_DATA_SIZE);
426 		if (res != TEE_SUCCESS)
427 			goto func_exit;
428 	}
429 
430 	res = crypto_mac_final(ctx, TEE_ALG_HMAC_SHA256, mac, macsize);
431 	if (res != TEE_SUCCESS)
432 		goto func_exit;
433 
434 	res = TEE_SUCCESS;
435 
436 func_exit:
437 	free(ctx);
438 	return res;
439 }
440 
441 struct tee_rpmb_mem {
442 	struct mobj *phreq_mobj;
443 	uint64_t phreq_cookie;
444 	struct mobj *phresp_mobj;
445 	uint64_t phresp_cookie;
446 	size_t req_size;
447 	size_t resp_size;
448 };
449 
450 static void tee_rpmb_free(struct tee_rpmb_mem *mem)
451 {
452 	if (!mem)
453 		return;
454 
455 	if (mem->phreq_mobj) {
456 		thread_rpc_free_payload(mem->phreq_cookie, mem->phreq_mobj);
457 		mem->phreq_cookie = 0;
458 		mem->phreq_mobj = NULL;
459 	}
460 	if (mem->phresp_mobj) {
461 		thread_rpc_free_payload(mem->phresp_cookie, mem->phresp_mobj);
462 		mem->phresp_cookie = 0;
463 		mem->phresp_mobj = NULL;
464 	}
465 }
466 
467 
468 static TEE_Result tee_rpmb_alloc(size_t req_size, size_t resp_size,
469 		struct tee_rpmb_mem *mem, void **req, void **resp)
470 {
471 	TEE_Result res = TEE_SUCCESS;
472 	size_t req_s = ROUNDUP(req_size, sizeof(uint32_t));
473 	size_t resp_s = ROUNDUP(resp_size, sizeof(uint32_t));
474 
475 	if (!mem)
476 		return TEE_ERROR_BAD_PARAMETERS;
477 
478 	memset(mem, 0, sizeof(*mem));
479 
480 	mem->phreq_mobj = thread_rpc_alloc_payload(req_s, &mem->phreq_cookie);
481 	mem->phresp_mobj =
482 		thread_rpc_alloc_payload(resp_s, &mem->phresp_cookie);
483 
484 	if (!mem->phreq_mobj || !mem->phresp_mobj) {
485 		res = TEE_ERROR_OUT_OF_MEMORY;
486 		goto out;
487 	}
488 
489 	*req = mobj_get_va(mem->phreq_mobj, 0);
490 	*resp = mobj_get_va(mem->phresp_mobj, 0);
491 	if (!*req || !*resp) {
492 		res = TEE_ERROR_GENERIC;
493 		goto out;
494 	}
495 
496 	mem->req_size = req_size;
497 	mem->resp_size = resp_size;
498 
499 out:
500 	if (res != TEE_SUCCESS)
501 		tee_rpmb_free(mem);
502 	return res;
503 }
504 
505 static TEE_Result tee_rpmb_invoke(struct tee_rpmb_mem *mem)
506 {
507 	struct optee_msg_param params[2];
508 
509 	memset(params, 0, sizeof(params));
510 
511 	if (!msg_param_init_memparam(params + 0, mem->phreq_mobj, 0,
512 				     mem->req_size, mem->phreq_cookie,
513 				     MSG_PARAM_MEM_DIR_IN))
514 		return TEE_ERROR_BAD_STATE;
515 
516 	if (!msg_param_init_memparam(params + 1, mem->phresp_mobj, 0,
517 				     mem->resp_size, mem->phresp_cookie,
518 				     MSG_PARAM_MEM_DIR_OUT))
519 		return TEE_ERROR_BAD_STATE;
520 
521 	return thread_rpc_cmd(OPTEE_MSG_RPC_CMD_RPMB, 2, params);
522 }
523 
524 static bool is_zero(const uint8_t *buf, size_t size)
525 {
526 	size_t i;
527 
528 	for (i = 0; i < size; i++)
529 		if (buf[i])
530 			return false;
531 	return true;
532 }
533 
534 static TEE_Result encrypt_block(uint8_t *out, const uint8_t *in,
535 				uint16_t blk_idx, const uint8_t *fek,
536 				const TEE_UUID *uuid)
537 {
538 	return tee_fs_crypt_block(uuid, out, in, RPMB_DATA_SIZE,
539 				  blk_idx, fek, TEE_MODE_ENCRYPT);
540 }
541 
542 static TEE_Result decrypt_block(uint8_t *out, const uint8_t *in,
543 				uint16_t blk_idx, const uint8_t *fek,
544 				const TEE_UUID *uuid)
545 {
546 	return tee_fs_crypt_block(uuid, out, in, RPMB_DATA_SIZE,
547 				  blk_idx, fek, TEE_MODE_DECRYPT);
548 }
549 
550 /* Decrypt/copy at most one block of data */
551 static TEE_Result decrypt(uint8_t *out, const struct rpmb_data_frame *frm,
552 			  size_t size, size_t offset,
553 			  uint16_t blk_idx __maybe_unused, const uint8_t *fek,
554 			  const TEE_UUID *uuid)
555 {
556 	uint8_t *tmp __maybe_unused;
557 
558 
559 	if ((size + offset < size) || (size + offset > RPMB_DATA_SIZE))
560 		panic("invalid size or offset");
561 
562 	if (!fek) {
563 		/* Block is not encrypted (not a file data block) */
564 		memcpy(out, frm->data + offset, size);
565 	} else if (is_zero(fek, TEE_FS_KM_FEK_SIZE)) {
566 		/* The file was created with encryption disabled */
567 		return TEE_ERROR_SECURITY;
568 	} else {
569 		/* Block is encrypted */
570 		if (size < RPMB_DATA_SIZE) {
571 			/*
572 			 * Since output buffer is not large enough to hold one
573 			 * block we must allocate a temporary buffer.
574 			 */
575 			tmp = malloc(RPMB_DATA_SIZE);
576 			if (!tmp)
577 				return TEE_ERROR_OUT_OF_MEMORY;
578 			decrypt_block(tmp, frm->data, blk_idx, fek, uuid);
579 			memcpy(out, tmp + offset, size);
580 			free(tmp);
581 		} else {
582 			decrypt_block(out, frm->data, blk_idx, fek, uuid);
583 		}
584 	}
585 
586 	return TEE_SUCCESS;
587 }
588 
589 static TEE_Result tee_rpmb_req_pack(struct rpmb_req *req,
590 				    struct rpmb_raw_data *rawdata,
591 				    uint16_t nbr_frms, uint16_t dev_id,
592 				    const uint8_t *fek, const TEE_UUID *uuid)
593 {
594 	TEE_Result res = TEE_ERROR_GENERIC;
595 	int i;
596 	struct rpmb_data_frame *datafrm;
597 
598 	if (!req || !rawdata || !nbr_frms)
599 		return TEE_ERROR_BAD_PARAMETERS;
600 
601 	/*
602 	 * Check write blockcount is not bigger than reliable write
603 	 * blockcount.
604 	 */
605 	if ((rawdata->msg_type == RPMB_MSG_TYPE_REQ_AUTH_DATA_WRITE) &&
606 	    (nbr_frms > rpmb_ctx->rel_wr_blkcnt)) {
607 		DMSG("wr_blkcnt(%d) > rel_wr_blkcnt(%d)", nbr_frms,
608 		     rpmb_ctx->rel_wr_blkcnt);
609 		return TEE_ERROR_GENERIC;
610 	}
611 
612 	req->cmd = RPMB_CMD_DATA_REQ;
613 	req->dev_id = dev_id;
614 
615 	/* Allocate memory for construct all data packets and calculate MAC. */
616 	datafrm = calloc(nbr_frms, RPMB_DATA_FRAME_SIZE);
617 	if (!datafrm)
618 		return TEE_ERROR_OUT_OF_MEMORY;
619 
620 	for (i = 0; i < nbr_frms; i++) {
621 		u16_to_bytes(rawdata->msg_type, datafrm[i].msg_type);
622 
623 		if (rawdata->block_count)
624 			u16_to_bytes(*rawdata->block_count,
625 				     datafrm[i].block_count);
626 
627 		if (rawdata->blk_idx) {
628 			/* Check the block index is within range. */
629 			if ((*rawdata->blk_idx + nbr_frms) >
630 			    rpmb_ctx->max_blk_idx) {
631 				res = TEE_ERROR_GENERIC;
632 				goto func_exit;
633 			}
634 			u16_to_bytes(*rawdata->blk_idx, datafrm[i].address);
635 		}
636 
637 		if (rawdata->write_counter)
638 			u32_to_bytes(*rawdata->write_counter,
639 				     datafrm[i].write_counter);
640 
641 		if (rawdata->nonce)
642 			memcpy(datafrm[i].nonce, rawdata->nonce,
643 			       RPMB_NONCE_SIZE);
644 
645 		if (rawdata->data) {
646 			if (fek)
647 				encrypt_block(datafrm[i].data,
648 					rawdata->data + (i * RPMB_DATA_SIZE),
649 					*rawdata->blk_idx + i, fek, uuid);
650 			else
651 				memcpy(datafrm[i].data,
652 				       rawdata->data + (i * RPMB_DATA_SIZE),
653 				       RPMB_DATA_SIZE);
654 		}
655 	}
656 
657 	if (rawdata->key_mac) {
658 		if (rawdata->msg_type == RPMB_MSG_TYPE_REQ_AUTH_DATA_WRITE) {
659 			res =
660 			    tee_rpmb_mac_calc(rawdata->key_mac,
661 					      RPMB_KEY_MAC_SIZE, rpmb_ctx->key,
662 					      RPMB_KEY_MAC_SIZE, datafrm,
663 					      nbr_frms);
664 			if (res != TEE_SUCCESS)
665 				goto func_exit;
666 		}
667 		memcpy(datafrm[nbr_frms - 1].key_mac,
668 		       rawdata->key_mac, RPMB_KEY_MAC_SIZE);
669 	}
670 
671 	memcpy(TEE_RPMB_REQ_DATA(req), datafrm,
672 	       nbr_frms * RPMB_DATA_FRAME_SIZE);
673 
674 #ifdef CFG_RPMB_FS_DEBUG_DATA
675 	for (i = 0; i < nbr_frms; i++) {
676 		DMSG("Dumping data frame %d:", i);
677 		DHEXDUMP((uint8_t *)&datafrm[i] + RPMB_STUFF_DATA_SIZE,
678 			 512 - RPMB_STUFF_DATA_SIZE);
679 	}
680 #endif
681 
682 	res = TEE_SUCCESS;
683 func_exit:
684 	free(datafrm);
685 	return res;
686 }
687 
688 static TEE_Result data_cpy_mac_calc_1b(struct rpmb_raw_data *rawdata,
689 				       struct rpmb_data_frame *frm,
690 				       const uint8_t *fek, const TEE_UUID *uuid)
691 {
692 	TEE_Result res;
693 	uint8_t *data;
694 	uint16_t idx;
695 
696 	if (rawdata->len + rawdata->byte_offset > RPMB_DATA_SIZE)
697 		return TEE_ERROR_BAD_PARAMETERS;
698 
699 	res = tee_rpmb_mac_calc(rawdata->key_mac, RPMB_KEY_MAC_SIZE,
700 				rpmb_ctx->key, RPMB_KEY_MAC_SIZE, frm, 1);
701 	if (res != TEE_SUCCESS)
702 		return res;
703 
704 	data = rawdata->data;
705 	bytes_to_u16(frm->address, &idx);
706 
707 	res = decrypt(data, frm, rawdata->len, rawdata->byte_offset, idx, fek,
708 		      uuid);
709 	return res;
710 }
711 
712 static TEE_Result tee_rpmb_data_cpy_mac_calc(struct rpmb_data_frame *datafrm,
713 					     struct rpmb_raw_data *rawdata,
714 					     uint16_t nbr_frms,
715 					     struct rpmb_data_frame *lastfrm,
716 					     const uint8_t *fek,
717 					     const TEE_UUID *uuid)
718 {
719 	TEE_Result res = TEE_ERROR_GENERIC;
720 	int i;
721 	uint8_t *ctx = NULL;
722 	uint16_t offset;
723 	uint32_t size;
724 	uint8_t *data;
725 	uint16_t start_idx;
726 	struct rpmb_data_frame localfrm;
727 
728 	if (!datafrm || !rawdata || !nbr_frms || !lastfrm)
729 		return TEE_ERROR_BAD_PARAMETERS;
730 
731 	if (nbr_frms == 1)
732 		return data_cpy_mac_calc_1b(rawdata, lastfrm, fek, uuid);
733 
734 	/* nbr_frms > 1 */
735 
736 	data = rawdata->data;
737 
738 	ctx = malloc(rpmb_ctx->hash_ctx_size);
739 	if (!ctx) {
740 		res = TEE_ERROR_OUT_OF_MEMORY;
741 		goto func_exit;
742 	}
743 
744 	res = crypto_mac_init(ctx, TEE_ALG_HMAC_SHA256, rpmb_ctx->key,
745 			      RPMB_KEY_MAC_SIZE);
746 	if (res != TEE_SUCCESS)
747 		goto func_exit;
748 
749 	/*
750 	 * Note: JEDEC JESD84-B51: "In every packet the address is the start
751 	 * address of the full access (not address of the individual half a
752 	 * sector)"
753 	 */
754 	bytes_to_u16(lastfrm->address, &start_idx);
755 
756 	for (i = 0; i < (nbr_frms - 1); i++) {
757 
758 		/*
759 		 * By working on a local copy of the RPMB frame, we ensure that
760 		 * the data can not be modified after the MAC is computed but
761 		 * before the payload is decrypted/copied to the output buffer.
762 		 */
763 		memcpy(&localfrm, &datafrm[i], RPMB_DATA_FRAME_SIZE);
764 
765 		res = crypto_mac_update(ctx, TEE_ALG_HMAC_SHA256, localfrm.data,
766 					RPMB_MAC_PROTECT_DATA_SIZE);
767 		if (res != TEE_SUCCESS)
768 			goto func_exit;
769 
770 		if (i == 0) {
771 			/* First block */
772 			offset = rawdata->byte_offset;
773 			size = RPMB_DATA_SIZE - offset;
774 		} else {
775 			/* Middle blocks */
776 			size = RPMB_DATA_SIZE;
777 			offset = 0;
778 		}
779 
780 		res = decrypt(data, &localfrm, size, offset, start_idx + i,
781 			      fek, uuid);
782 		if (res != TEE_SUCCESS)
783 			goto func_exit;
784 
785 		data += size;
786 	}
787 
788 	/* Last block */
789 	size = (rawdata->len + rawdata->byte_offset) % RPMB_DATA_SIZE;
790 	if (size == 0)
791 		size = RPMB_DATA_SIZE;
792 	res = decrypt(data, lastfrm, size, 0, start_idx + nbr_frms - 1, fek,
793 		      uuid);
794 	if (res != TEE_SUCCESS)
795 		goto func_exit;
796 
797 	/* Update MAC against the last block */
798 	res = crypto_mac_update(ctx, TEE_ALG_HMAC_SHA256, lastfrm->data,
799 				RPMB_MAC_PROTECT_DATA_SIZE);
800 	if (res != TEE_SUCCESS)
801 		goto func_exit;
802 
803 	res = crypto_mac_final(ctx, TEE_ALG_HMAC_SHA256, rawdata->key_mac,
804 			       RPMB_KEY_MAC_SIZE);
805 	if (res != TEE_SUCCESS)
806 		goto func_exit;
807 
808 	res = TEE_SUCCESS;
809 
810 func_exit:
811 	free(ctx);
812 	return res;
813 }
814 
815 static TEE_Result tee_rpmb_resp_unpack_verify(struct rpmb_data_frame *datafrm,
816 					      struct rpmb_raw_data *rawdata,
817 					      uint16_t nbr_frms,
818 					      const uint8_t *fek,
819 					      const TEE_UUID *uuid)
820 {
821 	TEE_Result res = TEE_ERROR_GENERIC;
822 	uint16_t msg_type;
823 	uint32_t wr_cnt;
824 	uint16_t blk_idx;
825 	uint16_t op_result;
826 	struct rpmb_data_frame lastfrm;
827 
828 	if (!datafrm || !rawdata || !nbr_frms)
829 		return TEE_ERROR_BAD_PARAMETERS;
830 
831 #ifdef CFG_RPMB_FS_DEBUG_DATA
832 	for (uint32_t i = 0; i < nbr_frms; i++) {
833 		DMSG("Dumping data frame %d:", i);
834 		DHEXDUMP((uint8_t *)&datafrm[i] + RPMB_STUFF_DATA_SIZE,
835 			 512 - RPMB_STUFF_DATA_SIZE);
836 	}
837 #endif
838 
839 	/* Make sure the last data packet can't be modified once verified */
840 	memcpy(&lastfrm, &datafrm[nbr_frms - 1], RPMB_DATA_FRAME_SIZE);
841 
842 	/* Handle operation result and translate to TEEC error code. */
843 	bytes_to_u16(lastfrm.op_result, &op_result);
844 	if (rawdata->op_result)
845 		*rawdata->op_result = op_result;
846 	if (op_result != RPMB_RESULT_OK)
847 		return TEE_ERROR_GENERIC;
848 
849 	/* Check the response msg_type. */
850 	bytes_to_u16(lastfrm.msg_type, &msg_type);
851 	if (msg_type != rawdata->msg_type) {
852 		DMSG("Unexpected msg_type (0x%04x != 0x%04x)", msg_type,
853 		     rawdata->msg_type);
854 		return TEE_ERROR_GENERIC;
855 	}
856 
857 	if (rawdata->blk_idx) {
858 		bytes_to_u16(lastfrm.address, &blk_idx);
859 		if (blk_idx != *rawdata->blk_idx) {
860 			DMSG("Unexpected block index");
861 			return TEE_ERROR_GENERIC;
862 		}
863 	}
864 
865 	if (rawdata->write_counter) {
866 		wr_cnt = *rawdata->write_counter;
867 		bytes_to_u32(lastfrm.write_counter, rawdata->write_counter);
868 		if (msg_type == RPMB_MSG_TYPE_RESP_AUTH_DATA_WRITE) {
869 			/* Verify the write counter is incremented by 1 */
870 			if (*rawdata->write_counter != wr_cnt + 1) {
871 				DMSG("Counter mismatched (0x%04x/0x%04x)",
872 				     *rawdata->write_counter, wr_cnt + 1);
873 				return TEE_ERROR_SECURITY;
874 			}
875 			rpmb_ctx->wr_cnt++;
876 		}
877 	}
878 
879 	if (rawdata->nonce) {
880 		if (buf_compare_ct(rawdata->nonce, lastfrm.nonce,
881 				   RPMB_NONCE_SIZE) != 0) {
882 			DMSG("Nonce mismatched");
883 			return TEE_ERROR_SECURITY;
884 		}
885 	}
886 
887 	if (rawdata->key_mac) {
888 		if (msg_type == RPMB_MSG_TYPE_RESP_AUTH_DATA_READ) {
889 			if (!rawdata->data)
890 				return TEE_ERROR_GENERIC;
891 
892 			res = tee_rpmb_data_cpy_mac_calc(datafrm, rawdata,
893 							 nbr_frms, &lastfrm,
894 							 fek, uuid);
895 
896 			if (res != TEE_SUCCESS)
897 				return res;
898 		} else {
899 			/*
900 			 * There should be only one data frame for
901 			 * other msg types.
902 			 */
903 			if (nbr_frms != 1)
904 				return TEE_ERROR_GENERIC;
905 
906 			res = tee_rpmb_mac_calc(rawdata->key_mac,
907 						RPMB_KEY_MAC_SIZE,
908 						rpmb_ctx->key,
909 						RPMB_KEY_MAC_SIZE,
910 						&lastfrm, 1);
911 
912 			if (res != TEE_SUCCESS)
913 				return res;
914 		}
915 
916 #ifndef CFG_RPMB_FS_NO_MAC
917 		if (buf_compare_ct(rawdata->key_mac,
918 				   (datafrm + nbr_frms - 1)->key_mac,
919 				   RPMB_KEY_MAC_SIZE) != 0) {
920 			DMSG("MAC mismatched:");
921 #ifdef CFG_RPMB_FS_DEBUG_DATA
922 			DHEXDUMP((uint8_t *)rawdata->key_mac, 32);
923 #endif
924 			return TEE_ERROR_SECURITY;
925 		}
926 #endif /* !CFG_RPMB_FS_NO_MAC */
927 	}
928 
929 	return TEE_SUCCESS;
930 }
931 
932 static TEE_Result tee_rpmb_get_dev_info(uint16_t dev_id,
933 					struct rpmb_dev_info *dev_info)
934 {
935 	TEE_Result res = TEE_ERROR_GENERIC;
936 	struct tee_rpmb_mem mem;
937 	struct rpmb_dev_info *di;
938 	struct rpmb_req *req = NULL;
939 	uint8_t *resp = NULL;
940 	uint32_t req_size;
941 	uint32_t resp_size;
942 
943 	if (!dev_info)
944 		return TEE_ERROR_BAD_PARAMETERS;
945 
946 	req_size = sizeof(struct rpmb_req);
947 	resp_size = sizeof(struct rpmb_dev_info);
948 	res = tee_rpmb_alloc(req_size, resp_size, &mem,
949 			     (void *)&req, (void *)&resp);
950 	if (res != TEE_SUCCESS)
951 		goto func_exit;
952 
953 	req->cmd = RPMB_CMD_GET_DEV_INFO;
954 	req->dev_id = dev_id;
955 
956 	di = (struct rpmb_dev_info *)resp;
957 	di->ret_code = RPMB_CMD_GET_DEV_INFO_RET_ERROR;
958 
959 	res = tee_rpmb_invoke(&mem);
960 	if (res != TEE_SUCCESS)
961 		goto func_exit;
962 
963 	if (di->ret_code != RPMB_CMD_GET_DEV_INFO_RET_OK) {
964 		res = TEE_ERROR_GENERIC;
965 		goto func_exit;
966 	}
967 
968 	memcpy((uint8_t *)dev_info, resp, sizeof(struct rpmb_dev_info));
969 
970 #ifdef CFG_RPMB_FS_DEBUG_DATA
971 	DMSG("Dumping dev_info:");
972 	DHEXDUMP((uint8_t *)dev_info, sizeof(struct rpmb_dev_info));
973 #endif
974 
975 	res = TEE_SUCCESS;
976 
977 func_exit:
978 	tee_rpmb_free(&mem);
979 	return res;
980 }
981 
982 static TEE_Result tee_rpmb_init_read_wr_cnt(uint16_t dev_id,
983 					    uint32_t *wr_cnt,
984 					    uint16_t *op_result)
985 {
986 	TEE_Result res = TEE_ERROR_GENERIC;
987 	struct tee_rpmb_mem mem;
988 	uint16_t msg_type;
989 	uint8_t nonce[RPMB_NONCE_SIZE];
990 	uint8_t hmac[RPMB_KEY_MAC_SIZE];
991 	struct rpmb_req *req = NULL;
992 	struct rpmb_data_frame *resp = NULL;
993 	struct rpmb_raw_data rawdata;
994 	uint32_t req_size;
995 	uint32_t resp_size;
996 
997 	if (!wr_cnt)
998 		return TEE_ERROR_BAD_PARAMETERS;
999 
1000 	req_size = sizeof(struct rpmb_req) + RPMB_DATA_FRAME_SIZE;
1001 	resp_size = RPMB_DATA_FRAME_SIZE;
1002 	res = tee_rpmb_alloc(req_size, resp_size, &mem,
1003 			     (void *)&req, (void *)&resp);
1004 	if (res != TEE_SUCCESS)
1005 		goto func_exit;
1006 
1007 	res = crypto_rng_read(nonce, RPMB_NONCE_SIZE);
1008 	if (res != TEE_SUCCESS)
1009 		goto func_exit;
1010 
1011 	msg_type = RPMB_MSG_TYPE_REQ_WRITE_COUNTER_VAL_READ;
1012 
1013 	memset(&rawdata, 0x00, sizeof(struct rpmb_raw_data));
1014 	rawdata.msg_type = msg_type;
1015 	rawdata.nonce = nonce;
1016 
1017 	res = tee_rpmb_req_pack(req, &rawdata, 1, dev_id, NULL, NULL);
1018 	if (res != TEE_SUCCESS)
1019 		goto func_exit;
1020 
1021 	res = tee_rpmb_invoke(&mem);
1022 	if (res != TEE_SUCCESS)
1023 		goto func_exit;
1024 
1025 	msg_type = RPMB_MSG_TYPE_RESP_WRITE_COUNTER_VAL_READ;
1026 
1027 	memset(&rawdata, 0x00, sizeof(struct rpmb_raw_data));
1028 	rawdata.msg_type = msg_type;
1029 	rawdata.op_result = op_result;
1030 	rawdata.write_counter = wr_cnt;
1031 	rawdata.nonce = nonce;
1032 	rawdata.key_mac = hmac;
1033 
1034 	res = tee_rpmb_resp_unpack_verify(resp, &rawdata, 1, NULL, NULL);
1035 	if (res != TEE_SUCCESS)
1036 		goto func_exit;
1037 
1038 	res = TEE_SUCCESS;
1039 
1040 func_exit:
1041 	tee_rpmb_free(&mem);
1042 	return res;
1043 }
1044 
1045 static TEE_Result tee_rpmb_verify_key_sync_counter(uint16_t dev_id)
1046 {
1047 	uint16_t op_result = 0;
1048 	TEE_Result res = TEE_ERROR_GENERIC;
1049 
1050 	res = tee_rpmb_init_read_wr_cnt(dev_id, &rpmb_ctx->wr_cnt,
1051 					&op_result);
1052 
1053 	if (res == TEE_SUCCESS) {
1054 		rpmb_ctx->key_verified = true;
1055 		rpmb_ctx->wr_cnt_synced = true;
1056 	}
1057 
1058 	DMSG("Verify key returning 0x%x\n", res);
1059 	return res;
1060 }
1061 
1062 #ifdef CFG_RPMB_WRITE_KEY
1063 static TEE_Result tee_rpmb_write_key(uint16_t dev_id)
1064 {
1065 	TEE_Result res = TEE_ERROR_GENERIC;
1066 	struct tee_rpmb_mem mem = { 0 };
1067 	uint16_t msg_type;
1068 	struct rpmb_req *req = NULL;
1069 	struct rpmb_data_frame *resp = NULL;
1070 	struct rpmb_raw_data rawdata;
1071 	uint32_t req_size;
1072 	uint32_t resp_size;
1073 
1074 	req_size = sizeof(struct rpmb_req) + RPMB_DATA_FRAME_SIZE;
1075 	resp_size = RPMB_DATA_FRAME_SIZE;
1076 	res = tee_rpmb_alloc(req_size, resp_size, &mem,
1077 			     (void *)&req, (void *)&resp);
1078 	if (res != TEE_SUCCESS)
1079 		goto func_exit;
1080 
1081 	msg_type = RPMB_MSG_TYPE_REQ_AUTH_KEY_PROGRAM;
1082 
1083 	memset(&rawdata, 0x00, sizeof(struct rpmb_raw_data));
1084 	rawdata.msg_type = msg_type;
1085 	rawdata.key_mac = rpmb_ctx->key;
1086 
1087 	res = tee_rpmb_req_pack(req, &rawdata, 1, dev_id, NULL, NULL);
1088 	if (res != TEE_SUCCESS)
1089 		goto func_exit;
1090 
1091 	res = tee_rpmb_invoke(&mem);
1092 	if (res != TEE_SUCCESS)
1093 		goto func_exit;
1094 
1095 	msg_type = RPMB_MSG_TYPE_RESP_AUTH_KEY_PROGRAM;
1096 
1097 	memset(&rawdata, 0x00, sizeof(struct rpmb_raw_data));
1098 	rawdata.msg_type = msg_type;
1099 
1100 	res = tee_rpmb_resp_unpack_verify(resp, &rawdata, 1, NULL, NULL);
1101 	if (res != TEE_SUCCESS)
1102 		goto func_exit;
1103 
1104 	res = TEE_SUCCESS;
1105 
1106 func_exit:
1107 	tee_rpmb_free(&mem);
1108 	return res;
1109 }
1110 
1111 static TEE_Result tee_rpmb_write_and_verify_key(uint16_t dev_id)
1112 {
1113 	TEE_Result res;
1114 
1115 	DMSG("RPMB INIT: Writing Key");
1116 	res = tee_rpmb_write_key(dev_id);
1117 	if (res == TEE_SUCCESS) {
1118 		DMSG("RPMB INIT: Verifying Key");
1119 		res = tee_rpmb_verify_key_sync_counter(dev_id);
1120 	}
1121 	return res;
1122 }
1123 #else
1124 static TEE_Result tee_rpmb_write_and_verify_key(uint16_t dev_id __unused)
1125 {
1126 	return TEE_ERROR_BAD_STATE;
1127 }
1128 #endif
1129 
1130 /* This function must never return TEE_SUCCESS if rpmb_ctx == NULL */
1131 static TEE_Result tee_rpmb_init(uint16_t dev_id)
1132 {
1133 	TEE_Result res = TEE_SUCCESS;
1134 	struct rpmb_dev_info dev_info;
1135 
1136 	if (!rpmb_ctx) {
1137 		rpmb_ctx = calloc(1, sizeof(struct tee_rpmb_ctx));
1138 		if (!rpmb_ctx)
1139 			return TEE_ERROR_OUT_OF_MEMORY;
1140 	} else if (rpmb_ctx->dev_id != dev_id) {
1141 		memset(rpmb_ctx, 0x00, sizeof(struct tee_rpmb_ctx));
1142 	}
1143 
1144 	rpmb_ctx->dev_id = dev_id;
1145 
1146 	if (!rpmb_ctx->dev_info_synced) {
1147 		DMSG("RPMB: Syncing device information");
1148 
1149 		dev_info.rpmb_size_mult = 0;
1150 		dev_info.rel_wr_sec_c = 0;
1151 		res = tee_rpmb_get_dev_info(dev_id, &dev_info);
1152 		if (res != TEE_SUCCESS)
1153 			goto func_exit;
1154 
1155 		DMSG("RPMB: RPMB size is %d*128 KB", dev_info.rpmb_size_mult);
1156 		DMSG("RPMB: Reliable Write Sector Count is %d",
1157 		     dev_info.rel_wr_sec_c);
1158 
1159 		if (dev_info.rpmb_size_mult == 0) {
1160 			res = TEE_ERROR_GENERIC;
1161 			goto func_exit;
1162 		}
1163 
1164 		rpmb_ctx->max_blk_idx = (dev_info.rpmb_size_mult *
1165 					 RPMB_SIZE_SINGLE / RPMB_DATA_SIZE) - 1;
1166 
1167 		memcpy(rpmb_ctx->cid, dev_info.cid, RPMB_EMMC_CID_SIZE);
1168 
1169 		if ((rpmb_ctx->hash_ctx_size == 0) &&
1170 		    crypto_mac_get_ctx_size(TEE_ALG_HMAC_SHA256,
1171 					    &rpmb_ctx->hash_ctx_size)) {
1172 			rpmb_ctx->hash_ctx_size = 0;
1173 			res = TEE_ERROR_GENERIC;
1174 			goto func_exit;
1175 		}
1176 
1177 #ifdef RPMB_DRIVER_MULTIPLE_WRITE_FIXED
1178 		rpmb_ctx->rel_wr_blkcnt = dev_info.rel_wr_sec_c * 2;
1179 #else
1180 		rpmb_ctx->rel_wr_blkcnt = 1;
1181 #endif
1182 
1183 		rpmb_ctx->dev_info_synced = true;
1184 	}
1185 
1186 	if (!rpmb_ctx->key_derived) {
1187 		DMSG("RPMB INIT: Deriving key");
1188 
1189 		res = tee_rpmb_key_gen(dev_id, rpmb_ctx->key,
1190 				       RPMB_KEY_MAC_SIZE);
1191 		if (res != TEE_SUCCESS)
1192 			goto func_exit;
1193 
1194 		rpmb_ctx->key_derived = true;
1195 	}
1196 
1197 	/* Perform a write counter read to verify if the key is ok. */
1198 	if (!rpmb_ctx->wr_cnt_synced || !rpmb_ctx->key_verified) {
1199 		DMSG("RPMB INIT: Verifying Key");
1200 
1201 		res = tee_rpmb_verify_key_sync_counter(dev_id);
1202 		if (res != TEE_SUCCESS && !rpmb_ctx->key_verified) {
1203 			/*
1204 			 * Need to write the key here and verify it.
1205 			 */
1206 			res = tee_rpmb_write_and_verify_key(dev_id);
1207 		}
1208 	}
1209 
1210 func_exit:
1211 	return res;
1212 }
1213 
1214 /*
1215  * Read RPMB data in bytes.
1216  *
1217  * @dev_id     Device ID of the eMMC device.
1218  * @addr       Byte address of data.
1219  * @data       Pointer to the data.
1220  * @len        Size of data in bytes.
1221  * @fek        Encrypted File Encryption Key or NULL.
1222  */
1223 static TEE_Result tee_rpmb_read(uint16_t dev_id, uint32_t addr, uint8_t *data,
1224 				uint32_t len, const uint8_t *fek,
1225 				const TEE_UUID *uuid)
1226 {
1227 	TEE_Result res = TEE_ERROR_GENERIC;
1228 	struct tee_rpmb_mem mem = { 0 };
1229 	uint16_t msg_type;
1230 	uint8_t nonce[RPMB_NONCE_SIZE];
1231 	uint8_t hmac[RPMB_KEY_MAC_SIZE];
1232 	struct rpmb_req *req = NULL;
1233 	struct rpmb_data_frame *resp = NULL;
1234 	struct rpmb_raw_data rawdata;
1235 	uint32_t req_size;
1236 	uint32_t resp_size;
1237 	uint16_t blk_idx;
1238 	uint16_t blkcnt;
1239 	uint8_t byte_offset;
1240 
1241 	if (!data || !len)
1242 		return TEE_ERROR_BAD_PARAMETERS;
1243 
1244 	blk_idx = addr / RPMB_DATA_SIZE;
1245 	byte_offset = addr % RPMB_DATA_SIZE;
1246 
1247 	blkcnt =
1248 	    ROUNDUP(len + byte_offset, RPMB_DATA_SIZE) / RPMB_DATA_SIZE;
1249 	res = tee_rpmb_init(dev_id);
1250 	if (res != TEE_SUCCESS)
1251 		goto func_exit;
1252 
1253 	req_size = sizeof(struct rpmb_req) + RPMB_DATA_FRAME_SIZE;
1254 	resp_size = RPMB_DATA_FRAME_SIZE * blkcnt;
1255 	res = tee_rpmb_alloc(req_size, resp_size, &mem,
1256 			     (void *)&req, (void *)&resp);
1257 	if (res != TEE_SUCCESS)
1258 		goto func_exit;
1259 
1260 	msg_type = RPMB_MSG_TYPE_REQ_AUTH_DATA_READ;
1261 	res = crypto_rng_read(nonce, RPMB_NONCE_SIZE);
1262 	if (res != TEE_SUCCESS)
1263 		goto func_exit;
1264 
1265 	memset(&rawdata, 0x00, sizeof(struct rpmb_raw_data));
1266 	rawdata.msg_type = msg_type;
1267 	rawdata.nonce = nonce;
1268 	rawdata.blk_idx = &blk_idx;
1269 	res = tee_rpmb_req_pack(req, &rawdata, 1, dev_id, NULL, NULL);
1270 	if (res != TEE_SUCCESS)
1271 		goto func_exit;
1272 
1273 	req->block_count = blkcnt;
1274 
1275 	DMSG("Read %u block%s at index %u", blkcnt, ((blkcnt > 1) ? "s" : ""),
1276 	     blk_idx);
1277 
1278 	res = tee_rpmb_invoke(&mem);
1279 	if (res != TEE_SUCCESS)
1280 		goto func_exit;
1281 
1282 	msg_type = RPMB_MSG_TYPE_RESP_AUTH_DATA_READ;
1283 
1284 	memset(&rawdata, 0x00, sizeof(struct rpmb_raw_data));
1285 	rawdata.msg_type = msg_type;
1286 	rawdata.block_count = &blkcnt;
1287 	rawdata.blk_idx = &blk_idx;
1288 	rawdata.nonce = nonce;
1289 	rawdata.key_mac = hmac;
1290 	rawdata.data = data;
1291 
1292 	rawdata.len = len;
1293 	rawdata.byte_offset = byte_offset;
1294 
1295 	res = tee_rpmb_resp_unpack_verify(resp, &rawdata, blkcnt, fek, uuid);
1296 	if (res != TEE_SUCCESS)
1297 		goto func_exit;
1298 
1299 	res = TEE_SUCCESS;
1300 
1301 func_exit:
1302 	tee_rpmb_free(&mem);
1303 	return res;
1304 }
1305 
1306 static TEE_Result tee_rpmb_write_blk(uint16_t dev_id, uint16_t blk_idx,
1307 				     const uint8_t *data_blks, uint16_t blkcnt,
1308 				     const uint8_t *fek, const TEE_UUID *uuid)
1309 {
1310 	TEE_Result res;
1311 	struct tee_rpmb_mem mem;
1312 	uint16_t msg_type;
1313 	uint32_t wr_cnt;
1314 	uint8_t hmac[RPMB_KEY_MAC_SIZE];
1315 	struct rpmb_req *req = NULL;
1316 	struct rpmb_data_frame *resp = NULL;
1317 	struct rpmb_raw_data rawdata;
1318 	uint32_t req_size;
1319 	uint32_t resp_size;
1320 	uint32_t nbr_writes;
1321 	uint16_t tmp_blkcnt;
1322 	uint16_t tmp_blk_idx;
1323 	uint16_t i;
1324 
1325 	DMSG("Write %u block%s at index %u", blkcnt, ((blkcnt > 1) ? "s" : ""),
1326 	     blk_idx);
1327 
1328 	if (!data_blks || !blkcnt)
1329 		return TEE_ERROR_BAD_PARAMETERS;
1330 
1331 	res = tee_rpmb_init(dev_id);
1332 	if (res != TEE_SUCCESS)
1333 		return res;
1334 
1335 	/*
1336 	 * We need to split data when block count
1337 	 * is bigger than reliable block write count.
1338 	 */
1339 	if (blkcnt < rpmb_ctx->rel_wr_blkcnt)
1340 		req_size = sizeof(struct rpmb_req) +
1341 		    RPMB_DATA_FRAME_SIZE * blkcnt;
1342 	else
1343 		req_size = sizeof(struct rpmb_req) +
1344 		    RPMB_DATA_FRAME_SIZE * rpmb_ctx->rel_wr_blkcnt;
1345 
1346 	resp_size = RPMB_DATA_FRAME_SIZE;
1347 	res = tee_rpmb_alloc(req_size, resp_size, &mem,
1348 			     (void *)&req, (void *)&resp);
1349 	if (res != TEE_SUCCESS)
1350 		return res;
1351 
1352 	nbr_writes = blkcnt / rpmb_ctx->rel_wr_blkcnt;
1353 	if (blkcnt % rpmb_ctx->rel_wr_blkcnt > 0)
1354 		nbr_writes += 1;
1355 
1356 	tmp_blkcnt = rpmb_ctx->rel_wr_blkcnt;
1357 	tmp_blk_idx = blk_idx;
1358 	for (i = 0; i < nbr_writes; i++) {
1359 		/*
1360 		 * To handle the last write of block count which is
1361 		 * equal or smaller than reliable write block count.
1362 		 */
1363 		if (i == nbr_writes - 1)
1364 			tmp_blkcnt = blkcnt - rpmb_ctx->rel_wr_blkcnt *
1365 			    (nbr_writes - 1);
1366 
1367 		msg_type = RPMB_MSG_TYPE_REQ_AUTH_DATA_WRITE;
1368 		wr_cnt = rpmb_ctx->wr_cnt;
1369 
1370 		memset(req, 0x00, req_size);
1371 		memset(resp, 0x00, resp_size);
1372 
1373 		memset(&rawdata, 0x00, sizeof(struct rpmb_raw_data));
1374 		rawdata.msg_type = msg_type;
1375 		rawdata.block_count = &tmp_blkcnt;
1376 		rawdata.blk_idx = &tmp_blk_idx;
1377 		rawdata.write_counter = &wr_cnt;
1378 		rawdata.key_mac = hmac;
1379 		rawdata.data = (uint8_t *)data_blks +
1380 				i * rpmb_ctx->rel_wr_blkcnt * RPMB_DATA_SIZE;
1381 
1382 		res = tee_rpmb_req_pack(req, &rawdata, tmp_blkcnt, dev_id,
1383 					fek, uuid);
1384 		if (res != TEE_SUCCESS)
1385 			goto out;
1386 
1387 		res = tee_rpmb_invoke(&mem);
1388 		if (res != TEE_SUCCESS) {
1389 			/*
1390 			 * To force wr_cnt sync next time, as it might get
1391 			 * out of sync due to inconsistent operation result!
1392 			 */
1393 			rpmb_ctx->wr_cnt_synced = false;
1394 			goto out;
1395 		}
1396 
1397 		msg_type = RPMB_MSG_TYPE_RESP_AUTH_DATA_WRITE;
1398 
1399 		memset(&rawdata, 0x00, sizeof(struct rpmb_raw_data));
1400 		rawdata.msg_type = msg_type;
1401 		rawdata.block_count = &tmp_blkcnt;
1402 		rawdata.blk_idx = &tmp_blk_idx;
1403 		rawdata.write_counter = &wr_cnt;
1404 		rawdata.key_mac = hmac;
1405 
1406 		res = tee_rpmb_resp_unpack_verify(resp, &rawdata, 1, NULL,
1407 						  NULL);
1408 		if (res != TEE_SUCCESS) {
1409 			/*
1410 			 * To force wr_cnt sync next time, as it might get
1411 			 * out of sync due to inconsistent operation result!
1412 			 */
1413 			rpmb_ctx->wr_cnt_synced = false;
1414 			goto out;
1415 		}
1416 
1417 		tmp_blk_idx += tmp_blkcnt;
1418 	}
1419 
1420 out:
1421 	tee_rpmb_free(&mem);
1422 	return res;
1423 }
1424 
1425 static bool tee_rpmb_write_is_atomic(uint16_t dev_id __unused, uint32_t addr,
1426 				     uint32_t len)
1427 {
1428 	uint8_t byte_offset = addr % RPMB_DATA_SIZE;
1429 	uint16_t blkcnt = ROUNDUP(len + byte_offset,
1430 				  RPMB_DATA_SIZE) / RPMB_DATA_SIZE;
1431 
1432 	return (blkcnt <= rpmb_ctx->rel_wr_blkcnt);
1433 }
1434 
1435 /*
1436  * Write RPMB data in bytes.
1437  *
1438  * @dev_id     Device ID of the eMMC device.
1439  * @addr       Byte address of data.
1440  * @data       Pointer to the data.
1441  * @len        Size of data in bytes.
1442  * @fek        Encrypted File Encryption Key or NULL.
1443  */
1444 static TEE_Result tee_rpmb_write(uint16_t dev_id, uint32_t addr,
1445 				 const uint8_t *data, uint32_t len,
1446 				 const uint8_t *fek, const TEE_UUID *uuid)
1447 {
1448 	TEE_Result res = TEE_ERROR_GENERIC;
1449 	uint8_t *data_tmp = NULL;
1450 	uint16_t blk_idx;
1451 	uint16_t blkcnt;
1452 	uint8_t byte_offset;
1453 
1454 	blk_idx = addr / RPMB_DATA_SIZE;
1455 	byte_offset = addr % RPMB_DATA_SIZE;
1456 
1457 	blkcnt =
1458 	    ROUNDUP(len + byte_offset, RPMB_DATA_SIZE) / RPMB_DATA_SIZE;
1459 
1460 	if (byte_offset == 0 && (len % RPMB_DATA_SIZE) == 0) {
1461 		res = tee_rpmb_write_blk(dev_id, blk_idx, data, blkcnt, fek,
1462 					 uuid);
1463 		if (res != TEE_SUCCESS)
1464 			goto func_exit;
1465 	} else {
1466 		data_tmp = calloc(blkcnt, RPMB_DATA_SIZE);
1467 		if (!data_tmp) {
1468 			res = TEE_ERROR_OUT_OF_MEMORY;
1469 			goto func_exit;
1470 		}
1471 
1472 		/* Read the complete blocks */
1473 		res = tee_rpmb_read(dev_id, blk_idx * RPMB_DATA_SIZE, data_tmp,
1474 				    blkcnt * RPMB_DATA_SIZE, fek, uuid);
1475 		if (res != TEE_SUCCESS)
1476 			goto func_exit;
1477 
1478 		/* Partial update of the data blocks */
1479 		memcpy(data_tmp + byte_offset, data, len);
1480 
1481 		res = tee_rpmb_write_blk(dev_id, blk_idx, data_tmp, blkcnt,
1482 					 fek, uuid);
1483 		if (res != TEE_SUCCESS)
1484 			goto func_exit;
1485 	}
1486 
1487 	res = TEE_SUCCESS;
1488 
1489 func_exit:
1490 	free(data_tmp);
1491 	return res;
1492 }
1493 
1494 /*
1495  * Read the RPMB write counter.
1496  *
1497  * @dev_id     Device ID of the eMMC device.
1498  * @counter    Pointer to the counter.
1499  */
1500 static TEE_Result tee_rpmb_get_write_counter(uint16_t dev_id,
1501 					     uint32_t *counter)
1502 {
1503 	TEE_Result res = TEE_SUCCESS;
1504 
1505 	if (!counter)
1506 		return TEE_ERROR_BAD_PARAMETERS;
1507 
1508 	if (!rpmb_ctx || !rpmb_ctx->wr_cnt_synced) {
1509 		res = tee_rpmb_init(dev_id);
1510 		if (res != TEE_SUCCESS)
1511 			goto func_exit;
1512 	}
1513 
1514 	*counter = rpmb_ctx->wr_cnt;
1515 
1516 func_exit:
1517 	return res;
1518 }
1519 
1520 /*
1521  * Read the RPMB max block.
1522  *
1523  * @dev_id     Device ID of the eMMC device.
1524  * @counter    Pointer to receive the max block.
1525  */
1526 static TEE_Result tee_rpmb_get_max_block(uint16_t dev_id, uint32_t *max_block)
1527 {
1528 	TEE_Result res = TEE_SUCCESS;
1529 
1530 	if (!max_block)
1531 		return TEE_ERROR_BAD_PARAMETERS;
1532 
1533 	if (!rpmb_ctx || !rpmb_ctx->dev_info_synced) {
1534 		res = tee_rpmb_init(dev_id);
1535 		if (res != TEE_SUCCESS)
1536 			goto func_exit;
1537 	}
1538 
1539 	*max_block = rpmb_ctx->max_blk_idx;
1540 
1541 func_exit:
1542 	return res;
1543 }
1544 
1545 /*
1546  * End of lower interface to RPMB device
1547  */
1548 
1549 static TEE_Result get_fat_start_address(uint32_t *addr);
1550 
1551 static void dump_fat(void)
1552 {
1553 	TEE_Result res = TEE_ERROR_GENERIC;
1554 	struct rpmb_fat_entry *fat_entries = NULL;
1555 	uint32_t fat_address;
1556 	size_t size;
1557 	int i;
1558 	bool last_entry_found = false;
1559 
1560 	res = get_fat_start_address(&fat_address);
1561 	if (res != TEE_SUCCESS)
1562 		goto out;
1563 
1564 	size = N_ENTRIES * sizeof(struct rpmb_fat_entry);
1565 	fat_entries = malloc(size);
1566 	if (!fat_entries) {
1567 		res = TEE_ERROR_OUT_OF_MEMORY;
1568 		goto out;
1569 	}
1570 
1571 	while (!last_entry_found) {
1572 		res = tee_rpmb_read(CFG_RPMB_FS_DEV_ID, fat_address,
1573 				    (uint8_t *)fat_entries, size, NULL, NULL);
1574 		if (res != TEE_SUCCESS)
1575 			goto out;
1576 
1577 		for (i = 0; i < N_ENTRIES; i++) {
1578 
1579 			FMSG("flags 0x%x, size %d, address 0x%x, filename '%s'",
1580 				fat_entries[i].flags,
1581 				fat_entries[i].data_size,
1582 				fat_entries[i].start_address,
1583 				fat_entries[i].filename);
1584 
1585 			if ((fat_entries[i].flags & FILE_IS_LAST_ENTRY) != 0) {
1586 				last_entry_found = true;
1587 				break;
1588 			}
1589 
1590 			/* Move to next fat_entry. */
1591 			fat_address += sizeof(struct rpmb_fat_entry);
1592 		}
1593 	}
1594 
1595 out:
1596 	free(fat_entries);
1597 }
1598 
1599 #if (TRACE_LEVEL >= TRACE_DEBUG)
1600 static void dump_fh(struct rpmb_file_handle *fh)
1601 {
1602 	DMSG("fh->filename=%s", fh->filename);
1603 	DMSG("fh->rpmb_fat_address=%u", fh->rpmb_fat_address);
1604 	DMSG("fh->fat_entry.start_address=%u", fh->fat_entry.start_address);
1605 	DMSG("fh->fat_entry.data_size=%u", fh->fat_entry.data_size);
1606 }
1607 #else
1608 static void dump_fh(struct rpmb_file_handle *fh __unused)
1609 {
1610 }
1611 #endif
1612 
1613 static struct rpmb_file_handle *alloc_file_handle(struct tee_pobj *po,
1614 						  bool temporary)
1615 {
1616 	struct rpmb_file_handle *fh = NULL;
1617 
1618 	fh = calloc(1, sizeof(struct rpmb_file_handle));
1619 	if (!fh)
1620 		return NULL;
1621 
1622 	if (po)
1623 		tee_svc_storage_create_filename(fh->filename,
1624 						sizeof(fh->filename), po,
1625 						temporary);
1626 
1627 	return fh;
1628 }
1629 
1630 /**
1631  * write_fat_entry: Store info in a fat_entry to RPMB.
1632  */
1633 static TEE_Result write_fat_entry(struct rpmb_file_handle *fh,
1634 				  bool update_write_counter)
1635 {
1636 	TEE_Result res = TEE_ERROR_GENERIC;
1637 
1638 	/* Protect partition data. */
1639 	if (fh->rpmb_fat_address < sizeof(struct rpmb_fs_partition)) {
1640 		res = TEE_ERROR_ACCESS_CONFLICT;
1641 		goto out;
1642 	}
1643 
1644 	if (fh->rpmb_fat_address % sizeof(struct rpmb_fat_entry) != 0) {
1645 		res = TEE_ERROR_BAD_PARAMETERS;
1646 		goto out;
1647 	}
1648 
1649 	if (update_write_counter) {
1650 		res = tee_rpmb_get_write_counter(CFG_RPMB_FS_DEV_ID,
1651 						 &fh->fat_entry.write_counter);
1652 		if (res != TEE_SUCCESS)
1653 			goto out;
1654 	}
1655 
1656 	res = tee_rpmb_write(CFG_RPMB_FS_DEV_ID, fh->rpmb_fat_address,
1657 			     (uint8_t *)&fh->fat_entry,
1658 			     sizeof(struct rpmb_fat_entry), NULL, NULL);
1659 
1660 	dump_fat();
1661 
1662 out:
1663 	return res;
1664 }
1665 
1666 /**
1667  * rpmb_fs_setup: Setup rpmb fs.
1668  * Set initial partition and FS values and write to RPMB.
1669  * Store frequently used data in RAM.
1670  */
1671 static TEE_Result rpmb_fs_setup(void)
1672 {
1673 	TEE_Result res = TEE_ERROR_GENERIC;
1674 	struct rpmb_fs_partition *partition_data = NULL;
1675 	struct rpmb_file_handle *fh = NULL;
1676 	uint32_t max_rpmb_block = 0;
1677 
1678 	if (fs_par) {
1679 		res = TEE_SUCCESS;
1680 		goto out;
1681 	}
1682 
1683 	res = tee_rpmb_get_max_block(CFG_RPMB_FS_DEV_ID, &max_rpmb_block);
1684 	if (res != TEE_SUCCESS)
1685 		goto out;
1686 
1687 	partition_data = calloc(1, sizeof(struct rpmb_fs_partition));
1688 	if (!partition_data) {
1689 		res = TEE_ERROR_OUT_OF_MEMORY;
1690 		goto out;
1691 	}
1692 
1693 	res = tee_rpmb_read(CFG_RPMB_FS_DEV_ID, RPMB_STORAGE_START_ADDRESS,
1694 			    (uint8_t *)partition_data,
1695 			    sizeof(struct rpmb_fs_partition), NULL, NULL);
1696 	if (res != TEE_SUCCESS)
1697 		goto out;
1698 
1699 #ifndef CFG_RPMB_RESET_FAT
1700 	if (partition_data->rpmb_fs_magic == RPMB_FS_MAGIC) {
1701 		if (partition_data->fs_version == FS_VERSION) {
1702 			res = TEE_SUCCESS;
1703 			goto store_fs_par;
1704 		} else {
1705 			/* Wrong software is in use. */
1706 			res = TEE_ERROR_ACCESS_DENIED;
1707 			goto out;
1708 		}
1709 	}
1710 #else
1711 	EMSG("**** Clearing Storage ****");
1712 #endif
1713 
1714 	/* Setup new partition data. */
1715 	partition_data->rpmb_fs_magic = RPMB_FS_MAGIC;
1716 	partition_data->fs_version = FS_VERSION;
1717 	partition_data->fat_start_address = RPMB_FS_FAT_START_ADDRESS;
1718 
1719 	/* Initial FAT entry with FILE_IS_LAST_ENTRY flag set. */
1720 	fh = alloc_file_handle(NULL, false);
1721 	if (!fh) {
1722 		res = TEE_ERROR_OUT_OF_MEMORY;
1723 		goto out;
1724 	}
1725 	fh->fat_entry.flags = FILE_IS_LAST_ENTRY;
1726 	fh->rpmb_fat_address = partition_data->fat_start_address;
1727 
1728 	/* Write init FAT entry and partition data to RPMB. */
1729 	res = write_fat_entry(fh, true);
1730 	if (res != TEE_SUCCESS)
1731 		goto out;
1732 
1733 	res =
1734 	    tee_rpmb_get_write_counter(CFG_RPMB_FS_DEV_ID,
1735 				       &partition_data->write_counter);
1736 	if (res != TEE_SUCCESS)
1737 		goto out;
1738 	res = tee_rpmb_write(CFG_RPMB_FS_DEV_ID, RPMB_STORAGE_START_ADDRESS,
1739 			     (uint8_t *)partition_data,
1740 			     sizeof(struct rpmb_fs_partition), NULL, NULL);
1741 
1742 #ifndef CFG_RPMB_RESET_FAT
1743 store_fs_par:
1744 #endif
1745 
1746 	/* Store FAT start address. */
1747 	fs_par = calloc(1, sizeof(struct rpmb_fs_parameters));
1748 	if (!fs_par) {
1749 		res = TEE_ERROR_OUT_OF_MEMORY;
1750 		goto out;
1751 	}
1752 
1753 	fs_par->fat_start_address = partition_data->fat_start_address;
1754 	fs_par->max_rpmb_address = max_rpmb_block << RPMB_BLOCK_SIZE_SHIFT;
1755 
1756 	dump_fat();
1757 
1758 out:
1759 	free(fh);
1760 	free(partition_data);
1761 	return res;
1762 }
1763 
1764 /**
1765  * get_fat_start_address:
1766  * FAT start_address from fs_par.
1767  */
1768 static TEE_Result get_fat_start_address(uint32_t *addr)
1769 {
1770 	if (!fs_par)
1771 		return TEE_ERROR_NO_DATA;
1772 
1773 	*addr = fs_par->fat_start_address;
1774 
1775 	return TEE_SUCCESS;
1776 }
1777 
1778 /**
1779  * read_fat: Read FAT entries
1780  * Return matching FAT entry for read, rm rename and stat.
1781  * Build up memory pool and return matching entry for write operation.
1782  * "Last FAT entry" can be returned during write.
1783  */
1784 static TEE_Result read_fat(struct rpmb_file_handle *fh, tee_mm_pool_t *p)
1785 {
1786 	TEE_Result res = TEE_ERROR_GENERIC;
1787 	tee_mm_entry_t *mm = NULL;
1788 	struct rpmb_fat_entry *fat_entries = NULL;
1789 	uint32_t fat_address;
1790 	size_t size;
1791 	int i;
1792 	bool entry_found = false;
1793 	bool last_entry_found = false;
1794 	bool expand_fat = false;
1795 	struct rpmb_file_handle last_fh;
1796 
1797 	DMSG("fat_address %d", fh->rpmb_fat_address);
1798 
1799 	res = rpmb_fs_setup();
1800 	if (res != TEE_SUCCESS)
1801 		goto out;
1802 
1803 	res = get_fat_start_address(&fat_address);
1804 	if (res != TEE_SUCCESS)
1805 		goto out;
1806 
1807 	size = N_ENTRIES * sizeof(struct rpmb_fat_entry);
1808 	fat_entries = malloc(size);
1809 	if (!fat_entries) {
1810 		res = TEE_ERROR_OUT_OF_MEMORY;
1811 		goto out;
1812 	}
1813 
1814 	/*
1815 	 * The pool is used to represent the current RPMB layout. To find
1816 	 * a slot for the file tee_mm_alloc is called on the pool. Thus
1817 	 * if it is not NULL the entire FAT must be traversed to fill in
1818 	 * the pool.
1819 	 */
1820 	while (!last_entry_found && (!entry_found || p)) {
1821 		res = tee_rpmb_read(CFG_RPMB_FS_DEV_ID, fat_address,
1822 				    (uint8_t *)fat_entries, size, NULL, NULL);
1823 		if (res != TEE_SUCCESS)
1824 			goto out;
1825 
1826 		for (i = 0; i < N_ENTRIES; i++) {
1827 			/*
1828 			 * Look for an entry, matching filenames. (read, rm,
1829 			 * rename and stat.). Only store first filename match.
1830 			 */
1831 			if (fh->filename &&
1832 			    (strcmp(fh->filename,
1833 				    fat_entries[i].filename) == 0) &&
1834 			    (fat_entries[i].flags & FILE_IS_ACTIVE) &&
1835 			    (!entry_found)) {
1836 				entry_found = true;
1837 				fh->rpmb_fat_address = fat_address;
1838 				memcpy(&fh->fat_entry, &fat_entries[i],
1839 				       sizeof(struct rpmb_fat_entry));
1840 				if (!p)
1841 					break;
1842 			}
1843 
1844 			/* Add existing files to memory pool. (write) */
1845 			if (p) {
1846 				if ((fat_entries[i].flags & FILE_IS_ACTIVE) &&
1847 				    (fat_entries[i].data_size > 0)) {
1848 
1849 					mm = tee_mm_alloc2
1850 						(p,
1851 						 fat_entries[i].start_address,
1852 						 fat_entries[i].data_size);
1853 					if (!mm) {
1854 						res = TEE_ERROR_OUT_OF_MEMORY;
1855 						goto out;
1856 					}
1857 				}
1858 
1859 				/* Unused FAT entries can be reused (write) */
1860 				if (((fat_entries[i].flags & FILE_IS_ACTIVE) ==
1861 				     0) && (fh->rpmb_fat_address == 0)) {
1862 					fh->rpmb_fat_address = fat_address;
1863 					memcpy(&fh->fat_entry, &fat_entries[i],
1864 					       sizeof(struct rpmb_fat_entry));
1865 				}
1866 			}
1867 
1868 			if ((fat_entries[i].flags & FILE_IS_LAST_ENTRY) != 0) {
1869 				last_entry_found = true;
1870 
1871 				/*
1872 				 * If the last entry was reached and was chosen
1873 				 * by the previous check, then the FAT needs to
1874 				 * be expanded.
1875 				 * fh->rpmb_fat_address is the address chosen
1876 				 * to store the files FAT entry and fat_address
1877 				 * is the current FAT entry address being
1878 				 * compared.
1879 				 */
1880 				if (p && fh->rpmb_fat_address == fat_address)
1881 					expand_fat = true;
1882 				break;
1883 			}
1884 
1885 			/* Move to next fat_entry. */
1886 			fat_address += sizeof(struct rpmb_fat_entry);
1887 		}
1888 	}
1889 
1890 	/*
1891 	 * Represent the FAT table in the pool.
1892 	 */
1893 	if (p) {
1894 		/*
1895 		 * Since fat_address is the start of the last entry it needs to
1896 		 * be moved up by an entry.
1897 		 */
1898 		fat_address += sizeof(struct rpmb_fat_entry);
1899 
1900 		/* Make room for yet a FAT entry and add to memory pool. */
1901 		if (expand_fat)
1902 			fat_address += sizeof(struct rpmb_fat_entry);
1903 
1904 		mm = tee_mm_alloc2(p, RPMB_STORAGE_START_ADDRESS, fat_address);
1905 		if (!mm) {
1906 			res = TEE_ERROR_OUT_OF_MEMORY;
1907 			goto out;
1908 		}
1909 
1910 		if (expand_fat) {
1911 			/*
1912 			 * Point fat_address to the beginning of the new
1913 			 * entry.
1914 			 */
1915 			fat_address -= sizeof(struct rpmb_fat_entry);
1916 			memset(&last_fh, 0, sizeof(last_fh));
1917 			last_fh.fat_entry.flags = FILE_IS_LAST_ENTRY;
1918 			last_fh.rpmb_fat_address = fat_address;
1919 			res = write_fat_entry(&last_fh, true);
1920 			if (res != TEE_SUCCESS)
1921 				goto out;
1922 		}
1923 	}
1924 
1925 	if (fh->filename && !fh->rpmb_fat_address)
1926 		res = TEE_ERROR_ITEM_NOT_FOUND;
1927 
1928 out:
1929 	free(fat_entries);
1930 	return res;
1931 }
1932 
1933 static TEE_Result generate_fek(struct rpmb_fat_entry *fe, const TEE_UUID *uuid)
1934 {
1935 	TEE_Result res;
1936 
1937 again:
1938 	res = tee_fs_generate_fek(uuid, fe->fek, sizeof(fe->fek));
1939 	if (res != TEE_SUCCESS)
1940 		return res;
1941 
1942 	if (is_zero(fe->fek, sizeof(fe->fek)))
1943 		goto again;
1944 
1945 	return res;
1946 }
1947 
1948 static TEE_Result rpmb_fs_open_internal(struct rpmb_file_handle *fh,
1949 					const TEE_UUID *uuid, bool create)
1950 {
1951 	tee_mm_pool_t p;
1952 	bool pool_result;
1953 	TEE_Result res = TEE_ERROR_GENERIC;
1954 
1955 	/* We need to do setup in order to make sure fs_par is filled in */
1956 	res = rpmb_fs_setup();
1957 	if (res != TEE_SUCCESS)
1958 		goto out;
1959 
1960 	fh->uuid = uuid;
1961 	if (create) {
1962 		/* Upper memory allocation must be used for RPMB_FS. */
1963 		pool_result = tee_mm_init(&p,
1964 					  RPMB_STORAGE_START_ADDRESS,
1965 					  fs_par->max_rpmb_address,
1966 					  RPMB_BLOCK_SIZE_SHIFT,
1967 					  TEE_MM_POOL_HI_ALLOC);
1968 
1969 		if (!pool_result) {
1970 			res = TEE_ERROR_OUT_OF_MEMORY;
1971 			goto out;
1972 		}
1973 
1974 		res = read_fat(fh, &p);
1975 		tee_mm_final(&p);
1976 		if (res != TEE_SUCCESS)
1977 			goto out;
1978 	} else {
1979 		res = read_fat(fh, NULL);
1980 		if (res != TEE_SUCCESS)
1981 			goto out;
1982 	}
1983 
1984 	/*
1985 	 * If this is opened with create and the entry found was not active
1986 	 * then this is a new file and the FAT entry must be written
1987 	 */
1988 	if (create) {
1989 		if ((fh->fat_entry.flags & FILE_IS_ACTIVE) == 0) {
1990 			memset(&fh->fat_entry, 0,
1991 				sizeof(struct rpmb_fat_entry));
1992 			memcpy(fh->fat_entry.filename, fh->filename,
1993 				strlen(fh->filename));
1994 			/* Start address and size are 0 */
1995 			fh->fat_entry.flags = FILE_IS_ACTIVE;
1996 
1997 			res = generate_fek(&fh->fat_entry, uuid);
1998 			if (res != TEE_SUCCESS)
1999 				goto out;
2000 			DMSG("GENERATE FEK key: %p",
2001 			     (void *)fh->fat_entry.fek);
2002 			DHEXDUMP(fh->fat_entry.fek, sizeof(fh->fat_entry.fek));
2003 
2004 			res = write_fat_entry(fh, true);
2005 			if (res != TEE_SUCCESS)
2006 				goto out;
2007 		}
2008 	}
2009 
2010 	res = TEE_SUCCESS;
2011 
2012 out:
2013 	return res;
2014 }
2015 
2016 static void rpmb_fs_close(struct tee_file_handle **tfh)
2017 {
2018 	struct rpmb_file_handle *fh = (struct rpmb_file_handle *)*tfh;
2019 
2020 	free(fh);
2021 	*tfh = NULL;
2022 }
2023 
2024 static TEE_Result rpmb_fs_read(struct tee_file_handle *tfh, size_t pos,
2025 			       void *buf, size_t *len)
2026 {
2027 	TEE_Result res;
2028 	struct rpmb_file_handle *fh = (struct rpmb_file_handle *)tfh;
2029 	size_t size = *len;
2030 
2031 	if (!size)
2032 		return TEE_SUCCESS;
2033 
2034 	mutex_lock(&rpmb_mutex);
2035 
2036 	dump_fh(fh);
2037 
2038 	res = read_fat(fh, NULL);
2039 	if (res != TEE_SUCCESS)
2040 		goto out;
2041 
2042 	if (pos >= fh->fat_entry.data_size) {
2043 		*len = 0;
2044 		goto out;
2045 	}
2046 
2047 	size = MIN(size, fh->fat_entry.data_size - pos);
2048 	if (size) {
2049 		res = tee_rpmb_read(CFG_RPMB_FS_DEV_ID,
2050 				    fh->fat_entry.start_address + pos, buf,
2051 				    size, fh->fat_entry.fek, fh->uuid);
2052 		if (res != TEE_SUCCESS)
2053 			goto out;
2054 	}
2055 	*len = size;
2056 
2057 out:
2058 	mutex_unlock(&rpmb_mutex);
2059 	return res;
2060 }
2061 
2062 static TEE_Result rpmb_fs_write_primitive(struct rpmb_file_handle *fh,
2063 					  size_t pos, const void *buf,
2064 					  size_t size)
2065 {
2066 	TEE_Result res;
2067 	tee_mm_pool_t p;
2068 	bool pool_result = false;
2069 	tee_mm_entry_t *mm;
2070 	size_t end;
2071 	size_t newsize;
2072 	uint8_t *newbuf = NULL;
2073 	uintptr_t newaddr;
2074 	uint32_t start_addr;
2075 
2076 	if (!size)
2077 		return TEE_SUCCESS;
2078 
2079 	if (!fs_par) {
2080 		res = TEE_ERROR_GENERIC;
2081 		goto out;
2082 	}
2083 
2084 	dump_fh(fh);
2085 
2086 	/* Upper memory allocation must be used for RPMB_FS. */
2087 	pool_result = tee_mm_init(&p,
2088 				  RPMB_STORAGE_START_ADDRESS,
2089 				  fs_par->max_rpmb_address,
2090 				  RPMB_BLOCK_SIZE_SHIFT,
2091 				  TEE_MM_POOL_HI_ALLOC);
2092 	if (!pool_result) {
2093 		res = TEE_ERROR_OUT_OF_MEMORY;
2094 		goto out;
2095 	}
2096 
2097 	res = read_fat(fh, &p);
2098 	if (res != TEE_SUCCESS)
2099 		goto out;
2100 
2101 	if (fh->fat_entry.flags & FILE_IS_LAST_ENTRY)
2102 		panic("invalid last entry flag");
2103 
2104 	end = pos + size;
2105 	start_addr = fh->fat_entry.start_address + pos;
2106 
2107 	if (end <= fh->fat_entry.data_size &&
2108 	    tee_rpmb_write_is_atomic(CFG_RPMB_FS_DEV_ID, start_addr, size)) {
2109 
2110 		DMSG("Updating data in-place");
2111 		res = tee_rpmb_write(CFG_RPMB_FS_DEV_ID, start_addr, buf,
2112 				     size, fh->fat_entry.fek, fh->uuid);
2113 		if (res != TEE_SUCCESS)
2114 			goto out;
2115 	} else {
2116 		/*
2117 		 * File must be extended, or update cannot be atomic: allocate,
2118 		 * read, update, write.
2119 		 */
2120 
2121 		DMSG("Need to re-allocate");
2122 		newsize = MAX(end, fh->fat_entry.data_size);
2123 		mm = tee_mm_alloc(&p, newsize);
2124 		newbuf = calloc(1, newsize);
2125 		if (!mm || !newbuf) {
2126 			res = TEE_ERROR_OUT_OF_MEMORY;
2127 			goto out;
2128 		}
2129 
2130 		if (fh->fat_entry.data_size) {
2131 			res = tee_rpmb_read(CFG_RPMB_FS_DEV_ID,
2132 					    fh->fat_entry.start_address,
2133 					    newbuf, fh->fat_entry.data_size,
2134 					    fh->fat_entry.fek, fh->uuid);
2135 			if (res != TEE_SUCCESS)
2136 				goto out;
2137 		}
2138 
2139 		memcpy(newbuf + pos, buf, size);
2140 
2141 		newaddr = tee_mm_get_smem(mm);
2142 		res = tee_rpmb_write(CFG_RPMB_FS_DEV_ID, newaddr, newbuf,
2143 				     newsize, fh->fat_entry.fek, fh->uuid);
2144 		if (res != TEE_SUCCESS)
2145 			goto out;
2146 
2147 		fh->fat_entry.data_size = newsize;
2148 		fh->fat_entry.start_address = newaddr;
2149 		res = write_fat_entry(fh, true);
2150 		if (res != TEE_SUCCESS)
2151 			goto out;
2152 	}
2153 
2154 out:
2155 	if (pool_result)
2156 		tee_mm_final(&p);
2157 	if (newbuf)
2158 		free(newbuf);
2159 
2160 	return res;
2161 }
2162 
2163 static TEE_Result rpmb_fs_write(struct tee_file_handle *tfh, size_t pos,
2164 				const void *buf, size_t size)
2165 {
2166 	TEE_Result res;
2167 
2168 	mutex_lock(&rpmb_mutex);
2169 	res = rpmb_fs_write_primitive((struct rpmb_file_handle *)tfh, pos,
2170 				      buf, size);
2171 	mutex_unlock(&rpmb_mutex);
2172 
2173 	return res;
2174 }
2175 
2176 static TEE_Result rpmb_fs_remove_internal(struct rpmb_file_handle *fh)
2177 {
2178 	TEE_Result res;
2179 
2180 	res = read_fat(fh, NULL);
2181 	if (res)
2182 		return res;
2183 
2184 	/* Clear this file entry. */
2185 	memset(&fh->fat_entry, 0, sizeof(struct rpmb_fat_entry));
2186 	return write_fat_entry(fh, false);
2187 }
2188 
2189 static TEE_Result rpmb_fs_remove(struct tee_pobj *po)
2190 {
2191 	TEE_Result res;
2192 	struct rpmb_file_handle *fh = alloc_file_handle(po, po->temporary);
2193 
2194 	if (!fh)
2195 		return TEE_ERROR_OUT_OF_MEMORY;
2196 
2197 	mutex_lock(&rpmb_mutex);
2198 
2199 	res = rpmb_fs_remove_internal(fh);
2200 
2201 	mutex_unlock(&rpmb_mutex);
2202 
2203 	free(fh);
2204 	return res;
2205 }
2206 
2207 static  TEE_Result rpmb_fs_rename_internal(struct tee_pobj *old,
2208 					   struct tee_pobj *new,
2209 					   bool overwrite)
2210 {
2211 	TEE_Result res = TEE_ERROR_GENERIC;
2212 	struct rpmb_file_handle *fh_old = NULL;
2213 	struct rpmb_file_handle *fh_new = NULL;
2214 
2215 	if (!old) {
2216 		res = TEE_ERROR_BAD_PARAMETERS;
2217 		goto out;
2218 	}
2219 
2220 	if (new)
2221 		fh_old = alloc_file_handle(old, old->temporary);
2222 	else
2223 		fh_old = alloc_file_handle(old, true);
2224 	if (!fh_old) {
2225 		res = TEE_ERROR_OUT_OF_MEMORY;
2226 		goto out;
2227 	}
2228 
2229 	if (new)
2230 		fh_new = alloc_file_handle(new, new->temporary);
2231 	else
2232 		fh_new = alloc_file_handle(old, false);
2233 	if (!fh_new) {
2234 		res = TEE_ERROR_OUT_OF_MEMORY;
2235 		goto out;
2236 	}
2237 
2238 	res = read_fat(fh_old, NULL);
2239 	if (res != TEE_SUCCESS)
2240 		goto out;
2241 
2242 	res = read_fat(fh_new, NULL);
2243 	if (res == TEE_SUCCESS) {
2244 		if (!overwrite) {
2245 			res = TEE_ERROR_ACCESS_CONFLICT;
2246 			goto out;
2247 		}
2248 
2249 		/* Clear this file entry. */
2250 		memset(&fh_new->fat_entry, 0, sizeof(struct rpmb_fat_entry));
2251 		res = write_fat_entry(fh_new, false);
2252 		if (res != TEE_SUCCESS)
2253 			goto out;
2254 	}
2255 
2256 	memset(fh_old->fat_entry.filename, 0, TEE_RPMB_FS_FILENAME_LENGTH);
2257 	memcpy(fh_old->fat_entry.filename, fh_new->filename,
2258 	       strlen(fh_new->filename));
2259 
2260 	res = write_fat_entry(fh_old, false);
2261 
2262 out:
2263 	free(fh_old);
2264 	free(fh_new);
2265 
2266 	return res;
2267 }
2268 
2269 static  TEE_Result rpmb_fs_rename(struct tee_pobj *old, struct tee_pobj *new,
2270 				  bool overwrite)
2271 {
2272 	TEE_Result res;
2273 
2274 	mutex_lock(&rpmb_mutex);
2275 	res = rpmb_fs_rename_internal(old, new, overwrite);
2276 	mutex_unlock(&rpmb_mutex);
2277 
2278 	return res;
2279 }
2280 
2281 static TEE_Result rpmb_fs_truncate(struct tee_file_handle *tfh, size_t length)
2282 {
2283 	struct rpmb_file_handle *fh = (struct rpmb_file_handle *)tfh;
2284 	tee_mm_pool_t p;
2285 	bool pool_result = false;
2286 	tee_mm_entry_t *mm;
2287 	uint32_t newsize;
2288 	uint8_t *newbuf = NULL;
2289 	uintptr_t newaddr;
2290 	TEE_Result res = TEE_ERROR_GENERIC;
2291 
2292 	mutex_lock(&rpmb_mutex);
2293 
2294 	if (length > INT32_MAX) {
2295 		res = TEE_ERROR_BAD_PARAMETERS;
2296 		goto out;
2297 	}
2298 	newsize = length;
2299 
2300 	res = read_fat(fh, NULL);
2301 	if (res != TEE_SUCCESS)
2302 		goto out;
2303 
2304 	if (newsize > fh->fat_entry.data_size) {
2305 		/* Extend file */
2306 
2307 		pool_result = tee_mm_init(&p,
2308 					  RPMB_STORAGE_START_ADDRESS,
2309 					  fs_par->max_rpmb_address,
2310 					  RPMB_BLOCK_SIZE_SHIFT,
2311 					  TEE_MM_POOL_HI_ALLOC);
2312 		if (!pool_result) {
2313 			res = TEE_ERROR_OUT_OF_MEMORY;
2314 			goto out;
2315 		}
2316 		res = read_fat(fh, &p);
2317 		if (res != TEE_SUCCESS)
2318 			goto out;
2319 
2320 		mm = tee_mm_alloc(&p, newsize);
2321 		newbuf = calloc(1, newsize);
2322 		if (!mm || !newbuf) {
2323 			res = TEE_ERROR_OUT_OF_MEMORY;
2324 			goto out;
2325 		}
2326 
2327 		if (fh->fat_entry.data_size) {
2328 			res = tee_rpmb_read(CFG_RPMB_FS_DEV_ID,
2329 					    fh->fat_entry.start_address,
2330 					    newbuf, fh->fat_entry.data_size,
2331 					    fh->fat_entry.fek, fh->uuid);
2332 			if (res != TEE_SUCCESS)
2333 				goto out;
2334 		}
2335 
2336 		newaddr = tee_mm_get_smem(mm);
2337 		res = tee_rpmb_write(CFG_RPMB_FS_DEV_ID, newaddr, newbuf,
2338 				     newsize, fh->fat_entry.fek, fh->uuid);
2339 		if (res != TEE_SUCCESS)
2340 			goto out;
2341 
2342 	} else {
2343 		/* Don't change file location */
2344 		newaddr = fh->fat_entry.start_address;
2345 	}
2346 
2347 	/* fh->pos is unchanged */
2348 	fh->fat_entry.data_size = newsize;
2349 	fh->fat_entry.start_address = newaddr;
2350 	res = write_fat_entry(fh, true);
2351 
2352 out:
2353 	mutex_unlock(&rpmb_mutex);
2354 	if (pool_result)
2355 		tee_mm_final(&p);
2356 	if (newbuf)
2357 		free(newbuf);
2358 
2359 	return res;
2360 }
2361 
2362 static void rpmb_fs_dir_free(struct tee_fs_dir *dir)
2363 {
2364 	struct tee_rpmb_fs_dirent *e;
2365 
2366 	if (!dir)
2367 		return;
2368 
2369 	free(dir->current);
2370 
2371 	while ((e = SIMPLEQ_FIRST(&dir->next))) {
2372 		SIMPLEQ_REMOVE_HEAD(&dir->next, link);
2373 		free(e);
2374 	}
2375 }
2376 
2377 static TEE_Result rpmb_fs_dir_populate(const char *path,
2378 				       struct tee_fs_dir *dir)
2379 {
2380 	struct tee_rpmb_fs_dirent *current = NULL;
2381 	struct rpmb_fat_entry *fat_entries = NULL;
2382 	uint32_t fat_address;
2383 	uint32_t filelen;
2384 	char *filename;
2385 	int i;
2386 	bool last_entry_found = false;
2387 	bool matched;
2388 	struct tee_rpmb_fs_dirent *next = NULL;
2389 	uint32_t pathlen;
2390 	TEE_Result res = TEE_ERROR_GENERIC;
2391 	uint32_t size;
2392 	char temp;
2393 
2394 	mutex_lock(&rpmb_mutex);
2395 
2396 	res = rpmb_fs_setup();
2397 	if (res != TEE_SUCCESS)
2398 		goto out;
2399 
2400 	res = get_fat_start_address(&fat_address);
2401 	if (res != TEE_SUCCESS)
2402 		goto out;
2403 
2404 	size = N_ENTRIES * sizeof(struct rpmb_fat_entry);
2405 	fat_entries = malloc(size);
2406 	if (!fat_entries) {
2407 		res = TEE_ERROR_OUT_OF_MEMORY;
2408 		goto out;
2409 	}
2410 
2411 	pathlen = strlen(path);
2412 	while (!last_entry_found) {
2413 		res = tee_rpmb_read(CFG_RPMB_FS_DEV_ID, fat_address,
2414 				    (uint8_t *)fat_entries, size, NULL, NULL);
2415 		if (res != TEE_SUCCESS)
2416 			goto out;
2417 
2418 		for (i = 0; i < N_ENTRIES; i++) {
2419 			filename = fat_entries[i].filename;
2420 			if (fat_entries[i].flags & FILE_IS_ACTIVE) {
2421 				matched = false;
2422 				filelen = strlen(filename);
2423 				if (filelen > pathlen) {
2424 					temp = filename[pathlen];
2425 					filename[pathlen] = '\0';
2426 					if (strcmp(filename, path) == 0)
2427 						matched = true;
2428 
2429 					filename[pathlen] = temp;
2430 				}
2431 
2432 				if (matched) {
2433 					next = malloc(sizeof(*next));
2434 					if (!next) {
2435 						res = TEE_ERROR_OUT_OF_MEMORY;
2436 						goto out;
2437 					}
2438 
2439 					next->entry.oidlen = tee_hs2b(
2440 						(uint8_t *)&filename[pathlen],
2441 						next->entry.oid,
2442 						filelen - pathlen,
2443 						sizeof(next->entry.oid));
2444 					if (next->entry.oidlen) {
2445 						SIMPLEQ_INSERT_TAIL(&dir->next,
2446 								    next, link);
2447 						current = next;
2448 					} else {
2449 						free(next);
2450 						next = NULL;
2451 					}
2452 
2453 				}
2454 			}
2455 
2456 			if (fat_entries[i].flags & FILE_IS_LAST_ENTRY) {
2457 				last_entry_found = true;
2458 				break;
2459 			}
2460 
2461 			/* Move to next fat_entry. */
2462 			fat_address += sizeof(struct rpmb_fat_entry);
2463 		}
2464 	}
2465 
2466 	if (current)
2467 		res = TEE_SUCCESS;
2468 	else
2469 		res = TEE_ERROR_ITEM_NOT_FOUND; /* No directories were found. */
2470 
2471 out:
2472 	mutex_unlock(&rpmb_mutex);
2473 	if (res != TEE_SUCCESS)
2474 		rpmb_fs_dir_free(dir);
2475 	if (fat_entries)
2476 		free(fat_entries);
2477 
2478 	return res;
2479 }
2480 
2481 static TEE_Result rpmb_fs_opendir(const TEE_UUID *uuid, struct tee_fs_dir **dir)
2482 {
2483 	uint32_t len;
2484 	char path_local[TEE_RPMB_FS_FILENAME_LENGTH];
2485 	TEE_Result res = TEE_ERROR_GENERIC;
2486 	struct tee_fs_dir *rpmb_dir = NULL;
2487 
2488 	if (!uuid || !dir) {
2489 		res = TEE_ERROR_BAD_PARAMETERS;
2490 		goto out;
2491 	}
2492 
2493 	memset(path_local, 0, sizeof(path_local));
2494 	if (tee_svc_storage_create_dirname(path_local, sizeof(path_local) - 1,
2495 					   uuid) != TEE_SUCCESS) {
2496 		res = TEE_ERROR_BAD_PARAMETERS;
2497 		goto out;
2498 	}
2499 	len = strlen(path_local);
2500 
2501 	/* Add a slash to correctly match the full directory name. */
2502 	if (path_local[len - 1] != '/')
2503 		path_local[len] = '/';
2504 
2505 	rpmb_dir = calloc(1, sizeof(*rpmb_dir));
2506 	if (!rpmb_dir) {
2507 		res = TEE_ERROR_OUT_OF_MEMORY;
2508 		goto out;
2509 	}
2510 	SIMPLEQ_INIT(&rpmb_dir->next);
2511 
2512 	res = rpmb_fs_dir_populate(path_local, rpmb_dir);
2513 	if (res != TEE_SUCCESS) {
2514 		free(rpmb_dir);
2515 		rpmb_dir = NULL;
2516 		goto out;
2517 	}
2518 
2519 	*dir = rpmb_dir;
2520 
2521 out:
2522 	return res;
2523 }
2524 
2525 static TEE_Result rpmb_fs_readdir(struct tee_fs_dir *dir,
2526 				  struct tee_fs_dirent **ent)
2527 {
2528 	if (!dir)
2529 		return TEE_ERROR_GENERIC;
2530 
2531 	free(dir->current);
2532 
2533 	dir->current = SIMPLEQ_FIRST(&dir->next);
2534 	if (!dir->current)
2535 		return TEE_ERROR_ITEM_NOT_FOUND;
2536 
2537 	SIMPLEQ_REMOVE_HEAD(&dir->next, link);
2538 
2539 	*ent = &dir->current->entry;
2540 	return TEE_SUCCESS;
2541 }
2542 
2543 static void rpmb_fs_closedir(struct tee_fs_dir *dir)
2544 {
2545 	if (dir) {
2546 		rpmb_fs_dir_free(dir);
2547 		free(dir);
2548 	}
2549 }
2550 
2551 static TEE_Result rpmb_fs_open(struct tee_pobj *po, size_t *size,
2552 			       struct tee_file_handle **ret_fh)
2553 {
2554 	TEE_Result res;
2555 	struct rpmb_file_handle *fh = alloc_file_handle(po, po->temporary);
2556 
2557 	if (!fh)
2558 		return TEE_ERROR_OUT_OF_MEMORY;
2559 
2560 	mutex_lock(&rpmb_mutex);
2561 
2562 	res = rpmb_fs_open_internal(fh, &po->uuid, false);
2563 	if (!res && size)
2564 		*size = fh->fat_entry.data_size;
2565 
2566 	mutex_unlock(&rpmb_mutex);
2567 
2568 	if (res)
2569 		free(fh);
2570 	else
2571 		*ret_fh = (struct tee_file_handle *)fh;
2572 
2573 	return res;
2574 }
2575 
2576 static TEE_Result rpmb_fs_create(struct tee_pobj *po, bool overwrite,
2577 				 const void *head, size_t head_size,
2578 				 const void *attr, size_t attr_size,
2579 				 const void *data, size_t data_size,
2580 				 struct tee_file_handle **ret_fh)
2581 {
2582 	TEE_Result res;
2583 	size_t pos = 0;
2584 	struct rpmb_file_handle *fh = alloc_file_handle(po, po->temporary);
2585 
2586 	if (!fh)
2587 		return TEE_ERROR_OUT_OF_MEMORY;
2588 
2589 	mutex_lock(&rpmb_mutex);
2590 	res = rpmb_fs_open_internal(fh, &po->uuid, true);
2591 	if (res)
2592 		goto out;
2593 
2594 	if (head && head_size) {
2595 		res = rpmb_fs_write_primitive(fh, pos, head, head_size);
2596 		if (res)
2597 			goto out;
2598 		pos += head_size;
2599 	}
2600 
2601 	if (attr && attr_size) {
2602 		res = rpmb_fs_write_primitive(fh, pos, attr, attr_size);
2603 		if (res)
2604 			goto out;
2605 		pos += attr_size;
2606 	}
2607 
2608 	if (data && data_size) {
2609 		res = rpmb_fs_write_primitive(fh, pos, data, data_size);
2610 		if (res)
2611 			goto out;
2612 	}
2613 
2614 	if (po->temporary) {
2615 		/*
2616 		 * If it's a temporary filename (which it normally is)
2617 		 * rename into the final filename now that the file is
2618 		 * fully initialized.
2619 		 */
2620 		po->temporary = false;
2621 		res = rpmb_fs_rename_internal(po, NULL, overwrite);
2622 		if (res) {
2623 			po->temporary = true;
2624 			goto out;
2625 		}
2626 		/* Update file handle after rename. */
2627 		tee_svc_storage_create_filename(fh->filename,
2628 						sizeof(fh->filename),
2629 						po, false);
2630 	}
2631 
2632 out:
2633 	if (res) {
2634 		rpmb_fs_remove_internal(fh);
2635 		free(fh);
2636 	} else {
2637 		*ret_fh = (struct tee_file_handle *)fh;
2638 	}
2639 	mutex_unlock(&rpmb_mutex);
2640 
2641 	return res;
2642 }
2643 
2644 const struct tee_file_operations rpmb_fs_ops = {
2645 	.open = rpmb_fs_open,
2646 	.create = rpmb_fs_create,
2647 	.close = rpmb_fs_close,
2648 	.read = rpmb_fs_read,
2649 	.write = rpmb_fs_write,
2650 	.truncate = rpmb_fs_truncate,
2651 	.rename = rpmb_fs_rename,
2652 	.remove = rpmb_fs_remove,
2653 	.opendir = rpmb_fs_opendir,
2654 	.closedir = rpmb_fs_closedir,
2655 	.readdir = rpmb_fs_readdir,
2656 };
2657 
2658 TEE_Result tee_rpmb_fs_raw_open(const char *fname, bool create,
2659 				struct tee_file_handle **ret_fh)
2660 {
2661 	TEE_Result res;
2662 	struct rpmb_file_handle *fh = calloc(1, sizeof(*fh));
2663 	static const TEE_UUID uuid = { 0 };
2664 
2665 	if (!fh)
2666 		return TEE_ERROR_OUT_OF_MEMORY;
2667 
2668 	snprintf(fh->filename, sizeof(fh->filename), "/%s", fname);
2669 
2670 	mutex_lock(&rpmb_mutex);
2671 
2672 	res = rpmb_fs_open_internal(fh, &uuid, create);
2673 
2674 	mutex_unlock(&rpmb_mutex);
2675 
2676 	if (res) {
2677 		if (create)
2678 			rpmb_fs_remove_internal(fh);
2679 		free(fh);
2680 	} else {
2681 		*ret_fh = (struct tee_file_handle *)fh;
2682 	}
2683 
2684 	return res;
2685 }
2686