I'm hacking around with making a "fast reboot" that puts a copy of the MBR from disk into address 0x7c00 and, after disabling various translation bits and stopping other CPUs, branches to it, to skip the hardware self test that normally happens on boot.
I haven't gotten to the point of attempting to run the code at 0x7c00 because I'm first hitting a different error. Despite my attempts to enter a translation into the hardware page table, I get a panic trying to write to address 0x7000, where I intended to put the trampoline code that turns off translation. Rebooting... Attempt to reset to MBR... XXX attempting pmap_kenter()... XXX copying bootstrap code... panic @ time 1285760103.939, thread 0xffffff000775d960: Fatal trap 12: page fault while in kernel mode cpuid = 0 Panic occurred in module kernel loaded at 0xffffffff80100000: Stack: -------------------------------------------------- kernel:trap_fatal+0xac kernel:trap_pfault+0x24c kernel:trap+0x42e kernel:bcopy+0x16 kernel:shutdown_reset+0x48 kernel:boot+0x317 kernel:reboot+0x60 kernel:ia32_syscall+0x1cd -------------------------------------------------- cpuid = 0; apic id = 00 fault virtual address = 0x7000 fault code = supervisor write data, page not present stack pointer = 0x10:0xffffff8059e07670 frame pointer = 0x10:0xffffff8059e07780 Here's what I think is the relevant snippets of code. Note that I reserved the vm_page_t for physical page 7 as mbr_page early in boot, so I know the memory is free. void pmap_kenter_VR(vm_paddr_t pa) { pmap_t pmap = kernel_pmap; vm_page_t mpte; pd_entry_t *pde; pt_entry_t *pte; vm_page_lock_queues(); PMAP_LOCK(pmap); mpte = pmap_allocpte(pmap, pa, M_WAITOK); pde = pmap_pde(pmap, pa); if (pde == NULL || (*pde & PG_V) == 0) panic("%s: invalid page directory va=%#lx", __func__, pa); if ((*pde & PG_PS) != 0) panic("%s: attempted pmap_enter on 2MB page", __func__); pte = pmap_pde_to_pte(pde, pa); if (pte == NULL) panic("%s: no pte va=%#lx", __func__, pa); if (*pte != 0) { /* Remove extra pte reference. */ mpte->wire_count--; } pte_store(pte, pa | PG_RW | PG_V | PG_G | pg_nx); vm_page_unlock_queues(); PMAP_UNLOCK(pmap); } Then in cpu_reset(): /* * Establish a V=R mapping for the MBR page, and copy a * reasonable guess at the size of the bootstrap code into the * beginning of the page. */ printf("XXX attempting pmap_kenter()...\n"); pmap_kenter_VR(trunc_page(mbaddr)); printf("XXX copying bootstrap code...\n"); to_copy = (uintptr_t)xxx_reset_end - (uintptr_t)xxx_reset_real; if (to_copy > mbaddr - trunc_page(mbaddr)) to_copy = mbaddr - trunc_page(mbaddr); bcopy(xxx_reset_real, (void *)trunc_page(mbaddr), to_copy); /* die here */ printf("XXX attempting to turn off xlation and re-run MBR...\n"); xxx_reset_real(mbaddr); My first attempt was a call to pmap_kenter(trunc_page(0x7c00), trunc_page(0x7c00)); which failed trying to dereference the non-existent PDE. My second attempt called pmap_enter(kernel_pmap, trunc_page(0x7c00), VM_PROT_WRITE, mbr_page, VM_PROT_ALL, 0); That failed with the same crash as the attempt using pmap_kenter_VR(). So... any thoughts as to why, after an apparently successful installation of an xlation, I still get a panic as though there were no xlation? Thanks, matthew _______________________________________________ freebsd-hackers@freebsd.org mailing list http://lists.freebsd.org/mailman/listinfo/freebsd-hackers To unsubscribe, send any mail to "freebsd-hackers-unsubscr...@freebsd.org"