@@ -14,6 +14,8 @@ use std::io::{BufRead, BufReader, Read, Write};
14
14
use std:: path:: { Path , PathBuf } ;
15
15
use std:: process:: { Child , Command , Stdio } ;
16
16
use tempfile:: TempDir ;
17
+ #[ cfg( target_os = "linux" ) ]
18
+ use { std:: fs:: Permissions , std:: os:: unix:: fs:: PermissionsExt } ;
17
19
18
20
#[ derive( Clone , Copy , Debug ) ]
19
21
enum OvmfFileType {
@@ -127,6 +129,34 @@ impl OvmfPaths {
127
129
}
128
130
}
129
131
132
+ /// Get the NixOS OVMF paths for the given guest arch.
133
+ fn nixos ( arch : UefiArch ) -> Option < Self > {
134
+ let os_info = os_info:: get ( ) ;
135
+ if os_info. os_type ( ) != os_info:: Type :: NixOS {
136
+ return None ;
137
+ }
138
+ let path = std:: env:: var_os ( "OVMF" ) . expect ( "Must have OVMF env var. Run '$ nix-shell'" ) ;
139
+ let path = path. to_str ( ) . unwrap ( ) ;
140
+ let paths = match arch {
141
+ // Package "edk2-aarch64".
142
+ UefiArch :: AArch64 => Self {
143
+ code : format ! ( "{path}/FV/AAVMF_CODE.fd" ) . into ( ) ,
144
+ vars : format ! ( "{path}/FV/AAVMF_VARS.fd" ) . into ( ) ,
145
+ } ,
146
+ // Package "edk2-ovmf-ia32".
147
+ UefiArch :: IA32 => Self {
148
+ code : format ! ( "{path}/FV/OVMF_CODE.fd" ) . into ( ) ,
149
+ vars : format ! ( "{path}/FV/OVMF_VARS.fd" ) . into ( ) ,
150
+ } ,
151
+ // Package "edk2-ovmf".
152
+ UefiArch :: X86_64 => Self {
153
+ code : format ! ( "{path}/FV/OVMF_CODE.fd" ) . into ( ) ,
154
+ vars : format ! ( "{path}/FV/OVMF_VARS.fd" ) . into ( ) ,
155
+ } ,
156
+ } ;
157
+ Some ( paths)
158
+ }
159
+
130
160
/// Get the Windows OVMF paths for the given guest arch.
131
161
fn windows ( arch : UefiArch ) -> Self {
132
162
match arch {
@@ -157,6 +187,9 @@ impl OvmfPaths {
157
187
}
158
188
candidates. push ( Self :: debian_linux ( arch) ) ;
159
189
candidates. push ( Self :: fedora_linux ( arch) ) ;
190
+ if let Some ( paths) = Self :: nixos ( arch) {
191
+ candidates. push ( paths) ;
192
+ }
160
193
}
161
194
if platform:: is_windows ( ) {
162
195
candidates. push ( Self :: windows ( arch) ) ;
@@ -497,6 +530,10 @@ pub fn run_qemu(arch: UefiArch, opt: &QemuOpt) -> Result<()> {
497
530
// versions of OVMF won't boot if the vars file isn't writeable.
498
531
let ovmf_vars = tmp_dir. join ( "ovmf_vars" ) ;
499
532
fs_err:: copy ( & ovmf_paths. vars , & ovmf_vars) ?;
533
+ // Necessary, as for example on NixOS, the files are read-only inside
534
+ // the Nix store.
535
+ #[ cfg( target_os = "linux" ) ]
536
+ fs_err:: set_permissions ( & ovmf_vars, Permissions :: from_mode ( 0o666 ) ) ?;
500
537
501
538
add_pflash_args ( & mut cmd, & ovmf_paths. code , PflashMode :: ReadOnly ) ;
502
539
add_pflash_args ( & mut cmd, & ovmf_vars, PflashMode :: ReadWrite ) ;
0 commit comments