Slide 1

Slide 1 text

@morimolymoly Porting Golang Runtime To Baremetal Dentoo.LT #22

Slide 2

Slide 2 text

WHO AM I ❖ I am morimolymoly a.k.a GNM ❖ Interests ❖ InfoSec ❖ Hypervisor ❖ Aikatsu! ❖ Details available at morimolymoly.com * GNM means “ήΩΧϫͶ͜ΈΈϝΠυ”. It sound better right?

Slide 3

Slide 3 text

You guys find many vulnerabilities related to memory corruption or race condition

Slide 4

Slide 4 text

Most of OS kernel is written in C

Slide 5

Slide 5 text

We want altC.

Slide 6

Slide 6 text

Operating System written in HLL(High Level Language)

Slide 7

Slide 7 text

Operating System written in Rust?

Slide 8

Slide 8 text

Operating System written in Golang!

Slide 9

Slide 9 text

mit-pdos/biscuit ❖ POSIX compatible kernel written in Golang ❖ Secure, fast, USEFUL FEATURES(channels, interface, goroutine, etc…) ❖ 4-Components ❖ Bootloader(C, asm) + Kernel(Golang) + Go runtime(Golang, C, asm) + UserProgram(C) ❖ You can utilize goroutine, memory safety, etc … IN KERNEL LAND!

Slide 10

Slide 10 text

But how……?

Slide 11

Slide 11 text

Golang Runtime ❖ Runtime do initialization and goroutine stuff. ❖ Kernel loads Go program into memory and call initialize function of Golang Runtime.(For Linux, ELF header’s entrypoint defines it) ❖ Initialization stage is huge. ❖ Init goroutine ❖ Get args passed by OS ❖ Init scheduler(stack, mm, GC, etc…) ❖ Runtime needs kernel!

Slide 12

Slide 12 text

Without kernel ❖ Who loads Go Runtime? ❖ Write some bootloader to load runtime!(Runtime loads kernel main function) ❖ How initialize goroutine, memory, some low level stuff(Interrupt, I/O)? ❖ Replace system call with own system call ❖ Get memory map from BIOS and set it. ❖ WRITE LOW LEVEL CODE IN ASSEMBLY(ಀ͛ͪΌͩΊͩ)

Slide 13

Slide 13 text

Boot Sequence BIOS Bootloader Runtime Biscuit ❖ Runtime and Biscuit build actual KERNEL ❖ BIOS gives primitive services(PS/2 Keyboard and Mouse, Serial, VGA, get memory map) to KERNEL Boot sector:0x00007c00

Slide 14

Slide 14 text

Runtime is gonna be KERNEL

Slide 15

Slide 15 text

Minimize Biscuit code and analyze it ❖ Biscuit forked golang:1.4(Above golang:1.5, most of runtime code is written in Go rather than C) ❖ You can see commits related to biscuit by command below ❖ git log --author="Cody Cutler" —reverse ❖ I forked and minimzed biscuit ❖ https://github.com/morimolymoly/biscuit ❖ I focused on commits before c14beb90191e74163c20c48596a5eed576fbc664(It is so primitive but there is goroutine, interface, collections…)

Slide 16

Slide 16 text

Important Modified files under `src/runtime` ❖ src/runtime/asm_amd64.s - register ops(rdmsr, invlpg, change CRx), in/out, ❖ src/runtime/os_linux.c - system call implementation ❖ src/runtime/rt0_linux_amd64.s - entrypoint code ❖ src/runtime/sys_linux_amd64.s - runtime syscall wrapper

Slide 17

Slide 17 text

Detail of runtime initialization ❖ Makefile makes main.gobin which is ELF binary from kernel code ❖ biscuit/kernel/chentry.c changes entrypoint of main.gobin to _rt0_hack ❖ _rt0_hack is like a _rt0_amd64_linux which is used when you launch Go program in Linux AMD64 arch ❖ _rt0_hack calls runtime·rt0_go_hack in src/runtime/asm_amd64.s ❖ runtime·rt0_go_hack init segment, interrupt, syscall table, first goroutine

Slide 18

Slide 18 text

goroutine on Baremetal ❖ goroutine = Kernel Thread ❖ Kenel’s main function is also goroutine(created by runtime·newproc in rt0_go_hack) ❖ After setting up Virtual Memory(Paging, Segment), you can free to fire it! ❖ Set M(Machine), P(Processor) up.(M(Machine) and P is used in Golang runtime internal)

Slide 19

Slide 19 text

Conclusion ❖ Sorry for ultra fast tour! ❖ HLL gives us new perspective of next generation Operating System ❖ e.g. Keyboard driver uses goroutine in biscuit ❖ Reading runtime is absolutely fun!(Try it ! Fork and read it for free!) ❖ Read code and hack it!

Slide 20

Slide 20 text

References ❖ Cody Cutler, M. Frans Kaashoek, and Robert T. Morris. “The benefits and costs of writing a POSIX kernel in a high-level language”. In: 13th USENIX Symposium on Operating Systems Design and Implementation (OSDI 18). ❖ Yoshiki Shibukawa, “Biscuit Code Reading”. In: GoCon2018 Autumn ❖ Achilleas Anagnostopoulos, “Bare Metal Gophers: can you write an OS Kernel in Go?”. In: GolangUK2017