xref: /DragonOS/kernel/src/driver/virtio/sysfs.rs (revision 0102d69fdd231e472d7bb3d609a41ae56a3799ee)
1e32effb1SLoGin use alloc::{
2e32effb1SLoGin     string::{String, ToString},
3e32effb1SLoGin     sync::{Arc, Weak},
4e32effb1SLoGin };
5e32effb1SLoGin use ida::IdAllocator;
6e32effb1SLoGin use intertrait::cast::CastArc;
7e32effb1SLoGin use system_error::SystemError;
8e32effb1SLoGin use unified_init::macros::unified_init;
9e32effb1SLoGin 
10e32effb1SLoGin use crate::{
11*0102d69fSLoGin     driver::{
12*0102d69fSLoGin         base::{
13e32effb1SLoGin             device::{
14e32effb1SLoGin                 bus::{bus_manager, Bus},
15e32effb1SLoGin                 device_manager,
16e32effb1SLoGin                 driver::{driver_manager, Driver},
17e32effb1SLoGin                 Device,
18e32effb1SLoGin             },
19e32effb1SLoGin             kobject::KObject,
20e32effb1SLoGin             subsys::SubSysPrivate,
21e32effb1SLoGin         },
22*0102d69fSLoGin         virtio::irq::{virtio_irq_manager, DefaultVirtioIrqHandler},
23*0102d69fSLoGin     },
24*0102d69fSLoGin     exception::{irqdesc::IrqHandleFlags, manage::irq_manager},
25e32effb1SLoGin     filesystem::{
26e32effb1SLoGin         sysfs::{
27e32effb1SLoGin             file::sysfs_emit_str, Attribute, AttributeGroup, SysFSOpsSupport, SYSFS_ATTR_MODE_RO,
28e32effb1SLoGin         },
29e32effb1SLoGin         vfs::syscall::ModeType,
30e32effb1SLoGin     },
31e32effb1SLoGin     init::initcall::INITCALL_CORE,
32e32effb1SLoGin };
33e32effb1SLoGin 
34e32effb1SLoGin use super::{VirtIODevice, VirtIODeviceIndex, VirtIODriver};
35e32effb1SLoGin 
36e32effb1SLoGin static mut VIRTIO_BUS: Option<Arc<VirtIOBus>> = None;
37e32effb1SLoGin 
38e32effb1SLoGin #[inline(always)]
39e32effb1SLoGin pub fn virtio_bus() -> Arc<VirtIOBus> {
40e32effb1SLoGin     unsafe { VIRTIO_BUS.as_ref().unwrap().clone() }
41e32effb1SLoGin }
42e32effb1SLoGin 
43e32effb1SLoGin #[derive(Debug)]
44e32effb1SLoGin pub struct VirtIOBus {
45e32effb1SLoGin     private: SubSysPrivate,
46e32effb1SLoGin }
47e32effb1SLoGin 
48e32effb1SLoGin impl VirtIOBus {
49e32effb1SLoGin     pub fn new() -> Arc<Self> {
50e32effb1SLoGin         let w: Weak<Self> = Weak::new();
51e32effb1SLoGin         let private = SubSysPrivate::new("virtio".to_string(), Some(w), None, &[]);
52e32effb1SLoGin         let bus = Arc::new(Self { private });
53e32effb1SLoGin         bus.subsystem()
54e32effb1SLoGin             .set_bus(Some(Arc::downgrade(&(bus.clone() as Arc<dyn Bus>))));
55e32effb1SLoGin 
56e32effb1SLoGin         return bus;
57e32effb1SLoGin     }
58e32effb1SLoGin }
59e32effb1SLoGin 
60e32effb1SLoGin impl Bus for VirtIOBus {
61e32effb1SLoGin     fn name(&self) -> String {
62e32effb1SLoGin         self.private.name()
63e32effb1SLoGin     }
64e32effb1SLoGin 
65e32effb1SLoGin     fn dev_name(&self) -> String {
66e32effb1SLoGin         return self.name();
67e32effb1SLoGin     }
68e32effb1SLoGin 
69e32effb1SLoGin     fn dev_groups(&self) -> &'static [&'static dyn AttributeGroup] {
70e32effb1SLoGin         // todo: VirtIODeviceAttrGroup
71e32effb1SLoGin         return &[];
72e32effb1SLoGin     }
73e32effb1SLoGin 
74e32effb1SLoGin     fn subsystem(&self) -> &SubSysPrivate {
75e32effb1SLoGin         return &self.private;
76e32effb1SLoGin     }
77e32effb1SLoGin 
78e32effb1SLoGin     fn probe(&self, device: &Arc<dyn Device>) -> Result<(), SystemError> {
79e32effb1SLoGin         let drv = device.driver().ok_or(SystemError::EINVAL)?;
80e32effb1SLoGin         let virtio_drv = drv.cast::<dyn VirtIODriver>().map_err(|_| {
81e32effb1SLoGin             kerror!(
82e32effb1SLoGin                 "VirtIOBus::probe() failed: device.driver() is not a VirtioDriver. Device: '{:?}'",
83e32effb1SLoGin                 device.name()
84e32effb1SLoGin             );
85e32effb1SLoGin             SystemError::EINVAL
86e32effb1SLoGin         })?;
87e32effb1SLoGin 
88e32effb1SLoGin         let virtio_dev = device.clone().cast::<dyn VirtIODevice>().map_err(|_| {
89e32effb1SLoGin             kerror!(
90e32effb1SLoGin                 "VirtIOBus::probe() failed: device is not a VirtIODevice. Device: '{:?}'",
91e32effb1SLoGin                 device.name()
92e32effb1SLoGin             );
93e32effb1SLoGin             SystemError::EINVAL
94e32effb1SLoGin         })?;
95e32effb1SLoGin 
96e32effb1SLoGin         return virtio_drv.probe(&virtio_dev);
97e32effb1SLoGin     }
98e32effb1SLoGin 
99e32effb1SLoGin     fn remove(&self, _device: &Arc<dyn Device>) -> Result<(), SystemError> {
100e32effb1SLoGin         todo!()
101e32effb1SLoGin     }
102e32effb1SLoGin 
103e32effb1SLoGin     fn sync_state(&self, _device: &Arc<dyn Device>) {
104e32effb1SLoGin         todo!()
105e32effb1SLoGin     }
106e32effb1SLoGin 
107e32effb1SLoGin     fn shutdown(&self, _device: &Arc<dyn Device>) {
108e32effb1SLoGin         todo!()
109e32effb1SLoGin     }
110e32effb1SLoGin 
111e32effb1SLoGin     fn resume(&self, _device: &Arc<dyn Device>) -> Result<(), SystemError> {
112e32effb1SLoGin         todo!()
113e32effb1SLoGin     }
114e32effb1SLoGin 
115e32effb1SLoGin     fn match_device(
116e32effb1SLoGin         &self,
117e32effb1SLoGin         _device: &Arc<dyn Device>,
118e32effb1SLoGin         _driver: &Arc<dyn Driver>,
119e32effb1SLoGin     ) -> Result<bool, SystemError> {
120e32effb1SLoGin         // todo: https://code.dragonos.org.cn/xref/linux-6.6.21/drivers/virtio/virtio.c#85
121e32effb1SLoGin         todo!("VirtIOBus::match_device() is not implemented")
122e32effb1SLoGin     }
123e32effb1SLoGin }
124e32effb1SLoGin 
125e32effb1SLoGin #[unified_init(INITCALL_CORE)]
126e32effb1SLoGin fn virtio_init() -> Result<(), SystemError> {
127e32effb1SLoGin     let bus = VirtIOBus::new();
128e32effb1SLoGin     unsafe {
129e32effb1SLoGin         VIRTIO_BUS = Some(bus.clone());
130e32effb1SLoGin     }
131e32effb1SLoGin     bus_manager()
132e32effb1SLoGin         .register(bus)
133e32effb1SLoGin         .expect("Failed to register virtio bus!");
134e32effb1SLoGin     Ok(())
135e32effb1SLoGin }
136e32effb1SLoGin 
137e32effb1SLoGin #[inline(always)]
138e32effb1SLoGin pub fn virtio_driver_manager() -> &'static VirtIODriverManager {
139e32effb1SLoGin     &VirtIODriverManager
140e32effb1SLoGin }
141e32effb1SLoGin 
142e32effb1SLoGin pub struct VirtIODriverManager;
143e32effb1SLoGin 
144e32effb1SLoGin impl VirtIODriverManager {
145e32effb1SLoGin     pub fn register(&self, driver: Arc<dyn VirtIODriver>) -> Result<(), SystemError> {
146e32effb1SLoGin         driver.set_bus(Some(Arc::downgrade(&(virtio_bus() as Arc<dyn Bus>))));
147e32effb1SLoGin         return driver_manager().register(driver as Arc<dyn Driver>);
148e32effb1SLoGin     }
149e32effb1SLoGin 
150e32effb1SLoGin     #[allow(dead_code)]
151e32effb1SLoGin     pub fn unregister(&self, driver: &Arc<dyn VirtIODriver>) {
152e32effb1SLoGin         driver_manager().unregister(&(driver.clone() as Arc<dyn Driver>));
153e32effb1SLoGin     }
154e32effb1SLoGin }
155e32effb1SLoGin 
156e32effb1SLoGin #[inline(always)]
157e32effb1SLoGin pub fn virtio_device_manager() -> &'static VirtIODeviceManager {
158e32effb1SLoGin     &VirtIODeviceManager
159e32effb1SLoGin }
160e32effb1SLoGin 
161e32effb1SLoGin pub struct VirtIODeviceManager;
162e32effb1SLoGin 
163e32effb1SLoGin impl VirtIODeviceManager {
164e32effb1SLoGin     pub fn device_add(&self, dev: Arc<dyn VirtIODevice>) -> Result<(), SystemError> {
165e32effb1SLoGin         dev.set_bus(Some(Arc::downgrade(&(virtio_bus() as Arc<dyn Bus>))));
166e32effb1SLoGin         device_manager().device_default_initialize(&(dev.clone() as Arc<dyn Device>));
167e32effb1SLoGin         let drv = dev.driver().ok_or(SystemError::EINVAL)?;
168e32effb1SLoGin 
169e32effb1SLoGin         let virtio_drv = drv.cast::<dyn VirtIODriver>().map_err(|_| {
170e32effb1SLoGin             kerror!(
171e32effb1SLoGin                 "VirtIODeviceManager::device_add() failed: device.driver() is not a VirtioDriver. Device: '{:?}'",
172e32effb1SLoGin                 dev.name()
173e32effb1SLoGin             );
174e32effb1SLoGin             SystemError::EINVAL
175e32effb1SLoGin         })?;
176e32effb1SLoGin         let virtio_index = VIRTIO_DEVICE_INDEX_MANAGER.alloc();
177e32effb1SLoGin         dev.set_virtio_device_index(virtio_index);
178e32effb1SLoGin         dev.set_device_name(format!("virtio{}", virtio_index.data()));
179e32effb1SLoGin         virtio_drv.probe(&dev)?;
180e32effb1SLoGin 
181e32effb1SLoGin         device_manager().add_device(dev.clone() as Arc<dyn Device>)?;
182*0102d69fSLoGin         let r = device_manager()
183*0102d69fSLoGin             .add_groups(&(dev.clone() as Arc<dyn Device>), &[&VirtIODeviceAttrGroup]);
184*0102d69fSLoGin 
185*0102d69fSLoGin         self.setup_irq(&dev).ok();
186*0102d69fSLoGin 
187*0102d69fSLoGin         return r;
188*0102d69fSLoGin     }
189*0102d69fSLoGin 
190*0102d69fSLoGin     /// # setup_irq - 设置中断
191*0102d69fSLoGin     ///
192*0102d69fSLoGin     /// 为virtio设备设置中断。
193*0102d69fSLoGin     fn setup_irq(&self, dev: &Arc<dyn VirtIODevice>) -> Result<(), SystemError> {
194*0102d69fSLoGin         let irq = dev.irq().ok_or(SystemError::EINVAL)?;
195*0102d69fSLoGin         if let Err(e) = irq_manager().request_irq(
196*0102d69fSLoGin             irq,
197*0102d69fSLoGin             dev.device_name(),
198*0102d69fSLoGin             &DefaultVirtioIrqHandler,
199*0102d69fSLoGin             IrqHandleFlags::IRQF_SHARED,
200*0102d69fSLoGin             Some(dev.dev_id().clone()),
201*0102d69fSLoGin         ) {
202*0102d69fSLoGin             kerror!(
203*0102d69fSLoGin                 "Failed to request irq for virtio device '{}': irq: {:?}, error {:?}",
204*0102d69fSLoGin                 dev.device_name(),
205*0102d69fSLoGin                 irq,
206*0102d69fSLoGin                 e
207*0102d69fSLoGin             );
208*0102d69fSLoGin             return Err(e);
209*0102d69fSLoGin         }
210*0102d69fSLoGin 
211*0102d69fSLoGin         virtio_irq_manager()
212*0102d69fSLoGin             .register_device(dev.clone())
213*0102d69fSLoGin             .map_err(|e| {
214*0102d69fSLoGin                 kerror!(
215*0102d69fSLoGin                     "Failed to register virtio device's irq, dev: '{}', irq: {:?}, error {:?}",
216*0102d69fSLoGin                     dev.device_name(),
217*0102d69fSLoGin                     irq,
218*0102d69fSLoGin                     e
219*0102d69fSLoGin                 );
220*0102d69fSLoGin                 e
221*0102d69fSLoGin             })?;
222*0102d69fSLoGin         return Ok(());
223e32effb1SLoGin     }
224e32effb1SLoGin 
225e32effb1SLoGin     #[allow(dead_code)]
226e32effb1SLoGin     pub fn device_remove(&self, dev: &Arc<dyn VirtIODevice>) -> Result<(), SystemError> {
227e32effb1SLoGin         device_manager().remove(&(dev.clone() as Arc<dyn Device>));
228e32effb1SLoGin         return Ok(());
229e32effb1SLoGin     }
230e32effb1SLoGin }
231e32effb1SLoGin 
232e32effb1SLoGin static VIRTIO_DEVICE_INDEX_MANAGER: VirtIODeviceIndexManager = VirtIODeviceIndexManager::new();
233e32effb1SLoGin 
234e32effb1SLoGin /// VirtIO设备索引管理器
235e32effb1SLoGin ///
236e32effb1SLoGin /// VirtIO设备索引管理器用于分配和管理VirtIO设备的唯一索引。
237e32effb1SLoGin pub struct VirtIODeviceIndexManager {
238e32effb1SLoGin     // ID分配器
239e32effb1SLoGin     ///
240e32effb1SLoGin     /// ID分配器用于分配唯一的索引给VirtIO设备。
241e32effb1SLoGin     ida: IdAllocator,
242e32effb1SLoGin }
243e32effb1SLoGin 
244e32effb1SLoGin // VirtIO设备索引管理器的新建实例
245e32effb1SLoGin impl VirtIODeviceIndexManager {
246e32effb1SLoGin     /// 创建新的VirtIO设备索引管理器实例
247e32effb1SLoGin     ///
248e32effb1SLoGin     /// 创建一个新的VirtIO设备索引管理器实例,初始时分配器从0开始,直到最大usize值。
249e32effb1SLoGin     const fn new() -> Self {
250e32effb1SLoGin         Self {
251e32effb1SLoGin             ida: IdAllocator::new(0, usize::MAX),
252e32effb1SLoGin         }
253e32effb1SLoGin     }
254e32effb1SLoGin 
255e32effb1SLoGin     /// 分配一个新的VirtIO设备索引
256e32effb1SLoGin     ///
257e32effb1SLoGin     /// 分配一个唯一的索引给VirtIO设备。
258e32effb1SLoGin     pub fn alloc(&self) -> VirtIODeviceIndex {
259e32effb1SLoGin         VirtIODeviceIndex(self.ida.alloc().unwrap())
260e32effb1SLoGin     }
261e32effb1SLoGin 
262e32effb1SLoGin     // 释放一个VirtIO设备索引
263e32effb1SLoGin     ///
264e32effb1SLoGin     /// 释放之前分配的VirtIO设备索引,使其可以被重新使用。
265e32effb1SLoGin     #[allow(dead_code)]
266e32effb1SLoGin     pub fn free(&self, index: VirtIODeviceIndex) {
267e32effb1SLoGin         self.ida.free(index.0);
268e32effb1SLoGin     }
269e32effb1SLoGin }
270e32effb1SLoGin 
271e32effb1SLoGin /// VirtIO设备属性组
272e32effb1SLoGin ///
273e32effb1SLoGin /// 参考 https://code.dragonos.org.cn/xref/linux-6.6.21/drivers/virtio/virtio.c#64
274e32effb1SLoGin #[derive(Debug)]
275e32effb1SLoGin pub struct VirtIODeviceAttrGroup;
276e32effb1SLoGin 
277e32effb1SLoGin impl AttributeGroup for VirtIODeviceAttrGroup {
278e32effb1SLoGin     fn name(&self) -> Option<&str> {
279e32effb1SLoGin         None
280e32effb1SLoGin     }
281e32effb1SLoGin 
282e32effb1SLoGin     fn attrs(&self) -> &[&'static dyn Attribute] {
283e32effb1SLoGin         &[&AttrDevice, &AttrVendor]
284e32effb1SLoGin     }
285e32effb1SLoGin }
286e32effb1SLoGin 
287e32effb1SLoGin #[derive(Debug)]
288e32effb1SLoGin struct AttrDevice;
289e32effb1SLoGin 
290e32effb1SLoGin impl Attribute for AttrDevice {
291e32effb1SLoGin     fn name(&self) -> &str {
292e32effb1SLoGin         "device"
293e32effb1SLoGin     }
294e32effb1SLoGin 
295e32effb1SLoGin     fn mode(&self) -> ModeType {
296e32effb1SLoGin         SYSFS_ATTR_MODE_RO
297e32effb1SLoGin     }
298e32effb1SLoGin 
299e32effb1SLoGin     fn support(&self) -> SysFSOpsSupport {
300e32effb1SLoGin         SysFSOpsSupport::ATTR_SHOW
301e32effb1SLoGin     }
302e32effb1SLoGin 
303e32effb1SLoGin     fn show(&self, kobj: Arc<dyn KObject>, buf: &mut [u8]) -> Result<usize, SystemError> {
304e32effb1SLoGin         let dev = kobj.cast::<dyn VirtIODevice>().map_err(|_| {
305e32effb1SLoGin             kerror!("AttrDevice::show() failed: kobj is not a VirtIODevice");
306e32effb1SLoGin             SystemError::EINVAL
307e32effb1SLoGin         })?;
308e32effb1SLoGin         let device_type_id = dev.device_type_id();
309e32effb1SLoGin 
310e32effb1SLoGin         return sysfs_emit_str(buf, &format!("0x{:04x}\n", device_type_id));
311e32effb1SLoGin     }
312e32effb1SLoGin }
313e32effb1SLoGin 
314e32effb1SLoGin #[derive(Debug)]
315e32effb1SLoGin struct AttrVendor;
316e32effb1SLoGin 
317e32effb1SLoGin impl Attribute for AttrVendor {
318e32effb1SLoGin     fn name(&self) -> &str {
319e32effb1SLoGin         "vendor"
320e32effb1SLoGin     }
321e32effb1SLoGin 
322e32effb1SLoGin     fn mode(&self) -> ModeType {
323e32effb1SLoGin         SYSFS_ATTR_MODE_RO
324e32effb1SLoGin     }
325e32effb1SLoGin 
326e32effb1SLoGin     fn support(&self) -> SysFSOpsSupport {
327e32effb1SLoGin         SysFSOpsSupport::ATTR_SHOW
328e32effb1SLoGin     }
329e32effb1SLoGin 
330e32effb1SLoGin     fn show(&self, kobj: Arc<dyn KObject>, buf: &mut [u8]) -> Result<usize, SystemError> {
331e32effb1SLoGin         let dev = kobj.cast::<dyn VirtIODevice>().map_err(|_| {
332e32effb1SLoGin             kerror!("AttrVendor::show() failed: kobj is not a VirtIODevice");
333e32effb1SLoGin             SystemError::EINVAL
334e32effb1SLoGin         })?;
335e32effb1SLoGin         let vendor = dev.vendor();
336e32effb1SLoGin 
337e32effb1SLoGin         return sysfs_emit_str(buf, &format!("0x{:04x}\n", vendor));
338e32effb1SLoGin     }
339e32effb1SLoGin }
340