M2 step 3: route every physical dereference through the physmap
paging.init now builds the physmap (physToVirt(phys)) alongside the low identity map, so both addressing modes resolve during the transition. tableAt (the page-table walk hinge), the pmm bitmap, the framebuffer, LAPIC/IOAPIC/HPET/PM-timer/SPCR MMIO, the ACPI table walk, AML OperationRegions, the ACPI power registers, the user-ELF frame fills, and the AP trampoline arm/disarm all reach physical memory through the physmap. Hal.mapMmio now maps into the physmap and returns the virtual address, so the device layer never learns the layout. boot_info and its pointees are converted at kmain entry. The kernel still links and runs low; identity is the safety net until it's removed. Suite 27/27. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Fable 5
parent
75bc429aa1
commit
724de7bbd0
+13
-12
@@ -147,7 +147,7 @@ var aml_block_count: usize = 0;
|
||||
|
||||
fn addAmlBlock(sdt_phys: u64) void {
|
||||
if (aml_block_count >= aml_block_phys.len or sdt_phys == 0) return;
|
||||
const h: *const SystemDescriptorTableHeader = @ptrFromInt(sdt_phys);
|
||||
const h: *const SystemDescriptorTableHeader = @ptrFromInt(danos.physToVirt(sdt_phys));
|
||||
if (h.length <= @sizeOf(SystemDescriptorTableHeader)) return;
|
||||
aml_block_phys[aml_block_count] = sdt_phys + @sizeOf(SystemDescriptorTableHeader);
|
||||
aml_block_len[aml_block_count] = h.length - @sizeOf(SystemDescriptorTableHeader);
|
||||
@@ -376,14 +376,14 @@ pub fn discover(rsdp_phys: u64, dt: *DeviceTree, hal: Hal) !void {
|
||||
dsdt_phys = 0;
|
||||
aml_block_count = 0;
|
||||
|
||||
const rsdp: *const RootSystemDescriptionPointer = @ptrFromInt(rsdp_phys);
|
||||
const rsdp: *const RootSystemDescriptionPointer = @ptrFromInt(danos.physToVirt(rsdp_phys));
|
||||
if (!std.mem.eql(u8, &rsdp.signature, "RSD PTR ")) return error.BadRsdpSignature;
|
||||
// Revision 0 checksums only the first 20 bytes (the v1.0 RSDP).
|
||||
if (!checksumOk(@ptrFromInt(rsdp_phys), 20)) return error.BadRsdpChecksum;
|
||||
if (!checksumOk(@ptrFromInt(danos.physToVirt(rsdp_phys)), 20)) return error.BadRsdpChecksum;
|
||||
|
||||
if (rsdp.revision >= 2) {
|
||||
const xsdp: *const ExtendedSystemDescriptorPointer = @ptrFromInt(rsdp_phys);
|
||||
if (!checksumOk(@ptrFromInt(rsdp_phys), xsdp.length)) return error.BadXsdpChecksum;
|
||||
const xsdp: *const ExtendedSystemDescriptorPointer = @ptrFromInt(danos.physToVirt(rsdp_phys));
|
||||
if (!checksumOk(@ptrFromInt(danos.physToVirt(rsdp_phys)), xsdp.length)) return error.BadXsdpChecksum;
|
||||
try walkRoot(u64, xsdp.extended_system_descriptor_table_address, dt, hal);
|
||||
} else {
|
||||
try walkRoot(u32, rsdp.root_system_description_table_address, dt, hal);
|
||||
@@ -393,7 +393,7 @@ pub fn discover(rsdp_phys: u64, dt: *DeviceTree, hal: Hal) !void {
|
||||
// read the sleep types from it.
|
||||
var blocks: [aml_block_phys.len][]const u8 = undefined;
|
||||
for (0..aml_block_count) |i| {
|
||||
blocks[i] = @as([*]const u8, @ptrFromInt(aml_block_phys[i]))[0..aml_block_len[i]];
|
||||
blocks[i] = @as([*]const u8, @ptrFromInt(danos.physToVirt(aml_block_phys[i])))[0..aml_block_len[i]];
|
||||
}
|
||||
const active = blocks[0..aml_block_count];
|
||||
if (aml.parse(dt.allocator, active)) |pr| {
|
||||
@@ -412,11 +412,11 @@ pub fn discover(rsdp_phys: u64, dt: *DeviceTree, hal: Hal) !void {
|
||||
/// Walk the RSDT (Entry = u32) or XSDT (Entry = u64): validate it, then dispatch
|
||||
/// each SDT it points at. A bad individual table is skipped, not fatal.
|
||||
fn walkRoot(comptime Entry: type, root_phys: u64, dt: *DeviceTree, hal: Hal) !void {
|
||||
const header: *const SystemDescriptorTableHeader = @ptrFromInt(root_phys);
|
||||
if (!checksumOk(@ptrFromInt(root_phys), header.length)) return error.BadRootChecksum;
|
||||
const header: *const SystemDescriptorTableHeader = @ptrFromInt(danos.physToVirt(root_phys));
|
||||
if (!checksumOk(@ptrFromInt(danos.physToVirt(root_phys)), header.length)) return error.BadRootChecksum;
|
||||
|
||||
const count = (header.length - @sizeOf(SystemDescriptorTableHeader)) / @sizeOf(Entry);
|
||||
const base: [*]const u8 = @ptrFromInt(root_phys);
|
||||
const base: [*]const u8 = @ptrFromInt(danos.physToVirt(root_phys));
|
||||
const entries: [*]align(1) const Entry = @ptrCast(base + @sizeOf(SystemDescriptorTableHeader));
|
||||
|
||||
for (entries[0..count]) |ent| {
|
||||
@@ -427,7 +427,7 @@ fn walkRoot(comptime Entry: type, root_phys: u64, dt: *DeviceTree, hal: Hal) !vo
|
||||
|
||||
/// Dispatch a single SDT on its signature.
|
||||
fn handleTable(dt: *DeviceTree, hal: Hal, sdt_phys: u64) !void {
|
||||
const header: *const SystemDescriptorTableHeader = @ptrFromInt(sdt_phys);
|
||||
const header: *const SystemDescriptorTableHeader = @ptrFromInt(danos.physToVirt(sdt_phys));
|
||||
const sig = header.signature;
|
||||
if (std.mem.eql(u8, &sig, &APIC)) {
|
||||
try parseMadt(dt, header);
|
||||
@@ -1080,8 +1080,9 @@ fn pciConfigPtr(alloc: McfgAllocation, hal: Hal, bus: u8, dev: u8, func: u8) [*]
|
||||
(@as(u64, bus - alloc.start_bus) << 20) +
|
||||
(@as(u64, dev) << 15) +
|
||||
(@as(u64, func) << 12);
|
||||
hal.mapMmio(phys, phys, true); // identity-map this config page (writable)
|
||||
return @ptrFromInt(phys);
|
||||
// Map the config page (writable, for BAR sizing) and use the virtual
|
||||
// address the HAL hands back.
|
||||
return @ptrFromInt(hal.mapMmio(phys, danos.page_size, true));
|
||||
}
|
||||
|
||||
/// Read a little-endian integer at `off` from a (possibly unaligned) byte pointer.
|
||||
|
||||
Reference in New Issue
Block a user