blob: bcf9fc9d6e0b2d913c0f047774b7e418433857bc [file] [log] [blame]
Raymond Mao98983392023-07-25 07:53:35 -07001/*
Harrison Mutai60438ee2023-12-01 14:57:57 +00002 * Copyright (c) 2023-2024, Linaro Limited and Contributors. All rights reserved.
Raymond Mao98983392023-07-25 07:53:35 -07003 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 */
6
7#ifndef __TRANSFER_LIST_H
8#define __TRANSFER_LIST_H
9
10#include <stdbool.h>
11#include <stdint.h>
12
Raymond Mao60c3c972023-10-04 09:19:16 -070013#include <common/ep_info.h>
Raymond Mao98983392023-07-25 07:53:35 -070014#include <lib/utils_def.h>
15
Raymond Mao60c3c972023-10-04 09:19:16 -070016#define TRANSFER_LIST_SIGNATURE U(0x4a0fb10b)
17#define TRANSFER_LIST_VERSION U(0x0001)
Raymond Mao98983392023-07-25 07:53:35 -070018
Raymond Mao60c3c972023-10-04 09:19:16 -070019/*
20 * Init value of maximum alignment required by any TE data in the TL
21 * specified as a power of two
22 */
23#define TRANSFER_LIST_INIT_MAX_ALIGN U(3)
Raymond Mao98983392023-07-25 07:53:35 -070024
Raymond Mao60c3c972023-10-04 09:19:16 -070025/* Alignment required by TE header start address, in bytes */
26#define TRANSFER_LIST_GRANULE U(8)
Raymond Mao98983392023-07-25 07:53:35 -070027
Raymond Mao60c3c972023-10-04 09:19:16 -070028/*
29 * Version of the register convention used.
30 * Set to 1 for both AArch64 and AArch32 according to fw handoff spec v0.9
31 */
levi.yun010d2ae2024-05-13 10:27:17 +010032#define REGISTER_CONVENTION_VERSION_SHIFT_64 UL(32)
33#define REGISTER_CONVENTION_VERSION_SHIFT_32 UL(24)
34#define REGISTER_CONVENTION_VERSION_MASK UL(0xff)
35#define REGISTER_CONVENTION_VERSION UL(1)
36
37#define TRANSFER_LIST_HANDOFF_X1_VALUE(__version) \
38 ((TRANSFER_LIST_SIGNATURE & \
39 ((1UL << REGISTER_CONVENTION_VERSION_SHIFT_64) - 1)) | \
40 (((__version) & REGISTER_CONVENTION_VERSION_MASK) << \
41 REGISTER_CONVENTION_VERSION_SHIFT_64))
42
43#define TRANSFER_LIST_HANDOFF_R1_VALUE(__version) \
44 ((TRANSFER_LIST_SIGNATURE & \
45 ((1UL << REGISTER_CONVENTION_VERSION_SHIFT_32) - 1)) | \
46 (((__version) & REGISTER_CONVENTION_VERSION_MASK) << \
47 REGISTER_CONVENTION_VERSION_SHIFT_32))
Raymond Mao98983392023-07-25 07:53:35 -070048
49#ifndef __ASSEMBLER__
50
Raymond Mao60c3c972023-10-04 09:19:16 -070051#define TL_FLAGS_HAS_CHECKSUM BIT(0)
52
Raymond Mao98983392023-07-25 07:53:35 -070053enum transfer_list_tag_id {
54 TL_TAG_EMPTY = 0,
55 TL_TAG_FDT = 1,
56 TL_TAG_HOB_BLOCK = 2,
57 TL_TAG_HOB_LIST = 3,
58 TL_TAG_ACPI_TABLE_AGGREGATE = 4,
Raymond Mao1fccc722024-12-27 07:17:14 -080059 TL_TAG_TPM_EVLOG = 5,
Raymond Mao60c3c972023-10-04 09:19:16 -070060 TL_TAG_OPTEE_PAGABLE_PART = 0x100,
Harrison Mutai60438ee2023-12-01 14:57:57 +000061 TL_TAG_DT_SPMC_MANIFEST = 0x101,
62 TL_TAG_EXEC_EP_INFO64 = 0x102,
Harrison Mutai803d22b2024-01-04 16:25:47 +000063 TL_TAG_SRAM_LAYOUT64 = 0x104,
Harrison Mutai61aaf272024-11-06 14:21:00 +000064 TL_TAG_MBEDTLS_HEAP_INFO = 0x105,
Raymond Mao98983392023-07-25 07:53:35 -070065};
66
67enum transfer_list_ops {
Raymond Mao60c3c972023-10-04 09:19:16 -070068 TL_OPS_NON, /* invalid for any operation */
69 TL_OPS_ALL, /* valid for all operations */
70 TL_OPS_RO, /* valid for read only */
71 TL_OPS_CUS, /* abort or switch to special code to interpret */
Raymond Mao98983392023-07-25 07:53:35 -070072};
73
74struct transfer_list_header {
Raymond Mao60c3c972023-10-04 09:19:16 -070075 uint32_t signature;
76 uint8_t checksum;
77 uint8_t version;
78 uint8_t hdr_size;
79 uint8_t alignment; /* max alignment of TE data */
80 uint32_t size; /* TL header + all TEs */
81 uint32_t max_size;
82 uint32_t flags;
83 uint32_t reserved; /* spare bytes */
Raymond Mao98983392023-07-25 07:53:35 -070084 /*
85 * Commented out element used to visualize dynamic part of the
86 * data structure.
87 *
88 * Note that struct transfer_list_entry also is dynamic in size
89 * so the elements can't be indexed directly but instead must be
90 * traversed in order
91 *
92 * struct transfer_list_entry entries[];
93 */
94};
95
Harrison Mutai4490cd02024-03-20 14:37:51 +000096struct __attribute__((packed)) transfer_list_entry {
97 uint32_t tag_id : 24;
Raymond Mao60c3c972023-10-04 09:19:16 -070098 uint8_t hdr_size;
99 uint32_t data_size;
Raymond Mao98983392023-07-25 07:53:35 -0700100 /*
101 * Commented out element used to visualize dynamic part of the
102 * data structure.
103 *
104 * Note that padding is added at the end of @data to make to reach
105 * a 8-byte boundary.
106 *
107 * uint8_t data[ROUNDUP(data_size, 8)];
108 */
109};
110
Harrison Mutai4490cd02024-03-20 14:37:51 +0000111CASSERT(sizeof(struct transfer_list_entry) == U(0x8), assert_transfer_list_entry_size);
112
Raymond Mao98983392023-07-25 07:53:35 -0700113void transfer_list_dump(struct transfer_list_header *tl);
Harrison Mutaiae1f7802024-11-06 10:03:51 +0000114struct transfer_list_header *transfer_list_ensure(void *addr, size_t size);
Raymond Mao60c3c972023-10-04 09:19:16 -0700115entry_point_info_t *
116transfer_list_set_handoff_args(struct transfer_list_header *tl,
117 entry_point_info_t *ep_info);
Raymond Mao98983392023-07-25 07:53:35 -0700118struct transfer_list_header *transfer_list_init(void *addr, size_t max_size);
119
Raymond Mao60c3c972023-10-04 09:19:16 -0700120struct transfer_list_header *
121transfer_list_relocate(struct transfer_list_header *tl, void *addr,
122 size_t max_size);
123enum transfer_list_ops
124transfer_list_check_header(const struct transfer_list_header *tl);
Raymond Mao98983392023-07-25 07:53:35 -0700125
126void transfer_list_update_checksum(struct transfer_list_header *tl);
127bool transfer_list_verify_checksum(const struct transfer_list_header *tl);
128
129bool transfer_list_set_data_size(struct transfer_list_header *tl,
130 struct transfer_list_entry *entry,
131 uint32_t new_data_size);
132
133void *transfer_list_entry_data(struct transfer_list_entry *entry);
Raymond Mao60c3c972023-10-04 09:19:16 -0700134bool transfer_list_rem(struct transfer_list_header *tl,
135 struct transfer_list_entry *entry);
Raymond Mao98983392023-07-25 07:53:35 -0700136
137struct transfer_list_entry *transfer_list_add(struct transfer_list_header *tl,
Harrison Mutai4490cd02024-03-20 14:37:51 +0000138 uint32_t tag_id,
Raymond Mao60c3c972023-10-04 09:19:16 -0700139 uint32_t data_size,
Raymond Mao98983392023-07-25 07:53:35 -0700140 const void *data);
141
Raymond Mao60c3c972023-10-04 09:19:16 -0700142struct transfer_list_entry *
Harrison Mutai4490cd02024-03-20 14:37:51 +0000143transfer_list_add_with_align(struct transfer_list_header *tl, uint32_t tag_id,
Raymond Mao60c3c972023-10-04 09:19:16 -0700144 uint32_t data_size, const void *data,
145 uint8_t alignment);
Raymond Mao98983392023-07-25 07:53:35 -0700146
Raymond Mao60c3c972023-10-04 09:19:16 -0700147struct transfer_list_entry *
148transfer_list_next(struct transfer_list_header *tl,
149 struct transfer_list_entry *last);
Raymond Mao98983392023-07-25 07:53:35 -0700150
151struct transfer_list_entry *transfer_list_find(struct transfer_list_header *tl,
Harrison Mutai4490cd02024-03-20 14:37:51 +0000152 uint32_t tag_id);
Raymond Mao98983392023-07-25 07:53:35 -0700153
154#endif /*__ASSEMBLER__*/
155#endif /*__TRANSFER_LIST_H*/