1
0
mirror of https://github.com/taigrr/gopher-os synced 2025-01-18 04:43:13 -08:00
Achilleas Anagnostopoulos e67e2644e2 mm: refactor package layout for the memory management code
Summary of changes:
- kernel/mem renamed to kernel/mm
- consolidated page/frame defs into one file which now lives in the
kernel/mm package and is referenced by both pmm and vmm pkgs
- consolidated parts of the vmm code (e.g. PDT+PTE)
- memcopy/memset helpers moved to the kernel package
- physical allocators moved to the kernel/mm/pmm package
- break vmm -> pmm pkg dependency by moving AllocFrame() into the mm
package.
2018-05-28 08:16:26 +01:00

122 lines
3.6 KiB
Go

package vmm
import (
"gopheros/kernel"
"gopheros/kernel/cpu"
"gopheros/kernel/irq"
"gopheros/kernel/mm"
"gopheros/multiboot"
"testing"
"unsafe"
)
func TestInit(t *testing.T) {
defer func() {
mm.SetFrameAllocator(nil)
activePDTFn = cpu.ActivePDT
switchPDTFn = cpu.SwitchPDT
translateFn = Translate
mapTemporaryFn = MapTemporary
unmapFn = Unmap
handleExceptionWithCodeFn = irq.HandleExceptionWithCode
}()
// reserve space for an allocated page
reservedPage := make([]byte, mm.PageSize)
multiboot.SetInfoPtr(uintptr(unsafe.Pointer(&emptyInfoData[0])))
t.Run("success", func(t *testing.T) {
// fill page with junk
for i := 0; i < len(reservedPage); i++ {
reservedPage[i] = byte(i % 256)
}
mm.SetFrameAllocator(func() (mm.Frame, *kernel.Error) {
addr := uintptr(unsafe.Pointer(&reservedPage[0]))
return mm.Frame(addr >> mm.PageShift), nil
})
activePDTFn = func() uintptr {
return uintptr(unsafe.Pointer(&reservedPage[0]))
}
switchPDTFn = func(_ uintptr) {}
unmapFn = func(p mm.Page) *kernel.Error { return nil }
mapTemporaryFn = func(f mm.Frame) (mm.Page, *kernel.Error) { return mm.Page(f), nil }
handleExceptionWithCodeFn = func(_ irq.ExceptionNum, _ irq.ExceptionHandlerWithCode) {}
if err := Init(0); err != nil {
t.Fatal(err)
}
// reserved page should be zeroed
for i := 0; i < len(reservedPage); i++ {
if reservedPage[i] != 0 {
t.Errorf("expected reserved page to be zeroed; got byte %d at index %d", reservedPage[i], i)
}
}
})
t.Run("setupPDT fails", func(t *testing.T) {
expErr := &kernel.Error{Module: "test", Message: "out of memory"}
// Allow the PDT allocation to succeed and then return an error when
// trying to allocate the blank fram
mm.SetFrameAllocator(func() (mm.Frame, *kernel.Error) {
return mm.InvalidFrame, expErr
})
if err := Init(0); err != expErr {
t.Fatalf("expected error: %v; got %v", expErr, err)
}
})
t.Run("blank page allocation error", func(t *testing.T) {
expErr := &kernel.Error{Module: "test", Message: "out of memory"}
// Allow the PDT allocation to succeed and then return an error when
// trying to allocate the blank fram
var allocCount int
mm.SetFrameAllocator(func() (mm.Frame, *kernel.Error) {
defer func() { allocCount++ }()
if allocCount == 0 {
addr := uintptr(unsafe.Pointer(&reservedPage[0]))
return mm.Frame(addr >> mm.PageShift), nil
}
return mm.InvalidFrame, expErr
})
activePDTFn = func() uintptr {
return uintptr(unsafe.Pointer(&reservedPage[0]))
}
switchPDTFn = func(_ uintptr) {}
unmapFn = func(p mm.Page) *kernel.Error { return nil }
mapTemporaryFn = func(f mm.Frame) (mm.Page, *kernel.Error) { return mm.Page(f), nil }
handleExceptionWithCodeFn = func(_ irq.ExceptionNum, _ irq.ExceptionHandlerWithCode) {}
if err := Init(0); err != expErr {
t.Fatalf("expected error: %v; got %v", expErr, err)
}
})
t.Run("blank page mapping error", func(t *testing.T) {
expErr := &kernel.Error{Module: "test", Message: "map failed"}
mm.SetFrameAllocator(func() (mm.Frame, *kernel.Error) {
addr := uintptr(unsafe.Pointer(&reservedPage[0]))
return mm.Frame(addr >> mm.PageShift), nil
})
activePDTFn = func() uintptr {
return uintptr(unsafe.Pointer(&reservedPage[0]))
}
switchPDTFn = func(_ uintptr) {}
unmapFn = func(p mm.Page) *kernel.Error { return nil }
mapTemporaryFn = func(f mm.Frame) (mm.Page, *kernel.Error) { return mm.Page(f), expErr }
handleExceptionWithCodeFn = func(_ irq.ExceptionNum, _ irq.ExceptionHandlerWithCode) {}
if err := Init(0); err != expErr {
t.Fatalf("expected error: %v; got %v", expErr, err)
}
})
}