💻
UEFI 프로젝트
  • 🧑‍🏫프로젝트 개요
  • 📖UEFI 개념
    • 1. BIOS의 과거
    • 2. UEFI 개념
    • 3. BIOS vs UEFI
    • 4. UEFI 부팅 단계
  • 🖥️UEFI 개발
    • UEFI 개발 시작하기
      • 0. EDK II 빌드 환경 구성
      • 1. 간단한 EFI application 만들기
      • 2. 간단한 Pkg 만들기
      • 3. Hello World 출력하기
      • 4. 라이브러리와 Hello World
      • 5. Conf를 통한 Build 단순화
    • 핸들 및 프로토콜
      • 6. 핸들/프로토콜 데이터 베이스 구조 - Part 1
      • 7. 핸들/프로토콜 데이터 베이스 구조 - Part 2
      • 8. HandleProtocol API 함수 & ImageHandle 프로토콜을 통한 정보
      • 9. ProtocolsPerHandle API를 통한 ImageHandle 프로토콜 가져오기
      • 10. EFI_STATUS 타입 과 EFI_ERROR 매크로
    • 메모리 맵
      • 11. EFI 메모리 맵 정보 얻기
      • 12. EFI 메모리 맵을 리눅스 커널 스타일로 바꾸기
    • 명령줄 인수를 받는 간단한 앱 만들기
      • 13.ShellAppMain Entry point
      • 14.gRT->GetNextVariableName API를 사용하여 모든 변수 이름 및 GUID 가져오기
    • 부팅 옵션
      • 15. gRT->GetVariable API를 사용하여 부팅 변수 가져오기 및 구문 분석
      • 16. OVMF 이미지 내에 부팅 옵션 추가
      • 17. 부팅 옵션에 WaitForEvent 함수 추가
      • 18. ReadKeyStroke 함수로 사용자 입력 처리
      • 19. bcfg 명령어를 사용한 부팅 옵션 수정
    • PCD
      • 20. PCD 소개
      • 21. PCD 변수에 대한 Overriding
      • 22. Feature Flag PCD와 BOOLEAN FixedAtBuild PCD의 비교
      • 23. PatchableInModule PCD 및 GenPatchPcdTable/PatchPcdValue 유틸리티를 통해 PCD를 변경하는 방법
      • 24. Dynamic/DynamiEx PCDs
      • 25. PCD 더 알아보기
    • 테이블
      • 26. EFI_CONFIGURATION_TABLE에서 참조되는 테이블
      • 27. dmem/EFI_SMBIOS_PROTOCOL/smbiosview를 통해서 SMBIOS 정보 가져오기
      • 28. EFI_SHELL_PROTOCOL을 통하여 ACPI 테이블을 파일에 저장하기
      • 29. EFI_ACPI_SDT_PROTOCOL 및 ShellLib를 사용하여 ACPI BGRT 테이블에서 BMP 이미지 저장하기
    • PCI
      • 30. PCI 루트 브리지 찾은 후 시스템의 모든 PCI 기능 가져오기
      • 31. ShellLib/PrintLib 함수를 사용해 PCI Vendor/Device 정보 가져오기
      • 32. EFI_PCI_IO_PROTOCOL을 사용해 PCI Option ROM 이미지 표시
      • 33. EfiRom 유틸리티를 사용한 PCI Option ROM 이미지 파싱 및 생성
    • 드라이버 및 라이브러리
      • 34. 간단한 UEFI 드라이버 생성
      • 35. 애플리케이션에서 사용할 간단한 라이브러리 생성
      • 36. Library의 constructor와 destructor, NULL Library
      • 37. Shell에 acpiview 명령을 추가하는 방법 조사
      • 38. 사용자 지정 프로토콜을 만들고 사용하기
      • 39. RegisterKeyNotify / UnrigisterKeyNotify 함수를 사용해 단축키 기능을 추가하는 드라이버 만들기
      • 40. Key #### NVRAM 변수
    • 디버그
      • 41. DEBUG 출력문 내부 구조와 DEBUG 문 제어를 위한 PCD 분석, 그리고 OVMF 부트 로그 가져오기
      • 42. GDB를 이용한 Driver/Application 및 OVMF Debug
    • HII
      • 43. HII 데이터베이스 개념 및 출력
      • 44. HII 데이터베이스 내부
      • 45. EFI_HII_DATABASE_PROTOCOL의 NewPackageList를 사용하여 문자열 패키지가 포함된 문자열 목록 게시
      • 46. EFI_HII_DATABASE_PROTOCOL의 NewPackageList를 사용하여 문자열 패키지가 포함된 HII 패키지 목록 게시
      • 47. EFI_HII_DATABASE_PROTOCOL의 NewPackageList를 사용하여 문자열 패키지가 포함된 HII 패키지 목록 게시
      • 48. UNI 파일 및 HiiLib를 사용하여 HII String 패키지 게시 및 작업하기
      • 49.MODULE_UNI_FILE/PACKAGE_UNI_FILE/[UserExtensions.TianoCore."ExtraFiles"]의 도움으로 UNI 파일 선언하기
      • 50.UEFI_HII_RESOURCE_SECTION을 사용하여 문자열 패키지와 함께 HII 패키지 목록 게시하기
      • 51. UEFI APP에 메뉴얼 추가하기(shell의 -?와 help 옵션)
      • 52. Russian 글꼴 추가 - Part 1.
      • 53. Russian 글꼴 추가 - Part 2.
      • 54. EFI_HII_STRING_PROTOCOL의 NewString 및 SetString 함수를 사용하여 다른 언어에 대한 문자열 패키지를 동적으로 추가
      • 55. PlatformLangCodes EFI 변수 수정 및 다른 언어를 동적 추가하기
      • 56. 코드에서 FILE_GUID 및 BASE_NAME을 가져오기
    • VFR
      • 57. VFR을 사용해 간단한 폼 생성 및 EFI_FORM_BROWSER2_PROTOCOL.SendForm()를 통해 화면에 폼 표시하기
      • 58. VFR 요소 : subtitle 및 text
      • 59. 간단한 폼 애플리케이션을 UEFI 드라이버 Form으로 변환하기
      • 60. gRT->SetVariable() 함수를 사용한 UEFI 변수 생성, 변경 및 삭제
      • 61.dmpstore 명령을 사용하여 변수를 파일에 저장/로드하기
      • 62. UEFI Device path의 구조
      • 63. checkbox를 가진 HII 폼 만들기
      • 64. checkbox를 가진 HII폼 만들기
      • 65. VFR 추가 입력 요소 Part 1: number
      • 66. VFR 추가 입력 요소 Part 2: string
      • 67. VFR 추가 입력 요소 Part 3: date & time
      • 68. VFR 추가 입력 요소 Part 3: oneof & orderedlist
      • 69. VFR의 조건부 키워드
      • 70. VFR의 상수 및 연산자가 내장된 기본 조건문
      • 71. 기본 VFR 내장 문자열용 함수
      • 72. label 키워드를 이용하여 HII 양식에 동적 요소 추가하기
      • 73. VFR question 기본값 설정
  • 🔐UEFI 보안
    • 1. 개요
    • 2. 공격 벡터
    • 3. mitigation
    • 4. 정적 분석 방법
    • 5. 동적 분석 방법
Powered by GitBook
On this page
  • Compile acpiview as a separate app
  • 자체적으로 'acpiview' 명령을 사용하여 Shell을 컴파일하고 OVMF 실행
  • acpiview 명령어가 포함된 Shell로 OVMF image 업데이트
  1. UEFI 개발
  2. 드라이버 및 라이브러리

37. Shell에 acpiview 명령을 추가하는 방법 조사

Previous36. Library의 constructor와 destructor, NULL LibraryNext38. 사용자 지정 프로토콜을 만들고 사용하기

Last updated 2 years ago

ShellPkg 라이브러리()를 검색하면, UefiShellAcpiViewCommandLib() 폴더가 있다.

이 폴더는 in-shell acpiview 명령을 지원하는 라이브러리를 제공한다. INF 파일을 확인하면, 가 표시된다.

# Provides Shell 'acpiview' command functions

하지만, 지금의 OVMF 빌드에서 acpiview를 실행하려고 하면, 다음 명령이 인식되지 않는다.

FS0:\> acpiview
'acpiview' is not recognized as an internal or external command, operable program, or script file.

이 'acpiview' 명령 기능을 사용하는 데는 세 가지 방법이 있다.

  • acpiview를 별도의 애플리케이션으로 컴파일하고, 일반 UEFI shell 애플리케이션으로 실행한다.

  • 자체적으로 'acpiview' 명령을 사용하여 shell을 컴파일하고 OVMF에서 실행한다.

  • 'acpiview' 명령이 포함된 shell로 OVMF 이미지 업데이트

Compile acpiview as a separate app

짐작컨대 이 방법이 가장 쉬운 방법이라고 생각한다.

도움을 받아 이 작업을 수행할 수 있다.

소스 파일을 보면 매우 간단하다는 것을 알 수 있다. 기본 기능은 ShellCommandRunAcpiView 함수에서 라이브러리 호출을 수행한다.

EFI_STATUS
EFIAPI
AcpiViewAppMain (
  IN EFI_HANDLE        ImageHandle,
  IN EFI_SYSTEM_TABLE  *SystemTable
  )
{
  return ShellCommandRunAcpiView (gImageHandle, SystemTable);
}

애플리케이션 빌드실행

build --platform=ShellPkg/ShellPkg.dsc --module=ShellPkg/Application/AcpiViewApp/AcpiViewApp.inf --arch=X64 --buildtarget=RELEASE --tagname=GCC5

이 이미지를 QEMU 공유 폴더에 옮기고,

cp Build/Shell/RELEASE_GCC5/X64/AcpiViewApp.efi ~/UEFI_disk/

해당된 애플리케이션을 실행하면,

FS0:\> AcpiViewApp.efi -?
Display ACPI Table information.

ACPIVIEWAPP.EFI [[-?] | [[[[-l] | [-s AcpiTable [-d]]] [-q] [-h]] [-r Spec]]]


  -l - Display list of installed ACPI Tables.
  -s - Display only the specified AcpiTable type and only support single
       invocation option.
         AcpiTable    : The required ACPI Table type.
  -d - Generate a binary file dump of the specified AcpiTable.
  -q - Quiet. Suppress errors and warnings. Disables consistency checks.
  -h - Enable colour highlighting.
  -r - Validate that all required ACPI tables are installed
         Spec  : Specification to validate against.
                 For Arm, the possible values are:
                   0 - Server Base Boot Requirements v1.0
                   1 - Server Base Boot Requirements v1.1
                   2 - Server Base Boot Requirements v1.2
  -? - Show help.


  This program is provided to allow examination of ACPI table values from the
  UEFI Shell.  This can help with investigations, especially at that stage
  where the tables are not enabling an OS to boot.
  The program is not exhaustive, and only encapsulates detailed knowledge of a
  limited number of table types.

  Default behaviour is to display the content of all tables installed.
  'Known' table types (listed in NOTES below) will be parsed and displayed
  with descriptions and field values.  Where appropriate a degree of
  consistency checking is done and errors may be reported in the output.
  Other table types will be displayed as an array of Hexadecimal bytes.

  To facilitate debugging, the -s and -d options can be used to generate a
  binary file image of a table that can be copied elsewhere for investigation
  using tools such as those provided by acpica.org.  This is especially
  relevant for AML type tables like DSDT and SSDT.

NOTES:
  1. The AcpiTable parameter can match any installed table type.
     Tables without specific handling will be displayed as a raw hex dump (or
     dumped to a file if -d is used).
  2. -s option supports to display the specified AcpiTable type that is present
     in the system. For normal type AcpiTable, it would display the data of the
     AcpiTable and AcpiTable header. The following type may contain header type
     other than AcpiTable header. The actual header can refer to the ACPI spec
     6.3
     Extra A. Particular types:
       APIC  - Multiple APIC Description Table (MADT)
       BGRT  - Boot Graphics Resource Table
       DBG2  - Debug Port Table 2
       DSDT  - Differentiated System Description Table
       FACP  - Fixed ACPI Description Table (FADT)
       GTDT  - Generic Timer Description Table
       IORT  - IO Remapping Table
       MCFG  - Memory Mapped Config Space Base Address Description Table
       PPTT  - Processor Properties Topology Table
       RSDP  - Root System Description Pointer
       SLIT  - System Locality Information Table
       SPCR  - Serial Port Console Redirection Table
       SRAT  - System Resource Affinity Table
       SSDT  - Secondary SystemDescription Table
       XSDT  - Extended System Description Table



EXAMPLES:
  * To display a list of the installed table types:
    fs0:\> acpiviewapp.efi -l

  * To parse and display a specific table type:
    fs0:\> acpiviewapp.efi -s GTDT

  * To save a binary dump of the contents of a table to a file
    in the current working directory:
    fs0:\> acpiviewapp.efi -s DSDT -d

  * To display contents of all ACPI tables:
    fs0:\> acpiviewapp.efi

  * To check if all Server Base Boot Requirements (SBBR) v1.2 mandatory
    ACPI tables are installed (Arm only):
    fs0:\> acpiviewapp.efi -r 2

이 프로그램을 사용하면 시스템의 ACPI 테이블을 나열할 수 있다.

FS0:\> AcpiViewApp.efi -l

Installed Table(s):
           1. RSDP
           2. XSDT
           3. FACP
           4. FACS
           5. DSDT
           6. APIC
           7. HPET
           8. BGRT

테이블의 내용 표시

FS0:\> AcpiViewApp.efi -s BGRT


 --------------- BGRT Table ---------------

Address  : 0x7B77000
Length   : 56

00000000 : 42 47 52 54 38 00 00 00 - 01 C5 49 4E 54 45 4C 20   BGRT8.....INTEL
00000010 : 45 44 4B 32 20 20 20 20 - 02 00 00 00 20 20 20 20   EDK2    ....
00000020 : 13 00 00 01 01 00 01 00 - 18 30 8B 06 00 00 00 00   .........0......
00000030 : 2F 01 00 00 0F 01 00 00                             /.......

Table Checksum : OK

BGRT                                 :
  Signature                          : BGRT
  Length                             : 56
  Revision                           : 1
  Checksum                           : 0xC5
  Oem ID                             : INTEL
  Oem Table ID                       : EDK2
  Oem Revision                       : 0x2
  Creator ID                         :
  Creator Revision                   : 0x1000013
  Version                            : 0x1
  Status                             : 0x1
  Image Type                         : 0x0
  Image Address                      : 0x68B3018
  Image Offset X                     : 303
  Image Offset Y                     : 271

Table Statistics:
        0 Error(s)
        0 Warning(s)

혹은 ACPI 테이블의 덤프

FS0:\> AcpiViewApp.efi -s APIC -d
Dumping ACPI table to : .\APIC0000.bin ... DONE.

이 이미지는 우리가 이전에 했던 것처럼, iasl -d <file>로 disassemble을 해낼 수 있다.

자체적으로 'acpiview' 명령을 사용하여 Shell을 컴파일하고 OVMF 실행

이 방법은 좀 의아하긴 하지만, shell 애플리케이션 내부에서 shell 애플리케이션을 실행할 수 있다.

일반적인 경우는 아니지만, 프로젝트에서 실제로 사용할 수 있는 shell 이미지를 컴파일하는 방법을 아는 데 도움이 될 것이다.

  • general command가 있을 것이다.

  • 다른 하나는 모든 명령어가 있을 것이다.

ShellPkg/Application/Shell/Shell.inf {
  <PcdsFixedAtBuild>
    gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE
  <LibraryClasses>
    NULL|ShellPkg/Library/UefiShellLevel2CommandsLib/UefiShellLevel2CommandsLib.inf
    NULL|ShellPkg/Library/UefiShellLevel1CommandsLib/UefiShellLevel1CommandsLib.inf
    NULL|ShellPkg/Library/UefiShellLevel3CommandsLib/UefiShellLevel3CommandsLib.inf
fndef $(NO_SHELL_PROFILES)
    NULL|ShellPkg/Library/UefiShellDriver1CommandsLib/UefiShellDriver1CommandsLib.inf
    NULL|ShellPkg/Library/UefiShellInstall1CommandsLib/UefiShellInstall1CommandsLib.inf
    NULL|ShellPkg/Library/UefiShellDebug1CommandsLib/UefiShellDebug1CommandsLib.inf
    NULL|ShellPkg/Library/UefiShellNetwork1CommandsLib/UefiShellNetwork1CommandsLib.inf
    NULL|ShellPkg/Library/UefiShellNetwork2CommandsLib/UefiShellNetwork2CommandsLib.inf
ndif #$(NO_SHELL_PROFILES)
}

#
# Build a second version of the shell with all commands integrated
#
ShellPkg/Application/Shell/Shell.inf {
 <Defines>
    FILE_GUID = EA4BB293-2D7F-4456-A681-1F22F42CD0BC
  <PcdsFixedAtBuild>
    gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE
  <LibraryClasses>
    NULL|ShellPkg/Library/UefiShellLevel2CommandsLib/UefiShellLevel2CommandsLib.inf
    NULL|ShellPkg/Library/UefiShellLevel1CommandsLib/UefiShellLevel1CommandsLib.inf
    NULL|ShellPkg/Library/UefiShellLevel3CommandsLib/UefiShellLevel3CommandsLib.inf
    NULL|ShellPkg/Library/UefiShellDriver1CommandsLib/UefiShellDriver1CommandsLib.inf
    NULL|ShellPkg/Library/UefiShellInstall1CommandsLib/UefiShellInstall1CommandsLib.inf
    NULL|ShellPkg/Library/UefiShellDebug1CommandsLib/UefiShellDebug1CommandsLib.inf
    NULL|ShellPkg/Library/UefiShellNetwork1CommandsLib/UefiShellNetwork1CommandsLib.inf
    NULL|ShellPkg/Library/UefiShellNetwork2CommandsLib/UefiShellNetwork2CommandsLib.inf
    NULL|ShellPkg/Library/UefiShellAcpiViewCommandLib/UefiShellAcpiViewCommandLib.inf         <------- acpiview is present in this Shell version
}
[Defines]
  INF_VERSION                    = 0x00010019
  BASE_NAME                      = UefiShellAcpiViewCommandLib
  FILE_GUID                      = FB5B305E-84F5-461F-940D-82D345757AFA
  MODULE_TYPE                    = UEFI_APPLICATION
  VERSION_STRING                 = 1.0
  LIBRARY_CLASS                  = AcpiViewCommandLib|UEFI_APPLICATION UEFI_DRIVER
  CONSTRUCTOR                    = UefiShellAcpiViewCommandLibConstructor
  DESTRUCTOR                     = UefiShellAcpiViewCommandLibDestructor

  ...
EFI_STATUS
EFIAPI
UefiShellAcpiViewCommandLibConstructor (
  IN EFI_HANDLE        ImageHandle,
  IN EFI_SYSTEM_TABLE  *SystemTable
  )
{
 ...
  // Install our Shell command handler
  ShellCommandRegisterCommandName (
    L"acpiview",
    ShellCommandRunAcpiView,
    ShellCommandGetManFileNameAcpiView,
    0,
    L"acpiview",
    TRUE,
    gShellAcpiViewHiiHandle,
    STRING_TOKEN (STR_GET_HELP_ACPIVIEW)
    );

  return EFI_SUCCESS;
}

별로 복잡한 명령어가 아니기 때문에, 해당 명령어는 Shell에 추가해 줄 수도 있다. 이후 장에서 작성해 둘 생각이다.

이제 다음 명령어를 실행해 Shell 애플리케이션을 빌드 해보자.

build --platform=ShellPkg/ShellPkg.dsc --module=ShellPkg/Application/Shell/Shell.inf --arch=X64 --buildtarget=RELEASE --tagname=GCC5

빌드 이후에 build 폴더에는 다음 두 파일들이 존재하게 될 것이다.

$ ls Build/Shell/RELEASE_GCC5/X64/Shell*.efi
Build/Shell/RELEASE_GCC5/X64/Shell_7C04A583-9E3E-4f1c-AD65-E05268D0B4D1.efi
Build/Shell/RELEASE_GCC5/X64/Shell_EA4BB293-2D7F-4456-A681-1F22F42CD0BC.efi

ShellPkg.dsc 코드를 유심히 살펴보면, 우리가 필요로 하는 이미지가 EA4BB293-2D7F-4456-A681-1F22F42CD0BC를 GUID 값으로 하는 이미지 라는 것을 알 수 있다.

이를 QEMU 공유 폴더에 복사한다.

$ cp Build/Shell/RELEASE_GCC5/X64/Shell_EA4BB293-2D7F-4456-A681-1F22F42CD0BC.efi ~/UEFI_disk/

기본 shell에는 acpiview 명령이 없으나, Shell_EA4BB293-2D7F-4456-A681-1F22F42CD0BC.efi로 이동할 때는 acpiview 명령이 Shell에 존재한다.

FS0:\> acpiview -l
'acpiview' is not recognized as an internal or external command, operable program, or script file.
FS0:\> Shell_EA4BB293-2D7F-4456-A681-1F22F42CD0BC.efi
UEFI Interactive Shell v2.2
EDK II
UEFI v2.70 (EDK II, 0x00010000)
Mapping table
      FS0: Alias(s):HD0a1:;BLK1:
          PciRoot(0x0)/Pci(0x1,0x1)/Ata(0x0)/HD(1,MBR,0xBE1AFDFA,0x3F,0xFBFC1)
     BLK0: Alias(s):
          PciRoot(0x0)/Pci(0x1,0x1)/Ata(0x0)
     BLK2: Alias(s):
          PciRoot(0x0)/Pci(0x1,0x1)/Ata(0x0)
Press ESC in 4 seconds to skip startup.nsh or any other key to continue.
FS0:\> acpiview -l

Installed Table(s):
           1. RSDP
           2. XSDT
           3. FACP
           4. FACS
           5. DSDT
           6. APIC
           7. HPET
           8. BGRT

acpiview 명령어가 포함된 Shell로 OVMF image 업데이트

이번 섹션에서는 OvmfPkgX64.dsc를 수정한다. UefiShellAcpiViewCommandLib.inf를 Shell.inf 라이브러리 클래스를 추가한다.

[Components]
  ...
  ShellPkg/Application/Shell/Shell.inf {
    <LibraryClasses>
      ShellCommandLib|ShellPkg/Library/UefiShellCommandLib/UefiShellCommandLib.inf
      NULL|ShellPkg/Library/UefiShellLevel2CommandsLib/UefiShellLevel2CommandsLib.inf
      NULL|ShellPkg/Library/UefiShellLevel1CommandsLib/UefiShellLevel1CommandsLib.inf
      NULL|ShellPkg/Library/UefiShellLevel3CommandsLib/UefiShellLevel3CommandsLib.inf
      NULL|ShellPkg/Library/UefiShellDriver1CommandsLib/UefiShellDriver1CommandsLib.inf
      NULL|ShellPkg/Library/UefiShellDebug1CommandsLib/UefiShellDebug1CommandsLib.inf
      NULL|ShellPkg/Library/UefiShellInstall1CommandsLib/UefiShellInstall1CommandsLib.inf
      NULL|ShellPkg/Library/UefiShellNetwork1CommandsLib/UefiShellNetwork1CommandsLib.inf
      NULL|ShellPkg/Library/UefiShellAcpiViewCommandLib/UefiShellAcpiViewCommandLib.inf          <-----------
!if $(NETWORK_IP6_ENABLE) == TRUE
      NULL|ShellPkg/Library/UefiShellNetwork2CommandsLib/UefiShellNetwork2CommandsLib.inf
!endif
      HandleParsingLib|ShellPkg/Library/UefiHandleParsingLib/UefiHandleParsingLib.inf
      PrintLib|MdePkg/Library/BasePrintLib/BasePrintLib.inf
      BcfgCommandLib|ShellPkg/Library/UefiShellBcfgCommandLib/UefiShellBcfgCommandLib.inf

    <PcdsFixedAtBuild>
      gEfiMdePkgTokenSpaceGuid.PcdDebugPropertyMask|0xFF
      gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE
      gEfiMdePkgTokenSpaceGuid.PcdUefiLibMaxPrintBufferSize|8000
  }

수정을 마친 뒤, OVMF를 다시 빌드 한다.

build --platform=OvmfPkg/OvmfPkgX64.dsc --arch=X64 --buildtarget=RELEASE --tagname=GCC5

그리고 해당 OVMF 이미지 자체에 acpiview 명령어가 포함되었는지 테스트 해본다.

FS0:\> acpiview -l

Installed Table(s):
           1. RSDP
           2. XSDT
           3. FACP
           4. FACS
           5. DSDT
           6. APIC
           7. HPET
           8. BGRT

보면, ShellPkg를 빌드하면 Shell.inf의 두 가지 버전이 빌드된다는 것을 알 수 있다.

UefiShellAcpiViewCommandLib.inf가 새 명령을 등록하는 방법이 궁금한 경우, 해당 소스를 살펴보는 것을 추천한다.

🖥️
https://github.com/tianocore/edk2/tree/master/ShellPkg/Library
https://github.com/tianocore/edk2/tree/master/ShellPkg/Library/UefiShellAcpiViewCommandLib
https://github.com/tianocore/edk2/blob/master/ShellPkg/Library/UefiShellAcpiViewCommandLib/UefiShellAcpiViewCommandLib.inf
https://github.com/tianocore/edk2/tree/master/ShellPkg/Application/AcpiViewApp
https://github.com/tianocore/edk2/blob/master/ShellPkg/ShellPkg.dsc
https://github.com/tianocore/edk2/blob/master/ShellPkg/Library/UefiShellAcpiViewCommandLib/UefiShellAcpiViewCommandLib.inf
https://github.com/tianocore/edk2/blob/master/ShellPkg/Library/UefiShellAcpiViewCommandLib/UefiShellAcpiViewCommandLib.c