@@ -23,6 +23,7 @@ use super::helpers;
2323
2424pub struct Command {
2525 prog : OsString ,
26+ args : OsString ,
2627 stdout : Option < Stdio > ,
2728 stderr : Option < Stdio > ,
2829}
@@ -45,11 +46,17 @@ pub enum Stdio {
4546
4647impl Command {
4748 pub fn new ( program : & OsStr ) -> Command {
48- Command { prog : program. to_os_string ( ) , stdout : None , stderr : None }
49+ Command {
50+ prog : program. to_os_string ( ) ,
51+ args : program. to_os_string ( ) ,
52+ stdout : None ,
53+ stderr : None ,
54+ }
4955 }
5056
51- pub fn arg ( & mut self , _arg : & OsStr ) {
52- panic ! ( "unsupported" )
57+ pub fn arg ( & mut self , arg : & OsStr ) {
58+ self . args . push ( " " ) ;
59+ self . args . push ( arg) ;
5360 }
5461
5562 pub fn env_mut ( & mut self ) -> & mut CommandEnv {
@@ -137,11 +144,17 @@ impl Command {
137144 . map ( Some ) ,
138145 } ?;
139146
140- if let Some ( stdout) = stdout {
141- cmd. stdout_init ( stdout) ?;
142- }
143- if let Some ( stderr) = stderr {
144- cmd. stderr_init ( stderr) ?;
147+ match stdout {
148+ Some ( stdout) => cmd. stdout_init ( stdout) ,
149+ None => cmd. stdout_inherit ( ) ,
150+ } ;
151+ match stderr {
152+ Some ( stderr) => cmd. stderr_init ( stderr) ,
153+ None => cmd. stderr_inherit ( ) ,
154+ } ;
155+
156+ if !self . args . is_empty ( ) {
157+ cmd. set_args ( & self . args ) ;
145158 }
146159
147160 let stat = cmd. start_image ( ) ?;
@@ -308,8 +321,8 @@ mod uefi_command_internal {
308321 use crate :: ffi:: { OsStr , OsString } ;
309322 use crate :: io:: { self , const_io_error} ;
310323 use crate :: mem:: MaybeUninit ;
311- use crate :: os:: uefi:: env:: { boot_services, image_handle} ;
312- use crate :: os:: uefi:: ffi:: OsStringExt ;
324+ use crate :: os:: uefi:: env:: { boot_services, image_handle, system_table } ;
325+ use crate :: os:: uefi:: ffi:: { OsStrExt , OsStringExt } ;
313326 use crate :: ptr:: NonNull ;
314327 use crate :: slice;
315328 use crate :: sys_common:: wstr:: WStrUnits ;
@@ -319,14 +332,15 @@ mod uefi_command_internal {
319332 stdout : Option < helpers:: Protocol < PipeProtocol > > ,
320333 stderr : Option < helpers:: Protocol < PipeProtocol > > ,
321334 st : Box < r_efi:: efi:: SystemTable > ,
335+ args : Option < Vec < u16 > > ,
322336 }
323337
324338 impl Command {
325339 const fn new (
326340 handle : NonNull < crate :: ffi:: c_void > ,
327341 st : Box < r_efi:: efi:: SystemTable > ,
328342 ) -> Self {
329- Self { handle, stdout : None , stderr : None , st }
343+ Self { handle, stdout : None , stderr : None , st, args : None }
330344 }
331345
332346 pub fn load_image ( p : & OsStr ) -> io:: Result < Self > {
@@ -391,30 +405,34 @@ mod uefi_command_internal {
391405 Ok ( r)
392406 }
393407
394- pub fn stdout_init (
395- & mut self ,
396- mut protocol : helpers:: Protocol < PipeProtocol > ,
397- ) -> io:: Result < ( ) > {
408+ pub fn stdout_init ( & mut self , mut protocol : helpers:: Protocol < PipeProtocol > ) {
398409 self . st . console_out_handle = protocol. handle ( ) . as_ptr ( ) ;
399410 self . st . con_out =
400411 protocol. as_mut ( ) as * mut PipeProtocol as * mut simple_text_output:: Protocol ;
401412
402413 self . stdout = Some ( protocol) ;
414+ }
403415
404- Ok ( ( ) )
416+ pub fn stdout_inherit ( & mut self ) {
417+ let st: NonNull < r_efi:: efi:: SystemTable > = system_table ( ) . cast ( ) ;
418+
419+ self . st . console_out_handle = unsafe { ( * st. as_ptr ( ) ) . console_out_handle } ;
420+ self . st . con_out = unsafe { ( * st. as_ptr ( ) ) . con_out } ;
405421 }
406422
407- pub fn stderr_init (
408- & mut self ,
409- mut protocol : helpers:: Protocol < PipeProtocol > ,
410- ) -> io:: Result < ( ) > {
423+ pub fn stderr_init ( & mut self , mut protocol : helpers:: Protocol < PipeProtocol > ) {
411424 self . st . standard_error_handle = protocol. handle ( ) . as_ptr ( ) ;
412425 self . st . std_err =
413426 protocol. as_mut ( ) as * mut PipeProtocol as * mut simple_text_output:: Protocol ;
414427
415428 self . stderr = Some ( protocol) ;
429+ }
430+
431+ pub fn stderr_inherit ( & mut self ) {
432+ let st: NonNull < r_efi:: efi:: SystemTable > = system_table ( ) . cast ( ) ;
416433
417- Ok ( ( ) )
434+ self . st . standard_error_handle = unsafe { ( * st. as_ptr ( ) ) . standard_error_handle } ;
435+ self . st . std_err = unsafe { ( * st. as_ptr ( ) ) . std_err } ;
418436 }
419437
420438 pub fn stderr ( & self ) -> io:: Result < Vec < u8 > > {
@@ -430,6 +448,22 @@ mod uefi_command_internal {
430448 None => Ok ( Vec :: new ( ) ) ,
431449 }
432450 }
451+
452+ pub fn set_args ( & mut self , args : & OsStr ) {
453+ let loaded_image: NonNull < loaded_image:: Protocol > =
454+ helpers:: open_protocol ( self . handle , loaded_image:: PROTOCOL_GUID ) . unwrap ( ) ;
455+
456+ let mut args = args. encode_wide ( ) . collect :: < Vec < u16 > > ( ) ;
457+ let args_size = ( crate :: mem:: size_of :: < u16 > ( ) * args. len ( ) ) as u32 ;
458+
459+ unsafe {
460+ ( * loaded_image. as_ptr ( ) ) . load_options =
461+ args. as_mut_ptr ( ) as * mut crate :: ffi:: c_void ;
462+ ( * loaded_image. as_ptr ( ) ) . load_options_size = args_size;
463+ }
464+
465+ self . args = Some ( args) ;
466+ }
433467 }
434468
435469 impl Drop for Command {
0 commit comments