Skip to content

Commit b42062a

Browse files
committed
wip: add krun_add_disk3 API
Signed-off-by: Jake Correnti <[email protected]>
1 parent 1abe621 commit b42062a

File tree

5 files changed

+134
-5
lines changed

5 files changed

+134
-5
lines changed

include/libkrun.h

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -217,6 +217,22 @@ int32_t krun_add_disk2(uint32_t ctx_id,
217217
uint32_t disk_format,
218218
bool read_only);
219219

220+
221+
#define KRUN_SYNC_NONE 0;
222+
#define KRUN_SYNC_RELAXED 1;
223+
#define KRUN_SYNC_FULL 2;
224+
225+
#define KRUN_UNCACHED 0;
226+
#define KRUN_CACHED 1;
227+
228+
int32_t krun_add_disk3(uint32_t ctx_id,
229+
const char *block_id,
230+
const char *disk_path,
231+
uint32_t disk_format,
232+
bool read_only,
233+
uint32_t cache_mode,
234+
uint32_t sync_mode);
235+
220236
/**
221237
* NO LONGER SUPPORTED. DO NOT USE.
222238
*

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

Lines changed: 16 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,10 @@ use super::{
3535
Error, QUEUE_SIZES, SECTOR_SHIFT, SECTOR_SIZE,
3636
};
3737

38-
use crate::virtio::{block::ImageType, ActivateError, InterruptTransport};
38+
use crate::virtio::{
39+
block::{CacheMode, ImageType, SyncMode},
40+
ActivateError, InterruptTransport,
41+
};
3942

4043
/// Configuration options for disk caching.
4144
#[derive(Clone, Copy, Debug, Default, Eq, PartialEq)]
@@ -208,6 +211,9 @@ impl Block {
208211
disk_image_path: String,
209212
disk_image_format: ImageType,
210213
is_disk_read_only: bool,
214+
// TODO(jakecorrenti): should this even be here? Am i just re-writing essentially what's represented by `CacheType`?
215+
cache_mode: CacheMode,
216+
sync_mode: SyncMode,
211217
) -> io::Result<Block> {
212218
let disk_image = OpenOptions::new()
213219
.read(true)
@@ -218,7 +224,10 @@ impl Block {
218224

219225
let file_opts = StorageOpenOptions::new()
220226
.write(!is_disk_read_only)
221-
.filename(disk_image_path);
227+
.filename(disk_image_path)
228+
.direct(cache_mode == CacheMode::Uncached);
229+
230+
// TODO(jakecorrenti): how do I do a partial fsync on linux to handle that OS?
222231
#[cfg(target_os = "macos")]
223232
let file_opts = file_opts.relaxed_sync(true);
224233
let file = ImagoFile::open_sync(file_opts)?;
@@ -248,10 +257,14 @@ impl Block {
248257
DiskProperties::new(Arc::clone(&disk_image), disk_image_id.clone(), cache_type)?;
249258

250259
let mut avail_features = (1u64 << VIRTIO_F_VERSION_1)
251-
| (1u64 << VIRTIO_BLK_F_FLUSH)
260+
// | (1u64 << VIRTIO_BLK_F_FLUSH)
252261
| (1u64 << VIRTIO_BLK_F_SEG_MAX)
253262
| (1u64 << VIRTIO_RING_F_EVENT_IDX);
254263

264+
if sync_mode != SyncMode::None {
265+
avail_features |= 1u64 << VIRTIO_BLK_F_FLUSH;
266+
}
267+
255268
if is_disk_read_only {
256269
avail_features |= 1u64 << VIRTIO_BLK_F_RO;
257270
};

src/devices/src/virtio/block/mod.rs

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,3 +39,18 @@ pub enum ImageType {
3939
Raw,
4040
Qcow2,
4141
}
42+
43+
#[derive(Clone, Debug, Default, PartialEq, Eq)]
44+
pub enum CacheMode {
45+
Uncached,
46+
#[default]
47+
Cached,
48+
}
49+
50+
#[derive(Clone, Debug, Default, PartialEq, Eq)]
51+
pub enum SyncMode {
52+
None,
53+
Relaxed,
54+
#[default]
55+
Full,
56+
}

src/libkrun/src/lib.rs

Lines changed: 79 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ extern crate log;
33

44
use crossbeam_channel::unbounded;
55
#[cfg(feature = "blk")]
6-
use devices::virtio::block::ImageType;
6+
use devices::virtio::block::{CacheMode, ImageType, SyncMode};
77
#[cfg(feature = "gpu")]
88
use devices::virtio::gpu::display::DisplayInfo;
99
#[cfg(feature = "net")]
@@ -671,6 +671,8 @@ pub unsafe extern "C" fn krun_add_disk(
671671
disk_image_path: disk_path.to_string(),
672672
disk_image_format: ImageType::Raw,
673673
is_disk_read_only: read_only,
674+
cache_mode: CacheMode::Cached,
675+
sync_mode: SyncMode::Full,
674676
};
675677
cfg.add_block_cfg(block_device_config);
676678
}
@@ -718,6 +720,78 @@ pub unsafe extern "C" fn krun_add_disk2(
718720
disk_image_path: disk_path.to_string(),
719721
disk_image_format: format,
720722
is_disk_read_only: read_only,
723+
cache_mode: CacheMode::Cached,
724+
sync_mode: SyncMode::Full,
725+
};
726+
cfg.add_block_cfg(block_device_config);
727+
}
728+
Entry::Vacant(_) => return -libc::ENOENT,
729+
}
730+
731+
KRUN_SUCCESS
732+
}
733+
734+
#[allow(clippy::missing_safety_doc)]
735+
#[no_mangle]
736+
#[cfg(feature = "blk")]
737+
pub unsafe extern "C" fn krun_add_disk3(
738+
ctx_id: u32,
739+
c_block_id: *const c_char,
740+
c_disk_path: *const c_char,
741+
disk_format: u32,
742+
read_only: bool,
743+
cache_mode: u32,
744+
sync_mode: u32,
745+
) -> i32 {
746+
let disk_path = match CStr::from_ptr(c_disk_path).to_str() {
747+
Ok(disk) => disk,
748+
Err(_) => return -libc::EINVAL,
749+
};
750+
751+
let block_id = match CStr::from_ptr(c_block_id).to_str() {
752+
Ok(block_id) => block_id,
753+
Err(_) => return -libc::EINVAL,
754+
};
755+
756+
let format = match disk_format {
757+
0 => ImageType::Raw,
758+
1 => ImageType::Qcow2,
759+
_ => {
760+
// Do not continue if the user cannot specify a valid disk format
761+
return -libc::EINVAL;
762+
}
763+
};
764+
765+
let cache_mode = match cache_mode {
766+
0 => CacheMode::Uncached,
767+
1 => CacheMode::Cached,
768+
_ => {
769+
// Do not continue if the user cannot specify a valid cache mode
770+
return -libc::EINVAL;
771+
}
772+
};
773+
774+
let sync_mode = match sync_mode {
775+
0 => SyncMode::None,
776+
1 => SyncMode::Relaxed,
777+
2 => SyncMode::Full,
778+
_ => {
779+
// Do not continue if the user cannot specify a valid sync mode
780+
return -libc::EINVAL;
781+
}
782+
};
783+
784+
match CTX_MAP.lock().unwrap().entry(ctx_id) {
785+
Entry::Occupied(mut ctx_cfg) => {
786+
let cfg = ctx_cfg.get_mut();
787+
let block_device_config = BlockDeviceConfig {
788+
block_id: block_id.to_string(),
789+
cache_type: CacheType::auto(disk_path),
790+
disk_image_path: disk_path.to_string(),
791+
disk_image_format: format,
792+
is_disk_read_only: read_only,
793+
cache_mode,
794+
sync_mode,
721795
};
722796
cfg.add_block_cfg(block_device_config);
723797
}
@@ -745,6 +819,8 @@ pub unsafe extern "C" fn krun_set_root_disk(ctx_id: u32, c_disk_path: *const c_c
745819
disk_image_path: disk_path.to_string(),
746820
disk_image_format: ImageType::Raw,
747821
is_disk_read_only: false,
822+
cache_mode: CacheMode::Cached,
823+
sync_mode: SyncMode::Full,
748824
};
749825
cfg.set_root_block_cfg(block_device_config);
750826
}
@@ -772,6 +848,8 @@ pub unsafe extern "C" fn krun_set_data_disk(ctx_id: u32, c_disk_path: *const c_c
772848
disk_image_path: disk_path.to_string(),
773849
disk_image_format: ImageType::Raw,
774850
is_disk_read_only: false,
851+
cache_mode: CacheMode::Cached,
852+
sync_mode: SyncMode::Full,
775853
};
776854
cfg.set_data_block_cfg(block_device_config);
777855
}

src/vmm/src/vmm_config/block.rs

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,10 @@ use std::collections::VecDeque;
22
use std::fmt;
33
use std::sync::{Arc, Mutex};
44

5-
use devices::virtio::{block::ImageType, Block, CacheType};
5+
use devices::virtio::{
6+
block::{CacheMode, ImageType, SyncMode},
7+
Block, CacheType,
8+
};
69

710
#[derive(Debug)]
811
pub enum BlockConfigError {
@@ -28,6 +31,8 @@ pub struct BlockDeviceConfig {
2831
pub disk_image_path: String,
2932
pub disk_image_format: ImageType,
3033
pub is_disk_read_only: bool,
34+
pub cache_mode: CacheMode,
35+
pub sync_mode: SyncMode,
3136
}
3237

3338
#[derive(Clone, Debug, Eq, PartialEq)]
@@ -63,6 +68,8 @@ impl BlockBuilder {
6368
config.disk_image_path,
6469
config.disk_image_format,
6570
config.is_disk_read_only,
71+
config.cache_mode,
72+
config.sync_mode,
6673
)
6774
.map_err(BlockConfigError::CreateBlockDevice)
6875
}

0 commit comments

Comments
 (0)