@@ -39,6 +39,12 @@ pub enum Error {
3939 StartInfoPastRamEnd ,
4040 /// Error writing hvm_start_info to guest memory.
4141 StartInfoSetup ,
42+ /// The starting address for the modules descriptions wasn't passed to the boot configurator.
43+ ModulesAddressMissing ,
44+ /// The modules description table extends past the end of guest memory.
45+ ModulesPastRamEnd ,
46+ /// Error writing module descriptions to guest memory.
47+ ModulesSetup ,
4248}
4349
4450impl fmt:: Display for Error {
@@ -55,6 +61,9 @@ impl fmt::Display for Error {
5561 "the hvm_start_info structure extends past the end of guest memory."
5662 }
5763 StartInfoSetup => "error writing hvm_start_info to guest memory." ,
64+ ModulesAddressMissing => "the starting address for the modules descriptions wasn't passed to the boot configurator." ,
65+ ModulesPastRamEnd => "the modules description table extends past the end of guest memory." ,
66+ ModulesSetup => "error writing module descriptions to guest memory." ,
5867 } ;
5968
6069 write ! ( f, "PVH Boot Configurator: {}" , desc)
@@ -164,6 +173,16 @@ impl BootConfigurator for PvhBootConfigurator {
164173 . write_slice ( params. header . as_slice ( ) , params. header_start )
165174 . map_err ( |_| Error :: StartInfoSetup ) ?;
166175
176+ if let Some ( modules) = params. modules . as_ref ( ) {
177+ let modules_addr = params. modules_start . ok_or ( Error :: ModulesAddressMissing ) ?;
178+ guest_memory
179+ . checked_offset ( modules_addr, modules. len ( ) )
180+ . ok_or ( Error :: ModulesPastRamEnd ) ?;
181+ guest_memory
182+ . write_slice ( modules. as_slice ( ) , modules_addr)
183+ . map_err ( |_| Error :: ModulesSetup ) ?;
184+ }
185+
167186 Ok ( ( ) )
168187 }
169188}
@@ -182,7 +201,11 @@ mod tests {
182201 GuestMemoryMmap :: from_ranges ( & [ ( GuestAddress ( 0x0 ) , ( MEM_SIZE as usize ) ) ] ) . unwrap ( )
183202 }
184203
185- fn build_bootparams_common ( ) -> ( hvm_start_info , Vec < hvm_memmap_table_entry > ) {
204+ fn build_bootparams_common ( ) -> (
205+ hvm_start_info ,
206+ Vec < hvm_memmap_table_entry > ,
207+ Vec < hvm_modlist_entry > ,
208+ ) {
186209 let mut start_info = hvm_start_info:: default ( ) ;
187210 let memmap_entry = hvm_memmap_table_entry {
188211 addr : 0x7000 ,
@@ -191,21 +214,29 @@ mod tests {
191214 reserved : 0 ,
192215 } ;
193216
217+ let modlist_entry = hvm_modlist_entry {
218+ paddr : 0x10000 ,
219+ size : 0x100 ,
220+ cmdline_paddr : 0 ,
221+ reserved : 0 ,
222+ } ;
223+
194224 start_info. magic = XEN_HVM_START_MAGIC_VALUE ;
195225 start_info. version = 1 ;
196226 start_info. nr_modules = 0 ;
197227 start_info. memmap_entries = 0 ;
198228
199- ( start_info, vec ! [ memmap_entry] )
229+ ( start_info, vec ! [ memmap_entry] , vec ! [ modlist_entry ] )
200230 }
201231
202232 #[ test]
203233 fn test_configure_pvh_boot ( ) {
204- let ( mut start_info, memmap_entries) = build_bootparams_common ( ) ;
234+ let ( mut start_info, memmap_entries, modlist_entries ) = build_bootparams_common ( ) ;
205235 let guest_memory = create_guest_mem ( ) ;
206236
207237 let start_info_addr = GuestAddress ( 0x6000 ) ;
208238 let memmap_addr = GuestAddress ( 0x7000 ) ;
239+ let modlist_addr = GuestAddress ( 0x6040 ) ;
209240 start_info. memmap_paddr = memmap_addr. raw_value ( ) ;
210241
211242 let mut boot_params = BootParams :: new :: < hvm_start_info > ( & start_info, start_info_addr) ;
@@ -245,6 +276,7 @@ mod tests {
245276 ) ;
246277
247278 boot_params. set_sections :: < hvm_memmap_table_entry > ( & memmap_entries, memmap_addr) ;
279+ boot_params. set_modules :: < hvm_modlist_entry > ( & modlist_entries, modlist_addr) ;
248280 assert ! ( PvhBootConfigurator :: write_bootparams:: <GuestMemoryMmap >(
249281 & boot_params,
250282 & guest_memory,
0 commit comments