Showing posts with label Bluehat. Show all posts
Showing posts with label Bluehat. Show all posts

Sunday, February 12, 2023

Blue Hat 2023 and UEFI Secure Boot

“Victory has 100 fathers and defeat is an orphan.” This quote is attributed to John F. Kennedy in the wake of the Bay of Pigs but I believe a variant of this has been passed down over time. I was thinking of this quote in the context of UEFI Secure Boot this week at Blue Hat https://www.microsoft.com/bluehat/ at Microsoft building 92. Visiting the Microsoft campus reminded of me the many hours engaged with Microsoft during the build up to this feature in the mid-2000’s (including hours in the 40's buildings that were razed recently for the new MS campus).





The above talk from Eclypsium (now posted https://github.com/n0x08/ConferenceTalks/blob/master/0-Day_FirmWarez_BlueHat2023.pdf)  this last week also reminded me of how UEFI secure boot and firmware security is now part of the tech lexicon.

But back to the history discussion from the early 2000's. At that time, the industry was recovering from the lack of adoption of NGSCB https://en.wikipedia.org/wiki/Next-Generation_Secure_Computing_Base. Intel LaGrande Technology (LT), 

which is now Trusted Execution Technology, along w/ AMD Pacifica/Presidio, were features to add ‘late launch,’ or ‘dynamic root of trust for measurement’ (DRTM). The DRTM facility provided an RTM in the CPU, and the roots of trust for storage (RTS) and recording (RTR) were delegated to a ‘then’ off-chip element called the Trusted Platform Module (TPM) https://trustedcomputinggroup.org/work-groups/trusted-platform-module/.

Since NGSCB, with its “Trusted Applet” (TA) architecture ,was a mile too far both for privacy and application compatibility, LT and Pacifica didn’t get embraced by Windows. NGSCB entailed the need to refactor applications to put security sensitive codes into a memory-only execution regime. Although in 2023 folks may say ‘so what, SGX did it,’ recall this is 2002. So folks like Peter Bidell managed to build a full-disk encryption (FDE) feature around the TPM and a BIOS-based root-of-trust for measurement (RTM), called the Static RTM (SRTM).

This is where I entered the scene. I worked with folks like Mark Williams to author and enable the EFI TPM and platform specifications. The former entailed the API exposed to UEFI drivers and OS loaders/applications, and the latter defined what type of code and data objects to record or ‘measure’ in the TPM’s Platform Configuration Registers (PCRs). More information on the various RT*’s and the TPM can be found in https://www.intel.com/content/www/us/en/content-details/671466/trusted-platforms-uefi-pi-and-tcg-based-firmware.html.


 

While doing this work with Microsoft, I learned that recording the hash of the Portable Executable/COFF (PE/COFF) image was not so simple. It entailed hashing various portions of the binary and omitting others. It turns out this hash or ‘digest’ is a critical element for code integrity (i.e., what became documented as the Authenticode hashing algorithm). At the same time Microsoft was reeling from no DRTM, it moved to static verification with the invention in Vista of Code Integrity, or (CI). CI entailed having the OS loader cryptographically verify the digital signature of the early boot and kernel components in Windows, thus having something of a static root of trust for verification (RTV), with the ‘root’ being the OS loader.

I learned about how all of this CI worked after reading Matthew Conover’s paper https://github.com/tpn/pdfs/blob/master/Assessment%20of%20Windows%20Vista%20Kernel-Mode%20Security%20-%20Matthew%20Conover%20(Symantec).pdf



This feature is also described in https://csrc.nist.gov/csrc/media/projects/cryptographic-module-validation-program/documents/security-policies/140sp1327.pdf. Learning about how CI worked and the top-of-mind reminders from folks like Heasman

https://www.blackhat.com/presentations/bh-usa-07/Heasman/Presentation/bh-usa-07-heasman.pdf




led me to suggest adding an ‘SRTV’ to the firmware to complement the existing ‘SRTM’ we had been building. I roughed out some of those thoughts in the 2007 paper

https://github.com/vincentjzimmer/Documents/blob/master/SAM4542.pdf https://dblp.uni-trier.de/rec/conf/csreaSAM/Zimmer07.html?view=bibtex mentioned in earlier post

http://vzimmer.blogspot.com/2022/08/pqc.html, too. 


In other words, leaving the OS loader hanging in space to start the verification chain seemed fragile, so having the underlying firmware act as a static RTV for the loader would strengthen this static verification chain. It was also complemented by the SRTM since the TPM could provide evidence or an audit log of the verification actions. 

Given the difficulty in crafting pre-OS malware w/ MBR's for PC/AT boot, the lack of interoperable code integrity in UEFI would have made things so painful as I noted in http://vzimmer.blogspot.com/2012/09/late-september-mumbling.html. Also, extending CI into the host firmware felt as natural as extending the OS filesystem via the EFI System Partition (ESP) into the firmware for purposes of interoperability.

One of the challenges posed during this work was to have a reasoned approach to the infrastructure. That’s where Varugis (former NGSCB TA architect turned Windows CI architect) and I tried to create an integrity model of the pre-OS https://github.com/vincentjzimmer/Documents/blob/master/integrity-protection-analysis-of-OS-preboot.pdf. Varugis would often rail against folks who said the BitLocker was for code-integrity since it was largely a data integrity feature. He wanted to ensure that any functionality built into the ecosystem had a sound foundation. To that end the platform was decomposed into a series of Clark-Wilson compartments (although the CDI’s of CW and reuse of acronym of the same in TCG DICE is amusing). The OEM compartment, extensible pre-OS UEFI compartment, and finally, the OS compartment had rules, including guards and access controls.





It turns out that since CI was just for internal use by Microsoft tooling, the Authenticode hashing algorithm and signature section of the PE/COFF were not documented. Just as UEFI needs MS FAT and PE/COFF itself for purposes of interoperability, this information was added to the public document from Microsoft to support this capability

https://download.microsoft.com/download/9/c/5/9c5b2167-8017-4bae-9fde-d599bac8184a/authenticode_pe.docx, as were the required infrastructure elements in the 2.1+ specifications. The variant of UEFI Secure Boot that ultimately shipped as a required capability in Windows 8, along with UEFI measured boot, was the specification version 2.3.1 http://www.uefi.org/sites/default/files/resources/UEFI_Spec_2_3_1.pdf.

Another interesting tie-in to last week's Bluehat was the keynote from Mark Russinovich. Mark was one of the people to whom we presented this UEFI Secure boot work back in the day, too. Others in the audience at the included MS security arch, and former Intel colleague, Carl Ellison.


BTW
ECR48 was remastered in M279 https://uefi.org/specs/UEFI/2.10/Frontmatter/Revision_History.html



Mark's keynote at Bluehat covered confidential computing, large language models (LLMs) for security, open source firmware foundation, safe languages, and the software supply chain. 

On safe languages


And for the challenges of the open source supply chain, and software supply chains in general, I commiserated with



These slides reminded me of the long-used

from https://embeddedcomputing.com/technology/security/software-security/understanding-uefi-firmware-update-and-its-vital-role-in-keeping-computing-systems-secure, too.

OK. Back to the narrative. By this time the UEFI secure boot capability had iterated through early discussions and into the standards incubation mix. The final clean-up of how authenticated variables work, including the append option for servicing, were introduced by Magnus. Magnus Nystrom was the security lead in Windows core OS and managed to get the feature finally into the OS. We described some of this journey in https://www.intel.com/content/dam/www/public/us/en/documents/research/2011-vol15-iss-1-intel-technology-journal.pdf.


One of the challenges of this work was how to apply trust for the more open PC architecture. Cell-phones and other appliances had locked-down bootloaders, but with the PC and its ability multi-boot (think reason for UEFI existence) and adapter cards, the trust needed to be more interoperable. This is where the concept of the various stakeholders, through the OEM with the PK, the OS vendors and ISV’s with the KEK’s, and the hash or verification certificates in the allowed DB and disallowed DBX were created. 

Tim Lewis https://uefi.blogspot.com/ championed a lot of the details on this design through the forum, too. Tim also led the UEFI Security Subteam (USST) in those first heady years.

A spate of additional publications were created to describe this capability, including https://github.com/tianocore-docs/Docs/blob/master/White_Papers/A_Tour_Beyond_BIOS_into_UEFI_Secure_Boot_White_Paper.pdf created in the wake of my first ToorCamp talk, to https://www.intel.com/content/www/us/en/content-details/671464/a-tour-beyond-bios-with-the-uefi-tpm2-support-in-edk-ii.html and https://www.intel.com/content/www/us/en/content-details/671120/a-tour-beyond-bios-uefi-authenticated-variables-in-smm-with-edk-ii.html on how to use the code https://github.com/tianocore/edk2/tree/master/SecurityPkg. Given the long arc of this work, https://link.springer.com/book/10.1007/978-1-4842-6106-4 was created to collect this background in one location.

The evolution of UEFI secure boot wasn't without some controversy, especially from privacy groups and others who worried about lock-down of the PC https://www.csoonline.com/article/2221385/geeks-under-fire--war-on-privacy--freedom-and-general-computation.html, but Microsoft logo requirements like a physically-present user control for this feature, along with the UEFI CA signing Linux shim's, helped calm those concerns - some of the great work w/ Linux in this space was described in https://www.intel.com/content/dam/develop/external/us/en/documents/sf13-stts002-100p-820238.pdf, too, although it was always smooth sailing as I recall people glowering at me when I presented https://github.com/vincentjzimmer/Documents/blob/master/PLUG-UEFI-001.pdf in Portland. One of the MS PM's even told me that Sinofsky considered pulling all of the UEFI features from Windows 8 if the issue were not resolved in a timely fashion which makes sense given that wide-scale UEFI deployment without integrity controls would have led to unbounded pre-OS malware concerns for users.



Work continues apace in this area, from investigations into post quantum cryptography https://eprint.iacr.org/2021/041.pdf https://uefi.org/sites/default/files/resources/Post%20Quantum%20Webinar.pdf to better revocation models https://github.com/rhboot/shim/blob/main/SBAT.md. And DRTM is getting great traction in the platform now https://cdrdv2-public.intel.com/756963/DRTM-based-computing_whitepaper_FINAL_MAY2021.pdf, although contemporary with Windows 8 we worked hard to see if we could have a standards-based solution https://trustedcomputinggroup.org/work-groups/trusted-platform-module/, too. DRTM definitely reduces the trusted computing base (TCB),

thus why the DRTM and optional DRTV were mentioned in https://www.intel.com/content/www/us/en/content-details/671466/trusted-platforms-uefi-pi-and-tcg-based-firmware.html, too.

And some of the ecosystem challenges of distributed trust, as shown in the 'figure 5' above with the various trust anchors for UEFI secure boot (including the UEFI CA and revocation lists like the dbx https://uefi.org/revocationlistfile), don't magically disappear. I was reminded of Mark Twain's 'History never repeats itself, but it does often rhymes' recently during a presentation in the Open Compute Project Security team  https://www.opencompute.org/wiki/Security discussion on January 31 https://docs.google.com/document/d/1VVMUzYESZNuyT1_YJlQSdSKBy-5t1otJIyXTbXuOoX4/edit# regarding a CA for the device firmware for usages like SPDM. Some of those melodies included:

"If there is an explosion in the number of CAs how will verifier vet the trustworthiness of the CAs?

..

Want to see a manageable number of CAs under a common policy

..

Trust stores in components will have large number of anchors and have reoccuring updates

..

Devices without internet connectivity cannot retrieve trust anchor info

..

Small vendors may have difficulty operating root CAs

..

Common PKI CA policy."

These are many of the issues UEFI has encountered and grappled with since the late 2000's.

So back to the quote at the top of the posting. The reason for many ‘fathers’ is often that for an idea to come to market the originator of the concept needs many hands to help shepherd it forward through the vagaries of business, development, validation, and ultimately shipping at scale. And as I updated Ubuntu on a home PC this weekend and noticed,



this stuff is still pretty cool. 

PS

A PhD colleague of mine recently decried the lack of authoritative knowledge, from blogs to arxiv. Luckily in this scurrilous post (aka 'blog')  I haven't claimed any refereed, authoritative discourse. These are more the late weekend musings motivated by wonderful arc of interactions with colleagues, many of who have changed companies, retired, or passed away. 

Lest that sound unhappy, though, I did catch up with David and crew over Teriyaki on Thursday. As I offered them some Bluehat swag







David let me know that he and the Microsoft team who implemented UEFI Secure Boot in Windows actually won a Microsoft-wide award that year, viz.,


Very nice (although the referenced link is dead).

Even in the world of cyber-everything, I do like the physical relics (including security faux currencies)


spanning journey's from 



to

https://github.com/rrbranco/BlackHat2017 

I guess this closes the circle for this blog. I opened with Nate Warfield prezo https://www.helpnetsecurity.com/2022/06/19/eclypsium-executive-team/ and he's part of https://eclypsium.com/company/ which is led by Yuriy and John, my co-presenters from the 2013 Cisco seccon talk. 

Sunday, October 14, 2018

Ghosts of....

Ghosts of GUID's past. This post, like, many of my recent ones, walks backward in time. Recent events usually stir these memories. If you're not such a fan old these mutterings, I'd pass on this mid-month posting.

To begin, I couldn't help but remember

https://trustedcomputinggroup.org/wp-content/uploads/Platform-Reset-Attack-Mitigation-Specification.pdf during the F-Secure talk at Blue Hat https://www.microsoft.com/en-us/msrc/bluehat-conference recently.


That MEMORY_ONLY_RESET_CONTROL_GUID was GuidGen.exe'd https://blogs.msdn.microsoft.com/syedab/2010/05/09/generate-guid-using-guidgen-exe/ from my erstwhile cubicle in DuPont, WA http://vzimmer.blogspot.com/2018/07/the-march-of-time.html. I guess that I can now say 'buried' (thanks Fish for the latest pic) former campus.
This, along with other buried piles of GUIDs in the EDK code, the UEFI specification, and the PI specification http://uefi.org/specifications emanated from that dank DuPont corner cubicle. I've seen prezo's like this Bluehat one commencing in 2007 with Heasman's UEFI Black Hat talk through a decade of folks searching for GUID's in binaries and mentioning them in prezos and papers.

At the beginning of the hardware track a researcher came up to me and asked "Are you Vincent Zimmer? You're famous, man." I replied, "Er, 'famous', or 'infamous', given the queued up talks." He replied, "Nah, famous." That was nice.

Speaking of ghosts of technology past and true rock stars, people have been remarking this year that UEFI is a '20 year old technology.' I was curious about the precision of those statements, so I looked into an early Intel Boot Initiative (IBI) https://www.afterdawn.com/glossary/term.cfm/intel_boot_initiative tree. IBI was the original name of EFI. I found the following. 

/*++

Copyright (c) 1998  Intel Corporation

Module Name:

    ibiapi.h

Abstract:

    Global IBI runtime & boot service interfaces


Author:

    Ken Reneris     Oct-14-1998

Revision History

--*/

//
// IBI Memory
//

typedef
IBI_STATUS
(IBIAPI *IBI_ALLOCATE_PAGES) (
    IN IBI_ALLOCATE_TYPE            Type,
    IN IBI_MEMORY_TYPE              MemoryType,
    IN UINTN                        NoPages,
    OUT IBI_PHYSICAL_ADDRESS        *Memory
    );

typedef
IBI_STATUS
(IBIAPI *IBI_FREE_PAGES) (
    IN IBI_PHYSICAL_ADDRESS         Memory,
    IN UINTN                        NoPages
    );

typedef
IBI_STATUS
(IBIAPI *IBI_GET_MEMORY_MAP) (
    IN OUT UINTN                    *MemoryMapSize,
    IN OUT IBI_MEMORY_DESCRIPTOR    *MemoryMap,
    OUT UINTN                       *MapKey
    );

typedef
IBI_STATUS
(IBIAPI *IBI_ALLOCATE_POOL) (
    IN IBI_MEMORY_TYPE              PoolType,
    IN UINTN                        Size,
    OUT VOID                        **Buffer
    );

typedef
IBI_STATUS
(IBIAPI *IBI_FREE_POOL) (
    IN VOID                         *Buffer
    );

//
// IBI Events
//

typedef enum {
    EVT_NORMAL,
    EVT_TIMER,
    EVT_MAX_TYPE
} IBI_EVENT_TYPE;

typedef
VOID
(IBIAPI *IBI_EVENT_NOTIFY) (
    IN IBI_EVENT                Event,
    IN VOID                     *Context
    );

typedef
IBI_STATUS
(IBIAPI *IBI_CREATE_EVENT) (
    IN IBI_EVENT_TYPE           Type,
    IN IBI_TPL                  Tpl,
    IN IBI_EVENT_NOTIFY         NotifyFunction,
    IN VOID                     *NotifyContext,
    OUT IBI_EVENT               *Event
    );

typedef enum {
    TimerCancel,
    TimerPeriodic,
    TimerRelative
} IBI_TIMER_DELAY;

typedef
IBI_STATUS
(IBIAPI *IBI_SET_TIMER) (
    IN IBI_EVENT                Event,
    IN IBI_TIMER_DELAY          Type,
    IN UINT64                   TriggerTime
    );

typedef
IBI_STATUS
(IBIAPI *IBI_SIGNAL_EVENT) (
    IN IBI_EVENT                Event
    );

typedef
IBI_STATUS
(IBIAPI *IBI_CLOSE_EVENT) (
    IN IBI_EVENT                Event
    );


//
// Task priority level
//

#define TPL_NORMAL         4
#define TPL_CALLBACK       8
#define TPL_NOTIFY        16 
#define TPL_HIGH_LEVEL    31 

typedef
IBI_TPL
(IBIAPI *IBI_RAISE_TPL) (
    IN IBI_TPL      NewTpl
    );

typedef
VOID
(IBIAPI *IBI_RESTORE_TPL) (
    IN IBI_TPL      NewTpl
    );


//
// IBI platform varibles
//

#define IBI_GLOBAL_VARIABLE     \
    { 0x8BE4DF61, 0x93CA, 0x11d2, 0xAA, 0x0D, 0x00, 0xE0, 0x98, 0x03, 0x2B, 0x8C }

// Variable attributes
#define IBI_VARIABLE_NON_VOLATILE           0x00000001
#define IBI_VARIABLE_BOOTSERVICE_ACCESS     0x00000002
#define IBI_VARIABLE_RUNTIME_ACCESS         0x00000004


typedef
IBI_STATUS
(IBIAPI *IBI_GET_VARIABLE) (
    IN CHAR16                       *VariableName,
    IN IBI_GUID                     *VendorGuid,
    OUT UINT32                      *Attributes OPTIONAL,
    IN OUT UINTN                    *DataSize,
    OUT VOID                        *Data
    );

typedef
IBI_STATUS
(IBIAPI *IBI_GET_NEXT_VARIABLE_NAME) (
    IN OUT UINTN                    *VariableNameSize,
    IN OUT CHAR16                   *VariableName,
    IN OUT IBI_GUID                 *VendorGuid
    );


typedef
IBI_STATUS
(IBIAPI *IBI_SET_VARIABLE) (
    IN CHAR16                       *VariableName,
    IN IBI_GUID                     *VendorGuid,
    IN UINT32                       Attributes,
    IN UINTN                        DataSize,
    IN VOID                         *Data
    );

...

It looks like today is makes one milestone of 20 years if you use source artifacts as a sign post. You'll notice the code below matches chapter 7 of http://www.uefi.org/sites/default/files/resources/UEFI_Spec_2_7.pdf pretty closely, too (i.e., replace 'IBI' with 'EFI'). The code author is the same Ken Reneris mentioned in the Beyond BIOS https://www.amazon.com/Beyond-BIOS-Developing-Extensible-Interface/dp/1501514784 acknowledgement, too.

Although there's no explicit mention of IBI in the UEFI specification, it still lingers in

#define EFI_SYSTEM_TABLE_SIGNATURE 0x5453595320494249

or

'IBI SYST'.



Moving on from Bluehat and IBI, I am surprised by the feedback around Linus T's behavior https://www.zdnet.com/article/linus-torvalds-and-linux-code-of-conduct-myths/.

I recall one event (maybe the 2015 OSTS mentioned in http://vzimmer.blogspot.com/2015/05/ocp-csw-and-new-specifications.html) when I was introduced to Linus as a 'UEFI guy, so tell him what you don't like.'  Linus said 'That UEFI runtime is really screwed up.' I replied 'I agree, especially services like SetVirtualAddress that are not idempotent, so they break things like kexec where the latter kernel cannot re-invoke the service.' He looked at me and said 'Hmmm, but I like the UEFI Shell for debugging.' I responded 'It's OK, I guess.'  At this point the Linux die-hard who had initiated the interaction was fuming and shouted 'But Linus, what about ACPI?' Linus then looked at us both and said 'But wasn't ACPI screwed up before EFI and UEFI?'  Good times.

My philosophy on getting strident feedback from open source leaders, whether Linus, Minnich, or the spectrum in-between on the net, is to not take it person 'how' the message is delivered, but 'why.' I use the analogy of the bazooka.  Don't cavil about the calibre of weapon, but try to figure out why it's aimed at me. Often it's because the party delivering the message is passionate about a legitimate concern, and my job entails trying to understand and make progress against 'fixing' the concern, if possible.

Final thoughts are on grabbing the free Friday sessions as CppCon in Bellevue. I was impressed with the wisdom behind
As recently as a day ago I had to remind someone that adding new behavior to a 20 year API without changing software visible version indicia, such as version field or GUID of the API, was a doomed path. They replied 'but everyone builds with the latest code.' To which I responded 'that makes sense within one company, but the point of standardized API's is interoperability, and for the latter you cannot dictate the provenance or age of the caller.'

Speaking of Bellevue and the Pacific Northwest, I'll leave with a couple of shots from http://www.issaquahchamber.com/salmondays. Namely a 'before'




and 'after'
of the salmon.

© 2018, Vincent ZimmerThis work is licensed under a Creative Commons Attribution-ShareAlike 3.0 License