1 use log::{error, warn}; 2 3 use crate::mm::PhysAddr; 4 5 use super::{ 6 pci::{PciCam, SegmentGroupNumber}, 7 root::{pci_root_manager, PciRoot}, 8 }; 9 10 #[inline(always)] 11 pub fn pci_ecam_root_info_manager() -> &'static EcamRootInfoManager { 12 &EcamRootInfoManager 13 } 14 15 /// Ecam pci root info 16 #[derive(Clone, Debug, Copy)] 17 pub struct EcamRootInfo { 18 /// 段组号 19 pub segment_group_number: SegmentGroupNumber, 20 /// 该分组中的最小bus 21 pub bus_begin: u8, 22 /// 该分组中的最大bus 23 pub bus_end: u8, 24 /// 物理基地址 25 pub physical_address_base: PhysAddr, 26 } 27 28 impl EcamRootInfo { 29 pub fn new( 30 segment_group_number: SegmentGroupNumber, 31 bus_begin: u8, 32 bus_end: u8, 33 physical_address_base: PhysAddr, 34 ) -> Self { 35 let ecam_root_info = Self { 36 segment_group_number, 37 bus_begin, 38 bus_end, 39 physical_address_base, 40 }; 41 return ecam_root_info; 42 } 43 } 44 45 pub struct EcamRootInfoManager; 46 47 impl EcamRootInfoManager { 48 /// # add_ecam_root_info - 向EcamRootInfoManager添加EcamRootInfo 49 /// 50 /// 将一个新的EcamRootInfo添加到EcamRootInfoManager中。 51 /// 52 /// ## 参数 53 /// 54 /// - `ecam_root_info`: EcamRootInfo - 要添加的EcamRootInfo实例 55 pub fn add_ecam_root_info(&self, ecam_root_info: EcamRootInfo) { 56 if !pci_root_manager().has_root(ecam_root_info.segment_group_number) { 57 let root = PciRoot::new( 58 Some(ecam_root_info), 59 PciCam::Ecam, 60 ecam_root_info.bus_begin, 61 ecam_root_info.bus_end, 62 ); 63 64 if let Err(err) = root { 65 error!("add_ecam_root_info(): failed to create PciRoot: {:?}", err); 66 return; 67 } 68 69 pci_root_manager().add_pci_root(root.unwrap()); 70 } else { 71 warn!( 72 "add_ecam_root_info(): root {} already exists", 73 ecam_root_info.segment_group_number 74 ); 75 } 76 } 77 } 78