Page MenuHomeFreeBSD

D24912.1784990440.diff
No OneTemporary

Size
6 KB
Referenced Files
None
Subscribers
None

D24912.1784990440.diff

Index: sys/riscv/include/machdep.h
===================================================================
--- sys/riscv/include/machdep.h
+++ sys/riscv/include/machdep.h
@@ -42,12 +42,12 @@
vm_offset_t kern_phys; /* Kernel base (physical) addr */
vm_offset_t kern_stack;
vm_offset_t dtbp_virt; /* Device tree blob virtual addr */
+ vm_offset_t modulep; /* loader(8) metadata */
};
extern vm_paddr_t physmap[PHYS_AVAIL_ENTRIES];
extern u_int physmap_idx;
-vm_offset_t fake_preload_metadata(struct riscv_bootparams *rbp);
void initriscv(struct riscv_bootparams *);
#endif /* _MACHINE_MACHDEP_H_ */
Index: sys/riscv/riscv/genassym.c
===================================================================
--- sys/riscv/riscv/genassym.c
+++ sys/riscv/riscv/genassym.c
@@ -106,3 +106,4 @@
ASSYM(RISCV_BOOTPARAMS_KERN_STACK, offsetof(struct riscv_bootparams,
kern_stack));
ASSYM(RISCV_BOOTPARAMS_DTBP_VIRT, offsetof(struct riscv_bootparams, dtbp_virt));
+ASSYM(RISCV_BOOTPARAMS_MODULEP, offsetof(struct riscv_bootparams, modulep));
Index: sys/riscv/riscv/locore.S
===================================================================
--- sys/riscv/riscv/locore.S
+++ sys/riscv/riscv/locore.S
@@ -53,17 +53,20 @@
.text
.globl _start
_start:
+ /*
+ * Upon entry from FreeBSD's loader(8):
+ * a0 = modulep
+ * Upon entry from BBL/OpenSBI:
+ * a0 = hart id
+ * a1 = dtbp
+ */
+
/* Set the global pointer */
.option push
.option norelax
lla gp, __global_pointer$
.option pop
- /*
- * a0 = hart id
- * a1 = dtbp
- */
-
/* Pick a hart to run the boot process. */
lla t0, hart_lottery
li t1, 1
@@ -135,6 +138,13 @@
add t0, s1, a5
sd t6, (t0)
+ /*
+ * If a0 contains an address, then we booted from loader(8) and don't
+ * need to map the DTB.
+ */
+ li t2, KERNBASE
+ bgtu a0, t2, 3f
+
/* Create an L2 page superpage for DTB */
lla s1, pagetable_l2_devmap
mv s2, a1
@@ -154,6 +164,7 @@
/* Page tables END */
/* Setup supervisor trap vector */
+3:
lla t0, va
sub t0, t0, s9
li t1, KERNBASE
@@ -200,12 +211,25 @@
bltu s0, s1, 1b
#ifdef SMP
- /* Store boot hart id. */
+ /*
+ * Preset boot_hart to be invalid. If we booted via loader(8), then it
+ * must be retrieved later.
+ */
la t0, boot_hart
+ li t1, 0xffffffff
+ sw t1, 0(t0)
+
+ /* Check if a0 contains modulep (an address) */
+ li t2, KERNBASE
+ bgtu a0, t2, 2f
+
+ /* Otherwise, a0 contains the boot hart, and we can store it now */
sw a0, 0(t0)
+ mv a0, zero /* load zero for modulep */
#endif
/* Fill riscv_bootparams */
+2:
la t0, pagetable_l1
sd t0, RISCV_BOOTPARAMS_KERN_L1PT(sp)
sd s9, RISCV_BOOTPARAMS_KERN_PHYS(sp)
@@ -216,6 +240,8 @@
li t0, (VM_EARLY_DTB_ADDRESS)
sd t0, RISCV_BOOTPARAMS_DTBP_VIRT(sp)
+ sd a0, RISCV_BOOTPARAMS_MODULEP(sp)
+
mv a0, sp
call _C_LABEL(initriscv) /* Off we go */
call _C_LABEL(mi_startup)
Index: sys/riscv/riscv/machdep.c
===================================================================
--- sys/riscv/riscv/machdep.c
+++ sys/riscv/riscv/machdep.c
@@ -723,12 +723,11 @@
/*
* Fake up a boot descriptor table.
- * RISCVTODO: This needs to be done via loader (when it's available).
*/
-vm_offset_t
+static void
fake_preload_metadata(struct riscv_bootparams *rvbp)
{
- static uint32_t fake_preload[35];
+ static uint32_t fake_preload[48];
#ifdef DDB
vm_offset_t zstart = 0, zend = 0;
#endif
@@ -791,6 +790,14 @@
memmove((void *)lastaddr, (const void *)rvbp->dtbp_virt, dtb_size);
lastaddr = roundup(lastaddr + dtb_size, sizeof(int));
+ PRELOAD_PUSH_VALUE(uint32_t, MODINFO_METADATA | MODINFOMD_KERNEND);
+ PRELOAD_PUSH_VALUE(uint32_t, sizeof(vm_offset_t));
+ PRELOAD_PUSH_VALUE(vm_offset_t, lastaddr);
+
+ PRELOAD_PUSH_VALUE(uint32_t, MODINFO_METADATA | MODINFOMD_HOWTO);
+ PRELOAD_PUSH_VALUE(uint32_t, sizeof(int));
+ PRELOAD_PUSH_VALUE(int, RB_VERBOSE);
+
/* End marker */
PRELOAD_PUSH_VALUE(uint32_t, 0);
PRELOAD_PUSH_VALUE(uint32_t, 0);
@@ -798,7 +805,38 @@
KASSERT(fake_size < sizeof(fake_preload),
("Too many fake_preload items"));
+}
+static vm_offset_t
+parse_metadata(void)
+{
+ caddr_t kmdp;
+ vm_offset_t lastaddr;
+#ifdef DDB
+ vm_offset_t ksym_start, ksym_end;
+#endif
+ char *kern_envp;
+
+ /* Find the kernel address */
+ kmdp = preload_search_by_type("elf kernel");
+ if (kmdp == NULL)
+ kmdp = preload_search_by_type("elf64 kernel");
+ KASSERT(kmdp != NULL, ("No preload metadata found!"));
+
+ /* Read the boot metadata */
+ boothowto = MD_FETCH(kmdp, MODINFOMD_HOWTO, int);
+ lastaddr = MD_FETCH(kmdp, MODINFOMD_KERNEND, vm_offset_t);
+ kern_envp = MD_FETCH(kmdp, MODINFOMD_ENVP, char *);
+ if (kern_envp != NULL)
+ init_static_kenv(kern_envp, 0);
+#ifdef DDB
+ ksym_start = MD_FETCH(kmdp, MODINFOMD_SSYM, uintptr_t);
+ ksym_end = MD_FETCH(kmdp, MODINFOMD_ESYM, uintptr_t);
+ db_fetch_ksymtab(ksym_start, ksym_end);
+#endif
+#ifdef FDT
+ try_load_dtb(kmdp);
+#endif
return (lastaddr);
}
@@ -810,14 +848,16 @@
int mem_regions_sz;
vm_offset_t lastaddr;
vm_size_t kernlen;
- caddr_t kmdp;
+#ifdef FDT
+ phandle_t chosen;
+ uint32_t hart;
+#endif
TSRAW(&thread0, TS_ENTER, __func__, NULL);
/* Set the pcpu data, this is needed by pmap_bootstrap */
pcpup = &__pcpu[0];
pcpu_init(pcpup, 0, sizeof(struct pcpu));
- pcpup->pc_hart = boot_hart;
/* Set the pcpu pointer */
__asm __volatile("mv tp, %0" :: "r"(pcpup));
@@ -827,22 +867,31 @@
/* Initialize SBI interface. */
sbi_init();
- /* Set the module data location */
- lastaddr = fake_preload_metadata(rvbp);
-
- /* Find the kernel address */
- kmdp = preload_search_by_type("elf kernel");
- if (kmdp == NULL)
- kmdp = preload_search_by_type("elf64 kernel");
-
- boothowto = RB_VERBOSE | RB_SINGLE;
- boothowto = RB_VERBOSE;
-
- kern_envp = NULL;
+ /* Parse the boot metadata. */
+ if (rvbp->modulep != 0) {
+ preload_metadata = (caddr_t)rvbp->modulep;
+ } else {
+ fake_preload_metadata(rvbp);
+ }
+ lastaddr = parse_metadata();
#ifdef FDT
- try_load_dtb(kmdp);
+ /*
+ * Get the boot hart ID. This was either passed in directly from the
+ * SBI firmware and handled by locore, or was stored in the device tree
+ * by an earlier boot stage.
+ */
+ chosen = OF_finddevice("/chosen");
+ if (OF_getencprop(chosen, "boot-hartid", &hart, sizeof(hart)) != -1) {
+ boot_hart = (u_long)hart;
+ }
+#endif
+ if (boot_hart == 0xffffffff) {
+ panic("Boot hart ID was not properly set");
+ }
+ pcpup->pc_hart = boot_hart;
+#ifdef FDT
/*
* Exclude reserved memory specified by the device tree. Typically,
* this contains an entry for memory used by the runtime SBI firmware.

File Metadata

Mime Type
text/plain
Expires
Sat, Jul 25, 2:40 PM (10 h, 23 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
29256592
Default Alt Text
D24912.1784990440.diff (6 KB)

Event Timeline