Skip to content

Commit b514cfc

Browse files
committed
include, block: add krun_enable_relaxed_sync_for_disk API
Add an API that allows the user to explicitly specify whether they want to enable the relaxed sync behavior on macOS to match the Virtualization.Framework's behavior. Signed-off-by: Jake Correnti <[email protected]>
1 parent ed4e180 commit b514cfc

File tree

4 files changed

+63
-1
lines changed

4 files changed

+63
-1
lines changed

include/libkrun.h

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1034,6 +1034,27 @@ int32_t krun_add_serial_console_default(uint32_t ctx_id,
10341034
*/
10351035
int32_t krun_set_root_disk_remount(uint32_t ctx_id, const char *device, const char *fstype, const char *options);
10361036

1037+
/**
1038+
* On macOS, `std::fs::File::flush()` uses `F_FULLFSYNC`, which syncs the buffers to the drive an asks
1039+
* the drive to wait for flushing all the data to the permanent storage. In contrast, Apple
1040+
* Virtualization.Framework only issues an `fsync()`, which doesn't ask the drive to flush it's buffered
1041+
* data.
1042+
*
1043+
* Configure whether to match the Virtualization.Framework behavior.
1044+
*
1045+
* Arguments:
1046+
* "ctx_id" - the configuration context ID.
1047+
* "block_id" - a null-terminated string representing the partition to configure.
1048+
* "enable" - whether or not to enable relaxed sync behavior.
1049+
*
1050+
* Returns:
1051+
* Zero on success or a negative error number on failure.
1052+
*
1053+
* Notes:
1054+
* This is a macOS only API.
1055+
*/
1056+
int32_t krun_enable_relaxed_sync_for_disk(uint32_t ctx_id, const char *block_id, bool enable);
1057+
10371058
/**
10381059
* Starts and enters the microVM with the configured parameters. The VMM will attempt to take over
10391060
* stdin/stdout to manage them on behalf of the process running inside the isolated environment,

src/devices/src/virtio/block/device.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -208,6 +208,7 @@ impl Block {
208208
disk_image_path: String,
209209
disk_image_format: ImageType,
210210
is_disk_read_only: bool,
211+
#[cfg(target_os = "macos")] enable_relaxed_sync: bool,
211212
) -> io::Result<Block> {
212213
let disk_image = OpenOptions::new()
213214
.read(true)
@@ -220,7 +221,7 @@ impl Block {
220221
.write(!is_disk_read_only)
221222
.filename(disk_image_path);
222223
#[cfg(target_os = "macos")]
223-
let file_opts = file_opts.relaxed_sync(true);
224+
let file_opts = file_opts.relaxed_sync(enable_relaxed_sync);
224225
let file = ImagoFile::open_sync(file_opts)?;
225226

226227
let disk_image = match disk_image_format {

src/libkrun/src/lib.rs

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -656,6 +656,8 @@ pub unsafe extern "C" fn krun_add_disk(
656656
disk_image_path: disk_path.to_string(),
657657
disk_image_format: ImageType::Raw,
658658
is_disk_read_only: read_only,
659+
#[cfg(target_os = "macos")]
660+
enable_relaxed_sync: false,
659661
};
660662
cfg.add_block_cfg(block_device_config);
661663
}
@@ -703,6 +705,8 @@ pub unsafe extern "C" fn krun_add_disk2(
703705
disk_image_path: disk_path.to_string(),
704706
disk_image_format: format,
705707
is_disk_read_only: read_only,
708+
#[cfg(target_os = "macos")]
709+
enable_relaxed_sync: false,
706710
};
707711
cfg.add_block_cfg(block_device_config);
708712
}
@@ -730,6 +734,8 @@ pub unsafe extern "C" fn krun_set_root_disk(ctx_id: u32, c_disk_path: *const c_c
730734
disk_image_path: disk_path.to_string(),
731735
disk_image_format: ImageType::Raw,
732736
is_disk_read_only: false,
737+
#[cfg(target_os = "macos")]
738+
enable_relaxed_sync: false,
733739
};
734740
cfg.set_root_block_cfg(block_device_config);
735741
}
@@ -757,6 +763,8 @@ pub unsafe extern "C" fn krun_set_data_disk(ctx_id: u32, c_disk_path: *const c_c
757763
disk_image_path: disk_path.to_string(),
758764
disk_image_format: ImageType::Raw,
759765
is_disk_read_only: false,
766+
#[cfg(target_os = "macos")]
767+
enable_relaxed_sync: false,
760768
};
761769
cfg.set_data_block_cfg(block_device_config);
762770
}
@@ -2275,6 +2283,34 @@ pub unsafe extern "C" fn krun_set_kernel_console(ctx_id: u32, console_id: *const
22752283
KRUN_SUCCESS
22762284
}
22772285

2286+
#[allow(clippy::missing_safety_doc)]
2287+
#[no_mangle]
2288+
#[cfg(target_os = "macos")]
2289+
pub unsafe extern "C" fn krun_enable_relaxed_sync(
2290+
ctx_id: u32,
2291+
c_block_id: *const c_char,
2292+
enable: bool,
2293+
) -> i32 {
2294+
let block_id = match CStr::from_ptr(c_block_id).to_str() {
2295+
Ok(block_id) => block_id.to_string(),
2296+
Err(_) => return -libc::EINVAL,
2297+
};
2298+
match CTX_MAP.lock().unwrap().entry(ctx_id) {
2299+
Entry::Occupied(mut ctx_cfg) => {
2300+
let cfg = ctx_cfg.get_mut();
2301+
for blk in cfg.block_cfgs.iter_mut() {
2302+
if blk.block_id == block_id {
2303+
blk.enable_relaxed_sync = enable;
2304+
return KRUN_SUCCESS;
2305+
}
2306+
}
2307+
error!("no block device configured matching the provided block ID");
2308+
-libc::EINVAL
2309+
}
2310+
Entry::Vacant(_) => -libc::ENOENT,
2311+
}
2312+
}
2313+
22782314
#[no_mangle]
22792315
#[allow(unreachable_code)]
22802316
pub extern "C" fn krun_start_enter(ctx_id: u32) -> i32 {

src/vmm/src/vmm_config/block.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,8 @@ pub struct BlockDeviceConfig {
2828
pub disk_image_path: String,
2929
pub disk_image_format: ImageType,
3030
pub is_disk_read_only: bool,
31+
#[cfg(target_os = "macos")]
32+
pub enable_relaxed_sync: bool,
3133
}
3234

3335
#[derive(Clone, Debug, Eq, PartialEq)]
@@ -63,6 +65,8 @@ impl BlockBuilder {
6365
config.disk_image_path,
6466
config.disk_image_format,
6567
config.is_disk_read_only,
68+
#[cfg(target_os = "macos")]
69+
config.enable_relaxed_sync,
6670
)
6771
.map_err(BlockConfigError::CreateBlockDevice)
6872
}

0 commit comments

Comments
 (0)