目录
前言
This section explores console support protocols, including Simple Text Input, Simple Text Output, Simple Pointer, Serial IO, and Graphics Output protocols.
本节探讨控制台支持协议,包括简单文本输入、简单文本输出、简单指针、串行IO和图形输出协议。
1.Console I/O Protocol
这里还包括三个控制台设备的定义:一个用于输入,一个用于正常输出和错误。
UEFI控制台是由EFI_SIMPLE_TEXT_INPUT_PROTOCOL
和EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL
构建的。这两个协议实现了一个基本的基于文本的控制台。
UEFl控制台支持16位Unicode字符代码、一组简单的输入控制字符(扫描码)和一组面向输出的可编程接口,这些接口提供的功能相当于智能终端。控制台不支持输入上的指向设备或输出上的位图。
输入流包含表中所定义的Unicode字符和所需的EFI扫描码:
Mnemonic | Unicode | 描述 |
---|---|---|
Null | U+0000 | 接收时忽略空字符 |
BS | U+0008 | 退格键 |
TAB | U+0x0009 | Tab |
LF | U+000A | 换行 |
CR | U+000D | 回车 |
EFI Scan Codes Table请看:
Table 12-2 EFI Scan Codes for EFI_SIMPLE_TEXT_INPUT_PROTOCOL
And
Table 12-3 EFI Scan Codes for EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL
2.Simple Text Input Ex Protocol
typedef struct _EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL{
EFI_INPUT_RESET_EX Reset; //重启console设备
EFI_INPUT_READ_KEY_EX ReadKeyStrokeEx; //返回下一个输入字符
EFI_EVENT WaitForKeyEx; //事件与WaitForEvent()一起使用等待一个可用的键,事件只会在KeyData触发
EFI_SET_STATE SetState; //设置输入设备的EFI_KEY_TOGGLE_STATE状态设置
EFI_REGISTER_KEYSTROKE_NOTIFY RegisterKeyNotify; //注册一个通知函数,当一个给定的键序列被击中时调用
EFI_UNREGISTER_KEYSTROKE_NOTIFY UnregisterKeyNotify; //删除指定的通知功能
} EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL;
2.1ReadKeyStrokeEx()
从输入设备读取下一个击键。
Prototype
typedef
EFI_STATUS
(EFIAPI *EFI_INPUT_READ_KEY_EX) (
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This,
OUT EFI_KEY_DATA *KeyData //按下的键的状态数据
);
KeyData 结构体:
typedef struct {
EFI_INPUT_KEY Key; //从输入设备返回的EFI scan code and Unicode value
EFI_KEY_STATE KeyState; //状态以及输入修饰符值
} EFI_KEY_DATA
KeyState 结构体:
typedef struct EFI_KEY_STATE {
UINT32 KeyShiftState;
EFI_KEY_TOGGLE_STATE KeyToggleState;
} EFI_KEY_STATE;
2.2 SetState()
设置设备的KeyToggleState
2.3 RegisterKeyNotify()
为输入设备的特定击键注册一个通知函数。
typedef
EFI_STATUS
(EFIAPI *EFI_REGISTER_KEYSTROKE_NOTIFY) (
IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL *This,
IN EFI_KEY_DATA *KeyData,
IN EFI_KEY_NOTIFY_FUNCTION KeyNotificationFunction, //这个通知函数应该在<=TPL_CALLBACK被调用
OUT VOID **NotifyHandle //用这个句柄做参数可以使用UnregisterKeyNotify来删除
);
例子:注册监听CTRL+C
按键
KeyData.KeyState.KeyToggleState = 0;
KeyData.Key.ScanCode = 0;
KeyData.KeyState.KeyShiftState = EFI_SHIFT_STATE_VALID|EFI_LEFT_CONTROL_PRESSED;
KeyData.Key.UnicodeChar = L'c';
Status = SimpleEx->RegisterKeyNotify (
SimpleEx,
&KeyData,
NotificationFunction,
&ShellInfoObject.CtrlCNotifyHandle1
);
3.Simple Text Input Protocol
是ConsoleIn所需的最小协议。
typedef struct _EFI_SIMPLE_TEXT_INPUT_PROTOCOL {
EFI_INPUT_RESET Reset;
EFI_INPUT_READ_KEY ReadKeyStroke; //与ReadKeyStrokeEx相似,返回EFI_INPUT_KEY Key
EFI_EVENT WaitForKey;
} EFI_SIMPLE_TEXT_INPUT_PROTOCOL;
4.Simple Text Output Protocol
EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL
必须实现与EFI_SIMPLE_TEXT_INPUT_PROTOCOL
相同的Unicode代码页。该协议必须定义的Unicode控制字符。不支持定义的EFI扫描码。
typedef struct _EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL {
EFI_TEXT_RESET Reset; //重置ConsoleOut设备
EFI_TEXT_STRING OutputString; //将字符串写入输出设备
EFI_TEXT_TEST_STRING TestString; //测试ConsoleOut设备是否支持此字符串
EFI_TEXT_QUERY_MODE QueryMode;//显示设备上位于当前光标位置的字符串
EFI_TEXT_SET_MODE SetMode; //设置输出设备的当前模式
EFI_TEXT_SET_ATTRIBUTE SetAttribute; //设置输出文本的前景色和背景色
EFI_TEXT_CLEAR_SCREEN ClearScreen; //使用当前设置的背景色清除屏幕
EFI_TEXT_SET_CURSOR_POSITION SetCursorPosition;//设置当前光标位置
EFI_TEXT_ENABLE_CURSOR EnableCursor;//打开/关闭光标的可见性
SIMPLE_TEXT_OUTPUT_MODE *Mode; //指针指向SIMPLE_TEXT_OUTPUT_MODE数据
} EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL;
文本模式的Setup界面,Shell,串口,都属于输出设备
总结
后续有更深理解,会继续补充。
学艺不精,错误请指正;
如有侵权,请联系删除。
参考文档: 《UEFI_Spec_2_9_2021_03_18》