Sample code name
PaTest.py
Description
EfiPy adds new class EfiPy.Analyzer module
It is used for analyzed UEFI PROTOCOL calling flow in shell.
Source code is upload to sourceforge r0.0.2(1756).tgz
The output is in XML format.
If dOutClass parameter is string. its output to a file
Sample code
from EfiPy.Analyzer.Panalyzer import *
dOut = dOutClass()
dOut.section("Prepare")
t = pAnalyzer(dOut)
t.Build_Capability (EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL)
t.Detect_Protocol (gEfiSimpleTextOutProtocolGuid, EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL)
for target, handle in t.Target:
t.Filter.append (t.Build_Filter (target, handle))
t.install("Reset")
t.install("ABCD")
t.install("OutputString")
t.install("TestString")
t.install("QueryMode")
t.install("SetMode")
t.install("SetAttribute")
t.install("ClearScreen")
t.install("SetCursorPosition")
t.start("asd")
t.start("QueryMode")
t.debug_dump ()
dOut.section("Testing_1")
screen shot
Saturday, October 24, 2015
Saturday, August 22, 2015
EfiPy DevicePath
Sample code name
DevicePath.py
Description
In EfiPy, it uses DevicePath and DevicePathToText to build DevicePathEfiPy.
DevicePathEfiPy inherit from DevicePath and adds output DevicePath text by __str__().
DevicePath = (EfiPy.cast (TmpDevPath, EfiPy.POINTER(EFI_DEVICE_PATH_PROTOCOL)))[0]
print "%s" % DevicePath
This is LocateHandle sample from EfiPy.gBS.LocateHandle()
Status = EfiPy.gBS.LocateHandle(
EfiPy.ByProtocol,
EfiPy.byref(gEfiSimpleFileSystemProtocolGuid),
None,
EfiPy.byref(BufferSize),
HandleArray
)
Above results are put at array of handle.
It can be used by Python for loop to retrieve each handle.
for Handle in HandleArray:
TmpDevPath = EfiPy.PVOID ()
DevicePath.py
Description
In EfiPy, it uses DevicePath and DevicePathToText to build DevicePathEfiPy.
DevicePathEfiPy inherit from DevicePath and adds output DevicePath text by __str__().
DevicePath = (EfiPy.cast (TmpDevPath, EfiPy.POINTER(EFI_DEVICE_PATH_PROTOCOL)))[0]
print "%s" % DevicePath
This is LocateHandle sample from EfiPy.gBS.LocateHandle()
Status = EfiPy.gBS.LocateHandle(
EfiPy.ByProtocol,
EfiPy.byref(gEfiSimpleFileSystemProtocolGuid),
None,
EfiPy.byref(BufferSize),
HandleArray
)
Above results are put at array of handle.
It can be used by Python for loop to retrieve each handle.
for Handle in HandleArray:
TmpDevPath = EfiPy.PVOID ()
Screenshot
Saturday, August 15, 2015
EFI_GUID in EfiPy
Description
In EfiPy, it uses self-defined ctypes structure, similar to EDK II structure, rather then python uuid library.
This is for easy to transfer EFI program from C code to Python.
for example, in EFI C program, it uses
EFI_GUID guid_sample = \
{ \
0x8D59D32B, 0xC655, 0x4AE9, \
{0x9B, 0x15, 0xF2, 0x59, 0x04, 0x99, 0x2A, 0x43} \
};
In EfiPy, it can be codded as
>>> from EfiPy import *
>>> TestGuid1 = EFI_GUID \
(0x8D59D32B, 0xC655, 0x4AE9, \
(0x9B, 0x15, 0xF2, 0x59, 0x04, 0x99, 0x2A, 0x43))
>>> TestGuid2 = EFI_GUID \
(0x8D59D32B, 0xC655, 0x4AE9, \
(0x9B, 0x15, 0xF2, 0x59, 0x04, 0x99, 0x2A, 0x44))
EFI_GUID in EfiPy also provide object comparison and string output function
>>> print "TestGuid1 == TestGuid2 :", TestGuid1 == TestGuid2
TestGuid1 == TestGuid2 : False
Above result is false because these two GUID have different byte in their capability.
>>> print "%s" % TestGuid1
8D59D32B-C655-4AE9-9B15-F25904992A43
Screenshot of efi_guid.py
In EfiPy, it uses self-defined ctypes structure, similar to EDK II structure, rather then python uuid library.
This is for easy to transfer EFI program from C code to Python.
for example, in EFI C program, it uses
EFI_GUID guid_sample = \
{ \
0x8D59D32B, 0xC655, 0x4AE9, \
{0x9B, 0x15, 0xF2, 0x59, 0x04, 0x99, 0x2A, 0x43} \
};
In EfiPy, it can be codded as
>>> from EfiPy import *
>>> TestGuid1 = EFI_GUID \
(0x8D59D32B, 0xC655, 0x4AE9, \
(0x9B, 0x15, 0xF2, 0x59, 0x04, 0x99, 0x2A, 0x43))
>>> TestGuid2 = EFI_GUID \
(0x8D59D32B, 0xC655, 0x4AE9, \
(0x9B, 0x15, 0xF2, 0x59, 0x04, 0x99, 0x2A, 0x44))
>>> print "TestGuid1 == TestGuid2 :", TestGuid1 == TestGuid2
TestGuid1 == TestGuid2 : False
Above result is false because these two GUID have different byte in their capability.
>>> print "%s" % TestGuid1
8D59D32B-C655-4AE9-9B15-F25904992A43
Screenshot of efi_guid.py
Protocol - 3
Description
EfiPy also supports gBS.InstallMultipleProtocolInterfaces().
By EDK II definition,
typedef
EFI_STATUS
(EFIAPI *EFI_INSTALL_MULTIPLE_PROTOCOL_INTERFACES)(
IN OUT EFI_HANDLE *Handle,
...
);
EfiPy also supports gBS.InstallMultipleProtocolInterfaces().
By EDK II definition,
typedef
EFI_STATUS
(EFIAPI *EFI_INSTALL_MULTIPLE_PROTOCOL_INTERFACES)(
IN OUT EFI_HANDLE *Handle,
...
);
EfiPy follows this rule as possible as it can.
EFI_INSTALL_MULTIPLE_PROTOCOL_INTERFACES = CFUNCTYPE (
EFI_STATUS,
POINTER(EFI_HANDLE) # IN OUT *Handle
)
In run time, EfiPy changes ctypes CFUNCTYPE argument by re-arrange arguments members.
EfiPy.gBS.InstallMultipleProtocolInterfaces.argtypes = [
EfiPy.POINTER(EfiPy.EFI_HANDLE),
EfiPy.POINTER(EfiPy.EFI_GUID),
EfiPy.POINTER(EfiPy.PVOID),
EfiPy.POINTER(EfiPy.PVOID)
]
Finally, calling EfiPy.gBS.InstallMultipleProtocolInterfaces() for install protocols in one time.
Status = EfiPy.gBS.InstallMultipleProtocolInterfaces (
EfiPy.byref (Handle1),
EfiPy.byref (TestGuid1),
EfiPy.byref (TestProtocol1),
None
)
The same is as EfiPy.gBS.UninstallMultipleProtocolInterfaces()
Screenshot
Sample code in sourceforge is protocol_3.py
Friday, August 14, 2015
Protocol - 2
Description
This introduce how to install protocol, protocol event.
Install protocol,
there must be protocol structure and member function prototype defined.
#
# Protocol Structure
#
class TEST_PROTOCOL (EfiPy.Structure):
_fields_ = [("P1Func1", PROTOCOL_FUNC1),
("P1Val", EfiPy.UINT32),
("P1Func2", PROTOCOL_FUNC2)
]
#
# Building protocol object
#
P1 = PROTOCOL_FUNC1 (ProtocolFunc1)
P2 = PROTOCOL_FUNC2 (ProtocolFunc2)
TestProtocol1 = TEST_PROTOCOL (P1, 3, P2)
#
# InstallProtocolInterface
#
Status = EfiPy.gBS.InstallProtocolInterface (
EfiPy.byref (Handle1),
EfiPy.byref (TestGuid1),
EfiPy.EFI_NATIVE_INTERFACE,
EfiPy.byref (TestProtocol1)
)
Protocol event, as same as EDK II, CreateEvent() and RegisterProtocolNotify() are used.
#
# Protocl event variable
#
def ProtocolRegisterFunc (Event, Context):
print " Protocl Register notification call back."
Event = EfiPy.EFI_EVENT ()
tFunc = EfiPy.EFI_EVENT_NOTIFY(ProtocolRegisterFunc)
gContext = EfiPy.UINTN (1024)
Status = EfiPy.gBS.CreateEvent (
EfiPy.EVT_NOTIFY_SIGNAL,
EfiPy.TPL_NOTIFY,
tFunc,
EfiPy.PVOID.from_address (EfiPy.addressof(gContext)),
EfiPy.byref (Event)
)
#
# RegisterProtocolNotify
#
Registration = EfiPy.PVOID()
Status = EfiPy.gBS.RegisterProtocolNotify (
EfiPy.byref (TestGuid1),
Event,
EfiPy.byref(Registration)
)
screenshot
Sample code is protocol2.py at sourceforge.
This introduce how to install protocol, protocol event.
Install protocol,
there must be protocol structure and member function prototype defined.
#
# Protocol Structure
#
class TEST_PROTOCOL (EfiPy.Structure):
_fields_ = [("P1Func1", PROTOCOL_FUNC1),
("P1Val", EfiPy.UINT32),
("P1Func2", PROTOCOL_FUNC2)
]
#
# Building protocol object
#
P1 = PROTOCOL_FUNC1 (ProtocolFunc1)
P2 = PROTOCOL_FUNC2 (ProtocolFunc2)
TestProtocol1 = TEST_PROTOCOL (P1, 3, P2)
#
# InstallProtocolInterface
#
Status = EfiPy.gBS.InstallProtocolInterface (
EfiPy.byref (Handle1),
EfiPy.byref (TestGuid1),
EfiPy.EFI_NATIVE_INTERFACE,
EfiPy.byref (TestProtocol1)
)
#
# Protocl event variable
#
def ProtocolRegisterFunc (Event, Context):
print " Protocl Register notification call back."
Event = EfiPy.EFI_EVENT ()
tFunc = EfiPy.EFI_EVENT_NOTIFY(ProtocolRegisterFunc)
gContext = EfiPy.UINTN (1024)
Status = EfiPy.gBS.CreateEvent (
EfiPy.EVT_NOTIFY_SIGNAL,
EfiPy.TPL_NOTIFY,
tFunc,
EfiPy.PVOID.from_address (EfiPy.addressof(gContext)),
EfiPy.byref (Event)
)
#
# RegisterProtocolNotify
#
Registration = EfiPy.PVOID()
Status = EfiPy.gBS.RegisterProtocolNotify (
EfiPy.byref (TestGuid1),
Event,
EfiPy.byref(Registration)
)
screenshot
Sample code is protocol2.py at sourceforge.
Tuesday, August 11, 2015
Error Handle
Description
By these 2 reason,
1. Python output run time error to standard error.
2. Some BIOS standard error is not the same as standard output.
We can use try ... exception for output error to standard output
print traceback.format_exc()
Sample code
import traceback
By these 2 reason,
1. Python output run time error to standard error.
2. Some BIOS standard error is not the same as standard output.
We can use try ... exception for output error to standard output
print traceback.format_exc()
Sample code
import traceback
import EfiPy
from EfiPy.MdePkg.Protocol.SimpleTextOut import \
gEfiSimpleTextOutProtocolGuid, \
EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL
try:
Status = EfiPy.gBS.LocateProtocol (
EfiPy.byref (gEfiSimpleTextOutProtocolGuid),
None,
EfiPy.byref (Interface)
)
except:
print "Exception Test"
print traceback.format_exc()
Due to variable Interface is not initialed before EfiPy.gBS.LocateProtocol, it is exception.
screenshot
Monday, August 10, 2015
Protocol - 1
Description
In UEFI Spec., locate protocl with following declaration.
typedef
EFI_STATUS
(EFIAPI *EFI_LOCATE_PROTOCOL)(
IN EFI_GUID *Protocol,
IN VOID *Registration, OPTIONAL
OUT VOID **Interface
);
In EfiPy, it has this mapping declaration.
EFI_LOCATE_PROTOCOL = CFUNCTYPE (
EFI_STATUS,
POINTER(EFI_GUID), # IN *Protocol
PVOID, # IN *Registration, OPTIONAL
POINTER(PVOID) # OUT **Interface
)
Above, First argument (EFI_STATUS) is function return type.
By ctypes implementation, C language data structure is strong type.
Define PVOID object before locate protocol and transfer it to wanted protocol data object by ctypes cast() function after locate protocol success.
Sample Code
Interface = EfiPy.PVOID ()
Status = EfiPy.gBS.LocateProtocol (
EfiPy.byref (gEfiSimpleTextOutProtocolGuid),
None,
EfiPy.byref (Interface)
)
In UEFI Spec., locate protocl with following declaration.
typedef
EFI_STATUS
(EFIAPI *EFI_LOCATE_PROTOCOL)(
IN EFI_GUID *Protocol,
IN VOID *Registration, OPTIONAL
OUT VOID **Interface
);
In EfiPy, it has this mapping declaration.
EFI_LOCATE_PROTOCOL = CFUNCTYPE (
EFI_STATUS,
POINTER(EFI_GUID), # IN *Protocol
PVOID, # IN *Registration, OPTIONAL
POINTER(PVOID) # OUT **Interface
)
Above, First argument (EFI_STATUS) is function return type.
By ctypes implementation, C language data structure is strong type.
Define PVOID object before locate protocol and transfer it to wanted protocol data object by ctypes cast() function after locate protocol success.
Sample Code
Interface = EfiPy.PVOID ()
Status = EfiPy.gBS.LocateProtocol (
EfiPy.byref (gEfiSimpleTextOutProtocolGuid),
None,
EfiPy.byref (Interface)
)
TestConOut = EfiPy.cast (
Interface,
EfiPy.POINTER(EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL)
)
screenshot
sample source code can be download from sourceforge protocol_1.py
Sunday, August 9, 2015
Variable Operation
Description
Unicode string in Python is codded as u"string".
EfiPy provides GUID declare, which is similar to EDKII GUID declaration.
NULL (in C language) is codded as None in Python (also in ctypes/EfiPy).
Address of object in python ctypes, it is noted as byref() function
Address of object in python ctypes, it is noted as byref() function
C compatible string in Python ctypes is used by create_string_buffer.
Sample code - simplest EDK II get variable by EfiPy
import EfiPy
VariableName = u"EfiPyDemo"
VariableGuid = EfiPy.EFI_GUID( 0x8BE4DF61, 0x93CA, 0x11d2, \
(0xAA, 0x0D, 0x00, 0xE0, 0x98, 0x03, 0x2B, 0x8D))
DataSize = EfiPy.UINTN (0x00)
Sample code - simplest EDK II get variable by EfiPy
import EfiPy
VariableName = u"EfiPyDemo"
VariableGuid = EfiPy.EFI_GUID( 0x8BE4DF61, 0x93CA, 0x11d2, \
(0xAA, 0x0D, 0x00, 0xE0, 0x98, 0x03, 0x2B, 0x8D))
DataSize = EfiPy.UINTN (0x00)
DataBuffer = (EfiPy.CHAR8 * 5) ()
Attributes = EfiPy.UINT32 ()
Status = EfiPy.gRT.GetVariable(
VariableName,
EfiPy.byref (VariableGuid),
EfiPy.byref (Attributes),
EfiPy.byref (DataSize),
EfiPy.byref (DataBuffer)
)
Saturday, August 8, 2015
ReadKey.py
Description
ReadKey.py has these samples, EDKII event (EFI_EVENT), SimpleTextIn protocol and function return value.
In ReadKey.py file, it waits EfiPy.gST.ConIn[0].WaitForKey event in while loop.
EfiPy.gST.ConIn[0] protocol read user input key while event function return EFI_SUCCESS.
In output message, it output EFI_INPUT_KEY data.
source code - WaitForEvent
# while (RETURN_ERROR (Status)) {
while EfiPy.RETURN_ERROR (Status):
# Status = gBS->WaitForEvent (
# 1,
# & (EFI_EVENT)(gST->ConIn[0].WaitForKey),
# & EventIndex,
# );
Status = EfiPy.gBS.WaitForEvent (
1,
EfiPy.byref(EfiPy.EFI_EVENT(EfiPy.gST.ConIn[0].WaitForKey)),
EfiPy.byref(EventIndex)
)
source code - ReadKeyStroke
# Status = gST->ConIn[0].ReadKeyStroke (
# gST.ConIn, &InputKey
# );
Status = EfiPy.gST.ConIn[0].ReadKeyStroke (
EfiPy.gST.ConIn, EfiPy.byref (InputKey)
)
EfiPy.gST.ConOut[0].OutputString (
ReadKey.py has these samples, EDKII event (EFI_EVENT), SimpleTextIn protocol and function return value.
In ReadKey.py file, it waits EfiPy.gST.ConIn[0].WaitForKey event in while loop.
EfiPy.gST.ConIn[0] protocol read user input key while event function return EFI_SUCCESS.
In output message, it output EFI_INPUT_KEY data.
source code - WaitForEvent
# while (RETURN_ERROR (Status)) {
while EfiPy.RETURN_ERROR (Status):
# Status = gBS->WaitForEvent (
# 1,
# & (EFI_EVENT)(gST->ConIn[0].WaitForKey),
# & EventIndex,
# );
Status = EfiPy.gBS.WaitForEvent (
1,
EfiPy.byref(EfiPy.EFI_EVENT(EfiPy.gST.ConIn[0].WaitForKey)),
EfiPy.byref(EventIndex)
)
source code - ReadKeyStroke
# Status = gST->ConIn[0].ReadKeyStroke (
# gST.ConIn, &InputKey
# );
Status = EfiPy.gST.ConIn[0].ReadKeyStroke (
EfiPy.gST.ConIn, EfiPy.byref (InputKey)
)
source code - EFI_INPUT_KEY
if InputKey.ScanCode != Si.SCAN_NULL:
EfiPy.gST.ConOut[0].OutputString (
EfiPy.gST.ConOut,
u"Scan code 0x%04X is input\r\n" % InputKey.ScanCode
)
else:
EfiPy.gST.ConOut[0].OutputString (
EfiPy.gST.ConOut,
u"Input key \"%c\"\r\n" % InputKey.UnicodeChar
)
screenshot
Sample code from screenshot is uploaded to sourceforge
import EfiPy
Description
EfiPy uses python ctypes, which has been ported to UEFI Python package, can be downloaded from EfiPy download site.
EfiPy is almost mapped to EDKII MdePkg/Include.
#
# import EfiPy package
#
import EfiPy
With above python code, import EfiPy, and running it in UEFI shell environment, it has following benefit.
1. Basic data type inherited from ctypes (UINTN, UINT32, ...)
2. EFI_SYSTEM_TABLE, EFI_BOOT_SERVICES and EFI_RUNTIME_SERVICES data structure
3. ISA (Instruction Set Architecture) related structure
4. gRT, gST and gBS objects
5. gImageHandle and pImageHandle
6. EFI basic data structure
There are many macro #define in EDKII source code, it is transferred to constant value/function in EfiPy
source code - Table and Services
#
# UEFI basic tables gST, gRT, gBS
#
gRT = EFI_RUNTIME_SERVICES.from_address (_EfiPy.EfiPygRtAddr)
gST = EFI_SYSTEM_TABLE.from_address (_EfiPy.EfiPygStAddr)
gBS = EFI_BOOT_SERVICES.from_address (_EfiPy.EfiPygBsAddr)
source code - Handles
#
# EDK basic image handle
#
gImageHandle = EFI_HANDLE.from_address( _EfiPy.gImageHandle)
pImageHandle = EFI_HANDLE.from_address( _EfiPy.pImageHandle)
source code - basic data structure samples
UINT64 = c_uint64
INT64 = c_int64
UINT32 = c_uint32
EfiPy uses python ctypes, which has been ported to UEFI Python package, can be downloaded from EfiPy download site.
EfiPy is almost mapped to EDKII MdePkg/Include.
#
# import EfiPy package
#
import EfiPy
With above python code, import EfiPy, and running it in UEFI shell environment, it has following benefit.
1. Basic data type inherited from ctypes (UINTN, UINT32, ...)
2. EFI_SYSTEM_TABLE, EFI_BOOT_SERVICES and EFI_RUNTIME_SERVICES data structure
3. ISA (Instruction Set Architecture) related structure
4. gRT, gST and gBS objects
5. gImageHandle and pImageHandle
6. EFI basic data structure
There are many macro #define in EDKII source code, it is transferred to constant value/function in EfiPy
source code - Table and Services
#
# UEFI basic tables gST, gRT, gBS
#
gRT = EFI_RUNTIME_SERVICES.from_address (_EfiPy.EfiPygRtAddr)
gST = EFI_SYSTEM_TABLE.from_address (_EfiPy.EfiPygStAddr)
gBS = EFI_BOOT_SERVICES.from_address (_EfiPy.EfiPygBsAddr)
source code - Handles
#
# EDK basic image handle
#
gImageHandle = EFI_HANDLE.from_address( _EfiPy.gImageHandle)
pImageHandle = EFI_HANDLE.from_address( _EfiPy.pImageHandle)
source code - basic data structure samples
UINT64 = c_uint64
INT64 = c_int64
UINT32 = c_uint32
source code - EfiPy constant value/function
#
# ENCODE_ERROR function
#
def ENCODE_ERROR (StatusCode):
return StatusCode | MAX_BIT # MAX_BIT is exported from _EfiPy
#
# Return value
#
RETURN_INVALID_PARAMETER = ENCODE_ERROR (2)
Friday, August 7, 2015
EfiPy - Hello World
Description
To output string by EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL in EFI_SYSTEM_TABLE,
Import EfiPy in python source code and output string, directly.
source code
#
# HelloWorld.py
#
import EfiPy
# gST->ConOut[0].OutputString (gST->ConOut, L"Hello World");
EfiPy.gST.ConOut[0].OutputString(EfiPy.gST.ConOut, u"Hello World\r\n")
To output string by EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL in EFI_SYSTEM_TABLE,
Import EfiPy in python source code and output string, directly.
source code
#
# HelloWorld.py
#
import EfiPy
# gST->ConOut[0].OutputString (gST->ConOut, L"Hello World");
EfiPy.gST.ConOut[0].OutputString(EfiPy.gST.ConOut, u"Hello World\r\n")
screenshot
Thursday, August 6, 2015
EfiPy initial
Source Code: https://sourceforge.net/projects/efipy/
Sampe code: https://sourceforge.net/u/efipy/svn/HEAD/tree/
Sampe code: https://sourceforge.net/u/efipy/svn/HEAD/tree/
Description
EfiPy is a Python Module on UEFI shell which can access UEFI BIOS kernel interface
- System Table
- Runtime Services
- Boot Services
pAnalyzer package -
Tracing UEFI protocol calling flow
Output protocol flow to screen or file with XML format
CorePy (assembly package) -
Simple Assembly code in Python environment.
EfiPy Shell package-
Simple uefi shell program coded with EfiPy library to prove EfiPy workable
EfiPy leverage these open source packages - ctypes, CorePy.
Contact:
efipy.core@gmail.com
- System Table
- Runtime Services
- Boot Services
pAnalyzer package -
Tracing UEFI protocol calling flow
Output protocol flow to screen or file with XML format
CorePy (assembly package) -
Simple Assembly code in Python environment.
EfiPy Shell package-
Simple uefi shell program coded with EfiPy library to prove EfiPy workable
EfiPy leverage these open source packages - ctypes, CorePy.
Contact:
efipy.core@gmail.com
Subscribe to:
Posts (Atom)