94
qemu_fdt_add_subnode(fdt, "/cpus/cpu-map");
95
}
96
97
-void create_fdt_socket_cpus(void *fdt, RISCVCPU *socket_harts,
98
- int socket_id, int num_harts_socket,
99
- int socket_hartid_base, uint32_t *phandle,
100
- uint32_t *intc_phandles, bool numa_enabled,
101
- bool is_32_bit)
97
+static void
98
+create_fdt_socket_cpu_internal(void *fdt, char *clust_name, RISCVCPU *cpu_ptr,
99
+ int cpu, int socket_id, int socket_hartid_base,
100
+ uint32_t *phandle, uint32_t *intc_phandles,
101
+ bool numa_enabled, bool is_32_bit)
102
{
103
- g_autofree char *clust_name = NULL;
104
- uint32_t cpu_phandle;
105
-
106
- clust_name = g_strdup_printf("/cpus/cpu-map/cluster%d", socket_id);
107
- qemu_fdt_add_subnode(fdt, clust_name);
108
-
109
- for (int cpu = num_harts_socket - 1; cpu >= 0; cpu--) {
110
- RISCVCPU *cpu_ptr = &socket_harts[cpu];
103
+ g_autofree char *cpu_name = NULL;
104
+ g_autofree char *core_name = NULL;
105
+ g_autofree char *intc_name = NULL;
106
+ uint32_t cpu_phandle = (*phandle)++;
107
+ bool is_sifive_u = cpu_ptr == NULL;
108
+
109
+ cpu_name = g_strdup_printf("/cpus/cpu@%d", socket_hartid_base + cpu);
110
+
111
+ /*
112
+ * The sifive_u board has an exclusive satp and riscv,isa
113
+ * schema that can't be shared with other boards, so part
114
+ * of the CPU FDT creation (i.e. the /cpus/cpu@N subnode)
115
+ * is still being done by the board.
116
+ */
117
+ if (!is_sifive_u) {
118
int8_t satp_mode_max = cpu_ptr->cfg.max_satp_mode;
112
- g_autofree char *cpu_name = NULL;
113
- g_autofree char *core_name = NULL;
114
- g_autofree char *intc_name = NULL;
115
-
116
- cpu_phandle = (*phandle)++;
119
118
- cpu_name = g_strdup_printf("/cpus/cpu@%d", socket_hartid_base + cpu);
120
qemu_fdt_add_subnode(fdt, cpu_name);
121
122
if (satp_mode_max != -1) {
141
qemu_fdt_setprop_cell(fdt, cpu_name, "riscv,cbop-block-size",
142
cpu_ptr->cfg.cbop_blocksize);
143
}
144
+ }
145
144
- qemu_fdt_setprop_string(fdt, cpu_name, "compatible", "riscv");
145
- qemu_fdt_setprop_string(fdt, cpu_name, "status", "okay");
146
- qemu_fdt_setprop_cell(fdt, cpu_name, "reg",
147
- socket_hartid_base + cpu);
148
- qemu_fdt_setprop_string(fdt, cpu_name, "device_type", "cpu");
149
- if (numa_enabled) {
150
- qemu_fdt_setprop_cell(fdt, cpu_name, "numa-node-id", socket_id);
151
- }
152
- qemu_fdt_setprop_cell(fdt, cpu_name, "phandle", cpu_phandle);
153
-
154
- intc_phandles[cpu] = (*phandle)++;
155
-
156
- intc_name = g_strdup_printf("%s/interrupt-controller", cpu_name);
157
- qemu_fdt_add_subnode(fdt, intc_name);
158
- qemu_fdt_setprop_cell(fdt, intc_name, "phandle",
159
- intc_phandles[cpu]);
160
- qemu_fdt_setprop_string(fdt, intc_name, "compatible",
161
- "riscv,cpu-intc");
162
- qemu_fdt_setprop(fdt, intc_name, "interrupt-controller", NULL, 0);
163
- qemu_fdt_setprop_cell(fdt, intc_name, "#interrupt-cells", 1);
164
-
165
- core_name = g_strdup_printf("%s/core%d", clust_name, cpu);
166
- qemu_fdt_add_subnode(fdt, core_name);
167
- qemu_fdt_setprop_cell(fdt, core_name, "cpu", cpu_phandle);
146
+ qemu_fdt_setprop_string(fdt, cpu_name, "compatible", "riscv");
147
+ qemu_fdt_setprop_string(fdt, cpu_name, "status", "okay");
148
+ qemu_fdt_setprop_cell(fdt, cpu_name, "reg",
149
+ socket_hartid_base + cpu);
150
+ qemu_fdt_setprop_string(fdt, cpu_name, "device_type", "cpu");
151
+ if (numa_enabled) {
152
+ qemu_fdt_setprop_cell(fdt, cpu_name, "numa-node-id", socket_id);
153
+ }
154
+ qemu_fdt_setprop_cell(fdt, cpu_name, "phandle", cpu_phandle);
155
+
156
+ intc_phandles[cpu] = (*phandle)++;
157
+
158
+ intc_name = g_strdup_printf("%s/interrupt-controller", cpu_name);
159
+ qemu_fdt_add_subnode(fdt, intc_name);
160
+ qemu_fdt_setprop_cell(fdt, intc_name, "phandle",
161
+ intc_phandles[cpu]);
162
+ qemu_fdt_setprop_string(fdt, intc_name, "compatible",
163
+ "riscv,cpu-intc");
164
+ qemu_fdt_setprop(fdt, intc_name, "interrupt-controller", NULL, 0);
165
+ qemu_fdt_setprop_cell(fdt, intc_name, "#interrupt-cells", 1);
166
+
167
+ core_name = g_strdup_printf("%s/core%d", clust_name, cpu);
168
+ qemu_fdt_add_subnode(fdt, core_name);
169
+ qemu_fdt_setprop_cell(fdt, core_name, "cpu", cpu_phandle);
170
+}
171
+
172
+void create_fdt_socket_cpus(void *fdt, RISCVCPU *socket_harts,
173
+ int socket_id, int num_harts_socket,
174
+ int socket_hartid_base, uint32_t *phandle,
175
+ uint32_t *intc_phandles, bool numa_enabled,
176
+ bool is_32_bit)
177
+{
178
+ g_autofree char *clust_name = NULL;
179
+
180
+ clust_name = g_strdup_printf("/cpus/cpu-map/cluster%d", socket_id);
181
+ qemu_fdt_add_subnode(fdt, clust_name);
182
+
183
+ for (int cpu = num_harts_socket - 1; cpu >= 0; cpu--) {
184
+ RISCVCPU *cpu_ptr = &socket_harts[cpu];
185
+
186
+ create_fdt_socket_cpu_internal(fdt, clust_name, cpu_ptr, cpu,
187
+ socket_id, socket_hartid_base,
188
+ phandle, intc_phandles, numa_enabled,
189
+ is_32_bit);
190
}
191
}