blob: c4999a5d91f50b55eaeefe07d7a050a163fcf2c1 [file] [log] [blame]
Angel Pons274a0372020-04-03 01:23:27 +02001/* SPDX-License-Identifier: GPL-2.0-only */
Xiang Wang411a8b72019-01-23 11:45:06 +08002
3#include <stdint.h>
Elyes HAOUAS70a03dd2019-12-02 20:47:50 +01004#include <stdlib.h>
Xiang Wang411a8b72019-01-23 11:45:06 +08005#include <string.h>
Jacob Garber7da638c2019-05-30 16:11:41 -06006#include <console/console.h>
Xiang Wang411a8b72019-01-23 11:45:06 +08007#include <soc/otp.h>
8#include <soc/sdram.h>
9#include <cbfs.h>
Maximilian Bruneda336cd2023-09-16 20:08:41 +020010#include <commonlib/device_tree.h>
Xiang Wang411a8b72019-01-23 11:45:06 +080011#include <bootstate.h>
12#include <mcall.h>
13
14static void do_fixup_mac(struct device_tree_node *node)
15{
16 uint32_t serial = otp_read_serial();
17 static unsigned char mac[6] = { 0x70, 0xb3, 0xd5, 0x92, 0xf0, 0x00 };
18 if (serial != ~0) {
19 mac[5] |= (serial >> 0) & 0xff;
20 mac[4] |= (serial >> 8) & 0xff;
21 mac[3] |= (serial >> 16) & 0xff;
22 }
23 dt_add_bin_prop(node, "local-mac-address", mac, 6);
24}
25
26static void fixup_mac(struct device_tree_node *parent)
27{
28 struct device_tree_property *prop;
29 const char *name = "local-mac-address";
30
31 list_for_each(prop, parent->properties, list_node) {
32 if (!strcmp(name, prop->prop.name))
33 do_fixup_mac(parent);
34 }
35
36 struct device_tree_node *child;
37 list_for_each(child, parent->children, list_node) {
38 fixup_mac(child);
39 }
40}
41
42static void do_fixup_memory(struct device_tree_node *node)
43{
44 u64 addrs[1], sizes[1];
45 addrs[0] = 0x80000000;
46 sizes[0] = sdram_size_mb() * 1024 * 1024;
47 dt_add_reg_prop(node, addrs, sizes, 1, 2, 2);
48}
49
Xiang Wang411a8b72019-01-23 11:45:06 +080050static void fixup_memory(struct device_tree_node *parent)
51{
52 struct device_tree_property *prop;
53 const char *name = "device_type";
54 const char *value = "memory";
55
56 list_for_each(prop, parent->properties, list_node) {
57 if (!strcmp(name, prop->prop.name)) {
58 if (!strcmp(value, (char *)prop->prop.data))
59 do_fixup_memory(parent);
60 }
61 }
62
63 struct device_tree_node *child;
64 list_for_each(child, parent->children, list_node) {
65 fixup_memory(child);
66 }
67}
68
69static void fixup_fdt(void *unused)
70{
71 void *fdt_rom;
72 struct device_tree *tree;
73
74 /* load flat dt from cbfs */
Julius Werner834b3ec2020-03-04 16:52:08 -080075 fdt_rom = cbfs_map("fallback/DTB", NULL);
Xiang Wang411a8b72019-01-23 11:45:06 +080076
Jacob Garber7da638c2019-05-30 16:11:41 -060077 if (fdt_rom == NULL) {
78 printk(BIOS_ERR, "Unable to load fallback/DTB from CBFS\n");
79 return;
80 }
81
Xiang Wang411a8b72019-01-23 11:45:06 +080082 /* Expand DT into a tree */
83 tree = fdt_unflatten(fdt_rom);
84
85 /* fixup tree */
86 fixup_mac(tree->root);
87 fixup_memory(tree->root);
88
89 /* convert the tree to a flat dt */
90 void *dt = malloc(dt_flat_size(tree));
Jacob Garber7da638c2019-05-30 16:11:41 -060091
92 if (dt == NULL) {
93 printk(BIOS_ERR, "Unable to allocate memory for flat device tree\n");
94 return;
95 }
96
Xiang Wang411a8b72019-01-23 11:45:06 +080097 dt_flatten(tree, dt);
98
99 /* update HLS */
100 for (int i = 0; i < CONFIG_MAX_CPUS; i++)
101 OTHER_HLS(i)->fdt = dt;
102}
103
104BOOT_STATE_INIT_ENTRY(BS_WRITE_TABLES, BS_ON_EXIT, fixup_fdt, NULL);