@@ -11,7 +11,8 @@ use core::ops::{Deref, DerefMut};
11
11
use core:: ptr:: { self , NonNull } ;
12
12
use core:: sync:: atomic:: { AtomicPtr , Ordering } ;
13
13
use core:: { mem, slice} ;
14
- use uefi:: { table, Char16 , Event , Handle , Result , Status , StatusExt } ;
14
+ use uefi:: { table, Char16 , Event , Guid , Handle , Result , Status , StatusExt } ;
15
+ use uefi_raw:: table:: boot:: InterfaceType ;
15
16
16
17
#[ cfg( doc) ]
17
18
use {
@@ -299,6 +300,94 @@ pub fn disconnect_controller(
299
300
. to_result_with_err ( |_| ( ) )
300
301
}
301
302
303
+ /// Installs a protocol interface on a device handle.
304
+ ///
305
+ /// When a protocol interface is installed, firmware will call all functions
306
+ /// that have registered to wait for that interface to be installed.
307
+ ///
308
+ /// If `handle` is `None`, a new handle will be created and returned.
309
+ ///
310
+ /// # Safety
311
+ ///
312
+ /// The caller is responsible for ensuring that they pass a valid `Guid` for `protocol`.
313
+ ///
314
+ /// # Errors
315
+ ///
316
+ /// * [`Status::OUT_OF_RESOURCES`]: failed to allocate a new handle.
317
+ /// * [`Status::INVALID_PARAMETER`]: this protocol is already installed on the handle.
318
+ pub unsafe fn install_protocol_interface (
319
+ handle : Option < Handle > ,
320
+ protocol : & Guid ,
321
+ interface : * const c_void ,
322
+ ) -> Result < Handle > {
323
+ let bt = boot_services_raw_panicking ( ) ;
324
+ let bt = unsafe { bt. as_ref ( ) } ;
325
+
326
+ let mut handle = Handle :: opt_to_ptr ( handle) ;
327
+ ( ( bt. install_protocol_interface ) (
328
+ & mut handle,
329
+ protocol,
330
+ InterfaceType :: NATIVE_INTERFACE ,
331
+ interface,
332
+ ) )
333
+ . to_result_with_val ( || Handle :: from_ptr ( handle) . unwrap ( ) )
334
+ }
335
+
336
+ /// Reinstalls a protocol interface on a device handle. `old_interface` is replaced with `new_interface`.
337
+ /// These interfaces may be the same, in which case the registered protocol notifications occur for the handle
338
+ /// without replacing the interface.
339
+ ///
340
+ /// As with `install_protocol_interface`, any process that has registered to wait for the installation of
341
+ /// the interface is notified.
342
+ ///
343
+ /// # Safety
344
+ ///
345
+ /// The caller is responsible for ensuring that there are no references to the `old_interface` that is being
346
+ /// removed.
347
+ ///
348
+ /// # Errors
349
+ ///
350
+ /// * [`Status::NOT_FOUND`]: the old interface was not found on the handle.
351
+ /// * [`Status::ACCESS_DENIED`]: the old interface is still in use and cannot be uninstalled.
352
+ pub unsafe fn reinstall_protocol_interface (
353
+ handle : Handle ,
354
+ protocol : & Guid ,
355
+ old_interface : * const c_void ,
356
+ new_interface : * const c_void ,
357
+ ) -> Result < ( ) > {
358
+ let bt = boot_services_raw_panicking ( ) ;
359
+ let bt = unsafe { bt. as_ref ( ) } ;
360
+
361
+ ( bt. reinstall_protocol_interface ) ( handle. as_ptr ( ) , protocol, old_interface, new_interface)
362
+ . to_result ( )
363
+ }
364
+
365
+ /// Removes a protocol interface from a device handle.
366
+ ///
367
+ /// # Safety
368
+ ///
369
+ /// The caller is responsible for ensuring that there are no references to a protocol interface
370
+ /// that has been removed. Some protocols may not be able to be removed as there is no information
371
+ /// available regarding the references. This includes Console I/O, Block I/O, Disk I/o, and handles
372
+ /// to device protocols.
373
+ ///
374
+ /// The caller is responsible for ensuring that they pass a valid `Guid` for `protocol`.
375
+ ///
376
+ /// # Errors
377
+ ///
378
+ /// * [`Status::NOT_FOUND`]: the interface was not found on the handle.
379
+ /// * [`Status::ACCESS_DENIED`]: the interface is still in use and cannot be uninstalled.
380
+ pub unsafe fn uninstall_protocol_interface (
381
+ handle : Handle ,
382
+ protocol : & Guid ,
383
+ interface : * const c_void ,
384
+ ) -> Result < ( ) > {
385
+ let bt = boot_services_raw_panicking ( ) ;
386
+ let bt = unsafe { bt. as_ref ( ) } ;
387
+
388
+ ( bt. uninstall_protocol_interface ) ( handle. as_ptr ( ) , protocol, interface) . to_result ( )
389
+ }
390
+
302
391
/// Returns an array of handles that support the requested protocol in a
303
392
/// pool-allocated buffer.
304
393
///
0 commit comments