第1页
Porting Python to run without an OS
Josh Triplett josh@joshtriplett.org
PyCon 2015
第2页
BIOS Implementation Test Suite (BITS)
We ported Python to GRUB to run on BIOS and EFI.
第3页
BIOS Implementation Test Suite (BITS)
We ported Python to GRUB to run on BIOS and EFI.
Why?
第4页
BIOS Implementation Test Suite (BITS)
We ported Python to GRUB to run on BIOS and EFI.
Why? What do we provide?
第5页
BIOS Implementation Test Suite (BITS)
We ported Python to GRUB to run on BIOS and EFI.
Why? What do we provide? How does it work?
第6页
BIOS Implementation Test Suite (BITS)
We ported Python to GRUB to run on BIOS and EFI.
Why? What do we provide? How does it work? Platform APIs
第7页
BIOS Implementation Test Suite (BITS)
We ported Python to GRUB to run on BIOS and EFI.
Why? What do we provide? How does it work? Platform APIs Many demos along the way
第8页
Why?
To test hardware, BIOS, ACPI, and EFI
第9页
Why?
To test hardware, BIOS, ACPI, and EFI To replace myriad one-off tools targeting DOS or EFI
第10页
Why?
To test hardware, BIOS, ACPI, and EFI To replace myriad one-off tools targeting DOS or EFI To avoid writing more C, or pseudo-shell with C expressions
第11页
Why?
To test hardware, BIOS, ACPI, and EFI To replace myriad one-off tools targeting DOS or EFI To avoid writing more C, or pseudo-shell with C expressions As an exploratory environment
第12页
What?
Target platforms: 32-bit on BIOS, 32-bit EFI, 64-bit EFI
第13页
What?
Target platforms: 32-bit on BIOS, 32-bit EFI, 64-bit EFI CPython 2.7 (target audience familiarity)
第14页
What?
Target platforms: 32-bit on BIOS, 32-bit EFI, 64-bit EFI CPython 2.7 (target audience familiarity) Interactive REPL (including history and tab-completion)
第15页
What?
Target platforms: 32-bit on BIOS, 32-bit EFI, 64-bit EFI CPython 2.7 (target audience familiarity) Interactive REPL (including history and tab-completion) Substantial fraction of the standard library
第16页
What?
Target platforms: 32-bit on BIOS, 32-bit EFI, 64-bit EFI CPython 2.7 (target audience familiarity) Interactive REPL (including history and tab-completion) Substantial fraction of the standard library Additional modules for platform support: CPU, SMP, ACPI, EFI. . .
第17页
What?
Target platforms: 32-bit on BIOS, 32-bit EFI, 64-bit EFI CPython 2.7 (target audience familiarity) Interactive REPL (including history and tab-completion) Substantial fraction of the standard library Additional modules for platform support: CPU, SMP, ACPI, EFI. . . Test suite and exploratory tools, all written in Python
第18页
>>> import demo
第19页
How?
PyRun_InteractiveLoop(stdin, "<stdin>");
第20页
How?
PyRun_InteractiveLoop(stdin, "<stdin>"); Can’t use Python’s configure and make
第21页
How?
PyRun_InteractiveLoop(stdin, "<stdin>"); Can’t use Python’s configure and make
Using host Linux toolchain
第22页
How?
PyRun_InteractiveLoop(stdin, "<stdin>"); Can’t use Python’s configure and make
Using host Linux toolchain No GNU target string (cpu-vendor-os) for GRUB
第23页
How?
PyRun_InteractiveLoop(stdin, "<stdin>"); Can’t use Python’s configure and make
Using host Linux toolchain No GNU target string (cpu-vendor-os) for GRUB No target headers in “default” path for toolchain
第24页
How?
PyRun_InteractiveLoop(stdin, "<stdin>"); Can’t use Python’s configure and make
Using host Linux toolchain No GNU target string (cpu-vendor-os) for GRUB No target headers in “default” path for toolchain Add all of the necessary Python source files
第25页
How?
PyRun_InteractiveLoop(stdin, "<stdin>"); Can’t use Python’s configure and make
Using host Linux toolchain No GNU target string (cpu-vendor-os) for GRUB No target headers in “default” path for toolchain Add all of the necessary Python source files Manually write pyconfig.h
第26页
How?
PyRun_InteractiveLoop(stdin, "<stdin>"); Can’t use Python’s configure and make
Using host Linux toolchain No GNU target string (cpu-vendor-os) for GRUB No target headers in “default” path for toolchain Add all of the necessary Python source files Manually write pyconfig.h Provide functions expected by Python
第27页
C functions expected by Python
fstat/isatty/lseek etc on file descriptors
第28页
C functions expected by Python
fstat/isatty/lseek etc on file descriptors Wrote a simple file descriptor table
第29页
C functions expected by Python
fstat/isatty/lseek etc on file descriptors Wrote a simple file descriptor table
ungetc
第30页
C functions expected by Python
fstat/isatty/lseek etc on file descriptors Wrote a simple file descriptor table
ungetc Hack to seek backwards by one
第31页
C functions expected by Python
fstat/isatty/lseek etc on file descriptors Wrote a simple file descriptor table
ungetc Hack to seek backwards by one
qsort
第32页
C functions expected by Python
fstat/isatty/lseek etc on file descriptors Wrote a simple file descriptor table
ungetc Hack to seek backwards by one
qsort Floating-point math functions (fdlibm)
第33页
C functions expected by Python
fstat/isatty/lseek etc on file descriptors Wrote a simple file descriptor table
ungetc Hack to seek backwards by one
qsort Floating-point math functions (fdlibm) printf/sprintf
第34页
C functions expected by Python
fstat/isatty/lseek etc on file descriptors Wrote a simple file descriptor table
ungetc Hack to seek backwards by one
qsort Floating-point math functions (fdlibm) printf/sprintf
Mostly used GRUB’s
第35页
C functions expected by Python
fstat/isatty/lseek etc on file descriptors Wrote a simple file descriptor table
ungetc Hack to seek backwards by one
qsort Floating-point math functions (fdlibm) printf/sprintf
Mostly used GRUB’s Had to fix bugs (%%)
第36页
Performance issues
Slow boot time Extra painful in CPU simulation environments
第37页
Performance issues
Slow boot time Extra painful in CPU simulation environments Python parser reads characters and uses ungetc Minimal disk caching
第38页
Performance issues
Slow boot time Extra painful in CPU simulation environments Python parser reads characters and uses ungetc Minimal disk caching Compile Python on host, use it to byte-compile into .pyc files
第39页
Performance issues
Slow boot time Extra painful in CPU simulation environments Python parser reads characters and uses ungetc Minimal disk caching Compile Python on host, use it to byte-compile into .pyc files No mtime support, so zero the mtime
第40页
Performance issues
Slow boot time Extra painful in CPU simulation environments Python parser reads characters and uses ungetc Minimal disk caching Compile Python on host, use it to byte-compile into .pyc files No mtime support, so zero the mtime Still slow due to stat
第41页
Performance issues
Slow boot time Extra painful in CPU simulation environments Python parser reads characters and uses ungetc Minimal disk caching Compile Python on host, use it to byte-compile into .pyc files No mtime support, so zero the mtime Still slow due to stat zipimport
第42页
readline
Wanted history and completion readline depends heavily on POSIX and tty Didn’t want to write a pile of C code
第43页
readline
Wanted history and completion readline depends heavily on POSIX and tty Didn’t want to write a pile of C code Wrote Python’s readline in Python
第44页
readline
Wanted history and completion readline depends heavily on POSIX and tty Didn’t want to write a pile of C code Wrote Python’s readline in Python Implemented line editing, history, and completion in pure Python Set PyOS_ReadlineFunctionPointer to a C function that calls a previously set Python callback
第45页
(python) filesystem
Wanted to construct dynamic menus in GRUB
第46页
(python) filesystem
Wanted to construct dynamic menus in GRUB GRUB has disk and filesystem providers for (hd0), (cd)
第47页
(python) filesystem
Wanted to construct dynamic menus in GRUB GRUB has disk and filesystem providers for (hd0), (cd) Added a (python) device and filesystem (python) implementation calls Python callbacks to read Python code can add arbitrary in-memory files
第48页
(python) filesystem
Wanted to construct dynamic menus in GRUB GRUB has disk and filesystem providers for (hd0), (cd) Added a (python) device and filesystem (python) implementation calls Python callbacks to read Python code can add arbitrary in-memory files configfile (python)/menu.cfg
第49页
bits module
Various functions to access hardware functionality: CPUID MSRs Memory-mapped I/O I/O ports
第50页
SMP
Need to collect or modify state from all CPUs
第51页
SMP
Need to collect or modify state from all CPUs Wake up all CPUs at startup Put them in a power-efficient sleep (mwait) waiting for work to do Various functions to wake up CPUs and run specific functions on them
第52页
SMP
Need to collect or modify state from all CPUs Wake up all CPUs at startup Put them in a power-efficient sleep (mwait) waiting for work to do Various functions to wake up CPUs and run specific functions on them Python can easily correlate data across CPUs (dict, set)
第53页
ACPI
Advanced Configuration and Power Interface Configuration format used in PC firmware Static data tables and evaluatable bytecode methods
第54页
ACPI
Advanced Configuration and Power Interface Configuration format used in PC firmware Static data tables and evaluatable bytecode methods Ported ACPICA reference implementation to BITS Added Python bindings
Evaluate arbitary ACPI methods Arguments converted from Python to ACPI Result converted from ACPI to Python
第55页
ACPI
Advanced Configuration and Power Interface Configuration format used in PC firmware Static data tables and evaluatable bytecode methods Ported ACPICA reference implementation to BITS Added Python bindings
Evaluate arbitary ACPI methods Arguments converted from Python to ACPI Result converted from ACPI to Python >>> import acpi >>> acpi.dump("_HID") More detailed hardware exploration demoed elsewhere
第56页
EFI
Extensible Firmware Interface Replacement for classic PC BIOS “Extensible”:
Everything’s a “protocol” Protocols include native C functions to call >>> import efi
第57页
ctypes and libffi
ctypes: Interface to C types and functions from Python libffi: Foreign Function Interface, implements function calling conventions
第58页
ctypes and libffi
ctypes: Interface to C types and functions from Python libffi: Foreign Function Interface, implements function calling conventions Ported libffi to run in GRUB Added support for the EFI calling convention
第59页
ctypes and libffi
ctypes: Interface to C types and functions from Python libffi: Foreign Function Interface, implements function calling conventions Ported libffi to run in GRUB Added support for the EFI calling convention Declare EFI protocols and functions in Python Call them from Python
第60页
ctypes and libffi
ctypes: Interface to C types and functions from Python libffi: Foreign Function Interface, implements function calling conventions Ported libffi to run in GRUB Added support for the EFI calling convention Declare EFI protocols and functions in Python Call them from Python No C code required
第61页
efi file
File-like object built on EFI_FILE_PROTOCOL Make directories, write files efi.get_boot_fs().mkdir("dir").create("f").write("Hi")
第62页
EFI Graphics Output Protocol
GOP provides functions to read and write screen contents.
第63页
EFI Graphics Output Protocol
GOP provides functions to read and write screen contents. Such as presentation slides. Hello from EFI, BITS, and the bits.present module! No new C code needed to implement this presentation and demo.
第64页
EFI Graphics Output Protocol
GOP provides functions to read and write screen contents. Such as presentation slides. Hello from EFI, BITS, and the bits.present module! No new C code needed to implement this presentation and demo.
BIOS Implementation Test Suite (BITS) http://biosbits.org/