1+ use crate :: file_data_source:: FileDataSource ;
12use anyhow:: Context ;
2- use std:: { collections:: BTreeMap , fs, io, path:: Path } ;
3+ use fatfs:: Dir ;
4+ use std:: fs:: File ;
5+ use std:: { collections:: BTreeMap , fs, path:: Path } ;
36
47use crate :: KERNEL_FILE_NAME ;
58
69pub fn create_fat_filesystem (
7- files : BTreeMap < & str , & Path > ,
10+ files : BTreeMap < & str , & FileDataSource > ,
811 out_fat_path : & Path ,
912) -> anyhow:: Result < ( ) > {
1013 const MB : u64 = 1024 * 1024 ;
1114
1215 // calculate needed size
1316 let mut needed_size = 0 ;
14- for path in files. values ( ) {
15- let file_size = fs:: metadata ( path)
16- . with_context ( || format ! ( "failed to read metadata of file `{}`" , path. display( ) ) ) ?
17- . len ( ) ;
18- needed_size += file_size;
17+ for source in files. values ( ) {
18+ needed_size += source. len ( ) ?;
1919 }
2020
2121 // create new filesystem image file at the given path and set its length
@@ -31,7 +31,9 @@ pub fn create_fat_filesystem(
3131
3232 // choose a file system label
3333 let mut label = * b"MY_RUST_OS!" ;
34- if let Some ( path) = files. get ( KERNEL_FILE_NAME ) {
34+
35+ // This __should__ always be a file, but maybe not. Should we allow the caller to set the volume label instead?
36+ if let Some ( FileDataSource :: File ( path) ) = files. get ( KERNEL_FILE_NAME ) {
3537 if let Some ( name) = path. file_stem ( ) {
3638 let converted = name. to_string_lossy ( ) ;
3739 let name = converted. as_bytes ( ) ;
@@ -48,10 +50,17 @@ pub fn create_fat_filesystem(
4850 fatfs:: format_volume ( & fat_file, format_options) . context ( "Failed to format FAT file" ) ?;
4951 let filesystem = fatfs:: FileSystem :: new ( & fat_file, fatfs:: FsOptions :: new ( ) )
5052 . context ( "Failed to open FAT file system of UEFI FAT file" ) ?;
53+ let root_dir = filesystem. root_dir ( ) ;
5154
5255 // copy files to file system
53- let root_dir = filesystem. root_dir ( ) ;
54- for ( target_path_raw, file_path) in files {
56+ add_files_to_image ( & root_dir, files)
57+ }
58+
59+ pub fn add_files_to_image (
60+ root_dir : & Dir < & File > ,
61+ files : BTreeMap < & str , & FileDataSource > ,
62+ ) -> anyhow:: Result < ( ) > {
63+ for ( target_path_raw, source) in files {
5564 let target_path = Path :: new ( target_path_raw) ;
5665 // create parent directories
5766 let ancestors: Vec < _ > = target_path. ancestors ( ) . skip ( 1 ) . collect ( ) ;
@@ -70,12 +79,14 @@ pub fn create_fat_filesystem(
7079 . create_file ( target_path_raw)
7180 . with_context ( || format ! ( "failed to create file at `{}`" , target_path. display( ) ) ) ?;
7281 new_file. truncate ( ) . unwrap ( ) ;
73- io:: copy (
74- & mut fs:: File :: open ( file_path)
75- . with_context ( || format ! ( "failed to open `{}` for copying" , file_path. display( ) ) ) ?,
76- & mut new_file,
77- )
78- . with_context ( || format ! ( "failed to copy `{}` to FAT filesystem" , file_path. display( ) ) ) ?;
82+
83+ source. copy_to ( & mut new_file) . with_context ( || {
84+ format ! (
85+ "failed to copy source data `{:?}` to file at `{}`" ,
86+ source,
87+ target_path. display( )
88+ )
89+ } ) ?;
7990 }
8091
8192 Ok ( ( ) )
0 commit comments