50.UEFI_HII_RESOURCE_SECTION을 사용하여 문자열 패키지와 함께 HII 패키지 목록 게시하기

이번 장에서는 애플리케이션이 HII 문자열 패키지를 게시할 수 있는 또 다른 방법을 살펴본다. 이번에는 결과 EFI 파일 PE/COFF 리소스에 HII 데이터를 포함하는 것에 대해 알아본다.

애플리케이션 만들기

스크립트를 써서 평소와 같이 애플리케이션을 만든다.

./createNewApp.sh HIIStringsUNIRC

우리의 DSC 패키지 파일 UefiLessonsPkg/UefiLessonsPkg.dsc에 추가한다.

[Components]
  ...
  UefiLessonsPkg/HIIStringsUNI/HIIStringsUNI.inf

마지막으로 패키지 목록에 대한 GUID가 필요하며 패키지 DEC 파일인 UefiLessonsPkg/UefiLessonsPkg.dec에서 선언해준다.

[Guids]
  ...
  gHIIStringsUNIRCGuid = { 0x785693b4, 0x623e, 0x40fa, { 0x9a, 0x45, 0x68, 0xda, 0x38, 0x30, 0x89, 0xdd }}

이제 HIIStringsUNI 앱과 유사하도록 애플리케이션 파일을 수정해준다. Strings.uni 파일을 만들고 애플리케이션의 INF 및 *.c 파일을 수정해야한다.

  • UefiLessonsPkg/HIIStringsUNIRC/HIIStringsUNIRC.inf

  • UefiLessonsPkg/HIIStringsUNIRC/HIIStringsUNIRC.c

  • UefiLessonsPkg/HIIStringsUNIRC/Strings.uni

모든 작업을 완료하면 HIIStringsUNI 애플리케이션과 동일한 결과를 얻을 수 있다.

이제 애플리케이션을 수정할 준비가 다 되었다.

UEFI_HII_RESOURCE_SECTION

UefiLessonsPkg/HIIStringsUNIRC/HIIStringsUNIRC.inf에 다음을 추가한다.

UEFI_HII_RESOURCE_SECTION 플래그는 HII 리소스 섹션이 PE 이미지로 생성되는지 여부를 지정한다. 애플리케이션을 빌드하면 다음 오류로 인해 애플리케이션을 빌드할 수 없다.

Build/UefiLessonsPkg/RELEASE_GCC5/X64/UefiLessonsPkg/HIIStringsUNIRC/HIIStringsUNIRC/DEBUG/HIIStringsUNIRCStrDefs.h를 보면 이 파일에 여전히 문자열 토큰이 포함되어 있지만 HIIStringsUNIRCStrings는 더 이상 여기에 존재하지 않는 것을 알 수 있다.

그리고 AutoGen.c 파일에는 더 이상 HIIStringsUNIRCStrings 배열 초기화 코드가 포함되어 있지 않다(Build/UefiLessonsPkg/RELEASE_GCC5/X64/UefiLessonsPkg/HIIStringsUNIRC/HIIStringsUNIRC/DEBUG/AutoGen.c).

이제 우리의 문자열이 결과로 나오는 *.efi 이미지의 특수 섹션으로 인코딩되어 들어가는 것이다.

이를 우리가 얻으려면 애플리케이션 EFI_HANDLE ImageHandle에서 프로토콜 EFI_HII_PACKAGE_LIST_PROTOCOL을 검색해야 한다.

다음은 Shell이 모든 프로그램을 로드하는 데 사용하는 EFI_BOOT_SERVICES.LoadImage() 함수에 대한 UEFI 스펙의 관련 내용이다.

https://github.com/tianocore/edk2/blob/master/MdePkg/MdePkg.dec에 따르면 EFI_HII_PACKAGE_LIST_PROTOCOLgEfiHiiPackageListProtocolGuid로 식별된다.

우리의 INF 파일의 [Packages] 섹션에 MdeModulePkg/MdeModulePkg.dec가 이미 있으므로 이 GUID를 [Protocols] 섹션에 추가하기만 하면 된다.

코드에서는 OpenProtocol UEFI 부트 서비스의 도움으로 애플리케이션의 ImageHandle 에서 PackageList 프로토콜을 얻을 수 있다.

결과의 PackageListHIIStringsUNI 애플리케이션의 경우와 같이 StrGather 스크립트의 결과인 일부 size 헤더가 있는 문자열 패키지가 아니다. HIIStringsC 애플리케이션에서 수동으로 구성한 것과 같은 일반 PackageList이다. 따라서 HiiAddPackages 라이브러리 함수를 사용하는 대신 EFI_HII_DATABASE_PROTOCOL.NewPackageList()를 직접 사용해야 한다.

여기서는 gHiiDatabase를 사용했으므로 필요한 헤더인 #include <Library/UefiHiiServicesLib.h>를 추가하고 애플리케이션 INF 파일의 [LibraryClasses]UefiHiiServicesLib를 추가하는 것을 잊지 말자.

이제 애플리케이션을 빌드하고 실행해보면 모든 것이 정상인것을 확인할 수 있다.

유형이 'HII'인 PE/COFF 리소스

objdump를 사용하여 애플리케이션 헤더를 살펴보자. -x 옵션을 사용하여 모든 헤더의 내용을 출력할 수 있다.

화살표 뒤의 사항에 주의하면서 보자.

이제 UefiLessonsPkg/HIIStringsUNIRC/HIIStringsUNIRC.infUEFI_HII_RESOURCE_SECTION을 주석 처리해준다.

애플리케이션 빌드 후에 objdump를 다시 한 번 실행해보면 다음과 같은 결과를 얻을 수 있다.

이 버전의 애플리케이션을 실행하려고 하면 아래와 같이 실행된다.

Last updated