From 1bcd8530d254dbb5c2f76bcb376241424c01ee51 Mon Sep 17 00:00:00 2001
From: Connor Wood <connorwood71@gmail.com>
Date: Thu, 31 Aug 2017 10:52:59 +0100
Subject: [PATCH] Stored signature to include OEM signature and OEM table ID

---
 src/acpi/aml/type2opcode.rs |  13 +--
 src/acpi/dmar/mod.rs        |  54 +++++-----
 src/acpi/fadt.rs            |  35 ++++---
 src/acpi/hpet.rs            |  28 ++---
 src/acpi/madt.rs            | 204 ++++++++++++++++++------------------
 src/acpi/mod.rs             |  82 +++++++++------
 6 files changed, 220 insertions(+), 196 deletions(-)

diff --git a/src/acpi/aml/type2opcode.rs b/src/acpi/aml/type2opcode.rs
index f193575f..cd94e708 100644
--- a/src/acpi/aml/type2opcode.rs
+++ b/src/acpi/aml/type2opcode.rs
@@ -11,7 +11,7 @@ use super::namestring::{parse_super_name, parse_target, parse_name_string, parse
 use super::dataobj::parse_data_ref_obj;
 
 use time::monotonic;
-use acpi::ACPI_TABLE;
+use acpi::{ACPI_TABLE, SDT_POINTERS};
 
 #[derive(Debug, Clone)]
 pub enum MatchOpcode {
@@ -1346,11 +1346,10 @@ fn parse_def_load_table(data: &[u8],
     let parameter_path = parse_term_arg(&data[2 + signature.len + oem_id.len + oem_table_id.len + root_path.len..], ctx)?;
     let parameter_data = parse_term_arg(&data[2 + signature.len + oem_id.len + oem_table_id.len + root_path.len + parameter_path.len..], ctx)?;
 
-    let rxsdt_ptr = ACPI_TABLE.rxsdt.read();
-    
-    if let Some(ref rxsdt) = *rxsdt_ptr {
+    if let Some(ref ptrs) = *(SDT_POINTERS.read()) {
         let sig_str = unsafe {
-            *(signature.val.get_as_string()?.as_bytes().as_ptr() as *const [u8; 4])
+            let sig = *(signature.val.get_as_string()?.as_bytes().as_ptr() as *const [u8; 4]);
+            String::from_utf8(sig.to_vec()).expect("Error converting signature to string")
         };
         let oem_str = unsafe {
             *(oem_id.val.get_as_string()?.as_bytes().as_ptr() as *const [u8; 6])
@@ -1358,8 +1357,10 @@ fn parse_def_load_table(data: &[u8],
         let oem_table_str = unsafe {
             *(oem_table_id.val.get_as_string()?.as_bytes().as_ptr() as *const [u8; 8])
         };
+
+        let sdt_signature = (sig_str, oem_str, oem_table_str);
         
-        let sdt = rxsdt.find(sig_str, oem_str, oem_table_str);
+        let sdt = ptrs.get(&sdt_signature);
         
         if let Some(sdt) = sdt {
             let hdl = parse_aml_with_scope(sdt, root_path.val.get_as_string()?)?;
diff --git a/src/acpi/dmar/mod.rs b/src/acpi/dmar/mod.rs
index e2cf1848..549f6869 100644
--- a/src/acpi/dmar/mod.rs
+++ b/src/acpi/dmar/mod.rs
@@ -5,7 +5,7 @@ use self::drhd::Drhd;
 use memory::Frame;
 use paging::{entry, ActivePageTable, PhysicalAddress};
 
-use super::{ACPI_TABLE, SDT_POINTERS, get_sdt};
+use super::{ACPI_TABLE, SDT_POINTERS, get_sdt, find_sdt, load_table, get_sdt_signature};
 
 pub mod drhd;
 
@@ -20,32 +20,32 @@ pub struct Dmar {
 
 impl Dmar {
     pub fn init(active_table: &mut ActivePageTable) {
-        if let Some(ref ptrs) = *(SDT_POINTERS.read()) {
-            let dmar = if let Some(dmar_sdt) = ptrs.get("DMAR") {
-                Dmar::new(dmar_sdt)
-            } else {
-                println!("Unable to find DMAR");
-                return;
-            };
-            
-            if let Some(dmar) = dmar {
-                println!("  DMAR: {}: {}", dmar.addr_width, dmar.flags);
-
-                for dmar_entry in dmar.iter() {
-                    println!("      {:?}", dmar_entry);
-                    match dmar_entry {
-                        DmarEntry::Drhd(dmar_drhd) => {
-                            let drhd = dmar_drhd.get(active_table);
-
-                            println!("VER: {:X}", drhd.version);
-                            println!("CAP: {:X}", drhd.cap);
-                            println!("EXT_CAP: {:X}", drhd.ext_cap);
-                            println!("GCMD: {:X}", drhd.gl_cmd);
-                            println!("GSTS: {:X}", drhd.gl_sts);
-                            println!("RT: {:X}", drhd.root_table);
-                        },
-                        _ => ()
-                    }
+        let dmar_sdt = find_sdt("DMAR");
+        let dmar = if dmar_sdt.len() == 1 {
+            load_table(get_sdt_signature(dmar_sdt[0]));
+            Dmar::new(dmar_sdt[0])
+        } else {
+            println!("Unable to find DMAR");
+            return;
+        };
+        
+        if let Some(dmar) = dmar {
+            println!("  DMAR: {}: {}", dmar.addr_width, dmar.flags);
+
+            for dmar_entry in dmar.iter() {
+                println!("      {:?}", dmar_entry);
+                match dmar_entry {
+                    DmarEntry::Drhd(dmar_drhd) => {
+                        let drhd = dmar_drhd.get(active_table);
+
+                        println!("VER: {:X}", drhd.version);
+                        println!("CAP: {:X}", drhd.cap);
+                        println!("EXT_CAP: {:X}", drhd.ext_cap);
+                        println!("GCMD: {:X}", drhd.gl_cmd);
+                        println!("GSTS: {:X}", drhd.gl_sts);
+                        println!("RT: {:X}", drhd.root_table);
+                    },
+                    _ => ()
                 }
             }
         }
diff --git a/src/acpi/fadt.rs b/src/acpi/fadt.rs
index c6ff36c3..6dd82d86 100644
--- a/src/acpi/fadt.rs
+++ b/src/acpi/fadt.rs
@@ -2,7 +2,7 @@ use core::{mem, ptr};
 use collections::string::String;
 
 use super::sdt::Sdt;
-use super::{ACPI_TABLE, SDT_POINTERS, get_sdt};
+use super::{ACPI_TABLE, SDT_POINTERS, get_sdt, find_sdt, get_sdt_signature, load_table};
 
 use paging::ActivePageTable;
 
@@ -99,24 +99,27 @@ impl Fadt {
     }
     
     pub fn init(active_table: &mut ActivePageTable) {
-        if let Some(ref mut ptrs) = *(SDT_POINTERS.write()) {
-            let fadt = if let Some(fadt_sdt) = ptrs.get("FACP") {
-                Fadt::new(fadt_sdt)
-            } else {
-                println!("Unable to find FADT");
-                return;
-            };
+        let fadt_sdt = find_sdt("FACP");
+        let fadt = if fadt_sdt.len() == 1 {
+            load_table(get_sdt_signature(fadt_sdt[0]));
+            Fadt::new(fadt_sdt[0])
+        } else {
+            println!("Unable to find FADT");
+            return;
+        };
+
+        if let Some(fadt) = fadt {
+            println!("  FACP: {:X}", fadt.dsdt);
             
-            if let Some(fadt) = fadt {
-                println!("  FACP: {:X}", fadt.dsdt);
-                    
-                let dsdt_sdt = get_sdt(fadt.dsdt as usize, active_table);
-                let signature = String::from_utf8(dsdt_sdt.signature.to_vec()).expect("Error converting signature to string");
-                ptrs.insert(signature, dsdt_sdt);
+            let dsdt_sdt = get_sdt(fadt.dsdt as usize, active_table);
 
-                let mut fadt_t = ACPI_TABLE.fadt.write();
-                *fadt_t = Some(fadt);
+            let signature = get_sdt_signature(dsdt_sdt);
+            if let Some(ref mut ptrs) = *(SDT_POINTERS.write()) {
+                ptrs.insert(signature, dsdt_sdt);
             }
+
+            let mut fadt_t = ACPI_TABLE.fadt.write();
+            *fadt_t = Some(fadt);
         }
     }
 }
diff --git a/src/acpi/hpet.rs b/src/acpi/hpet.rs
index 7b926487..d2e5ecfb 100644
--- a/src/acpi/hpet.rs
+++ b/src/acpi/hpet.rs
@@ -6,7 +6,7 @@ use memory::Frame;
 use paging::{entry, ActivePageTable, PhysicalAddress, Page, VirtualAddress};
 
 use super::sdt::Sdt;
-use super::{ACPI_TABLE, SDT_POINTERS, get_sdt};
+use super::{ACPI_TABLE, SDT_POINTERS, get_sdt, find_sdt, load_table, get_sdt_signature};
 
 #[repr(packed)]
 #[derive(Clone, Copy, Debug, Default)]
@@ -36,20 +36,20 @@ pub struct Hpet {
 
 impl Hpet {
     pub fn init(active_table: &mut ActivePageTable) {
-        if let Some(ref ptrs) = *(SDT_POINTERS.read()) {
-            let hpet = if let Some(hpet_sdt) = ptrs.get("HPET") {
-                Hpet::new(hpet_sdt, active_table)
-            } else {
-                println!("Unable to find HPET");
-                return;
-            };
+        let hpet_sdt = find_sdt("HPET");
+        let hpet = if hpet_sdt.len() == 1 {
+            load_table(get_sdt_signature(hpet_sdt[0]));
+            Hpet::new(hpet_sdt[0], active_table)
+        } else {
+            println!("Unable to find HPET");
+            return;
+        };
+        
+        if let Some(hpet) = hpet {
+            println!("  HPET: {:X}", hpet.hpet_number);
             
-            if let Some(hpet) = hpet {
-                println!("  HPET: {:X}", hpet.hpet_number);
-                
-                let mut hpet_t = ACPI_TABLE.hpet.write();
-                *hpet_t = Some(hpet);
-            }
+            let mut hpet_t = ACPI_TABLE.hpet.write();
+            *hpet_t = Some(hpet);
         }
     }
     
diff --git a/src/acpi/madt.rs b/src/acpi/madt.rs
index 501bba59..c4f922a5 100644
--- a/src/acpi/madt.rs
+++ b/src/acpi/madt.rs
@@ -4,7 +4,7 @@ use memory::{allocate_frames, Frame};
 use paging::{entry, ActivePageTable, Page, PhysicalAddress, VirtualAddress};
 
 use super::sdt::Sdt;
-use super::{ACPI_TABLE, SDT_POINTERS, AP_STARTUP, TRAMPOLINE};
+use super::{ACPI_TABLE, SDT_POINTERS, AP_STARTUP, TRAMPOLINE, find_sdt, load_table, get_sdt_signature};
 
 use core::intrinsics::{atomic_load, atomic_store};
 use core::sync::atomic::Ordering;
@@ -33,118 +33,118 @@ pub struct Madt {
 
 impl Madt {
     pub fn init(active_table: &mut ActivePageTable) {
-        if let Some(ref ptrs) = *(SDT_POINTERS.read()) {
-            let madt = if let Some(madt_sdt) = ptrs.get("APIC") {
-                Madt::new(madt_sdt)
+        let madt_sdt = find_sdt("APIC");
+        let madt = if madt_sdt.len() == 1 {
+            load_table(get_sdt_signature(madt_sdt[0]));
+            Madt::new(madt_sdt[0])
+        } else {
+            println!("Unable to find MADT");
+            return;
+        };
+        
+        if let Some(madt) = madt {
+            println!("  APIC: {:>08X}: {}", madt.local_address, madt.flags);
+
+            let local_apic = unsafe { &mut LOCAL_APIC };
+            let me = local_apic.id() as u8;
+
+            if local_apic.x2 {
+                println!("    X2APIC {}", me);
             } else {
-                println!("Unable to find MADT");
-                return;
-            };
-            
-            if let Some(madt) = madt {
-                println!("  APIC: {:>08X}: {}", madt.local_address, madt.flags);
-
-                let local_apic = unsafe { &mut LOCAL_APIC };
-                let me = local_apic.id() as u8;
-
-                if local_apic.x2 {
-                    println!("    X2APIC {}", me);
-                } else {
-                    println!("    XAPIC {}: {:>08X}", me, local_apic.address);
-                }
-
-                if cfg!(feature = "multi_core"){
-                    let trampoline_frame = Frame::containing_address(PhysicalAddress::new(TRAMPOLINE));
-                    let trampoline_page = Page::containing_address(VirtualAddress::new(TRAMPOLINE));
-
-                    // Map trampoline
-                    let result = active_table.map_to(trampoline_page, trampoline_frame, entry::PRESENT | entry::WRITABLE);
-                    result.flush(active_table);
+                println!("    XAPIC {}: {:>08X}", me, local_apic.address);
+            }
 
-                    for madt_entry in madt.iter() {
-                        println!("      {:?}", madt_entry);
-                        match madt_entry {
-                            MadtEntry::LocalApic(ap_local_apic) => if ap_local_apic.id == me {
-                                println!("        This is my local APIC");
-                            } else {
-                                if ap_local_apic.flags & 1 == 1 {
-                                    // Increase CPU ID
-                                    CPU_COUNT.fetch_add(1, Ordering::SeqCst);
-
-                                    // Allocate a stack
-                                    let stack_start = allocate_frames(64).expect("no more frames in acpi stack_start").start_address().get() + ::KERNEL_OFFSET;
-                                    let stack_end = stack_start + 64 * 4096;
-
-                                    let ap_ready = TRAMPOLINE as *mut u64;
-                                    let ap_cpu_id = unsafe { ap_ready.offset(1) };
-                                    let ap_page_table = unsafe { ap_ready.offset(2) };
-                                    let ap_stack_start = unsafe { ap_ready.offset(3) };
-                                    let ap_stack_end = unsafe { ap_ready.offset(4) };
-                                    let ap_code = unsafe { ap_ready.offset(5) };
-
-                                    // Set the ap_ready to 0, volatile
-                                    unsafe { atomic_store(ap_ready, 0) };
-                                    unsafe { atomic_store(ap_cpu_id, ap_local_apic.id as u64) };
-                                    unsafe { atomic_store(ap_page_table, active_table.address() as u64) };
-                                    unsafe { atomic_store(ap_stack_start, stack_start as u64) };
-                                    unsafe { atomic_store(ap_stack_end, stack_end as u64) };
-                                    unsafe { atomic_store(ap_code, kstart_ap as u64) };
-                                    AP_READY.store(false, Ordering::SeqCst);
-
-                                    print!("        AP {}:", ap_local_apic.id);
-
-                                    // Send INIT IPI
-                                    {
-                                        let mut icr = 0x4500;
-                                        if local_apic.x2 {
-                                            icr |= (ap_local_apic.id as u64) << 32;
-                                        } else {
-                                            icr |= (ap_local_apic.id as u64) << 56;
-                                        }
-                                        print!(" IPI...");
-                                        local_apic.set_icr(icr);
+            if cfg!(feature = "multi_core"){
+                let trampoline_frame = Frame::containing_address(PhysicalAddress::new(TRAMPOLINE));
+                let trampoline_page = Page::containing_address(VirtualAddress::new(TRAMPOLINE));
+
+                // Map trampoline
+                let result = active_table.map_to(trampoline_page, trampoline_frame, entry::PRESENT | entry::WRITABLE);
+                result.flush(active_table);
+
+                for madt_entry in madt.iter() {
+                    println!("      {:?}", madt_entry);
+                    match madt_entry {
+                        MadtEntry::LocalApic(ap_local_apic) => if ap_local_apic.id == me {
+                            println!("        This is my local APIC");
+                        } else {
+                            if ap_local_apic.flags & 1 == 1 {
+                                // Increase CPU ID
+                                CPU_COUNT.fetch_add(1, Ordering::SeqCst);
+
+                                // Allocate a stack
+                                let stack_start = allocate_frames(64).expect("no more frames in acpi stack_start").start_address().get() + ::KERNEL_OFFSET;
+                                let stack_end = stack_start + 64 * 4096;
+
+                                let ap_ready = TRAMPOLINE as *mut u64;
+                                let ap_cpu_id = unsafe { ap_ready.offset(1) };
+                                let ap_page_table = unsafe { ap_ready.offset(2) };
+                                let ap_stack_start = unsafe { ap_ready.offset(3) };
+                                let ap_stack_end = unsafe { ap_ready.offset(4) };
+                                let ap_code = unsafe { ap_ready.offset(5) };
+
+                                // Set the ap_ready to 0, volatile
+                                unsafe { atomic_store(ap_ready, 0) };
+                                unsafe { atomic_store(ap_cpu_id, ap_local_apic.id as u64) };
+                                unsafe { atomic_store(ap_page_table, active_table.address() as u64) };
+                                unsafe { atomic_store(ap_stack_start, stack_start as u64) };
+                                unsafe { atomic_store(ap_stack_end, stack_end as u64) };
+                                unsafe { atomic_store(ap_code, kstart_ap as u64) };
+                                AP_READY.store(false, Ordering::SeqCst);
+
+                                print!("        AP {}:", ap_local_apic.id);
+
+                                // Send INIT IPI
+                                {
+                                    let mut icr = 0x4500;
+                                    if local_apic.x2 {
+                                        icr |= (ap_local_apic.id as u64) << 32;
+                                    } else {
+                                        icr |= (ap_local_apic.id as u64) << 56;
                                     }
+                                    print!(" IPI...");
+                                    local_apic.set_icr(icr);
+                                }
 
-                                    // Send START IPI
-                                    {
-                                        //Start at 0x0800:0000 => 0x8000. Hopefully the bootloader code is still there
-                                        let ap_segment = (AP_STARTUP >> 12) & 0xFF;
-                                        let mut icr = 0x4600 | ap_segment as u64;
-
-                                        if local_apic.x2 {
-                                            icr |= (ap_local_apic.id as u64) << 32;
-                                        } else {
-                                            icr |= (ap_local_apic.id as u64) << 56;
-                                        }
+                                // Send START IPI
+                                {
+                                    //Start at 0x0800:0000 => 0x8000. Hopefully the bootloader code is still there
+                                    let ap_segment = (AP_STARTUP >> 12) & 0xFF;
+                                    let mut icr = 0x4600 | ap_segment as u64;
 
-                                        print!(" SIPI...");
-                                        local_apic.set_icr(icr);
+                                    if local_apic.x2 {
+                                        icr |= (ap_local_apic.id as u64) << 32;
+                                    } else {
+                                        icr |= (ap_local_apic.id as u64) << 56;
                                     }
 
-                                    // Wait for trampoline ready
-                                    print!(" Wait...");
-                                    while unsafe { atomic_load(ap_ready) } == 0 {
-                                        interrupt::pause();
-                                    }
-                                    print!(" Trampoline...");
-                                    while ! AP_READY.load(Ordering::SeqCst) {
-                                        interrupt::pause();
-                                    }
-                                    println!(" Ready");
+                                    print!(" SIPI...");
+                                    local_apic.set_icr(icr);
+                                }
 
-                                    active_table.flush_all();
-                                } else {
-                                    println!("        CPU Disabled");
+                                // Wait for trampoline ready
+                                print!(" Wait...");
+                                while unsafe { atomic_load(ap_ready) } == 0 {
+                                    interrupt::pause();
                                 }
-                            },
-                            _ => ()
-                        }
-                    }
+                                print!(" Trampoline...");
+                                while ! AP_READY.load(Ordering::SeqCst) {
+                                    interrupt::pause();
+                                }
+                                println!(" Ready");
 
-                    // Unmap trampoline
-                    let (result, _frame) = active_table.unmap_return(trampoline_page, false);
-                    result.flush(active_table);
+                                active_table.flush_all();
+                            } else {
+                                println!("        CPU Disabled");
+                            }
+                        },
+                        _ => ()
+                    }
                 }
+
+                // Unmap trampoline
+                let (result, _frame) = active_table.unmap_return(trampoline_page, false);
+                result.flush(active_table);
             }
         }
     }
diff --git a/src/acpi/mod.rs b/src/acpi/mod.rs
index a1d5eccf..5902ebc5 100644
--- a/src/acpi/mod.rs
+++ b/src/acpi/mod.rs
@@ -97,34 +97,24 @@ fn init_namespace() {
         let mut namespace = ACPI_TABLE.namespace.write();
         *namespace = Some(BTreeMap::new());
     }
-
-    let dsdt: &'static Sdt = if let Some(ref ptrs) = *(SDT_POINTERS.read()) {
-        if let Some(dsdt_sdt) = ptrs.get("DSDT") {
-            print!("  DSDT");
-            dsdt_sdt
-        } else {
-            println!("No DSDT found");
-            return;
-        }
-    } else {
-        return;
-    };
-
-    init_aml_table(dsdt);
     
-    let ssdt: &'static Sdt = if let Some(ref ptrs) = *(SDT_POINTERS.read()) {
-        if let Some(ssdt_sdt) = ptrs.get("SSDT") {
-            print!("  SSDT");
-            ssdt_sdt
-        } else {
-            println!("No SSDT found");
-            return;
-        }
+    let dsdt = find_sdt("DSDT");
+    if dsdt.len() == 1 {
+        print!("  DSDT");
+        load_table(get_sdt_signature(dsdt[0]));
+        init_aml_table(dsdt[0]);
     } else {
+        println!("Unable to find DSDT");
         return;
     };
+    
+    let ssdts = find_sdt("SSDT");
 
-    init_aml_table(ssdt);
+    for ssdt in ssdts {
+        print!("  SSDT");
+        load_table(get_sdt_signature(ssdt));
+        init_aml_table(ssdt);
+    }
 }
 
 /// Parse the ACPI tables to gather CPU, interrupt, and timer information
@@ -133,6 +123,11 @@ pub unsafe fn init(active_table: &mut ActivePageTable) {
         let mut sdt_ptrs = SDT_POINTERS.write();
         *sdt_ptrs = Some(BTreeMap::new());
     }
+
+    {
+        let mut order = SDT_ORDER.write();
+        *order = Some(vec!());
+    }
     
     // Search for RSDP
     if let Some(rsdp) = RSDP::get_rsdp(active_table) {
@@ -157,11 +152,9 @@ pub unsafe fn init(active_table: &mut ActivePageTable) {
         for sdt_address in rxsdt.iter() {
             let sdt = unsafe { &*(sdt_address as *const Sdt) };
             
-            let signature = String::from_utf8(sdt.signature.to_vec()).expect("Error converting signature to string");
-            {
-                if let Some(ref mut ptrs) = *(SDT_POINTERS.write()) {
-                    ptrs.insert(signature, sdt);
-                }
+            let signature = get_sdt_signature(sdt);
+            if let Some(ref mut ptrs) = *(SDT_POINTERS.write()) {
+                ptrs.insert(signature, sdt);
             }
         }
 
@@ -203,10 +196,38 @@ pub fn set_global_s_state(state: u8) {
     }
 }
 
-pub static SDT_POINTERS: RwLock<Option<BTreeMap<String, &'static Sdt>>> = RwLock::new(None);
+type SdtSignature = (String, [u8; 6], [u8; 8]);
+pub static SDT_POINTERS: RwLock<Option<BTreeMap<SdtSignature, &'static Sdt>>> = RwLock::new(None);
+pub static SDT_ORDER: RwLock<Option<Vec<SdtSignature>>> = RwLock::new(None);
+
+pub fn find_sdt(name: &str) -> Vec<&'static Sdt> {
+    let mut sdts: Vec<&'static Sdt> = vec!();
+    
+    if let Some(ref ptrs) = *(SDT_POINTERS.read()) {
+        for (signature, sdt) in ptrs {
+            if signature.0 == name {
+                sdts.push(sdt);
+            }
+        }
+    }
+
+    sdts
+}
+
+pub fn get_sdt_signature(sdt: &'static Sdt) -> SdtSignature {
+    let signature = String::from_utf8(sdt.signature.to_vec()).expect("Error converting signature to string");
+    (signature, sdt.oem_id, sdt.oem_table_id)
+}
+
+pub fn load_table(signature: SdtSignature) {
+    let mut order = SDT_ORDER.write();
+
+    if let Some(ref mut o) = *order {
+        o.push(signature);
+    }
+}
 
 pub struct Acpi {
-    pub rxsdt: RwLock<Option<Box<Rxsdt + Send + Sync>>>,
     pub fadt: RwLock<Option<Fadt>>,
     pub namespace: RwLock<Option<BTreeMap<String, AmlValue>>>,
     pub hpet: RwLock<Option<Hpet>>,
@@ -214,7 +235,6 @@ pub struct Acpi {
 }
 
 pub static ACPI_TABLE: Acpi = Acpi {
-    rxsdt: RwLock::new(None),
     fadt: RwLock::new(None),
     namespace: RwLock::new(None),
     hpet: RwLock::new(None),
-- 
GitLab