disk_backend_resources/
lib.rs

1// Copyright (c) Microsoft Corporation.
2// Licensed under the MIT License.
3
4//! Disk resources, for use with [`vm_resource`].
5
6#![forbid(unsafe_code)]
7
8pub mod layer;
9
10use mesh::MeshPayload;
11use vm_resource::IntoResource;
12use vm_resource::Resource;
13use vm_resource::ResourceId;
14use vm_resource::kind::DiskHandleKind;
15use vm_resource::kind::DiskLayerHandleKind;
16
17// Define config types here so that you don't have to pull in the individual
18// crates just to describe the configuration.
19
20/// File-backed disk handle.
21#[derive(MeshPayload)]
22pub struct FileDiskHandle(pub std::fs::File);
23
24impl ResourceId<DiskHandleKind> for FileDiskHandle {
25    const ID: &'static str = "file";
26}
27
28/// Disk handle for a disk that emulates persistent reservation support.
29#[derive(MeshPayload)]
30pub struct DiskWithReservationsHandle(pub Resource<DiskHandleKind>);
31
32impl ResourceId<DiskHandleKind> for DiskWithReservationsHandle {
33    const ID: &'static str = "prwrap";
34}
35
36/// Disk handle for a fixed VHD1 disk.
37#[derive(MeshPayload)]
38pub struct FixedVhd1DiskHandle(pub std::fs::File);
39
40impl ResourceId<DiskHandleKind> for FixedVhd1DiskHandle {
41    const ID: &'static str = "fixed_vhd1";
42}
43
44/// Disk configuration for a striped disk.
45#[derive(MeshPayload)]
46pub struct StripedDiskHandle {
47    /// The underlying disks for the stripes.
48    pub devices: Vec<Resource<DiskHandleKind>>,
49    /// The size of each stripe.
50    pub chunk_size_in_bytes: Option<u32>,
51    /// The number of sectors to show for the disk.
52    pub logic_sector_count: Option<u64>,
53}
54
55impl ResourceId<DiskHandleKind> for StripedDiskHandle {
56    const ID: &'static str = "striped";
57}
58
59/// Configuration for a disk that is automatically formatted (if it is not
60/// already formatted) while being resolved.
61// DEVNOTE: this disk type supports a Azure-specific feature in Microsoft's
62// closed-source OpenHCL. Due to the NTFS formatting library being used, the
63// backing disk type and resolver are currently not able to be open-sourced.
64//
65// Unfortunately, this feature needs to "leak" into the open-source OpenVMM
66// codebase, due to tight coupling in the code of Vtl2Settings.
67#[derive(MeshPayload)]
68pub struct AutoFormattedDiskHandle {
69    /// The disk resource.
70    pub disk: Resource<DiskHandleKind>,
71    /// The GUID to check for.
72    pub guid: [u8; 16],
73}
74
75impl ResourceId<DiskHandleKind> for AutoFormattedDiskHandle {
76    const ID: &'static str = "ntfsfmt";
77}
78
79// blob
80
81/// Handle for a read-only disk backed by a blob served over HTTP.
82#[derive(MeshPayload)]
83pub struct BlobDiskHandle {
84    /// The URL to the disk.
85    pub url: String,
86    /// The format of the blob.
87    pub format: BlobDiskFormat,
88}
89
90impl ResourceId<DiskHandleKind> for BlobDiskHandle {
91    const ID: &'static str = "blob";
92}
93
94/// The format of a disk blob.
95#[derive(MeshPayload)]
96pub enum BlobDiskFormat {
97    /// A flat blob, with no additional metadata.
98    Flat,
99    /// A fixed VHD1, with a VHD footer specifying disk metadata.
100    FixedVhd1,
101}
102
103/// Handle for a disk that is backed by one or more layers.
104#[derive(MeshPayload)]
105pub struct LayeredDiskHandle {
106    /// The layers that make up the disk. The first layer is the top-most layer.
107    pub layers: Vec<DiskLayerDescription>,
108}
109
110impl LayeredDiskHandle {
111    /// Create a new layered disk handle with a single layer.
112    pub fn single_layer(layer: impl IntoResource<DiskLayerHandleKind>) -> Self {
113        Self {
114            layers: vec![layer.into_resource().into()],
115        }
116    }
117}
118
119impl ResourceId<DiskHandleKind> for LayeredDiskHandle {
120    const ID: &'static str = "layered";
121}
122
123/// Description of a disk layer.
124#[derive(MeshPayload)]
125pub struct DiskLayerDescription {
126    /// The layer resource.
127    pub layer: Resource<DiskLayerHandleKind>,
128    /// If true, reads that miss this layer are written back to this layer.
129    pub read_cache: bool,
130    /// If true, writes are written both to this layer and the next one.
131    pub write_through: bool,
132}
133
134impl From<Resource<DiskLayerHandleKind>> for DiskLayerDescription {
135    fn from(layer: Resource<DiskLayerHandleKind>) -> Self {
136        Self {
137            layer,
138            read_cache: false,
139            write_through: false,
140        }
141    }
142}