当前位置: 首页 > news >正文

[UEFI架构]必不可少的SecurityArch

在UEFI架构下,gEfiSecurityArchProtocolGuid作为一个必须实现的Protocol,gEfiSecurity2ArchProtocolGuid作为一个Option Protocol;

首先看看SecurityStubDxe的驱动内容如何

EFI_STATUS EFIAPI SecurityStubInitialize ( IN EFI_HANDLE ImageHandle, IN EFI_SYSTEM_TABLE *SystemTable ) { EFI_STATUS Status; // // Make sure the Security Architectural Protocol is not already installed in the system // ASSERT_PROTOCOL_ALREADY_INSTALLED (NULL, &gEfiSecurity2ArchProtocolGuid); ASSERT_PROTOCOL_ALREADY_INSTALLED (NULL, &gEfiSecurityArchProtocolGuid); // // Install the Security Architectural Protocol onto a new handle // Status = gBS->InstallMultipleProtocolInterfaces ( &mSecurityArchProtocolHandle, &gEfiSecurity2ArchProtocolGuid, &mSecurity2Stub, &gEfiSecurityArchProtocolGuid, &mSecurityStub, NULL ); ASSERT_EFI_ERROR (Status); Defer3rdPartyImageLoadInitialize ();

驱动本体看起来比较简单,安装gEfiSecurityArchProtocolGuid/gEfiSecurity2ArchProtocolGuid 两个 Protocol;

而Defer3rdPartyImageLoadInitialize中则会安装gEfiDeferredImageLoadProtocolGuid Protocol,并且在DxeSmmReadyToLock中检查是否有第三方的Module在 EndOfDxe 到 SmmReadyToLock 这个时间段被执行过, 如果有,那么这个系统认定为不可信状态,直接进入CpuDeadLoop,不在继续启动了;那一个正确的执行顺序应该是 EndOfDxe -> SmmReadyToLock -> 3rd Module;

VOID Defer3rdPartyImageLoadInitialize ( VOID ) { EFI_STATUS Status; EFI_HANDLE Handle; EFI_EVENT Event; VOID *Registration; Handle = NULL; Status = gBS->InstallMultipleProtocolInterfaces ( &Handle, &gEfiDeferredImageLoadProtocolGuid, &mDeferredImageLoad, NULL ); ASSERT_EFI_ERROR (Status); Status = gBS->CreateEventEx ( EVT_NOTIFY_SIGNAL, TPL_CALLBACK, EndOfDxe, NULL, &gEfiEndOfDxeEventGroupGuid, &Event ); ASSERT_EFI_ERROR (Status); EfiCreateProtocolNotifyEvent ( &gEfiDxeSmmReadyToLockProtocolGuid, TPL_CALLBACK, DxeSmmReadyToLock, NULL, &Registration ); } VOID EFIAPI DxeSmmReadyToLock ( IN EFI_EVENT Event, IN VOID *Context ) { EFI_STATUS Status; VOID *Interface; Status = gBS->LocateProtocol (&gEfiDxeSmmReadyToLockProtocolGuid, NULL, &Interface); if (EFI_ERROR (Status)) { return; } gBS->CloseEvent (Event); if (mImageLoadedAfterEndOfDxe) { // // Platform should not dispatch the 3rd party images after signaling EndOfDxe event // but before publishing DxeSmmReadyToLock protocol. // DEBUG (( DEBUG_ERROR, "[Security] 3rd party images must be dispatched after DxeSmmReadyToLock Protocol installation!\n" )); REPORT_STATUS_CODE ( EFI_ERROR_CODE | EFI_ERROR_UNRECOVERED, (EFI_SOFTWARE_DXE_BS_DRIVER | EFI_SW_EC_ILLEGAL_SOFTWARE_STATE) ); ASSERT (FALSE); CpuDeadLoop (); } }

我们继续看安装的gEfiSecurityArchProtocolGuid到底有什么作用

EFI_STATUS EFIAPI SecurityStubAuthenticateState ( IN CONST EFI_SECURITY_ARCH_PROTOCOL *This, IN UINT32 AuthenticationStatus, IN CONST EFI_DEVICE_PATH_PROTOCOL *File ) { EFI_STATUS Status; Status = ExecuteSecurity2Handlers ( EFI_AUTH_OPERATION_AUTHENTICATION_STATE, AuthenticationStatus, File, NULL, 0, FALSE ); if (Status == EFI_SUCCESS) { Status = ExecuteSecurityHandlers (AuthenticationStatus, File); } return Status; } ExecuteSecurity2Handlers ( IN UINT32 AuthenticationOperation, IN UINT32 AuthenticationStatus, IN CONST EFI_DEVICE_PATH_PROTOCOL *File OPTIONAL, IN VOID *FileBuffer, IN UINTN FileSize, IN BOOLEAN BootPolicy ) { ...... // // Directly return successfully when no handler is registered. // if (mNumberOfSecurity2Handler == 0) { return EFI_SUCCESS; } // // Run security handler in same order to their registered list // for (Index = 0; Index < mNumberOfSecurity2Handler; Index++) { // // If FileBuffer is not NULL, the input is Image, which will be handled by EFI_AUTH_IMAGE_OPERATION_MASK operation. // If FileBuffer is NULL, the input is not Image, which will be handled by EFI_AUTH_NONE_IMAGE_OPERATION_MASK operation. // Other cases are ignored. // if (((FileBuffer != NULL) && ((mSecurity2Table[Index].Security2Operation & EFI_AUTH_IMAGE_OPERATION_MASK) != 0)) || ((FileBuffer == NULL) && ((mSecurity2Table[Index].Security2Operation & EFI_AUTH_NONE_IMAGE_OPERATION_MASK) != 0))) { // // Execute registered handlers based on input AuthenticationOperation // if ((mSecurity2Table[Index].Security2Operation & AuthenticationOperation) != 0) { Status = mSecurity2Table[Index].Security2Handler ( AuthenticationStatus, File, FileBuffer, FileSize, BootPolicy );

从ExecuteSecurity2Handlers 中可以看到,如果mNumberOfSecurity2Handler>0,则根据条件执行对应的mSecurity2Table[Index].Security2Handler;

EFI_STATUS EFIAPI RegisterSecurity2Handler ( IN SECURITY2_FILE_AUTHENTICATION_HANDLER Security2Handler, IN UINT32 AuthenticationOperation ) { EFI_STATUS Status; ASSERT (Security2Handler != NULL); // // Make sure AuthenticationOperation is valid in the register order. // ASSERT (CheckAuthentication2Operation (mCurrentAuthOperation2, AuthenticationOperation)); mCurrentAuthOperation2 = mCurrentAuthOperation2 | AuthenticationOperation; // // Check whether the handler lists is enough to store new handler. // if (mNumberOfSecurity2Handler == mMaxNumberOfSecurity2Handler) { // // Allocate more resources for new handler. // Status = ReallocateSecurity2HandlerTable (); ASSERT_EFI_ERROR (Status); } // // Register new handler into the handler list. // mSecurity2Table[mNumberOfSecurity2Handler].Security2Operation = AuthenticationOperation; mSecurity2Table[mNumberOfSecurity2Handler].Security2Handler = Security2Handler; mNumberOfSecurity2Handler++; return EFI_SUCCESS; }

mNumberOfSecurity2Handler 则通过 RegisterSecurity2Handler 调用会递增;至于谁来调用RegisterSecurity2Handler,暂时先放置一边;

先来看看谁调用SecurityArch Protocol 里边的FileAuthentication,实际上在LoadImage的时候就调用了;

EFI_STATUS CoreLoadImageCommon ( IN BOOLEAN BootPolicy, IN EFI_HANDLE ParentImageHandle, IN EFI_DEVICE_PATH_PROTOCOL *FilePath, IN VOID *SourceBuffer OPTIONAL, IN UINTN SourceSize, IN EFI_PHYSICAL_ADDRESS DstBuffer OPTIONAL, IN OUT UINTN *NumberOfPages OPTIONAL, OUT EFI_HANDLE *ImageHandle, OUT EFI_PHYSICAL_ADDRESS *EntryPoint OPTIONAL, IN UINT32 Attribute ) { ...... if (gSecurity2 != NULL) { // // Verify File Authentication through the Security2 Architectural Protocol // SecurityStatus = gSecurity2->FileAuthentication ( gSecurity2, OriginalFilePath, FHand.Source, FHand.SourceSize, BootPolicy );

在Defer3rdPartyImageLoad中有如果是 FV里边的Image,则直接返回成功,后边则会继续调用ExecuteSecurity2Handlers来处理;

if (FileFromFv (File)) { return EFI_SUCCESS; }

那针对第三方驱动,如果已经EndOfDxe了,则也会返回成功,后边则会继续调用ExecuteSecurity2Handlers来处理;如果在EndOfDxe之前,则通过QueueImage放置在mDeferred3rdPartyImage中,并返回EFI_ACCESS_DENIED,暂时不执行;

if (mEndOfDxe) { mImageLoadedAfterEndOfDxe = TRUE; // // The image might be first time loaded after EndOfDxe, // So ImageInfo can be NULL. // if (ImageInfo != NULL) { ImageInfo->Loaded = TRUE; } return EFI_SUCCESS; } else { // // The image might be second time loaded before EndOfDxe, // So ImageInfo can be non-NULL. // if (ImageInfo == NULL) { QueueImage (File, BootPolicy); } return EFI_ACCESS_DENIED; }

那么3rdImage 什么时候执行 ?

VOID EFIAPI PlatformBootManagerBeforeConsole ( VOID ) { ...... // // We can't signal End-of-Dxe earlier than this. Namely, End-of-Dxe triggers // the preparation of S3 system information. That logic has a hard dependency // on the presence of the FACS ACPI table. Since our ACPI tables are only // installed after PCI enumeration completes, we must not trigger the S3 save // earlier, hence we can't signal End-of-Dxe earlier. // EfiEventGroupSignal (&gEfiEndOfDxeEventGroupGuid); ...... // // Prevent further changes to LockBoxes or SMRAM. // Any TPM 2 Physical Presence Interface opcode must be handled before. // Handle = NULL; Status = gBS->InstallProtocolInterface ( &Handle, &gEfiDxeSmmReadyToLockProtocolGuid, EFI_NATIVE_INTERFACE, NULL ); ASSERT_EFI_ERROR (Status); // // Dispatch deferred images after EndOfDxe event and ReadyToLock // installation. // EfiBootManagerDispatchDeferredImages ();

在Bds阶段PlatformBootManagerBeforeConsole 会首先执行 EndOfDxe, 然后 SmmReadyToLock, 这时才会执行3rdImage, EfiBootManagerDispatchDeferredImages 通过LoadImage -> StartImage来执行;那这个时候LoadImage仍然会调用SecurityArch Protocol 里边的FileAuthentication,这时已经属于EndOfDxe了,则会继续调用ExecuteSecurity2Handlers来处理;

总结:

1.LoadImage时会调用SecurityArch Protocol, ExecuteSecurity2Handlers 可以用来针对Image进行一些安全机制相关的处理

2.如果在EndOfDxe之前,3rd Image则会保存到Deferred List 里边, 最后调用顺序为 EndOfDxe -> SmmReadyToLock -> 3rd Image Start Image

http://www.zskr.cn/news/1492021.html

相关文章:

  • Horizon UAG部署后连接服务器还是红叉?别慌,教你一步步排查(从日志分析到FQDN解析)
  • SolidWorks许可回收误杀率,对比三款横评
  • 2026长治市黄金回收铂金回收白银回收彩金回收机构实力:项链+戒指+手镯+吊坠专业鉴定上门服务及联系方式推荐 - 亦辰小黄鸭
  • 别再只用print了!Python格式化输出M和N运算结果的3种高级技巧
  • 生成式AI发展现状与中长期技术演进趋势分析
  • 《医院HIS药房模块实战避坑系列》之一:月中药品调价+跨价退药账务处理全解析
  • 跨境多店铺管理混乱,先排查浏览器环境边界
  • 别再为Aspose.Words水印发愁了!手把手教你用JD-GUI搞定19.1版本本地化部署
  • 从Mathtype到BibTeX:让你的IEEE LaTeX写作效率翻倍的几个隐藏技巧
  • PostgreSQL 技术日报 (6月8日)|索引预取迭代,AI 安全功能上新
  • 别再死记硬背了!用TensorFlow 2.x手把手复现Google的WideDeep推荐模型
  • C语言介绍——通用的计算机编程语言
  • 云尖信息亮相英特尔至强6+发布会暨数据中心创新日,以全栈能力构筑Agentic AI时代新算力底座
  • 从DH1到3DH5:一文读懂蓝牙射频测试中那些让人头疼的数据包与调制方式
  • 用C语言实战:最小公倍数在嵌入式编程和单片机开发中的一个具体应用案例
  • 告别均匀采样!用PER优先经验回放,让你的DQN在Atari游戏上快人一步
  • Python小说章节自动采集入库工具:含MySQL连接池、去重建表与配置化部署
  • 2026年6月岳阳楼区流量卡“闭眼入”指南:39元电信神卡杀疯了!
  • LLM多智能体语义传播监控与漂移治理方法
  • UniVidX——基于扩散先验的统一多模态视频生成框架
  • 手机拍证件照哪个好2026年专业证件照工具推荐
  • 告别迷茫!工业组态软件选型指南:从Qt、C#到Web,5分钟帮你找到最适合的技术栈
  • 基于STC89C52的智能洗衣机控制原型:三档面料适配+LCD实时显示+Proteus可运行仿真工程
  • 别再为VC++和LabVIEW报错头疼了!手把手教你搞定USB-CAN分析仪软件安装(附避坑指南)
  • STM32F4 CANopen SDO通信避坑指南:心跳关了没?COB-ID算对了吗?
  • 零基础可跑的MATLAB平面应力FEA代码包,含网格设置、求解与应力可视化
  • Kotlin 协程设计思想(九):Flow 到底是什么?为什么 suspend 函数还需要 Flow?
  • 【每日一题】LeetCode 11. 盛最多水的容器 TypeScript
  • 基于STM32物联网WiFi火灾烟雾自动灭火报警器Proteus仿真+代码+报告+视频
  • 从‘Hello World’到完整项目:我的Halcon视觉检测系统搭建全记录(附C#混合编程避坑指南)