> On Jul 6, 2016, at 1:39 PM, Carsey, Jaben <[email protected]> wrote:
>
> It works for libs. If you specify a specific LibraryClass implementation, it
> will not add a second of that library class.
>
> Side note: what if you turn off AutoInitialize PCD for the shell lib? That
> would get rid of your main issue (the constructor ASSERT)… then we can see
> what other issues you have.
>
This seems like the set of library APIs that would be needed (and one usage of
gEfiShellProtocol->SetCurDir()).
~/work/src/edk2/StdLib(master)>git grep Shell -- *.c
LibC/Main/Main.c:20:#include <Library/ShellCEntryLib.h>
LibC/Main/Main.c:130:ShellAppMain (
LibC/StdLib/Environs.c:23:#include <Library/ShellLib.h>
LibC/StdLib/Environs.c:155: OpStat = ShellExecute( &MyHandle, gMD->UString,
FALSE, NULL, &CmdStat);
LibC/StdLib/Environs.c:167: are determined by the underlying UEFI Shell
implementation.
LibC/StdLib/Environs.c:181: EfiEnv = ShellGetEnvironmentVariable(gMD->UString);
LibC/StdLib/Environs.c:248: HostName = ShellGetEnvironmentVariable ( UName );
LibC/StdLib/Environs.c:254: Status = ShellSetEnvironmentVariable ( UName,
UValue, TRUE );
LibC/StdLib/Environs.c:265: Status = ShellSetEnvironmentVariable (
UName, UValue, FALSE );
LibC/Uefi/Devices/UefiShell/daShell.c:2: Abstract device driver for the UEFI
Shell-hosted environment.
LibC/Uefi/Devices/UefiShell/daShell.c:4: In a Shell-hosted environment, this
is the driver that is called
LibC/Uefi/Devices/UefiShell/daShell.c:21:#include <Library/ShellLib.h>
LibC/Uefi/Devices/UefiShell/daShell.c:40:/** EFI Shell specific operations for
close().
LibC/Uefi/Devices/UefiShell/daShell.c:50:da_ShellClose(
LibC/Uefi/Devices/UefiShell/daShell.c:54: EFIerrno = ShellCloseFile(
(SHELL_FILE_HANDLE *)&Fp->devdata);
LibC/Uefi/Devices/UefiShell/daShell.c:61:/** EFI Shell specific operations for
deleting a file or directory.
LibC/Uefi/Devices/UefiShell/daShell.c:71:da_ShellDelete(
LibC/Uefi/Devices/UefiShell/daShell.c:77: Status = ShellDeleteFile(
(SHELL_FILE_HANDLE *)&filp->devdata);
LibC/Uefi/Devices/UefiShell/daShell.c:86:/** EFI Shell specific operations for
setting the position within a file.
LibC/Uefi/Devices/UefiShell/daShell.c:97:da_ShellSeek(
LibC/Uefi/Devices/UefiShell/daShell.c:113: Status = ShellSetFilePosition(
FileHandle, 0xFFFFFFFFFFFFFFFFULL);
LibC/Uefi/Devices/UefiShell/daShell.c:117: Status = ShellGetFilePosition(
FileHandle, (UINT64 *)&CurPos);
LibC/Uefi/Devices/UefiShell/daShell.c:128: Status = ShellSetFilePosition(
FileHandle, (UINT64)(CurPos + offset));
LibC/Uefi/Devices/UefiShell/daShell.c:131: Status = ShellGetFilePosition(
FileHandle, (UINT64 *)&CurPos);
LibC/Uefi/Devices/UefiShell/daShell.c:161:da_ShellMkdir(
LibC/Uefi/Devices/UefiShell/daShell.c:177: Status = ShellCreateDirectory(
NewPath, &FileHandle);
LibC/Uefi/Devices/UefiShell/daShell.c:179: FileInfo = ShellGetFileInfo(
FileHandle);
LibC/Uefi/Devices/UefiShell/daShell.c:180: Status = RETURN_ABORTED; // In
case ShellGetFileInfo() failed
LibC/Uefi/Devices/UefiShell/daShell.c:184: Status = ShellSetFileInfo(
FileHandle, FileInfo);
LibC/Uefi/Devices/UefiShell/daShell.c:187:
(void)ShellCloseFile(&FileHandle);
LibC/Uefi/Devices/UefiShell/daShell.c:199:/** EFI Shell specific operations for
reading from a file.
LibC/Uefi/Devices/UefiShell/daShell.c:212:da_ShellRead(
LibC/Uefi/Devices/UefiShell/daShell.c:224: BufSize =
(ssize_t)da_ShellSeek(filp, *offset, SEEK_SET);
LibC/Uefi/Devices/UefiShell/daShell.c:233: Status = ShellReadFile( FileHandle,
(UINTN *)&BufSize, Buffer);
LibC/Uefi/Devices/UefiShell/daShell.c:250:/** EFI Shell specific operations for
writing to a file.
LibC/Uefi/Devices/UefiShell/daShell.c:263:da_ShellWrite(
LibC/Uefi/Devices/UefiShell/daShell.c:286: BufSize =
(ssize_t)da_ShellSeek(filp, Position, How);
LibC/Uefi/Devices/UefiShell/daShell.c:295: Status = ShellWriteFile(
FileHandle, (UINTN *)&BufSize, (void *)Buffer);
LibC/Uefi/Devices/UefiShell/daShell.c:312:/** EFI Shell specific operations for
getting information about an open file.
LibC/Uefi/Devices/UefiShell/daShell.c:324:da_ShellStat(
LibC/Uefi/Devices/UefiShell/daShell.c:338: FileInfo = ShellGetFileInfo(
FileHandle);
LibC/Uefi/Devices/UefiShell/daShell.c:374:/** EFI Shell specific operations for
low-level control of a file or device.
LibC/Uefi/Devices/UefiShell/daShell.c:386:da_ShellIoctl(
LibC/Uefi/Devices/UefiShell/daShell.c:399: FileInfo = ShellGetFileInfo(
FileHandle);
LibC/Uefi/Devices/UefiShell/daShell.c:427: Status =
ShellSetFileInfo(FileHandle, FileInfo);
LibC/Uefi/Devices/UefiShell/daShell.c:446:/** EFI Shell specific operations for
opening a file or directory.
LibC/Uefi/Devices/UefiShell/daShell.c:459:da_ShellOpen(
LibC/Uefi/Devices/UefiShell/daShell.c:462: int DevInstance,
/* Not used by Shell */
LibC/Uefi/Devices/UefiShell/daShell.c:511: !!!!!!!!! Change this to use
ShellSetFileInfo() to actually truncate the file
LibC/Uefi/Devices/UefiShell/daShell.c:516: Status = ShellIsFile( WPath );
LibC/Uefi/Devices/UefiShell/daShell.c:544: // Call the EFI Shell's Open
function
LibC/Uefi/Devices/UefiShell/daShell.c:545: Status = ShellOpenFileByName(
WPath, &FileHandle, OpenMode, Attributes);
LibC/Uefi/Devices/UefiShell/daShell.c:592:da_ShellPoll(
LibC/Uefi/Devices/UefiShell/daShell.c:622:/** EFI Shell specific operations for
renaming a file.
LibC/Uefi/Devices/UefiShell/daShell.c:633:da_ShellRename(
LibC/Uefi/Devices/UefiShell/daShell.c:653: OldFileInfo = ShellGetFileInfo(
FileHandle);
LibC/Uefi/Devices/UefiShell/daShell.c:668: Status =
ShellSetFileInfo(FileHandle, NewFileInfo);
LibC/Uefi/Devices/UefiShell/daShell.c:695:/** EFI Shell specific operations for
deleting directories.
LibC/Uefi/Devices/UefiShell/daShell.c:705:da_ShellRmdir(
LibC/Uefi/Devices/UefiShell/daShell.c:721: FileInfo =
ShellGetFileInfo(FileHandle);
LibC/Uefi/Devices/UefiShell/daShell.c:727: FreePool(FileInfo); // Free up
the buffer from ShellGetFileInfo()
LibC/Uefi/Devices/UefiShell/daShell.c:729: Status = ShellFindFirstFile(
FileHandle, &FileInfo);
LibC/Uefi/Devices/UefiShell/daShell.c:733: Status = ShellFindNextFile(
FileHandle, FileInfo, &NoFile);
LibC/Uefi/Devices/UefiShell/daShell.c:744: /* Count == 99 and FileInfo
is allocated if ShellFindNextFile failed.
LibC/Uefi/Devices/UefiShell/daShell.c:745: ShellFindNextFile has
freed FileInfo itself if it sets NoFile TRUE.
LibC/Uefi/Devices/UefiShell/daShell.c:748: free(FileInfo); // Free
buffer from ShellFindFirstFile()
LibC/Uefi/Devices/UefiShell/daShell.c:752: Status = ShellDeleteFile(
&FileHandle);
LibC/Uefi/Devices/UefiShell/daShell.c:775: ShellCloseFile( &FileHandle);
LibC/Uefi/Devices/UefiShell/daShell.c:783:/** Construct an instance of the
abstract Shell device.
LibC/Uefi/Devices/UefiShell/daShell.c:797:__ctor_DevShell(
LibC/Uefi/Devices/UefiShell/daShell.c:814: Stream->Abstraction.fo_close =
&da_ShellClose;
LibC/Uefi/Devices/UefiShell/daShell.c:815: Stream->Abstraction.fo_read =
&da_ShellRead;
LibC/Uefi/Devices/UefiShell/daShell.c:816: Stream->Abstraction.fo_write =
&da_ShellWrite;
LibC/Uefi/Devices/UefiShell/daShell.c:818: Stream->Abstraction.fo_poll =
&da_ShellPoll;
LibC/Uefi/Devices/UefiShell/daShell.c:820: Stream->Abstraction.fo_stat =
&da_ShellStat;
LibC/Uefi/Devices/UefiShell/daShell.c:821: Stream->Abstraction.fo_ioctl =
&da_ShellIoctl;
LibC/Uefi/Devices/UefiShell/daShell.c:822: Stream->Abstraction.fo_delete =
&da_ShellDelete;
LibC/Uefi/Devices/UefiShell/daShell.c:823: Stream->Abstraction.fo_rmdir =
&da_ShellRmdir;
LibC/Uefi/Devices/UefiShell/daShell.c:824: Stream->Abstraction.fo_mkdir =
&da_ShellMkdir;
LibC/Uefi/Devices/UefiShell/daShell.c:825: Stream->Abstraction.fo_rename =
&da_ShellRename;
LibC/Uefi/Devices/UefiShell/daShell.c:826: Stream->Abstraction.fo_lseek =
&da_ShellSeek;
LibC/Uefi/Devices/UefiShell/daShell.c:828: Node = __DevRegister(NULL, NULL,
&da_ShellOpen, Stream, 1, sizeof(GenericInstance), O_RDWR);
LibC/Uefi/Devices/UefiShell/daShell.c:835:/** Destructor for previously
constructed EFI Shell device instances.
LibC/Uefi/Devices/UefiShell/daShell.c:844:__dtor_DevShell(
LibC/Uefi/SysCalls.c:20:#include <Library/ShellLib.h>
LibC/Uefi/SysCalls.c:605: The EFI ShellOpenFileByName() function is used to
perform the low-level
LibC/Uefi/SysCalls.c:618: The only valid flag combinations for
ShellOpenFileByName() are:
LibC/Uefi/SysCalls.c:990: The fstat() function is implemented using the
ShellGetFileInfo()
LibC/Uefi/SysCalls.c:1314: Cwd = ShellGetCurrentDir(NULL);
LibC/Uefi/SysCalls.c:1338: - EPERM: Operation not supported
with this Shell version.
LibC/Uefi/SysCalls.c:1351: /* Old Shell does not support Set Current Dir. */
LibC/Uefi/SysCalls.c:1352: if(gEfiShellProtocol != NULL) {
LibC/Uefi/SysCalls.c:1353: Cwd = ShellGetCurrentDir(NULL);
LibC/Uefi/SysCalls.c:1362: Status = gEfiShellProtocol->SetCurDir(NULL,
UnicodePath);
PosixLib/GetPass/GetPass.c:14:#include <Library/ShellLib.h>
PosixLib/GetPass/GetPass.c:30: ReturnString = ShellFileHandleReturnLine
(gEfiShellParametersProtocol->StdIn, &Ascii);
Thanks,
Andrew Fish
> <>From: Michael Zimmermann [mailto:[email protected]
> <mailto:[email protected]>]
> Sent: Wednesday, July 06, 2016 1:32 PM
> To: Carsey, Jaben <[email protected] <mailto:[email protected]>>
> Cc: Andrew Fish <[email protected] <mailto:[email protected]>>; Marvin Häuser
> <[email protected] <mailto:[email protected]>>;
> [email protected] <mailto:[email protected]>;
> [email protected] <mailto:[email protected]>
> Subject: Re: [edk2] StdLib usage for drivers?
> Importance: High
>
> > You can have different libs and different flags per driver. You use the {}
> > syntax on the INF file in the components section. This is already done in
> > the Shell.DSC to control PCDs separating the ShellLib when used for the
> > shell compared to ShellLib used for shell applications.
>
> Thanks for clearing that up. Looks like I totally misunderstood how the {}
> syntax works.
> Does this only work for Applications/Drivers or for Libraries too so you
> don't have to do this for every driver?
>
> I prefer fixing the behavior at build time over implementing a fallback
> because it would be weird if the application behaves totally different
> depending on if you start it via the BDS or from the Shell.
>
> Thanks
> Michael
>
> On Wed, Jul 6, 2016 at 10:20 PM, Carsey, Jaben <[email protected]
> <mailto:[email protected]>> wrote:
> Andrew,
>
> Note: The ShellLib is not part of the shell spec. The ShellProtocol and
> ShellParametersProtocol are. The current ShellLib is designed to facilitate
> porting and writing of apps for the shell. The porting will become obsolete
> over time as we encounter fewer and fewer EDKShell apps.
>
> That does’t mean that your conclusion is wrong. We could make a different
> ShellLib that is not actually dependent on the shell.
>
>
> Michael,
>
> You can have different libs and different flags per driver. You use the {}
> syntax on the INF file in the components section. This is already done in
> the Shell.DSC to control PCDs separating the ShellLib when used for the shell
> compared to ShellLib used for shell applications.
>
>
> -Jaben
>
>
>
> <>From: Michael Zimmermann [mailto:[email protected]
> <mailto:[email protected]>]
> Sent: Wednesday, July 06, 2016 1:13 PM
> To: Andrew Fish <[email protected] <mailto:[email protected]>>
> Cc: Marvin Häuser <[email protected]
> <mailto:[email protected]>>; [email protected]
> <mailto:[email protected]>; Carsey, Jaben <[email protected]
> <mailto:[email protected]>>; [email protected]
> <mailto:[email protected]>
> Subject: Re: [edk2] StdLib usage for drivers?
> Importance: High
>
> Andrew,
>
> the problem with multiple library instances is that this does only work
> globally and it gets in your way if you need different versions of a
> dependent library.
>
> In our case, Applications/Drivers only depend on LibC, an LibC then depends
> on ShellLib which means we'd have to create another LibC instance which
> depends on another version of ShellLib.
>
> In other words: you can't use the same Library with different build options
> in different drivers built by the same DSC. You'd have to create a renamed
> .inf with different build options which you can't do because your driver
> doesn't depend directly on that lib.
>
> Thanks
> Michael
>
> On Wed, Jul 6, 2016 at 9:55 PM, Andrew Fish <[email protected]
> <mailto:[email protected]>> wrote:
>
> On Jul 6, 2016, at 12:44 PM, Michael Zimmermann <[email protected]
> <mailto:[email protected]>> wrote:
>
> Andrew,
>
> sry for not reasing the Shell Spec but I think you can answer this faster.
> Does the Spec prevent implementing such a 'pure-EFI' fallback by default so
> we can use the same ShellLib globally?
>
>
> Michael,
>
> If I remember correctly the Shell Spec specifies how the shell functions and
> what protocols it produces that other code can depend on.
>
>
> and follow-up question: Libraries are not compiled multiple times right? so
> If I would specify additional CFLAGs these would only be used to build your
> package and not for the libraríes you are using right?
>
>
> The edk2 has the concept of library instances. The DSC file for the platform
> picks the instance of the library for the Module Type. Basically ShellLib.h
> would be the public API and ShellLib is the library class. The library class
> is the public API and it is names in the [Defines] section of the libraries
> INF file via LIBRARY_CLASS =. The build system is smart enough to only build
> the libraries that are actually being used.
>
> For example this would be the line in the DSC:
> ShellLib|ShellPkg/Library/UefiShellLib/UefiShellLib.inf
>
> And you could change it to:
> ShellLib | AltPathToUefiShellLib/AltUefiShellLib.inf
>
> The upside to all this is the same reason we introduced the concept of
> library classes in the 1st place, you can change the behavior of the StdLib
> without modifying any of the code in the standard lib. This would be a good
> way to experiment and if you get it working I guess it could get added to the
> StdLib at some point as an alternate way to build it.
>
> Thanks,
>
> Andrew Fish
>
>
> If that's correct then we should stay away from changing ShellLib's behavior
> using cflags in your DSC because it would prevent building both shell and efi
> users of ShellLib with one DSC file.
>
> Thanks,
> Michael
>
> On Wed, Jul 6, 2016 at 9:25 PM, Andrew Fish <[email protected]
> <mailto:[email protected]>> wrote:
>
> > On Jul 4, 2016, at 11:17 AM, Marvin Häuser <[email protected]
> > <mailto:[email protected]>> wrote:
> >
> > Daryl, Jaben,
> >
> > As you are the package maintainers of StdLib, could you please comment on
> > the situation?
> > If modifications to have StdLib working for drivers are welcome, I would
> > offer my help in cleaning up the existing stuff and/or write my own
> > patches, though of course there is little point if there is no reaction
> > from the reviewers.
> > If it is of any interest, I want to write a shim library for Capstone and
> > would prefer not to have three copies of Std functions in my tree (StdLib,
> > CryptoPkg (SSL) and Capstone), but rather an improved StdLib that works for
> > all.
> >
> > Thanks to those who have offered alternative solutions, but I prefer to
> > keep it ‚clean‘ and have the libraries shipping with EDK2 work. :)
> >
>
> Marvin,
>
> It looks like the StdLib has a dependency on the ShellLib and ShellCEntryLib.
> One option would be to implement a new instance of the ShellLib and the
> ShellCEntryLib that don't depend on the Shell. You can get a template of how
> to do file operations from
> here:https://github.com/tianocore/edk2/blob/master/EmbeddedPkg/Library/EfiFileLib/EfiFileLib.c
>
> <https://github.com/tianocore/edk2/blob/master/EmbeddedPkg/Library/EfiFileLib/EfiFileLib.c>
>
> You would have a couple of options. You good go with the EfiFileLib volume
> synatax, you could just do pure EFI (unclear how to specify a volume (driver
> letter)). You could also just add code to fallback if you can't find the
> shell protocols to due more pure EFI stuff. That way you don't need to modify
> the StdLib just how you build the StdLib from the DSC.
>
> For example you could implement the functions in the ShellLib that the StdLib
> requires and use something like the EfiFileLib to make it easier. I think
> ShellCEntryLib would just be a copy
> ofhttps://github.com/tianocore/edk2/tree/master/MdePkg/Library/UefiApplicationEntryPoint
>
> <https://github.com/tianocore/edk2/tree/master/MdePkg/Library/UefiApplicationEntryPoint>
>
> Thanks,
>
> Andrew Fish
>
> > Regards,
> > Marvin.
> >
> > From: Michael Zimmermann [mailto:[email protected]
> > <mailto:[email protected]>]
> > Sent: Thursday, June 23, 2016 5:32 AM
> > To: Marvin Häuser <[email protected]
> > <mailto:[email protected]>>
> > Cc: [email protected] <mailto:[email protected]>;
> > [email protected] <mailto:[email protected]>
> > Subject: Re: [edk2] StdLib usage for drivers?
> >
> > well for the patch to go upstream it would have to get improved a lot.
> > I've tried to implement this in a way that doesn't need a different dsc but
> > the problem is that ShellLib's constructor ASSERT's if it can't find the
> > shell protocol and removing that would probably be against the spec's.
> >
> > Also it appears that the StdLib maintainers are kinda busy because most of
> > the StdLib patches I've sent to this mailing list didn't get reviewed.
> >
> > Thanks
> > Michael
> >
> > On Wed, Jun 22, 2016 at 10:37 PM, Marvin Häuser <[email protected]
> > <mailto:[email protected]><mailto:[email protected]
> > <mailto:[email protected]>>> wrote:
> > Hey Michael,
> >
> > Thank you for your input! This looks interesting.
> > Maybe it would be a good idea to provide the libraries that depend on Shell
> > (in master) with functions that call ASSERT (FALSE); for drivers? I do not
> > need file I/O, so I think your modifications might work out well for me.
> > Would be very nice of course if such changes found their way upstream. :)
> >
> > And thank you very much for your comment as well, Andrew! It makes sense
> > that StdLib is primarily targeted at porting console applications to UEFI
> > Shell.
> >
> > Regards,
> > Marvin.
> >
> > From: Michael Zimmermann [mailto:[email protected]
> > <mailto:[email protected]><mailto:[email protected]
> > <mailto:[email protected]>>]
> > Sent: Wednesday, June 22, 2016 10:28 PM
> > To: Marvin H?user <[email protected]
> > <mailto:[email protected]><mailto:[email protected]
> > <mailto:[email protected]>>>
> > Cc: [email protected]
> > <mailto:[email protected]><mailto:[email protected]
> > <mailto:[email protected]>>
> > Subject: Re: [edk2] StdLib usage for drivers?
> >
> > In my fork of edk2 I've added support for using StdLib without the Shell.
> > It's quite hacky(setenv/getenv are stubs, no File IO and maybe other things
> > hidden by linker GC and me not using all features).
> >
> > But depending on which StdLib features you need this can work pretty good.
> >
> > here's the commit that does the magic:
> > https://github.com/efidroid/edk2/commit/bf7a296718486bafaf774ea8bcf187c162c3c167
> >
> > <https://github.com/efidroid/edk2/commit/bf7a296718486bafaf774ea8bcf187c162c3c167>
> >
> > and this is how you convert a Shell project to a NonShell one:
> > https://github.com/efidroid/uefi_apps_EFIDroidUi/commit/23f0fa08108b8f852564fae733c6a7bce62e2070
> >
> > <https://github.com/efidroid/uefi_apps_EFIDroidUi/commit/23f0fa08108b8f852564fae733c6a7bce62e2070>
> >
> > as you can see it works by using StdLib with different libraries/cflags so
> > you have to compile your driver separately if there are other modules which
> > need the normal StdLib.
> >
> > Thanks
> > Michael
> >
> > On Wed, Jun 22, 2016 at 9:38 PM, Marvin H?user <[email protected]
> > <mailto:[email protected]><mailto:[email protected]
> > <mailto:[email protected]>><mailto:[email protected]
> > <mailto:[email protected]><mailto:[email protected]
> > <mailto:[email protected]>>>> wrote:
> > Dear EDK2 developers,
> >
> > For an experimental project, I'm currently attempting to write a library
> > wrapper for the disassembler library 'Capstone' in a similar manner to
> > CryptoPkg's OpensslLib. As most C libraries, it also depends on the
> > standard headers, which are not provided by 'stock' EDK2. My first guess
> > has been to use StdLib, though its description states:
> > 'Due to the execution environment built by the StdLib component, execution
> > as a UEFI driver can cause system stability issues.'
> >
> > Inspecting OpensslLib I discovered that CryptoPkg deploys its own include
> > files for StdLib. Though, from your experience, what are the issues with
> > using StdLibPkg with DXE/UEFI drivers? It might be nice to reduce duplicate
> > code, though I honestly don't know anything about StdLibPkg and its
> > implementation and would be thankful for some insight on that manner.
> >
> > Thank you in advance for your time!
> >
> > Regards,
> > Marvin.
> > _______________________________________________
> > edk2-devel mailing list
> > [email protected]
> > <mailto:[email protected]><mailto:[email protected]
> > <mailto:[email protected]>><mailto:[email protected]
> > <mailto:[email protected]><mailto:[email protected]
> > <mailto:[email protected]>>>
> > https://lists.01.org/mailman/listinfo/edk2-devel
> > <https://lists.01.org/mailman/listinfo/edk2-devel>
> >
> > _______________________________________________
> > edk2-devel mailing list
> > [email protected]
> > <mailto:[email protected]><mailto:[email protected]
> > <mailto:[email protected]>>
> > https://lists.01.org/mailman/listinfo/edk2-devel
> > <https://lists.01.org/mailman/listinfo/edk2-devel>
> >
> > _______________________________________________
> > edk2-devel mailing list
> > [email protected] <mailto:[email protected]>
> > https://lists.01.org/mailman/listinfo/edk2-devel
> > <https://lists.01.org/mailman/listinfo/edk2-devel>
_______________________________________________
edk2-devel mailing list
[email protected]
https://lists.01.org/mailman/listinfo/edk2-devel