]> xenbits.xensource.com Git - people/aperard/ovmf.git/commitdiff
MdePkg: Create Stack Check Null Libs
authorTaylor Beebe <taylor.d.beebe@gmail.com>
Tue, 27 Aug 2024 21:31:48 +0000 (14:31 -0700)
committermergify[bot] <37929162+mergify[bot]@users.noreply.github.com>
Fri, 13 Sep 2024 03:58:46 +0000 (03:58 +0000)
Add Null libs for Stack Check and Stack Check Failure Hook Lib that
allow a platform to opt out of stack checks and the stack check failure
hook lib.

StackCheckLib allows implementation (or in this case null implementation)
of stack checks on binaries. There is a Host Application specific version
of this null lib because MSVC host applications must not be linked against
our lib (so the file here is a no-op but that doesn't cause the build
system to fail the build for not building a file for MSVC) as it links
against the MSVC C runtime lib that provides the stack cookie definitions.
GCC host applications do not link against such a C runtime lib and must
be linked against our version.

StackCheckFailureHookLib lets a platform do custom functionality when a
stack check failure occurs (such as log it to a platform defined
mechanism). The null lib simply returns.

Signed-off-by: Oliver Smith-Denny <osde@linux.microsoft.com>
15 files changed:
MdePkg/Include/Library/StackCheckFailureHookLib.h [new file with mode: 0644]
MdePkg/Library/StackCheckFailureHookLibNull/StackCheckFailureHook.c [new file with mode: 0644]
MdePkg/Library/StackCheckFailureHookLibNull/StackCheckFailureHookLibNull.inf [new file with mode: 0644]
MdePkg/Library/StackCheckLibNull/IA32/StackCheckFunctionsMsvc.nasm [new file with mode: 0644]
MdePkg/Library/StackCheckLibNull/StackCheckLibHostApplicationMsvc.c [new file with mode: 0644]
MdePkg/Library/StackCheckLibNull/StackCheckLibNull.inf [new file with mode: 0644]
MdePkg/Library/StackCheckLibNull/StackCheckLibNullGcc.c [new file with mode: 0644]
MdePkg/Library/StackCheckLibNull/StackCheckLibNullHostApplication.inf [new file with mode: 0644]
MdePkg/Library/StackCheckLibNull/StackCheckLibNullMsvc.c [new file with mode: 0644]
MdePkg/Library/StackCheckLibNull/X64/StackCheckFunctionsMsvc.nasm [new file with mode: 0644]
MdePkg/MdeLibs.dsc.inc
MdePkg/MdePkg.ci.yaml
MdePkg/MdePkg.dec
MdePkg/MdePkg.dsc
MdePkg/Test/MdePkgHostTest.dsc

diff --git a/MdePkg/Include/Library/StackCheckFailureHookLib.h b/MdePkg/Include/Library/StackCheckFailureHookLib.h
new file mode 100644 (file)
index 0000000..f0657dd
--- /dev/null
@@ -0,0 +1,26 @@
+/** @file\r
+  Library provides a hook called when a stack cookie check fails.\r
+\r
+  Copyright (c) Microsoft Corporation.\r
+  SPDX-License-Identifier: BSD-2-Clause-Patent\r
+**/\r
+\r
+#ifndef STACK_COOKIE_FAILURE_HOOK_LIB_H_\r
+#define STACK_COOKIE_FAILURE_HOOK_LIB_H_\r
+\r
+#include <Uefi.h>\r
+\r
+/**\r
+  This function gets called when a compiler generated stack cookie fails. This allows a platform to hook this\r
+  call and perform any required actions/telemetry at that time.\r
+\r
+  @param  FailureAddress  The address of the function that failed the stack cookie check.\r
+\r
+**/\r
+VOID\r
+EFIAPI\r
+StackCheckFailureHook (\r
+  VOID  *FailureAddress\r
+  );\r
+\r
+#endif\r
diff --git a/MdePkg/Library/StackCheckFailureHookLibNull/StackCheckFailureHook.c b/MdePkg/Library/StackCheckFailureHookLibNull/StackCheckFailureHook.c
new file mode 100644 (file)
index 0000000..0a258e4
--- /dev/null
@@ -0,0 +1,25 @@
+/** @file\r
+  Library provides a hook called when a stack cookie check fails.\r
+\r
+  Copyright (c) Microsoft Corporation.\r
+  SPDX-License-Identifier: BSD-2-Clause-Patent\r
+**/\r
+\r
+#include <Base.h>\r
+#include <Uefi.h>\r
+\r
+/**\r
+  This function gets called when a compiler generated stack cookie fails. This allows a platform to hook this\r
+  call and perform any required actions/telemetry at that time.\r
+\r
+  @param  FailureAddress  The address of the function that failed the stack cookie check.\r
+\r
+**/\r
+VOID\r
+EFIAPI\r
+StackCheckFailureHook (\r
+  VOID  *FailureAddress\r
+  )\r
+{\r
+  return;\r
+}\r
diff --git a/MdePkg/Library/StackCheckFailureHookLibNull/StackCheckFailureHookLibNull.inf b/MdePkg/Library/StackCheckFailureHookLibNull/StackCheckFailureHookLibNull.inf
new file mode 100644 (file)
index 0000000..300073a
--- /dev/null
@@ -0,0 +1,20 @@
+## @file\r
+#  Library provides a hook called when a stack cookie check fails.\r
+#\r
+#  Copyright (c) Microsoft Corporation.\r
+#  SPDX-License-Identifier: BSD-2-Clause-Patent\r
+##\r
+\r
+[Defines]\r
+  INF_VERSION                    = 1.29\r
+  BASE_NAME                      = StackCheckFailureHookLibNull\r
+  FILE_GUID                      = 9ca2587c-d1f2-451a-989a-d49a9a0a613e\r
+  MODULE_TYPE                    = BASE\r
+  VERSION_STRING                 = 1.0\r
+  LIBRARY_CLASS                  = StackCheckFailureHookLib\r
+\r
+[Sources]\r
+  StackCheckFailureHook.c\r
+\r
+[Packages]\r
+  MdePkg/MdePkg.dec\r
diff --git a/MdePkg/Library/StackCheckLibNull/IA32/StackCheckFunctionsMsvc.nasm b/MdePkg/Library/StackCheckLibNull/IA32/StackCheckFunctionsMsvc.nasm
new file mode 100644 (file)
index 0000000..510d500
--- /dev/null
@@ -0,0 +1,21 @@
+;------------------------------------------------------------------------------\r
+; IA32/StackCheckFunctionsMsvc.nasm\r
+;\r
+; Copyright (c) Microsoft Corporation.\r
+; SPDX-License-Identifier: BSD-2-Clause-Patent\r
+;------------------------------------------------------------------------------\r
+\r
+    DEFAULT REL\r
+    SECTION .text\r
+\r
+global ASM_PFX(__report_rangecheckfailure)\r
+ASM_PFX(__report_rangecheckfailure):\r
+    ret\r
+\r
+global ASM_PFX(__GSHandlerCheck)\r
+ASM_PFX(__GSHandlerCheck):\r
+    ret\r
+\r
+global @__security_check_cookie@4\r
+@__security_check_cookie@4:\r
+    ret\r
diff --git a/MdePkg/Library/StackCheckLibNull/StackCheckLibHostApplicationMsvc.c b/MdePkg/Library/StackCheckLibNull/StackCheckLibHostApplicationMsvc.c
new file mode 100644 (file)
index 0000000..6af9891
--- /dev/null
@@ -0,0 +1,13 @@
+/** @file\r
+  This file is empty to allow host applications\r
+  to use the MSVC C runtime lib that provides\r
+  stack cookie definitions without breaking the\r
+  build.\r
+\r
+  Copyright (c) Microsoft Corporation.\r
+  SPDX-License-Identifier: BSD-2-Clause-Patent\r
+**/\r
+\r
+#include <Uefi.h>\r
+\r
+extern VOID  *__security_cookie;\r
diff --git a/MdePkg/Library/StackCheckLibNull/StackCheckLibNull.inf b/MdePkg/Library/StackCheckLibNull/StackCheckLibNull.inf
new file mode 100644 (file)
index 0000000..bb42833
--- /dev/null
@@ -0,0 +1,41 @@
+## @file\r
+#  Null library instance for StackCheckLib which can be included\r
+#  when a build needs to include stack check functions but does\r
+#  not want to generate stack check failures.\r
+#\r
+#  Copyright (c) Microsoft Corporation.\r
+#  SPDX-License-Identifier: BSD-2-Clause-Patent\r
+##\r
+\r
+[Defines]\r
+  INF_VERSION                    = 1.29\r
+  BASE_NAME                      = StackCheckLibNull\r
+  FILE_GUID                      = f6ef2763-ca3b-4c6f-a931-2a48de3ce352\r
+  MODULE_TYPE                    = BASE\r
+  VERSION_STRING                 = 1.0\r
+  LIBRARY_CLASS                  = StackCheckLib\r
+\r
+[Sources]\r
+  StackCheckLibNullGcc.c  | GCC\r
+  StackCheckLibNullMsvc.c | MSFT\r
+\r
+[Sources.IA32]\r
+  IA32/StackCheckFunctionsMsvc.nasm | MSFT\r
+\r
+[Sources.X64]\r
+  X64/StackCheckFunctionsMsvc.nasm | MSFT\r
+\r
+[Packages]\r
+  MdePkg/MdePkg.dec\r
+\r
+[BuildOptions]\r
+  # We cannot build the MSVC version with /GL (whole program optimization) because we run into linker error\r
+  # LNK1237, which is a failure to link against a symbol from a library compiled with /GL. The whole program\r
+  # optimization tries to do away with references to this symbol. The solution is to not compile the stack\r
+  # check libs with /GL\r
+  MSFT:*_*_*_CC_FLAGS = /GL-\r
+\r
+  # We cannot build the GCC version with LTO (link time optimization) because we run into linker errors where\r
+  # the stack cookie variable has been optimized away, as it looks to GCC like the variable is not used, because\r
+  # the compiler inserts the usage.\r
+  GCC:*_*_*_CC_FLAGS = -fno-lto\r
diff --git a/MdePkg/Library/StackCheckLibNull/StackCheckLibNullGcc.c b/MdePkg/Library/StackCheckLibNull/StackCheckLibNullGcc.c
new file mode 100644 (file)
index 0000000..cc30632
--- /dev/null
@@ -0,0 +1,23 @@
+/** @file\r
+  Defines the stack cookie variable for GCC and Clang compilers.\r
+\r
+  Copyright (c) Microsoft Corporation.\r
+  SPDX-License-Identifier: BSD-2-Clause-Patent\r
+**/\r
+\r
+#include <Uefi.h>\r
+\r
+VOID  *__stack_chk_guard = (VOID *)(UINTN)0x0;\r
+\r
+/**\r
+  This function gets called when a gcc/clang generated stack cookie fails. This implementation does nothing when\r
+  a stack cookie failure occurs.\r
+\r
+**/\r
+VOID\r
+EFIAPI\r
+__stack_chk_fail (\r
+  VOID\r
+  )\r
+{\r
+}\r
diff --git a/MdePkg/Library/StackCheckLibNull/StackCheckLibNullHostApplication.inf b/MdePkg/Library/StackCheckLibNull/StackCheckLibNullHostApplication.inf
new file mode 100644 (file)
index 0000000..3e89826
--- /dev/null
@@ -0,0 +1,34 @@
+## @file\r
+#  Null library instance for StackCheckLib which can be included\r
+#  when a build needs to include stack check functions but does\r
+#  not want to generate stack check failures. This instance is used\r
+#  for HOST_APPLICATIONS specifically, as MSVC host applications link\r
+#  to the C runtime lib that contains the stack cookie definitions, so\r
+#  must link to a completely null version of this lib, whereas GCC host\r
+#  host applications do not link to a C runtime lib that contains the stack\r
+#  cookie definitions, so we must link against our version.\r
+#\r
+#  Copyright (c) Microsoft Corporation.\r
+#  SPDX-License-Identifier: BSD-2-Clause-Patent\r
+##\r
+\r
+[Defines]\r
+  INF_VERSION                    = 1.29\r
+  BASE_NAME                      = StackCheckLibNullHostApplication\r
+  FILE_GUID                      = 7EBE7BD1-0D92-4609-89AA-6EA3815CB844\r
+  MODULE_TYPE                    = HOST_APPLICATION\r
+  VERSION_STRING                 = 1.0\r
+  LIBRARY_CLASS                  = StackCheckLib|HOST_APPLICATION\r
+\r
+[Sources]\r
+  StackCheckLibHostApplicationMsvc.c | MSFT\r
+  StackCheckLibNullGcc.c             | GCC\r
+\r
+[Packages]\r
+  MdePkg/MdePkg.dec\r
+\r
+[BuildOptions]\r
+  # We cannot build the GCC version with LTO (link time optimization) because we run into linker errors where\r
+  # the stack cookie variable has been optimized away, as it looks to GCC like the variable is not used, because\r
+  # the compiler inserts the usage. We do not worry about the MSVC version here as it is a no-op.\r
+  GCC:*_*_*_CC_FLAGS = -fno-lto\r
diff --git a/MdePkg/Library/StackCheckLibNull/StackCheckLibNullMsvc.c b/MdePkg/Library/StackCheckLibNull/StackCheckLibNullMsvc.c
new file mode 100644 (file)
index 0000000..ba9a4e6
--- /dev/null
@@ -0,0 +1,10 @@
+/** @file\r
+  Defines the stack cookie variable for GCC, Clang and MSVC compilers.\r
+\r
+  Copyright (c) Microsoft Corporation.\r
+  SPDX-License-Identifier: BSD-2-Clause-Patent\r
+**/\r
+\r
+#include <Uefi.h>\r
+\r
+VOID  *__security_cookie = (VOID *)(UINTN)0x0;\r
diff --git a/MdePkg/Library/StackCheckLibNull/X64/StackCheckFunctionsMsvc.nasm b/MdePkg/Library/StackCheckLibNull/X64/StackCheckFunctionsMsvc.nasm
new file mode 100644 (file)
index 0000000..f4639a0
--- /dev/null
@@ -0,0 +1,21 @@
+;------------------------------------------------------------------------------\r
+; X64/StackCheckFunctionsMsvc.nasm\r
+;\r
+; Copyright (c) Microsoft Corporation.\r
+; SPDX-License-Identifier: BSD-2-Clause-Patent\r
+;------------------------------------------------------------------------------\r
+\r
+    DEFAULT REL\r
+    SECTION .text\r
+\r
+global ASM_PFX(__report_rangecheckfailure)\r
+ASM_PFX(__report_rangecheckfailure):\r
+    ret\r
+\r
+global ASM_PFX(__GSHandlerCheck)\r
+ASM_PFX(__GSHandlerCheck):\r
+    ret\r
+\r
+global ASM_PFX(__security_check_cookie)\r
+ASM_PFX(__security_check_cookie):\r
+    ret\r
index e40ff7d95e046bfd9655efbdda4f8d93b0017a10..4e3858edb62741bf813cc1fc6c0a1b5de7cd8676 100644 (file)
@@ -30,3 +30,9 @@
   # definitions for the intrinsic functions.\r
   #\r
   NULL|MdePkg/Library/CompilerIntrinsicsLib/CompilerIntrinsicsLib.inf\r
+\r
+# Stack Cookies cannot be generically applied to SEC modules because they may not define _ModuleEntryPoint and when we\r
+# link a library in, we have to be able to define the entry point. SEC modules that do define _ModuleEntryPoint can\r
+# apply a library class override to get StackCheckLibNull.inf\r
+[LibraryClasses.common.PEI_CORE, LibraryClasses.common.PEIM, LibraryClasses.common.DXE_CORE, LibraryClasses.common.SMM_CORE, LibraryClasses.common.MM_CORE_STANDALONE, LibraryClasses.common.DXE_DRIVER, LibraryClasses.common.DXE_RUNTIME_DRIVER, LibraryClasses.common.DXE_SMM_DRIVER, LibraryClasses.common.MM_STANDALONE, LibraryClasses.common.UEFI_DRIVER, LibraryClasses.common.UEFI_APPLICATION]\r
+  NULL|MdePkg/Library/StackCheckLibNull/StackCheckLibNull.inf\r
index f2d81af080eea5fcaac4a067297aa05579ecac37..cebccba59d2975482b5c881f5a3bac48f43c7ee8 100644 (file)
@@ -61,7 +61,9 @@
             "7007", "_EFI_SPI_NOR_FLASH_PROTOCOL",\r
             "7007", "_EFI_SPI_HC_PROTOCOL",\r
             "8002", "aligned (",\r
-            "4002", "_ReturnAddress"\r
+            "4002", "_ReturnAddress",\r
+            "8005", "__security_cookie",\r
+            "8006", "__stack_chk_fail"\r
         ],\r
         ## Both file path and directory path are accepted.\r
         "IgnoreFiles": [\r
index 8d5947fc9e9a165f3c13eb5a91e39289f5966469..b542d6d832354b59282a4d97628d5483ea26ad9d 100644 (file)
   #\r
   TraceHubDebugSysTLib|Include/Library/TraceHubDebugSysTLib.h\r
 \r
+  ##  @libraryclass  Provides a hook called when a stack cookie check fails.\r
+  #\r
+  StackCheckFailureHookLib|Include/Library/StackCheckFailureHookLib.h\r
+\r
 [LibraryClasses.IA32, LibraryClasses.X64, LibraryClasses.AARCH64]\r
   ##  @libraryclass  Provides services to generate random number.\r
   #\r
index ebcd79864d4fab1fd528c572986602450f7d8a8d..f410a89a00f2fc6767b89834b326ed276c1fe1b4 100644 (file)
   MdePkg/Library/JedecJep106Lib/JedecJep106Lib.inf\r
   MdePkg/Library/BaseFdtLib/BaseFdtLib.inf\r
 \r
+  MdePkg/Library/StackCheckFailureHookLibNull/StackCheckFailureHookLibNull.inf\r
+  MdePkg/Library/StackCheckLibNull/StackCheckLibNull.inf\r
+\r
 [Components.IA32, Components.X64, Components.ARM, Components.AARCH64]\r
   #\r
   # Add UEFI Target Based Unit Tests\r
index 6a85d02236a044f4148e93702b807130c0071e99..1351d191575ef7cd8c60b706bcc5899d11f65f9d 100644 (file)
@@ -47,3 +47,5 @@
   MdePkg/Test/Mock/Library/GoogleTest/MockPeiServicesLib/MockPeiServicesLib.inf\r
   MdePkg/Test/Mock/Library/GoogleTest/MockHobLib/MockHobLib.inf\r
   MdePkg/Test/Mock/Library/GoogleTest/MockFdtLib/MockFdtLib.inf\r
+\r
+  MdePkg/Library/StackCheckLibNull/StackCheckLibNullHostApplication.inf\r