Hi Daniel, On 5/1/25 17:14, Daniel Palmer wrote:
Short version: I want to start converting m68k (including nommu) to use DT for booting so I can add few cool boards I have (e.g. dual 040/060 VME board..). I need ideas, help etc. Maybe if someone converted an m68k machine they are using to DT alongside me this would have some hope of actually happening?
I have been thinking about this for a while for the ColdFire targets. In a few cases the drivers its uses are already devicetree enabled, since they are used on some of the NXP/Freescale ARM SoC devices. So this is interesting work to me.
All of my WIP in-progress very messy code etc is here: https://github.com/fifteenhex/m68kjunk Longer version: As of today I have: - Modern (2024.07) u-boot fork that works on 000/030/040 real hardware/QEMU that supports booting a Linux ELF image. For nommu a FDT blob address is passed via a regiser, for mmu the normal bootinfo is created and the FDT is passed via a bootinfo tag. nommu never used bootinfo and doesn't need to. - A Linux branch for nommu that removes most of the current DragonBall code, makes it into a devicetree based machine and adds a bunch of drivers etc. This works in a fork of QEMU I have and on the real hardware. The DragonBall even has a working 1bpp framebuffer. The nommu branch also works on 010 and better. - A Linux branch for mmu that uses the crappy patches in this series and some other bits to start moving the MVME147 board over to using DT. - A buildroot fork that can build a 000 nommu userland etc. A patch to add support for building for 030 is already in buildroot, I plan to send one for 060 later. - A bunch of DragonBall machines, an MVME147 030 machine, an Eltec E27 dual socket VME board with one 040 at the moment but I have 060s to go in it once I work out the need jumper changes, some other 060 VME boards, Amigas... What I'm thinking: - We initially add passing of an FDT via bootinfo for mmu - Add support for a generic machine that can boot almost anything so I can bring up my new (to Linux) machines. - I will migrate MVME147 to device tree. - Some like minded person migrates a machine they have to device tree. :) - Maybe embed a FDT for machines that'll never get a bootloader that supports this and use the machine type to select the embedded FDT and move all of that stuff over without needing to mess with bootloaders.
To that end that is what I have been playing with. Doing it in a similar way to what MIPS does. Example patch attached of what I did for non-MMU ColdFire. So no boot loader support required. Regards Greg
diff --git a/arch/m68k/Kconfig b/arch/m68k/Kconfig index 7c4f7bcc89d7..a4949b69e1dc 100644 --- a/arch/m68k/Kconfig +++ b/arch/m68k/Kconfig @@ -39,6 +39,8 @@ config M68K select OLD_SIGSUSPEND3 select UACCESS_MEMCPY if !MMU select ZONE_DMA + select OF if COLDFIRE + select OF_EARLY_FLATTREE if COLDFIRE config CPU_BIG_ENDIAN def_bool y diff --git a/arch/m68k/Kconfig.devices b/arch/m68k/Kconfig.devices index e6e3efac1840..ea0bce4db639 100644 --- a/arch/m68k/Kconfig.devices +++ b/arch/m68k/Kconfig.devices @@ -144,3 +144,14 @@ config SERIAL_CONSOLE endmenu endif + +config EMBEDDED_DTB + bool "Embedded devicetree ELF section" + help + If there is no capability for the boot loader to specify a + devicetree (DTB) then this option allows for it to be embedded + within the linux binary itself. Typically you can do this with + something like this: + + objcopy --update-section .embedded_dtb=<filename>.dtb vmlinux + diff --git a/arch/m68k/coldfire/head.S b/arch/m68k/coldfire/head.S index c6d7fd28c602..88fd8b5b3bda 100644 --- a/arch/m68k/coldfire/head.S +++ b/arch/m68k/coldfire/head.S @@ -133,6 +133,15 @@ _init_sp: .long 0 #endif +#ifdef CONFIG_EMBEDDED_DTB +/* + * If embedding a DTB in the kernel ELF binary then create a place holder + * for that section. It will be inserted after the final kernel build/link. + */ +.section ".embedded_dtb","aw" +.long 0 +#endif + /*****************************************************************************/ __HEAD diff --git a/arch/m68k/kernel/setup_no.c b/arch/m68k/kernel/setup_no.c index c926da9d5ec2..d1d79c41c6f0 100644 --- a/arch/m68k/kernel/setup_no.c +++ b/arch/m68k/kernel/setup_no.c @@ -33,6 +33,8 @@ #include <linux/initrd.h> #include <linux/root_dev.h> #include <linux/rtc.h> +#include <linux/of.h> +#include <linux/of_fdt.h> #include <asm/setup.h> #include <asm/bootinfo.h> @@ -70,6 +72,31 @@ void (*mach_halt)(void); #define CPU_NAME "UNKNOWN" #endif +#ifdef CONFIG_EMBEDDED_DTB +static void __init m68k_setup_fdt(void) +{ + extern void *embedded_dtb; + phys_addr_t fdt = (phys_addr_t) &embedded_dtb; + + pr_info("m68k generic DT machine support, FDT blob at 0x%08x\n", fdt); + if (!early_init_dt_verify(__va(fdt), fdt)) { + pr_err("FDT blob is bad?!\n"); + return; + } + early_init_dt_scan_nodes(); +} + +static void __init m68k_dtb_model(void) +{ + const char *model; + model = of_flat_dt_get_machine_name(); + if (model) + pr_info("DTB reports model = %s\n", model); + else + pr_warn("DTB has no model type?\n"); +} +#endif /* CONFIG_EMBEDDED_DTB */ + /* * Different cores have different instruction execution timings. * The old/traditional 68000 cores are basically all the same, at 16. @@ -166,6 +193,11 @@ void __init setup_arch(char **cmdline_p) * Get kmalloc into gear. */ paging_init(); + +#ifdef CONFIG_EMBEDDED_DTB + m68k_setup_fdt(); + m68k_dtb_model(); +#endif } /* diff --git a/arch/m68k/kernel/vmlinux-nommu.lds b/arch/m68k/kernel/vmlinux-nommu.lds index 2624fc18c131..1be3bfe31ba4 100644 --- a/arch/m68k/kernel/vmlinux-nommu.lds +++ b/arch/m68k/kernel/vmlinux-nommu.lds @@ -70,6 +70,15 @@ SECTIONS { INIT_TEXT_SECTION(PAGE_SIZE) INIT_DATA_SECTION(16) PERCPU_SECTION(16) + +#ifdef CONFIG_EMBEDDED_DTB + STRUCT_ALIGN(); + .embedded_dtb : { + embedded_dtb = .; + *(.embedded_dtb) + KEEP(*(.embedded_dtb)) + } +#endif .m68k_fixup : { __start_fixup = .; *(.m68k_fixup)