Step to UEFI (177)Setup String ITEM 的 Default Value

有时候,我们需要在Setup 中指定 String 的 Default值,例如:

如果你想直接给他指定一个字符串作为Default,需要添加如下的代码:

1. \MdeModulePkg\Universal\DriverSampleDxe\Vfr.vfr

    //
    // Define a string (EFI_IFR_STRING)
    //
    string    varid    = MyIfrNVData.MyStringData,
              prompt   = STRING_TOKEN(STR_MY_STRING_PROMPT2),
              help     = STRING_TOKEN(STR_MY_STRING_HELP2),
              
              flags    = INTERACTIVE,
              key      = 0x1236,
              minsize  = 6,
              maxsize  = 40,
              inconsistentif prompt = STRING_TOKEN(STR_STRING_CHECK_ERROR_POPUP),
                pushthis != stringref(STRING_TOKEN(STR_STRING_CHECK))
              endif;
              default  = STRING_TOKEN(STR_STRING_CHECK),
endstring;

2. \MdeModulePkg\Universal\DriverSampleDxe\VfrStrings.uni

#string STR_TEST        #language en-US  "LAB-Z"
                        #language fr-FR  "LAB-Z"

编译结果:

比较诡异的是default  = STRING_TOKEN(STR_TEST), 只能放在这个定义的末尾,如果放在中间,比如:

              help     = STRING_TOKEN(STR_MY_STRING_HELP2),
              default  = STRING_TOKEN(STR_TEST),
              flags    = INTERACTIVE,

     在编译的时候会出现下面的错误,不得不不说非常诡异。也正是因为这个原因,这个功能我研究了很久很久…….

《Step to UEFI (177)Setup String ITEM 的 Default Value》有8个想法

        1. 根据我的理解是:只有当这些 Protocol 的 GUID 已经存在才会执行这个模块。通过这样的方法可以控制执行顺序。如果对某一个功能有依赖,可以把那个功能创建的 GUID 写在这个位置,然后执行的时候会先检查,如果满足条件才会执行。

          1. 好的,谢谢。我自己添加了一个模块,加了debug 信息居然没打印出来,连entrypoint都没跑就觉得奇怪

          2. ziv2013是对的,补充一下个人理解,Depex本身主要是解决依赖,各种模块之间可能有复杂的依赖。
            一个模块要想运行,必须要满足依赖才能运行(这个dxe_dispatcher会帮我们自动分析依赖,让没有依赖的 或低依赖的先派发)(间接影响执行顺序。)
            一个模块还可以register_protocol_notify,等到依赖满足会自动call注册的回调函数,完成剩下的任务。
            只有DXE_DRIVER需要Depex,UEFI_DRIVER不需要Depex,因为UEFI_DRIVER已经隐含需要满足(所有architecture_protocols的依赖,参见PI spec),所以UEFI_DRIVER总是会(被自动由dxe_dispatcher)放到driver-list最后的去运行。

  1. 个人分析,这句“default = STRING_TOKEN(STR_STRING_CHECK),” 可以写到inconsistentif 前后,
    即可以写成:
    inconsistentif prompt = STRING_TOKEN(STR_STRING_CHECK_ERROR_POPUP),
    pushthis != stringref(STRING_TOKEN(STR_STRING_CHECK))
    endif;
    default = STRING_TOKEN(STR_STRING_CHECK),

    或写成:
    default = STRING_TOKEN(STR_STRING_CHECK),
    inconsistentif prompt = STRING_TOKEN(STR_STRING_CHECK_ERROR_POPUP),
    pushthis != stringref(STRING_TOKEN(STR_STRING_CHECK))
    endif;

    如果这样解析不过表示VFR解释器有bug。

    关于“只能放在这个定义的末尾,如果放在中间。。。”,不可以放到string那个中间,是因为不符合语法:
    "default = STRING_TOKEN(STR_STRING_CHECK),"这句是一个单独的vfrStatementDefault,不属于vfrStatementString.

    thanks.

发表回复

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