]>
Commit | Line | Data |
---|---|---|
1 | // SPDX-License-Identifier: GPL-2.0+ | |
2 | /* | |
3 | * EFI setup code | |
4 | * | |
5 | * Copyright (c) 2016-2018 Alexander Graf et al. | |
6 | */ | |
7 | ||
8 | #include <common.h> | |
9 | #include <bootm.h> | |
10 | #include <efi_loader.h> | |
11 | ||
12 | #define OBJ_LIST_NOT_INITIALIZED 1 | |
13 | ||
14 | static efi_status_t efi_obj_list_initialized = OBJ_LIST_NOT_INITIALIZED; | |
15 | ||
16 | /* | |
17 | * Allow unaligned memory access. | |
18 | * | |
19 | * This routine is overridden by architectures providing this feature. | |
20 | */ | |
21 | void __weak allow_unaligned(void) | |
22 | { | |
23 | } | |
24 | ||
25 | /** | |
26 | * efi_init_platform_lang() - define supported languages | |
27 | * | |
28 | * Set the PlatformLangCodes and PlatformLang variables. | |
29 | * | |
30 | * Return: status code | |
31 | */ | |
32 | static efi_status_t efi_init_platform_lang(void) | |
33 | { | |
34 | efi_status_t ret; | |
35 | efi_uintn_t data_size = 0; | |
36 | char *lang = CONFIG_EFI_PLATFORM_LANG_CODES; | |
37 | char *pos; | |
38 | ||
39 | /* | |
40 | * Variable PlatformLangCodes defines the language codes that the | |
41 | * machine can support. | |
42 | */ | |
43 | ret = EFI_CALL(efi_set_variable(L"PlatformLangCodes", | |
44 | &efi_global_variable_guid, | |
45 | EFI_VARIABLE_BOOTSERVICE_ACCESS | | |
46 | EFI_VARIABLE_RUNTIME_ACCESS, | |
47 | sizeof(CONFIG_EFI_PLATFORM_LANG_CODES), | |
48 | CONFIG_EFI_PLATFORM_LANG_CODES)); | |
49 | if (ret != EFI_SUCCESS) | |
50 | goto out; | |
51 | ||
52 | /* | |
53 | * Variable PlatformLang defines the language that the machine has been | |
54 | * configured for. | |
55 | */ | |
56 | ret = EFI_CALL(efi_get_variable(L"PlatformLang", | |
57 | &efi_global_variable_guid, | |
58 | NULL, &data_size, &pos)); | |
59 | if (ret == EFI_BUFFER_TOO_SMALL) { | |
60 | /* The variable is already set. Do not change it. */ | |
61 | ret = EFI_SUCCESS; | |
62 | goto out; | |
63 | } | |
64 | ||
65 | /* | |
66 | * The list of supported languages is semicolon separated. Use the first | |
67 | * language to initialize PlatformLang. | |
68 | */ | |
69 | pos = strchr(lang, ';'); | |
70 | if (pos) | |
71 | *pos = 0; | |
72 | ||
73 | ret = EFI_CALL(efi_set_variable(L"PlatformLang", | |
74 | &efi_global_variable_guid, | |
75 | EFI_VARIABLE_NON_VOLATILE | | |
76 | EFI_VARIABLE_BOOTSERVICE_ACCESS | | |
77 | EFI_VARIABLE_RUNTIME_ACCESS, | |
78 | 1 + strlen(lang), lang)); | |
79 | out: | |
80 | if (ret != EFI_SUCCESS) | |
81 | printf("EFI: cannot initialize platform language settings\n"); | |
82 | return ret; | |
83 | } | |
84 | ||
85 | /** | |
86 | * efi_init_obj_list() - Initialize and populate EFI object list | |
87 | * | |
88 | * Return: status code | |
89 | */ | |
90 | efi_status_t efi_init_obj_list(void) | |
91 | { | |
92 | u64 os_indications_supported = 0; /* None */ | |
93 | efi_status_t ret = EFI_SUCCESS; | |
94 | ||
95 | /* Initialize once only */ | |
96 | if (efi_obj_list_initialized != OBJ_LIST_NOT_INITIALIZED) | |
97 | return efi_obj_list_initialized; | |
98 | ||
99 | /* Allow unaligned memory access */ | |
100 | allow_unaligned(); | |
101 | ||
102 | /* On ARM switch from EL3 or secure mode to EL2 or non-secure mode */ | |
103 | switch_to_non_secure_mode(); | |
104 | ||
105 | /* Initialize variable services */ | |
106 | ret = efi_init_variables(); | |
107 | if (ret != EFI_SUCCESS) | |
108 | goto out; | |
109 | ||
110 | /* Define supported languages */ | |
111 | ret = efi_init_platform_lang(); | |
112 | if (ret != EFI_SUCCESS) | |
113 | goto out; | |
114 | ||
115 | /* Indicate supported features */ | |
116 | ret = EFI_CALL(efi_set_variable(L"OsIndicationsSupported", | |
117 | &efi_global_variable_guid, | |
118 | EFI_VARIABLE_BOOTSERVICE_ACCESS | | |
119 | EFI_VARIABLE_RUNTIME_ACCESS, | |
120 | sizeof(os_indications_supported), | |
121 | &os_indications_supported)); | |
122 | if (ret != EFI_SUCCESS) | |
123 | goto out; | |
124 | ||
125 | /* Initialize system table */ | |
126 | ret = efi_initialize_system_table(); | |
127 | if (ret != EFI_SUCCESS) | |
128 | goto out; | |
129 | ||
130 | /* Indicate supported runtime services */ | |
131 | ret = efi_init_runtime_supported(); | |
132 | if (ret != EFI_SUCCESS) | |
133 | goto out; | |
134 | ||
135 | /* Initialize root node */ | |
136 | ret = efi_root_node_register(); | |
137 | if (ret != EFI_SUCCESS) | |
138 | goto out; | |
139 | ||
140 | /* Initialize EFI driver uclass */ | |
141 | ret = efi_driver_init(); | |
142 | if (ret != EFI_SUCCESS) | |
143 | goto out; | |
144 | ||
145 | ret = efi_console_register(); | |
146 | if (ret != EFI_SUCCESS) | |
147 | goto out; | |
148 | #ifdef CONFIG_PARTITIONS | |
149 | ret = efi_disk_register(); | |
150 | if (ret != EFI_SUCCESS) | |
151 | goto out; | |
152 | #endif | |
153 | #if defined(CONFIG_LCD) || defined(CONFIG_DM_VIDEO) | |
154 | ret = efi_gop_register(); | |
155 | if (ret != EFI_SUCCESS) | |
156 | goto out; | |
157 | #endif | |
158 | #ifdef CONFIG_EFI_LOAD_FILE2_INITRD | |
159 | ret = efi_initrd_register(); | |
160 | if (ret != EFI_SUCCESS) | |
161 | goto out; | |
162 | #endif | |
163 | #ifdef CONFIG_NET | |
164 | ret = efi_net_register(); | |
165 | if (ret != EFI_SUCCESS) | |
166 | goto out; | |
167 | #endif | |
168 | #ifdef CONFIG_GENERATE_ACPI_TABLE | |
169 | ret = efi_acpi_register(); | |
170 | if (ret != EFI_SUCCESS) | |
171 | goto out; | |
172 | #endif | |
173 | #ifdef CONFIG_GENERATE_SMBIOS_TABLE | |
174 | ret = efi_smbios_register(); | |
175 | if (ret != EFI_SUCCESS) | |
176 | goto out; | |
177 | #endif | |
178 | ret = efi_watchdog_register(); | |
179 | if (ret != EFI_SUCCESS) | |
180 | goto out; | |
181 | ||
182 | /* Initialize EFI runtime services */ | |
183 | ret = efi_reset_system_init(); | |
184 | if (ret != EFI_SUCCESS) | |
185 | goto out; | |
186 | ||
187 | out: | |
188 | efi_obj_list_initialized = ret; | |
189 | return ret; | |
190 | } |