From: Waldemar Kozaczuk <[email protected]> Committer: Waldemar Kozaczuk <[email protected]> Branch: master
arm on firecracker: detect and enable mmio isa early console This patch adds logic to detect memory-mapped serial console configuration in DTB tree and enable it when running OSv on arm version of firecracker. Signed-off-by: Waldemar Kozaczuk <[email protected]> --- diff --git a/arch/aarch64/arch-dtb.cc b/arch/aarch64/arch-dtb.cc --- a/arch/aarch64/arch-dtb.cc +++ b/arch/aarch64/arch-dtb.cc @@ -189,6 +189,36 @@ u64 dtb_get_uart(int *irqid) return retval; } +u64 dtb_get_mmio_serial_console(int *irqid) +{ + int node; + struct dtb_int_spec int_spec[1]; + u64 address; + + if (!dtb) + return 0; + + node = fdt_node_offset_by_compatible(dtb, -1, "ns16550a"); + if (node < 0) + return 0; + + const char *node_name = fdt_get_name(dtb, node, NULL); + if (!node_name) { + return 0; + } + + if (sscanf(node_name,"uart@%x", &address) != 1) { + return 0; + } + + if( !dtb_get_int_spec(node, int_spec, 1)) { + return 0; + }; + + *irqid = int_spec[0].irq_id; + return address; +} + /* this gets the virtual timer irq, we are not interested * about the other timers. */ diff --git a/arch/aarch64/arch-dtb.hh b/arch/aarch64/arch-dtb.hh --- a/arch/aarch64/arch-dtb.hh +++ b/arch/aarch64/arch-dtb.hh @@ -49,6 +49,14 @@ size_t dtb_get_phys_memory(u64 *addr); */ u64 dtb_get_uart(int *irqid); +/* u64 dtb_get_mmio_serial_console(int *irqid) + * + * return the base address of the serial console and writes the + * irqid of the interrupt to irqid, + * or returns zero on failure. + */ +u64 dtb_get_mmio_serial_console(int *irqid); + /* int gdb_get_timer_irq() * * returns the irqid of the virtual timer from the dtb, diff --git a/arch/aarch64/arch-setup.cc b/arch/aarch64/arch-setup.cc --- a/arch/aarch64/arch-setup.cc +++ b/arch/aarch64/arch-setup.cc @@ -25,6 +25,7 @@ #include "drivers/pl011.hh" #include "early-console.hh" #include <osv/pci.hh> +#include "drivers/mmio-isa-serial.hh" #include <alloca.h> @@ -47,8 +48,9 @@ void arch_setup_pci() /* linear_map [TTBR0 - PCI config space] */ u64 pci_cfg; size_t pci_cfg_len; - if (!dtb_get_pci_cfg(&pci_cfg, &pci_cfg_len)) - return; + if (!dtb_get_pci_cfg(&pci_cfg, &pci_cfg_len)) { + return; + } pci::set_pci_cfg(pci_cfg, pci_cfg_len); pci_cfg = pci::get_pci_cfg(&pci_cfg_len); @@ -91,7 +93,7 @@ void arch_setup_free_memory() mmu::linear_map((void *)mmu::mem_addr, (mmu::phys)mmu::mem_addr, addr - mmu::mem_addr); - if (!is_xen()) { + if (console::PL011_Console::active) { /* linear_map [TTBR0 - UART] */ addr = (mmu::phys)console::aarch64_console.pl011.get_base_addr(); mmu::linear_map((void *)addr, addr, 0x1000, mmu::page_size, @@ -116,6 +118,8 @@ void arch_setup_free_memory() osv::parse_cmdline(cmdline); mmu::switch_to_runtime_page_tables(); + + console::mmio_isa_serial_console::memory_map(); } void arch_setup_tls(void *tls, const elf::tls_data& info) @@ -179,15 +183,28 @@ void arch_init_drivers() void arch_init_early_console() { + console::mmio_isa_serial_console::_phys_mmio_address = 0; + if (is_xen()) { new (&console::aarch64_console.xen) console::XEN_Console(); console::arch_early_console = console::aarch64_console.xen; return; } + int irqid; + u64 mmio_serial_address = dtb_get_mmio_serial_console(&irqid); + if (mmio_serial_address) { + console::mmio_isa_serial_console::early_init(mmio_serial_address); + + new (&console::aarch64_console.isa_serial) console::mmio_isa_serial_console(); + console::aarch64_console.isa_serial.set_irqid(irqid); + console::arch_early_console = console::aarch64_console.isa_serial; + return; + } + new (&console::aarch64_console.pl011) console::PL011_Console(); console::arch_early_console = console::aarch64_console.pl011; - int irqid; + console::PL011_Console::active = true; u64 addr = dtb_get_uart(&irqid); if (!addr) { /* keep using default addresses */ diff --git a/arch/aarch64/early-console.hh b/arch/aarch64/early-console.hh --- a/arch/aarch64/early-console.hh +++ b/arch/aarch64/early-console.hh @@ -11,12 +11,15 @@ #include <drivers/console-driver.hh> #include <drivers/pl011.hh> #include <drivers/xenconsole.hh> +#include <drivers/mmio-isa-serial.hh> + namespace console { union AARCH64_Console { PL011_Console pl011; XEN_Console xen; + mmio_isa_serial_console isa_serial; AARCH64_Console() {}; /* placement new is used to initialize object */ ~AARCH64_Console() {}; /* won't ever be called */ diff --git a/drivers/pl011.cc b/drivers/pl011.cc --- a/drivers/pl011.cc +++ b/drivers/pl011.cc @@ -25,6 +25,8 @@ enum { UARTICR = 0x044 }; +bool PL011_Console::active = false; + void PL011_Console::set_base_addr(u64 addr) { uart = (char *)addr; diff --git a/drivers/pl011.hh b/drivers/pl011.hh --- a/drivers/pl011.hh +++ b/drivers/pl011.hh @@ -25,6 +25,7 @@ public: u64 get_base_addr(); void set_irqid(int irqid); + static bool active; private: virtual void dev_start(); virtual const char *thread_name() { return "pl011-input"; } -- You received this message because you are subscribed to the Google Groups "OSv Development" group. To unsubscribe from this group and stop receiving emails from it, send an email to [email protected]. To view this discussion on the web visit https://groups.google.com/d/msgid/osv-dev/000000000000ee60c505a9128a9b%40google.com.
