@@ -292,33 +292,25 @@ impl Drop for DevicePath {
292
292
}
293
293
}
294
294
295
- pub ( crate ) struct Protocol < T > {
295
+ pub ( crate ) struct OwnedProtocol < T > {
296
296
guid : r_efi:: efi:: Guid ,
297
297
handle : NonNull < crate :: ffi:: c_void > ,
298
- protocol : Box < T > ,
298
+ protocol : * mut T ,
299
299
}
300
300
301
- impl < T > Protocol < T > {
302
- const fn new (
303
- guid : r_efi:: efi:: Guid ,
304
- handle : NonNull < crate :: ffi:: c_void > ,
305
- protocol : Box < T > ,
306
- ) -> Self {
307
- Self { guid, handle, protocol }
308
- }
309
-
301
+ impl < T > OwnedProtocol < T > {
310
302
pub ( crate ) fn create ( protocol : T , mut guid : r_efi:: efi:: Guid ) -> io:: Result < Self > {
311
303
let boot_services: NonNull < r_efi:: efi:: BootServices > =
312
304
boot_services ( ) . ok_or ( BOOT_SERVICES_UNAVAILABLE ) ?. cast ( ) ;
313
- let mut protocol = Box :: new ( protocol) ;
305
+ let protocol : * mut T = Box :: into_raw ( Box :: new ( protocol) ) ;
314
306
let mut handle: r_efi:: efi:: Handle = crate :: ptr:: null_mut ( ) ;
315
307
316
308
let r = unsafe {
317
309
( ( * boot_services. as_ptr ( ) ) . install_protocol_interface ) (
318
310
& mut handle,
319
311
& mut guid,
320
312
r_efi:: efi:: NATIVE_INTERFACE ,
321
- protocol. as_mut ( ) as * mut T as * mut crate :: ffi:: c_void ,
313
+ protocol as * mut crate :: ffi:: c_void ,
322
314
)
323
315
} ;
324
316
@@ -329,37 +321,78 @@ impl<T> Protocol<T> {
329
321
let handle = NonNull :: new ( handle)
330
322
. ok_or ( io:: const_io_error!( io:: ErrorKind :: Uncategorized , "found null handle" ) ) ?;
331
323
332
- Ok ( Self :: new ( guid, handle, protocol) )
324
+ Ok ( Self { guid, handle, protocol } )
333
325
}
334
326
335
327
pub ( crate ) fn handle ( & self ) -> NonNull < crate :: ffi:: c_void > {
336
328
self . handle
337
329
}
338
330
}
339
331
340
- impl < T > Drop for Protocol < T > {
332
+ impl < T > Drop for OwnedProtocol < T > {
341
333
fn drop ( & mut self ) {
342
334
if let Some ( bt) = boot_services ( ) {
343
335
let bt: NonNull < r_efi:: efi:: BootServices > = bt. cast ( ) ;
344
336
unsafe {
345
337
( ( * bt. as_ptr ( ) ) . uninstall_protocol_interface ) (
346
338
self . handle . as_ptr ( ) ,
347
339
& mut self . guid ,
348
- self . protocol . as_mut ( ) as * mut T as * mut crate :: ffi:: c_void ,
340
+ self . protocol as * mut crate :: ffi:: c_void ,
349
341
)
350
342
} ;
351
343
}
344
+
345
+ let _ = unsafe { Box :: from_raw ( self . protocol ) } ;
352
346
}
353
347
}
354
348
355
- impl < T > AsRef < T > for Protocol < T > {
349
+ impl < T > AsRef < T > for OwnedProtocol < T > {
356
350
fn as_ref ( & self ) -> & T {
357
- & self . protocol
351
+ unsafe { self . protocol . as_ref ( ) . unwrap ( ) }
352
+ }
353
+ }
354
+
355
+ pub ( crate ) struct OwnedTable < T > {
356
+ layout : crate :: alloc:: Layout ,
357
+ ptr : * mut T ,
358
+ }
359
+
360
+ impl < T > OwnedTable < T > {
361
+ pub ( crate ) fn from_table_header ( hdr : & r_efi:: efi:: TableHeader ) -> Self {
362
+ let header_size = hdr. header_size as usize ;
363
+ let layout = crate :: alloc:: Layout :: from_size_align ( header_size, 8 ) . unwrap ( ) ;
364
+ let ptr = unsafe { crate :: alloc:: alloc ( layout) as * mut T } ;
365
+ Self { layout, ptr }
366
+ }
367
+
368
+ pub ( crate ) const fn as_ptr ( & self ) -> * const T {
369
+ self . ptr
370
+ }
371
+
372
+ pub ( crate ) const fn as_mut_ptr ( & self ) -> * mut T {
373
+ self . ptr
374
+ }
375
+ }
376
+
377
+ impl OwnedTable < r_efi:: efi:: SystemTable > {
378
+ pub ( crate ) fn from_table ( tbl : * const r_efi:: efi:: SystemTable ) -> Self {
379
+ let hdr = unsafe { ( * tbl) . hdr } ;
380
+
381
+ let owned_tbl = Self :: from_table_header ( & hdr) ;
382
+ unsafe {
383
+ crate :: ptr:: copy_nonoverlapping (
384
+ tbl as * const u8 ,
385
+ owned_tbl. as_mut_ptr ( ) as * mut u8 ,
386
+ hdr. header_size as usize ,
387
+ )
388
+ } ;
389
+
390
+ owned_tbl
358
391
}
359
392
}
360
393
361
- impl < T > AsMut < T > for Protocol < T > {
362
- fn as_mut ( & mut self ) -> & mut T {
363
- & mut self . protocol
394
+ impl < T > Drop for OwnedTable < T > {
395
+ fn drop ( & mut self ) {
396
+ unsafe { crate :: alloc :: dealloc ( self . ptr as * mut u8 , self . layout ) } ;
364
397
}
365
398
}
0 commit comments