RaspberryPiPkg – 64-bit Tiano Core UEFI for the Raspberry Pi 3

64-bit Tiano Core UEFI for the Raspberry Pi 3

Last updated December 14th, 2017.

This is an implementation of a 64-bit UEFI firmware for the RPi3 platform, based off Ard Bisheuvel’s 64-bit http://www.workofard.com/2017/02/uefi-on-the-pi/ and Microsoft’s 32-bit https://github.com/ms-iot/RPi-UEFI/tree/ms-iot/Pi3BoardPkg. Initially, this was supposed to be an easy walk in the park, where the Microsoft drivers just sorta slide into Ard’s UEFI implementation, and I call it a day. It turned out to be a bit more frustrating of an experience than that :-). This is meant as a generally useful 64-bit UEFI implementation for the Pi3, good enough for most kinds of UEFI development and good enough for running real operating systems. It has been validated to install and boot Linux and FreeBSD.[…]


UefiToolsPkg: making UEFI more useful to system hackers

Andrei Warkentin has created UefiToolsPkg, readme excerpt below:

This is a Tiano Core (edk2) package with various goodies. The goal was to make the UEFI environment much more useful to system hackers. It may be a reduced environment, but there’s no need for it to remain a crippled one. People make the analogy of UEFI being the 21st century equivalent of DOS, yet DOS was a vastly more useful environment than UEFI is today. Hopefully, one day this will grow into a veritable distribution of software to be productive even without a “real OS” around. Contains: Useful utilities for developers and admins,Ported UNIX tools, Useful libraries for developers, Development tools for Windows/Linux, Other tools around the Web.

FdtDump: dump system device tree to storage
AcpiDump: dump system ACPI tables to storage
AcpiLoader: load system ACPI tables from storage
ShellPlatVars: set UEFI Shell variables based on platform configuration
MemResv: create new memory map entries
RangeIsMapped: validates ranges in the memory map
GopTool: Check and manipulate EFI_GRAPHICS_OUTPUT_PROTOCOL instances
tinycc: port of TinyCC to UEFI

There’s at least one other UEFI ‘distribution’ project on Github, mostly non-usable, I forget the name at the moment.  If I had some spare time, I’ve been wanting to do something like this, still looking to find the spare time… 😦 The next logical step is to include FPMurphy’s UEFI Utilities:


Porting UEFI to Apple PowerPC…

Porting UEFI to a new architecture:
So it turns out that blogging about something after the fact is pretty tough. I really wanted to blog about my PoC port of UEFI to the OpenPower ecosystem, but it’s incredibly difficult to go back and try to systematize something that’s been a few years back. So let’s try this again. This time, our victim will be a G4 12″ PowerBook6,8 with a 7447A. That’s a 32-bit PowerPC. Now, I’ll go in small steps and document everything. For added fun, we’ll begin porting on the target itself, at least until that gets too tedious. Also, I’ve a few OldWorld machines, a spare G4 12″ for parts and a G5, so hopefully this odyssey won’t be interrupted by old and failing hardware ;-). Keep in mind that each part is checked in along with the source code, so look at the entire commit. Each blog post will focus on the most important details.[…]




Interview with Andrei Warkentin, OpenPOWER UEFI porter

There are two ports of UEFI to the OpenPOWER architecture. Andrei E. Warkentin is a developer of one of them. I did an email interview with Andrei. I’ll hopefully have another post in the future with Benjamin, author of the second port. The answers below are from Andrei:

Q: Andrei, how goes your port?

A: So UEFI on OpenPOWER is my idea of a nice relaxing side project to hack on in the late hours with my family asleep, and I haven’t had much time in the last few months to work on it due to vacations, work, … 🙂 But the current state is being able to boot to a UEFI shell with just the OPAL console being supported.  A FAT filesystem image can be passed to qemu via the ‘initrd’ option to be accessible from UEFI. This means that my port is good enough to start writing UEFI applications, for example, or to start thinking about booting PPC64LE Linux, but there is no I/O support for PCI devices (no disk, no networking, no video console, etc).

Q: Is there any consideration of merging two projects into a single one?

A: Probably not. I’m not affiliated with Benjamin’s work, IBM or OzLabs and I am making a point of not looking over at Ben’s work as I address various parts of the UEFI port, because it’s fun to figure out things like this on your own and that’s why I’m working on OpenPOWER UEFI in the first place. I think it will be interesting to see the difference in approaches.

Q: Does OpenPOWER have any involvement in these ports, and official UEFI support, or are these strictly unofficial?

A: Actually one of the reasons I embarked on porting UEFI to PPC64LE is because I couldn’t find any evidence that a project like it was already being done by someone else :-). Power CPUs are not an officially supported platform for UEFI, but proof-of-concept work like this is the first step towards putting together an official specification, provided there is industry interest of course! Having two independent ports goes a long way towards identifying the real minimum requirements and any implementation assumptions to filter out. I think UEFI on OpenPower is interesting because it reduces the barrier to entry for hardware vendors to potentially start making more OpenPower gear. They will be able to use existing knowledge, skills, tooling, etc.

Q: Is there any hardware-level debugger, like an Intel ICE/ITP, for tracing at the instruction level, through OpenPOWER firmware? Perhaps a GUI dev toolchain like like ARM DS-5 or Intel ISS?

A: While I’m not aware of any hardware debuggers, I highly recommend Ben’s OpenPower QEMU ‘powernv’ target. This is what I have been using for my Power8 hacks and UEFI development, and while there’s always the risk of writing code that may not be 100% architecturally correct when using an emulator, it feels 1000x faster than the official IBM simulator, and you can use GDB for an ICE-like experience. For UEFI I have a Py script to facilitate source debugging (See https://github.com/andreiw/andreiw-wip/tree/master/gdb).

Q: How does your UEFI implementation interact — replace or chain after or otherwise integrate with — OpenPOWER’s firmware, OPAL (Open Power Abstraction Layer) firmware, hostboot, petitboot, and other related components I’m not aware of?

A: My UEFI implementation is just another ‘skiboot’ payload, to be loaded instead of ‘petitboot’, and fully meant to leverage OPAL. OPAL runtime services are used today for console access, and would be used for NVRAM, RTC, simple I/O, PCI, power state transitions, etc. The goal is a fully generic UEFI implementation that is not specific to any particular OpenPower platform. This is achieved by using OPAL and the skiboot-produced FDT to abstract platform binding and configuration. This way if a particular work flow requires UEFI, then it’s just another loader stage, similar to the OFW->ARC shim used for the old Windows NT PReP port. The goal is that OPAL services that don’t have corresponding UEFI RT matches would be provided as extra UEFI RT services, to avoid having the OS to deal with supporting two completely different runtime services environments.

Stepping back a bit, conceptually, I don’t think UEFI ought to replace the existing OpenPOWER booting strategy, but simply complement to give more power to the user, to the IHV, the OEM and the OS vendor. My 10 years of experience with both architecture- and platform ports of UEFI, both in writing and in dealing with buggy implementations and drivers has convinced me that it was a mistake to use this highly complex mini-OS, with a non-trivial driver and firmware<->OS interaction model as the first-stage system IPL to be flashed into ROM. This is not meant as a slight against UEFI or Tiano itself, as I think it would be equally a mistake to leverage any other OS or kernel here: it’s just too big. There is way too much code involved – too many moving parts. A lot of these moving parts are part of ‘generic’ code distributed as Tiano where no one looks until something catastrophic happens. The expectation that IHV and hardware engineers are going to write functionally correct drivers is flawed – not everyone is a kernel engineer! For example, UEFI implementers are expected to come up with a proper platform NVRAM driver and the ‘Bds’ driver, the later being a key part that basically unifies all of the end user’s interaction and boot selection activities. Writing NVRAM drivers and ‘Bds’ correctly is hard because introducing subtle bugs is easy and few seem to consider the ‘unexpected’ situations. We’ve already seen plenty industry bugs where setting or clearing the wrong NV variable from the OS turns computers into unusable bricks. I’ve seen a lot of bugs relating to folks not really understanding how runtime services really work, or what sort of things are allowed to be done during UEFI quiesce callbacks. But the conceptual problem here is an environment that pushes all the complexity of OS development onto firmware integrators.

Q: As I understand it, OpenPOWER has some form of Flattened Device Tree (FDT) support? Will that be exposed via your UEFI implementation?

A: The device tree is consumed by the UEFI implementation to figure out how the machine is configured, how to set itself and its own drivers and I/O support up. The device tree would be exposed to a booting Linux kernel, similar to how it is exposed on AArch32 and AArch64 UEFI implementations.

Q: FDT aside, what/how is your port dealing with ACPI, if at all?

A: One of the things I wanted to scope out specifically is presenting OpenPower as a ‘reduced-hardware’ ACPI environment, similar to how the AArch64 ecosystem is doing. ‘Reduced hardware’ means that the requirements around some legacy x86 fixed hardware are dropped, making it possible to support ACPI for platform discovery, configuration and power management across a wide range of very different environments, ranging from embedded SoCs to powerful servers. From a birds eye view, ACPI and device tree are quite similar – both describe hardware as a hierarchical tree of devices with certain identifiers and properties. ACPI differs from DT in that it removes the need to describe certain platform knowledge (and consume it in a driver) and hides it instead in device methods written in this interpreted byte code called AML. It is a heavier system, in many ways significantly less elegant than device tree, but it allows for potentially more homogenous-looking hardware, and it is a de facto standard across server and motherboard manufacturers, so I think having ACPI support for OpenPower would reduce the barrier to entry for hardware vendors to potentially start making more compatible OpenPower gear. I have not started thinking about ACPI support just yet, and this would of course involve changes to the ‘powernv’ support in the Linux kernel.

Q: Besides Github project, do either of you have any upcoming conference presentions or research papers on your projects that we should be looking for?

A: Not that I am aware of. Certainly, if there is interest, I would be happy to present my work at any applicable conferences.

Thanks for the answers, Andrei!

BTW, originally I thought that both ports were from IBM developers, but that’s not the case, Andrei is not from IBM. My previous OpenPOWER blog post is incorrect.


Tianocore for OpenPOWER

Andrei Warkentin has ported UEFI to OpenPOWER! Excerpt from readme:

TianoCore UEFI for OPAL/PowerNV (PPC64/PowerPC64 Little-Endian)

This is “UEFI” on top of OPAL firmware. “UEFI” because the specification doesn’t include PowerPC yet (ever?). At some point this experiment will implement reduced-hardware “ACPI” support, mapping the OPAL-based FDT into “ACPI” structures. “ACPI” because it’s also not specced out for PowerPC. It’s getting prototyped on top of QEMU and Skiboot (OPAL firmware).

Why? It’s thought experiment gone too far. In short, there’s IMO value in presenting a common firmware environment shared with other servers (X64, AARCH64). UEFI+ACPI keep the OEMs and IHVs in their comfort zone, and reduce pointless platform boot and configuration variance across different architectures. It also allows plug-in cards to work (assuming EBC ROMs). Petitboot is a nice idea in theory, but in practice it’s probably more suitable to embedded environments rather than whitebox servers that can compete with Intel boxes. UEFI gets us a bootloader environment and device drivers for I/O and booting via storage and networking. OPAL is the abstraction layer for the machine.