Skip to content

Commit bb648c9

Browse files
authored
Merge pull request #931 from nicholasbishop/bishop-uninstall-example
test-runner: Improve uninstall_protocol_interface example
2 parents f8168f7 + 4e43642 commit bb648c9

File tree

1 file changed

+40
-4
lines changed

1 file changed

+40
-4
lines changed

uefi-test-runner/src/boot/misc.rs

Lines changed: 40 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,12 @@
11
use core::ffi::c_void;
22
use core::ptr::{self, NonNull};
33

4+
use core::mem;
45
use uefi::proto::unsafe_protocol;
5-
use uefi::table::boot::{BootServices, EventType, MemoryType, SearchType, TimerTrigger, Tpl};
6+
use uefi::table::boot::{
7+
BootServices, EventType, MemoryType, OpenProtocolAttributes, OpenProtocolParams, SearchType,
8+
TimerTrigger, Tpl,
9+
};
610
use uefi::table::{Boot, SystemTable};
711
use uefi::{guid, Event, Guid, Identify};
812

@@ -84,7 +88,9 @@ fn test_watchdog(bt: &BootServices) {
8488

8589
/// Dummy protocol for tests
8690
#[unsafe_protocol("1a972918-3f69-4b5d-8cb4-cece2309c7f5")]
87-
struct TestProtocol {}
91+
struct TestProtocol {
92+
data: u32,
93+
}
8894

8995
unsafe extern "efiapi" fn _test_notify(_event: Event, _context: Option<NonNull<c_void>>) {
9096
info!("Protocol was (re)installed and this function notified.")
@@ -109,8 +115,17 @@ fn test_register_protocol_notify(bt: &BootServices) {
109115
fn test_install_protocol_interface(bt: &BootServices) {
110116
info!("Installing TestProtocol");
111117

118+
let alloc: *mut TestProtocol = bt
119+
.allocate_pool(
120+
MemoryType::BOOT_SERVICES_DATA,
121+
mem::size_of::<TestProtocol>(),
122+
)
123+
.unwrap()
124+
.cast();
125+
unsafe { alloc.write(TestProtocol { data: 123 }) };
126+
112127
let _ = unsafe {
113-
bt.install_protocol_interface(None, &TestProtocol::GUID, ptr::null_mut())
128+
bt.install_protocol_interface(None, &TestProtocol::GUID, alloc.cast())
114129
.expect("Failed to install protocol interface")
115130
};
116131

@@ -137,13 +152,34 @@ fn test_reinstall_protocol_interface(bt: &BootServices) {
137152

138153
fn test_uninstall_protocol_interface(bt: &BootServices) {
139154
info!("Uninstalling TestProtocol");
155+
140156
let handle = bt
141157
.locate_handle_buffer(SearchType::from_proto::<TestProtocol>())
142158
.expect("Failed to find protocol to uninstall")[0];
143159

144160
unsafe {
145-
bt.uninstall_protocol_interface(handle, &TestProtocol::GUID, ptr::null_mut())
161+
// Uninstalling a protocol interface requires knowing the interface
162+
// pointer. Open the protocol to get that pointer, making sure to drop
163+
// the `ScopedProtocol` _before_ uninstalling the protocol interface.
164+
let interface_ptr: *mut TestProtocol = {
165+
let mut sp = bt
166+
.open_protocol::<TestProtocol>(
167+
OpenProtocolParams {
168+
handle,
169+
agent: bt.image_handle(),
170+
controller: None,
171+
},
172+
OpenProtocolAttributes::GetProtocol,
173+
)
174+
.unwrap();
175+
assert_eq!(sp.data, 123);
176+
&mut *sp
177+
};
178+
179+
bt.uninstall_protocol_interface(handle, &TestProtocol::GUID, interface_ptr.cast())
146180
.expect("Failed to uninstall protocol interface");
181+
182+
bt.free_pool(interface_ptr.cast()).unwrap();
147183
}
148184
}
149185

0 commit comments

Comments
 (0)