From 5ab014e715fb430e98e7965efc25ae5fdedd9fa6 Mon Sep 17 00:00:00 2001 From: bunnie Date: Mon, 6 May 2024 18:55:11 +0800 Subject: [PATCH] cleanup the offsets for decrypt_src_page_at() We had a "coincidence" before that allowed things to work, where we had some data line up that we happened to think was some other header data, so we "fixed" it by subtracting the offset of the header data. Actually, it wasn't. Clarify that decrypt_src_page_at() offsets are relative to the beginning of encrypted data, and not relative to the absolute beginning of the disk. Image creation is now fixed so that stuff lines up to what this routine expects, and some asserts added to try and save ourselves in the future as we try to fix other bugs we discover over time. loaders are hard. --- .vscode/settings.json | 8 +++----- loader/src/main.rs | 4 ++-- loader/src/phase2.rs | 1 + loader/src/platform/cramium/swap.rs | 4 +--- loader/src/platform/precursor/swap.rs | 12 +++++------- xtask/src/main.rs | 9 ++++----- 6 files changed, 16 insertions(+), 22 deletions(-) diff --git a/.vscode/settings.json b/.vscode/settings.json index 7ecf0034c..e10973533 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -8,11 +8,9 @@ "--target-dir", "target/analyzer", "--features", - "precursor", + "cramium-soc", "--features", - "utralib/precursor", - "--features", - "utralib/precursor-pvt", + "utralib/cramium-soc", "--message-format", "json" ], @@ -20,7 +18,7 @@ "XOUS_SVD_FILE": "../precursors/soc.svd" }, "rust-analyzer.cargo.features": [ - "precursor", + "cramium-soc", "swap", "mass-storage" ], diff --git a/loader/src/main.rs b/loader/src/main.rs index 1938f49dc..aee4d672a 100644 --- a/loader/src/main.rs +++ b/loader/src/main.rs @@ -413,8 +413,8 @@ pub fn read_initial_config(cfg: &mut BootConfig) { #[cfg(feature = "swap")] pub fn read_swap_config(cfg: &mut BootConfig) { - // Read in the swap arguments: should be located at beginning of image in swap. - let page0 = cfg.swap_hal.as_mut().unwrap().decrypt_src_page_at(0x1000); + // Read in the swap arguments: should be located at beginning of the encrypted image in swap. + let page0 = cfg.swap_hal.as_mut().unwrap().decrypt_src_page_at(0x0); let swap_args = KernelArguments::new(page0.as_ptr() as *const usize); for tag in swap_args.iter() { if tag.name == u32::from_le_bytes(*b"IniS") { diff --git a/loader/src/phase2.rs b/loader/src/phase2.rs index 75ba4ef8a..7ad5bbc09 100644 --- a/loader/src/phase2.rs +++ b/loader/src/phase2.rs @@ -230,6 +230,7 @@ pub fn phase_2(cfg: &mut BootConfig, fs_prehash: &[u8; 64]) { // patch the entry to point at the virtual address *entry &= 0x3FF; *entry |= (vaddr & !0xFFF) >> 2; + println!("Remapping L2 PT @paddr {:x} -> vaddr {:x}", paddr, vaddr); swap_pt_vaddr_offset += PAGE_SIZE; } } diff --git a/loader/src/platform/cramium/swap.rs b/loader/src/platform/cramium/swap.rs index 93b08668b..b72516eb2 100644 --- a/loader/src/platform/cramium/swap.rs +++ b/loader/src/platform/cramium/swap.rs @@ -343,11 +343,9 @@ impl SwapHal { fn aad(&self) -> &[u8] { &self.aad_storage[..self.aad_len] } + /// `offset` is the offset from the beginning of the encrypted region (not full disk region) pub fn decrypt_src_page_at(&mut self, offset: usize) -> &[u8] { assert!((offset & 0xFFF) == 0, "offset is not page-aligned"); - assert!(offset >= 0x1000); - // compensate for the unencrypted header that is not included in the `src_data_area` slice - let offset = offset - 0x1000; self.buf_addr = offset; self.flash_spim.mem_read((self.image_start + offset) as u32, &mut self.buf.data, false); let mut nonce = [0u8; size_of::()]; diff --git a/loader/src/platform/precursor/swap.rs b/loader/src/platform/precursor/swap.rs index 66dc015fe..e52759970 100644 --- a/loader/src/platform/precursor/swap.rs +++ b/loader/src/platform/precursor/swap.rs @@ -106,11 +106,9 @@ impl SwapHal { pub fn get_swap_key(&self) -> &[u8] { &self.ram_swap_key } + /// `offset` is the offset from the beginning of the encrypted region (not full disk region) pub fn decrypt_src_page_at(&mut self, offset: usize) -> &[u8] { assert!((offset & 0xFFF) == 0, "offset is not page-aligned"); - assert!(offset >= 0x1000); - // compensate for the unencrypted header that is not included in the `src_data_area` slice - let offset = offset - 0x1000; self.buf_addr = offset; // println!("data area: {:x?}", &self.src_data_area[..4]); // println!("offset: {:x}", offset); @@ -172,8 +170,8 @@ impl SwapHal { /// Used to examine contents of swap RAM. Swap count is fixed at 0 by this routine. Decrypted data is /// returned as a slice. pub fn decrypt_swap_from(&mut self, src_offset: usize, dst_vaddr: usize, dst_pid: u8) -> &[u8] { - println!("Decrypt swap:"); - println!(" offset: {:x}, vaddr: {:x}, pid: {}", src_offset, dst_vaddr, dst_pid); + // println!("Decrypt swap:"); + // println!(" offset: {:x}, vaddr: {:x}, pid: {}", src_offset, dst_vaddr, dst_pid); assert!(src_offset & (PAGE_SIZE - 1) == 0); let mut nonce = [0u8; size_of::()]; nonce[0..4].copy_from_slice(&[0u8; 4]); // this is the `swap_count` field @@ -186,9 +184,9 @@ impl SwapHal { let mut tag = [0u8; size_of::()]; let mac_offset = (src_offset / PAGE_SIZE) * size_of::(); tag.copy_from_slice(&self.dst_mac_area[mac_offset..mac_offset + size_of::()]); - println!("dst_mac_area: {:x?}", &self.dst_mac_area[..32]); + // println!("dst_mac_area: {:x?}", &self.dst_mac_area[..32]); self.buf.data.copy_from_slice(&self.dst_data_area[src_offset..src_offset + PAGE_SIZE]); - println!("Nonce: {:x?}, tag: {:x?}", &nonce, &tag); + // println!("Nonce: {:x?}, tag: {:x?}", &nonce, &tag); match self.dst_cipher.decrypt_in_place_detached( Nonce::from_slice(&nonce), aad, diff --git a/xtask/src/main.rs b/xtask/src/main.rs index c9cf0ec7c..95fece991 100644 --- a/xtask/src/main.rs +++ b/xtask/src/main.rs @@ -280,11 +280,10 @@ fn main() -> Result<(), Box> { builder.add_loader_feature("swap"); builder.add_kernel_feature("swap"); builder.add_feature("swap"); - // builder.add_kernel_feature("debug-swap"); + builder.add_kernel_feature("debug-swap"); // builder.add_kernel_feature("debug-print"); - // It is important that this is the first service added, because the swapper *must* be in PID 2 - builder.add_service("xous-swapper", LoaderRegion::Ram); + builder.add_service("xous-swapper", LoaderRegion::Flash); builder.add_kernel_feature("swap"); for service in swap_pkgs { @@ -468,8 +467,8 @@ fn main() -> Result<(), Box> { // ------ Cramium hardware image configs ------ Some("cramium-fpga") | Some("cramium-soc") => { let cramium_flash_pkgs = - ["xous-ticktimer", "xous-log", "xous-names", "cram-hal-service", "cram-console"].to_vec(); - let cramium_swap_pkgs = ["test-swapper", "graphics-server"].to_vec(); + ["xous-ticktimer", "xous-log", "xous-names", "cram-hal-service"].to_vec(); + let cramium_swap_pkgs = ["test-swapper", "graphics-server", "cram-console"].to_vec(); if !builder.is_swap_set() { builder.set_swap(0, 4 * 1024 * 1024); }