bonzini / qboot Goto Github PK
View Code? Open in Web Editor NEWMinimal x86 firmware for booting Linux kernels
License: GNU General Public License v2.0
Minimal x86 firmware for booting Linux kernels
License: GNU General Public License v2.0
A simple x86 firmware that can boot Linux. Most of QEMU's startup time is spent: * in the dynamic linker. This can be reduced by 150 ms simply by compiling a stripped down QEMU: ./configure --disable-libssh2 --disable-tcmalloc --disable-glusterfs \ --disable-seccomp --disable-{bzip2,snappy,lzo} --disable-usb-redir \ --disable-libusb --disable-smartcard-nss --disable-libnfs \ --disable-libiscsi --disable-rbd --disable-spice --disable-attr \ --disable-cap-ng --disable-linux-aio --disable-brlapi \ --disable-vnc-{jpeg,tls,sasl,png,ws} --disable-rdma --disable-bluez \ --disable-fdt --disable-curl --disable-curses --disable-sdl \ --disable-gtk --disable-tpm --disable-vte --disable-vnc \ --disable-xen --disable-opengl --target-list=x86_64-softmmu * in the BIOS. qboot saves another 150 ms. * until QEMU 2.7+, in fw_cfg. qboot uses the DMA interface which is pretty much instantaneous. Compile qboot ============= Clone the source: $ git clone https://github.com/bonzini/qboot.git Compile the qboot firmware (you may need to install the relevant build time dependancies): $ meson build && ninja -C build The result will be a 64K file named bios.bin under the build/ directory. Usage ===== $ qemu-kvm -bios bios.bin \ -kernel /boot/vmlinuz-4.0.3-300.fc22.x86_64 \ -serial mon:stdio -append 'console=ttyS0,115200,8n1' TODO ==== * Add the possibility to configure out PIC and PCI bridge initialization
Without the qboot bios I get correct BARs:
sudo qemu-system-x86_64 --enable-kvm --cpu host -kernel IRCd -m 64 -nographic -netdev tap,id=net0,script=../IncludeOS/etc/to-be-installed/qemu-ifup -device virtio-net,netdev=net0,mac=c0:01:0a:00:00:2a
...
[ Virtio ] Attaching to PCI addr 0x18
[x] Vendor ID is VIRTIO
[x] Device ID 0x1000 is in a valid range (Virtio LEGACY)
[x] Device Revision ID (0x0) supported
[ Resource @ BAR 0 ]
Address: 0xc000 Size: 0x20
Type: IO Resource
[ Resource @ BAR 1 ]
Address: 0xfebd1000 Size: 0x1000
Type: Memory Resource
[ Resource @ BAR 4 ]
Address: 0xfe000000 Size: 0x800000
Type: Memory Resource
...
With qboot BIOS (only happens on this particular service, not on another):
sudo qemu-system-x86_64 --enable-kvm --cpu host -bios bios.bin -kernel IRCd -m 64 -nographic -netdev tap,id=net0,script=../IncludeOS/etc/to-be-installed/qemu-ifup -device virtio-net,netdev=net0,mac=c0:01:0a:00:00:2a
[ Resource @ BAR 0 ]
Address: 0x0 Size: 0x20
Type: IO Resource
[ Resource @ BAR 4 ]
Address: 0x0 Size: 0x800000
Type: Memory Resource
Both addresses are zero
The objcopy -Obinary
is leaving a relocation section which makes the resultant binary 66696 bytes long. readelf -a
reports:
Section Headers:
[Nr] Name Type Addr Off Size ES Flg Lk Inf Al
...
[13] .rel.dyn REL 00100000 007000 000488 08 A 5 0 4
Hello,
Do we need to hack qemu code to establish the startup is 40ms? Is there any profiling option in qemu to measure the qemu guest startup time?
This is not an issue, but could not find a good place to ask this question.
Is this project still maintained? I would have post a message to proper emailing list but could not locate one.
I have also come across the NEMU project that mentions using qboot. Will qboot be eventually integrated into NEMU?
I noticed there is still an open issue that prevents it from compiling thought it is easily fixable by applying proper changes to makefile.
Also I have been trying to use qboot to speedup boot on OSv unikernel on QEMU with qboot. I am encountering some PCI related issues that prevent me booting OSv with virtio-block or virtio-net devices. I only managed to boot OSv with ramfs with following setup:
qemu-system-x86_64 -m 2G -smp 1 -nographic
-bios ../qboot/bios.bin
-kernel kernel.elf
-enable-kvm -cpu host,+x2apic
-append "--console=serial /hello"
-gdb tcp::1234,server,nowait
-chardev stdio,mux=on,id=stdio,signal=off
-mon chardev=stdio,mode=readline
-device isa-serial,chardev=stdio
Once I add either block or networking device OSv fails to find the bar with index 2:
-device virtio-blk-pci,id=blk0,drive=hd0,scsi=off
-drive file=usr.img,if=none,id=hd0,cache=none,aio=threads
Hi may I ask a question, can qboot
be used on x86 machine directly, I feel like cannot, because there is a function fw_cfg_setup
and this function calls some qemu features.
And could someone explain what's the fw_cfg_setup
used for?
Should avoid unnecessary transition back into 16b mode and generally make execution time faster.
Some of the options have gone away. This worked for me:
/configure \
--disable-libssh2 \
--disable-tcmalloc \
--disable-glusterfs \
--disable-seccomp \
--disable-{bzip2,snappy,lzo} \
--disable-usb-redir \
--disable-libusb \
--disable-libnfs \
--disable-libiscsi \
--disable-rbd \
--disable-spice \
--disable-attr \
--disable-cap-ng \
--disable-linux-aio \
--disable-uuid \
--disable-brlapi \
--disable-vnc-{jpeg,sasl,png} \
--disable-rdma \
--disable-bluez \
--disable-fdt \
--disable-curl \
--disable-curses \
--disable-sdl \
--disable-gtk \
--disable-tpm \
--disable-vte \
--disable-vnc \
--disable-xen \
--disable-opengl \
--target-list=x86_64-softmmu
It does complain that --disable-uuid
is no longer effective.
I'm getting this error:
cc -O2 -g -MMD -MF .deps/cc-.-main.d -Wall -m32 -march=i386 -mregparm=3 -fno-stack-protector -fno-delete-null-pointer-checks -ffreestanding -Iinclude -c -s main.c -o main.o
main.c: In function 'main':
include/ioport.h:11: error: inconsistent operand constraints in an 'asm'
include/ioport.h:11: error: inconsistent operand constraints in an 'asm'
include/ioport.h:11: error: inconsistent operand constraints in an 'asm'
make: *** [main.o] Error 1
I'm using GCC 4.2.1.
% meson build
The Meson build system
Version: 0.45.1
Source dir: /home/hudson/build/clean-qboot
Build dir: /home/hudson/build/clean-qboot/build
Build type: native build
Project name: qboot
Native C compiler: ccache cc (gcc 7.5.0 "cc (Ubuntu 7.5.0-3ubuntu1~18.04) 7.5.0")
Build machine cpu family: x86_64
Build machine cpu: x86_64
Program objcopy found: YES (/usr/bin/objcopy)
meson.build:19:0: ERROR: Unknown method "get_supported_link_arguments" in object.
A full log can be found at /home/hudson/clean-qboot/build/meson-logs/meson-log.txt
I would like to point out that identifiers like "_IOPORT_H
" and "_PCI_H
" do not fit to the expected naming convention of the C language standard.
Would you like to adjust your selection for unique names?
missing a table?
main.o: In function main': /home/me/Desktop/code/qboot/main.c:82: undefined reference to
GLOBAL_OFFSET_TABLE'
code16.o: In function e820_query_map': /home/me/Desktop/code/qboot/code16.c:45: undefined reference to
GLOBAL_OFFSET_TABLE'
printf.o: In function print_str': /home/me/Desktop/code/qboot/printf.c:36: undefined reference to
GLOBAL_OFFSET_TABLE'
printf.o: In function print_int': /home/me/Desktop/code/qboot/printf.c:64: undefined reference to
GLOBAL_OFFSET_TABLE'
printf.o: In function print_unsigned': /home/me/Desktop/code/qboot/printf.c:99: undefined reference to
GLOBAL_OFFSET_TABLE'
printf.o:/home/me/Desktop/code/qboot/printf.c:141: more undefined references to `GLOBAL_OFFSET_TABLE' follow
When I tried to follow the commands in the readme to use cbfs, I get the following error
qemu-system-x86_64: -drive if=pflash,file=cbfs.rom,readonly=on: oversized backing file, pflash segments cannot be mapped under 00000000ff800000
I really like this idea of custom simpler BIOS!
However, when running it with my 1.4mb IRCd image, I just get:
qemu-system-x86_64 --enable-kvm -kernel IRCd -device virtio-net,netdev=net0,mac=c0:01:0a:00:00:2a -netdev tap,id=net0,script=/home/gonzo/IncludeOS_install/etc/qemu-ifup -nographic -smp 1,sockets=1,cores=1,threads=1 -m 128 -cpu host -k en-us -realtime mlock=off -rtc base=utc,driftfix=slew -global kvm-pit.lost_tick_policy=discard -no-hpet -bios bios.bin
dma: command 8 not supported
The image is 32-bit. That might be the reason?
My IRC server repo is here: https://github.com/fwsGonzo/IRCd
For convenience here are the images:
http://fwsnet.net/kernels/IRCd http://fwsnet.net/kernels/IRCd.img (with #bootloader)
The image I posted don't have any DMA code at all. 0x8 is DMA write, I think. We have a bootloader we can attach (second image) which loads the kernel with PIO.
To build on Fedora the glibc-devel.i686
package was required to provide <gnu/stubs-32.h>
.
Booting a minimal kernel config with qboot and an attached virtio drive causes a kernel hang somewhere in the startup. This was run as:
qemu-3.0.0/x86_64-softmmu/qemu-system-x86_64 \
--machine pc \
--drive file=disk.img,format=raw,if=virtio \
--device virtio-net,netdev=net0 \
--kernel vmlinux-tiny \
--initrd initrd-tiny \
--bios qboot/bios.bin \
The problem appears with qemu-2.7 and with accel=kvm
as well.
The dmesg
output compared to SeaBIOS looks like an interrupt or PCI configuration issue:
--- seabios.txt 2018-10-31 18:09:07.935999826 -0400
+++ qboot.txt 2018-10-31 18:09:11.991999825 -0400
@@ -4,60 +4,52 @@
e820: BIOS-provided physical RAM map:
BIOS-e820: [mem 0x0000000000000000-0x000000000009fbff] usable
BIOS-e820: [mem 0x000000000009fc00-0x000000000009ffff] reserved
+ BIOS-e820: [mem 0x00000000000d0000-0x00000000000effff] ACPI NVS
BIOS-e820: [mem 0x00000000000f0000-0x00000000000fffff] reserved
- BIOS-e820: [mem 0x0000000000100000-0x0000000007fddfff] usable
- BIOS-e820: [mem 0x0000000007fde000-0x0000000007ffffff] reserved
- BIOS-e820: [mem 0x00000000fffc0000-0x00000000ffffffff] reserved
+ BIOS-e820: [mem 0x0000000000100000-0x0000000007ffffff] usable
bootconsole [earlyser0] enabled
NX (Execute Disable) protection: active
tsc: Fast TSC calibration using PIT
e820: update [mem 0x00000000-0x00000fff] usable ==> reserved
e820: remove [mem 0x000a0000-0x000fffff] usable
- e820: last_pfn = 0x7fde max_arch_pfn = 0x400000000
+ e820: last_pfn = 0x8000 max_arch_pfn = 0x400000000
x86/PAT: Configuration [0-7]: WB WT UC- UC WB WT UC- UC
- found SMP MP-table at [mem 0x000f5930-0x000f593f] mapped at [ffffffffff200930]
Base memory trampoline at [ffff880000099000] 99000 size 24576
BRK [0x01b2e000, 0x01b2efff] PGTABLE
BRK [0x01b2f000, 0x01b2ffff] PGTABLE
BRK [0x01b30000, 0x01b30fff] PGTABLE
- BRK [0x01b31000, 0x01b31fff] PGTABLE
- RAMDISK: [mem 0x07a92000-0x07fcffff]
+ RAMDISK: [mem 0x07ac2000-0x07ffffff]
Zone ranges:
- DMA32 [mem 0x0000000000001000-0x0000000007fddfff]
+ DMA32 [mem 0x0000000000001000-0x0000000007ffffff]
Normal empty
Movable zone start for each node
Early memory node ranges
node 0: [mem 0x0000000000001000-0x000000000009efff]
- node 0: [mem 0x0000000000100000-0x0000000007fddfff]
- Initmem setup node 0 [mem 0x0000000000001000-0x0000000007fddfff]
- On node 0 totalpages: 32636
+ node 0: [mem 0x0000000000100000-0x0000000007ffffff]
+ Initmem setup node 0 [mem 0x0000000000001000-0x0000000007ffffff]
+ On node 0 totalpages: 32670
DMA32 zone: 448 pages used for memmap
DMA32 zone: 21 pages reserved
- DMA32 zone: 32636 pages, LIFO batch:7
- Intel MultiProcessor Specification v1.4
- MPTABLE: OEM ID: BOCHSCPU
- MPTABLE: Product ID: 0.1
- MPTABLE: APIC at: 0xFEE00000
- Processor #0 (Bootup-CPU)
- IOAPIC[0]: apic_id 0, version 32, address 0xfec00000, GSI 0-23
- Processors: 1
- e820: [mem 0x08000000-0xfffbffff] available for PCI devices
+ DMA32 zone: 32670 pages, LIFO batch:7
+ e820: [mem 0x08000000-0xffffffff] available for PCI devices
clocksource: refined-jiffies: mask: 0xffffffff max_cycles: 0xffffffff, max_idle_ns: 19112604462750000 ns
random: get_random_bytes called from 0xffffffff81a69a17 with crng_init=0
pcpu-alloc: s0 r0 d32768 u32768 alloc=1*32768
pcpu-alloc: [0] 0
- Built 1 zonelists, mobility grouping on. Total pages: 32167
+ Built 1 zonelists, mobility grouping on. Total pages: 32201
Kernel command line: console=ttyS0,57600 earlyprintk=ttyS0 console=ttyS0 debug
PID hash table entries: 512 (order: 0, 4096 bytes)
Dentry cache hash table entries: 16384 (order: 5, 131072 bytes)
Inode-cache hash table entries: 8192 (order: 4, 65536 bytes)
- Memory: 111292K/130544K available (6152K kernel code, 413K rwdata, 456K rodata, 516K init, 272K bss, 19252K reserved, 0K cma-reserved)
- NR_IRQS: 4352, nr_irqs: 48, preallocated irqs: 16
+ Memory: 111424K/130680K available (6152K kernel code, 413K rwdata, 456K rodata, 516K init, 272K bss, 19256K reserved, 0K cma-reserved)
+ NR_IRQS: 4352, nr_irqs: 24, preallocated irqs: 16
console [ttyS0] enabled
+ console [ttyS0] enabled
+ bootconsole [earlyser0] disabled
bootconsole [earlyser0] disabled
tsc: Fast TSC calibration using PIT
- tsc: Detected 2807.907 MHz processor
- Calibrating delay loop (skipped), value calculated using timer frequency.. 5615.81 BogoMIPS (lpj=28079070)
+ tsc: Detected 2807.903 MHz processor
+ Calibrating delay loop (skipped), value calculated using timer frequency.. 5615.80 BogoMIPS (lpj=28079030)
pid_max: default: 4096 minimum: 301
Mount-cache hash table entries: 512 (order: 0, 4096 bytes)
Mountpoint-cache hash table entries: 512 (order: 0, 4096 bytes)
@@ -67,7 +59,7 @@
Spectre V2 : Spectre mitigation: kernel not compiled with retpoline; no mitigation available!
Speculative Store Bypass: Vulnerable
Performance Events: PMU not available due to virtualization, using software events only.
- ..TIMER: vector=0x30 apic1=0 pin1=2 apic2=-1 pin2=-1
+ Not enabling interrupt remapping due to skipped IO-APIC setup
devtmpfs: initialized
clocksource: jiffies: mask: 0xffffffff max_cycles: 0xffffffff, max_idle_ns: 19112604462750000 ns
futex hash table entries: 16 (order: -4, 384 bytes)
@@ -87,7 +79,7 @@
pci 0000:00:00.0: [8086:1237] type 00 class 0x060000
pci 0000:00:01.0: [8086:7000] type 00 class 0x060100
pci 0000:00:01.1: [8086:7010] type 00 class 0x010180
- pci 0000:00:01.1: reg 0x20: [io 0xc060-0xc06f]
+ pci 0000:00:01.1: reg 0x20: [io 0x0000-0x000f]
pci 0000:00:01.1: legacy IDE quirk: reg 0x10: [io 0x01f0-0x01f7]
pci 0000:00:01.1: legacy IDE quirk: reg 0x14: [io 0x03f6]
pci 0000:00:01.1: legacy IDE quirk: reg 0x18: [io 0x0170-0x0177]
@@ -96,26 +88,34 @@
pci 0000:00:01.3: quirk: [io 0x0600-0x063f] claimed by PIIX4 ACPI
pci 0000:00:01.3: quirk: [io 0x0700-0x070f] claimed by PIIX4 SMB
pci 0000:00:02.0: [1234:1111] type 00 class 0x030000
- pci 0000:00:02.0: reg 0x10: [mem 0xfd000000-0xfdffffff pref]
- pci 0000:00:02.0: reg 0x18: [mem 0xfebd0000-0xfebd0fff]
- pci 0000:00:02.0: reg 0x30: [mem 0xfebc0000-0xfebcffff pref]
- pci 0000:00:02.0: vgaarb: setting as boot VGA device
- pci 0000:00:02.0: vgaarb: VGA device added: decodes=io+mem,owns=io+mem,locks=none
+ pci 0000:00:02.0: reg 0x10: [mem 0x00000000-0x00ffffff pref]
+ pci 0000:00:02.0: reg 0x18: [mem 0x00000000-0x00000fff]
+ pci 0000:00:02.0: reg 0x30: [mem 0x00000000-0x0000ffff pref]
+ pci 0000:00:02.0: vgaarb: VGA device added: decodes=io+mem,owns=none,locks=none
pci 0000:00:03.0: [1af4:1000] type 00 class 0x020000
- pci 0000:00:03.0: reg 0x10: [io 0xc040-0xc05f]
- pci 0000:00:03.0: reg 0x14: [mem 0xfebd1000-0xfebd1fff]
- pci 0000:00:03.0: reg 0x20: [mem 0xfe000000-0xfe003fff 64bit pref]
- pci 0000:00:03.0: reg 0x30: [mem 0xfeb80000-0xfebbffff pref]
+ pci 0000:00:03.0: reg 0x10: [io 0x0000-0x001f]
+ pci 0000:00:03.0: reg 0x14: [mem 0x00000000-0x00000fff]
+ pci 0000:00:03.0: reg 0x20: [mem 0x00000000-0x00003fff 64bit pref]
+ pci 0000:00:03.0: reg 0x30: [mem 0x00000000-0x0003ffff pref]
pci 0000:00:04.0: [1af4:1001] type 00 class 0x010000
- pci 0000:00:04.0: reg 0x10: [io 0xc000-0xc03f]
- pci 0000:00:04.0: reg 0x14: [mem 0xfebd2000-0xfebd2fff]
- pci 0000:00:04.0: reg 0x20: [mem 0xfe004000-0xfe007fff 64bit pref]
+ pci 0000:00:04.0: reg 0x10: [io 0x0000-0x003f]
+ pci 0000:00:04.0: reg 0x14: [mem 0x00000000-0x00000fff]
+ pci 0000:00:04.0: reg 0x20: [mem 0x00000000-0x00003fff 64bit pref]
pci_bus 0000:00: busn_res: [bus 00-ff] end is updated to 00
- pci 0000:00:01.0: PIIX/ICH IRQ router [8086:7000]
PCI: pci_cache_line_size set to 64 bytes
e820: reserve RAM buffer [mem 0x0009fc00-0x0009ffff]
- e820: reserve RAM buffer [mem 0x07fde000-0x07ffffff]
clocksource: Switched to clocksource refined-jiffies
+ pci 0000:00:02.0: BAR 0: assigned [mem 0x08000000-0x08ffffff pref]
+ pci 0000:00:03.0: BAR 6: assigned [mem 0x09000000-0x0903ffff pref]
+ pci 0000:00:02.0: BAR 6: assigned [mem 0x09040000-0x0904ffff pref]
+ pci 0000:00:03.0: BAR 4: assigned [mem 0x100000000-0x100003fff 64bit pref]
+ pci 0000:00:04.0: BAR 4: assigned [mem 0x100004000-0x100007fff 64bit pref]
+ pci 0000:00:02.0: BAR 2: assigned [mem 0x09050000-0x09050fff]
+ pci 0000:00:03.0: BAR 1: assigned [mem 0x09051000-0x09051fff]
+ pci 0000:00:04.0: BAR 1: assigned [mem 0x09052000-0x09052fff]
+ pci 0000:00:04.0: BAR 0: assigned [io 0x1000-0x103f]
+ pci 0000:00:03.0: BAR 0: assigned [io 0x1040-0x105f]
+ pci 0000:00:01.1: BAR 4: assigned [io 0x1060-0x106f]
pci_bus 0000:00: resource 4 [io 0x0000-0xffff]
pci_bus 0000:00: resource 5 [mem 0x00000000-0xffffffffff]
NET: Registered protocol family 2
@@ -128,7 +128,6 @@
pci 0000:00:00.0: Limiting direct PCI/PCI transfers
pci 0000:00:01.0: PIIX3: Enabling Passive Release
pci 0000:00:01.0: Activating ISA DMA hang workarounds
- pci 0000:00:02.0: Video device with shadowed ROM at [mem 0x000c0000-0x000dffff]
PCI: CLS 0 bytes, default 64
Unpacking initramfs...
Freeing initrd memory: 5368K
@@ -140,25 +139,9 @@
io scheduler cfq registered (default)
io scheduler mq-deadline registered
io scheduler kyber registered
- virtio-pci 0000:00:03.0: PCI->APIC IRQ transform: INT A -> IRQ 11
- virtio-pci 0000:00:04.0: PCI->APIC IRQ transform: INT A -> IRQ 11
+ virtio-pci 0000:00:03.0: enabling device (0000 -> 0003)
+ virtio-pci 0000:00:04.0: enabling device (0000 -> 0003)
Serial: 8250/16550 driver, 4 ports, IRQ sharing disabled
serial8250: ttyS0 at I/O 0x3f8 (irq = 4, base_baud = 115200) is a 16550A
A declarative, efficient, and flexible JavaScript library for building user interfaces.
๐ Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. ๐๐๐
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google โค๏ธ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.