Step to UEFI (87) EFI_UNICODE_COLLATION_PROTOCOL

查看UEFI下的大小写转换函数的时候,偶然发现了EFI_UNICODE_COLLATION_PROTOCOL【参考1】提供了几个有意思的函数。

u1

具体的头文件定义在 \MdePkg\Include\Protocol\UnicodeCollation.h

///
/// The EFI_UNICODE_COLLATION_PROTOCOL is used to perform case-insensitive 
/// comparisons of strings. 
///
struct _EFI_UNICODE_COLLATION_PROTOCOL {
  EFI_UNICODE_COLLATION_STRICOLL    StriColl;   
  EFI_UNICODE_COLLATION_METAIMATCH  MetaiMatch;
  EFI_UNICODE_COLLATION_STRLWR      StrLwr;
  EFI_UNICODE_COLLATION_STRUPR      StrUpr;

  //
  // for supporting fat volumes
  //
  EFI_UNICODE_COLLATION_FATTOSTR    FatToStr;
  EFI_UNICODE_COLLATION_STRTOFAT    StrToFat;
  
  ///
  /// A Null-terminated ASCII string array that contains one or more language codes.
  /// When this field is used for UnicodeCollation2, it is specified in RFC 4646 format.
  /// When it is used for UnicodeCollation, it is specified in ISO 639-2 format.
  ///
  CHAR8                             *SupportedLanguages;
};

 

根据介绍,大概的介绍一些功能(如果你发现有错误,欢迎eMail指出)
EFI_UNICODE_COLLATION_STRICOLL StriColl; //大小写不敏感的比较函数
EFI_UNICODE_COLLATION_METAIMATCH MetaiMatch; //正则表达式匹配
EFI_UNICODE_COLLATION_STRLWR StrLwr; //字符串转小写
EFI_UNICODE_COLLATION_STRUPR StrUpr; //字符串转大写
EFI_UNICODE_COLLATION_FATTOSTR FatToStr; //8.3格式的OEM定义字符文件名转String
EFI_UNICODE_COLLATION_STRTOFAT StrToFat; //String转8.3格式的OEM定义字符
CHAR8 *SupportedLanguages; //列出当前系统支持的语言代码

之后,根据上面的介绍,编写一个测试例子:

#include  <Uefi.h>
#include  <Library/UefiLib.h>
#include  <Library/ShellCEntryLib.h>

#include <Protocol/UnicodeCollation.h>

extern EFI_BOOT_SERVICES         *gBS;
extern EFI_SYSTEM_TABLE			 *gST;
extern EFI_RUNTIME_SERVICES 	 *gRT;

int
EFIAPI
main (
  IN int Argc,
  IN CHAR16 **Argv
  )
{
	EFI_STATUS	Status;
	EFI_UNICODE_COLLATION_PROTOCOL *mUnicodeCollation;
	CHAR16	*TestStr=L"wWw.LaB-z.cOm";
	CHAR16  *Pattern1=L"w*";
	CHAR16  *Pattern2=L"*z.c*";
	CHAR16  *Pattern3=L"c*";
	
	Status = gBS->LocateProtocol(
				&gEfiUnicodeCollation2ProtocolGuid, 
				NULL, 
				&mUnicodeCollation);
    if (EFI_ERROR (Status)) {
      Print(L"Can't Locate Protocol\n");
      return Status;
    }
	
	mUnicodeCollation->StrLwr(mUnicodeCollation,TestStr);
	Print(L"%s\n",TestStr);
	
	mUnicodeCollation->StrUpr(mUnicodeCollation,TestStr);
	Print(L"%s\n",TestStr);

	Print(L"%d\n",(mUnicodeCollation->
					MetaiMatch(mUnicodeCollation,
					   TestStr,
					   Pattern1)));

	Print(L"%d\n",(mUnicodeCollation->
					MetaiMatch(mUnicodeCollation,
					   TestStr,
					   Pattern2)));

	Print(L"%d\n",(mUnicodeCollation->
					MetaiMatch(mUnicodeCollation,
					   TestStr,
					   Pattern3)));					   
  return EFI_SUCCESS;
}

 

运行结果:
u2

其中测试了大小写转换不必细说,多说两句关于正则表达式的用法:

	CHAR16	*TestStr=L"wWw.LaB-z.cOm";
	CHAR16  *Pattern1=L"w*";
	CHAR16  *Pattern2=L"*z.c*";
	CHAR16  *Pattern3=L"c*";

 

其中 “*” 表示匹配一个或者任意多个字符, Pattern1 表示的是“以w开头的字符串”;Pattern2 表示的是“中间含有 z.c 字符的字符串”;Pattern3 表示的是“以c开头的字符串”。最终运行结果如下:

完整的代码下载:
UnicTest

参考:
1. UEFI 2.4 P592

《Step to UEFI (87) EFI_UNICODE_COLLATION_PROTOCOL》有14个想法

        1. 不在 Super IO 下面的话,不需要看 SuperIO 的spec

          直接看南桥的Spec就好了。最好是对照BIOS Source Code看一下。

          1. read 我是用SPIBAR+ offset 的register操作完成的
            那write呢? 是不是可以用SPI cmd, opcode? 該如何寫呢?

发表回复

您的电子邮箱地址不会被公开。 必填项已用 * 标注