nvme/ds/controller/properties/
capabilities.rs1use modular_bitfield::prelude::*;
2
3use crate::ds::HalfSeconds;
4
5#[derive(Clone, Copy)]
6#[bitfield(bits = 64)]
7#[repr(u64)]
8pub struct ControllerCap {
9 #[skip(setters)]
10 pub max_queue_entries: u16,
11 #[skip(setters)]
12 pub contiguous_queues_required: bool,
13 #[skip(setters)]
14 arbitration_mechanism: B2,
15 #[skip]
16 res: B5,
17 #[skip(setters)]
18 pub timeout: HalfSeconds,
19 #[skip(setters)]
20 pub doorbell_stride: B4,
21 #[skip(setters)]
22 pub nvm_subsystem_reset_supported: bool,
23 #[skip(setters)]
24 command_sets_supported: B8,
25 #[skip(setters)]
26 pub boot_partition_supported: bool,
27 #[skip(setters)]
28 pub controller_power_scope: ControllerPowerScope,
29 #[skip(setters)]
30 pub memory_page_sz_min: B4,
31 #[skip(setters)]
32 pub memory_page_sz_max: B4,
33 #[skip(setters)]
34 pub persistent_mem_region_supported: bool,
35 #[skip(setters)]
36 pub controller_mem_buffer_supported: bool,
37 #[skip(setters)]
38 pub nvm_subsystem_shutdown_supported: bool,
39 #[skip(setters)]
40 pub controller_ready_modes_supported: B2,
41 #[skip]
42 res2: B3,
43}
44
45#[derive(Clone, Copy, BitfieldSpecifier, Debug)]
46#[bits = 2]
47pub enum ControllerPowerScope {
48 NotReported,
49 Controller,
50 Domain,
51 NVMSubSystem,
52}
53
54impl ControllerCap {
55 pub fn controller_ready_with_media_support(&self) -> bool {
56 self.controller_ready_modes_supported() & 1 != 0
57 }
58
59 pub fn controller_ready_independent_of_media_support(&self) -> bool {
60 self.controller_ready_modes_supported() & 2 != 0
61 }
62
63 pub fn arbitration_urgent_with_wrr(&self) -> bool {
64 self.arbitration_mechanism() & 1 != 0
65 }
66
67 pub fn arbitration_vendor_specific(&self) -> bool {
68 self.arbitration_mechanism() & 2 != 0
69 }
70
71 pub fn supports_nvm_command_set(&self) -> bool {
72 self.command_sets_supported() & 1 != 0
73 }
74
75 pub fn supports_more_io_command_sets(&self) -> bool {
76 self.command_sets_supported() & (1 << 6) != 0
77 }
78
79 pub fn doorbell_stride_bytes(&self) -> usize {
80 1 << (self.doorbell_stride() as usize + 2)
81 }
82
83 pub fn memory_page_sz_min_bytes(&self) -> usize {
84 1 << (self.memory_page_sz_min() + 12)
85 }
86
87 pub fn memory_page_sz_max_bytes(&self) -> usize {
88 1 << (self.memory_page_sz_max() + 12)
89 }
90}