1
0
mirror of https://github.com/taigrr/gopher-os synced 2025-01-18 04:43:13 -08:00

Define virtual memory page type

This is equivalent to pmm.Frame (also a uintptr) but having different
types for physical and virtual frames serves as an additional layer of
protection for functions/methods that receive physical and/or virtual
page arguments.
This commit is contained in:
Achilleas Anagnostopoulos 2017-05-31 16:02:55 +01:00
parent c596bc96c3
commit b67a2045b9
2 changed files with 54 additions and 0 deletions

19
kernel/mem/vmm/page.go Normal file
View File

@ -0,0 +1,19 @@
package vmm
import "github.com/achilleasa/gopher-os/kernel/mem"
// Page describes a virtual memory page index.
type Page uintptr
// Address returns a pointer to the virtual memory address pointed to by this Page.
func (f Page) Address() uintptr {
return uintptr(f << mem.PageShift)
}
// PageFromAddress returns a Page that corresponds to the given virtual
// address. This function can handle both page-aligned and not aligned virtual
// addresses. in the latter case, the input address will be rounded down to the
// page that contains it.
func PageFromAddress(virtAddr uintptr) Page {
return Page((virtAddr & ^(uintptr(mem.PageSize - 1))) >> mem.PageShift)
}

View File

@ -0,0 +1,35 @@
package vmm
import (
"testing"
"github.com/achilleasa/gopher-os/kernel/mem"
)
func TestPageMethods(t *testing.T) {
for pageIndex := uint64(0); pageIndex < 128; pageIndex++ {
page := Page(pageIndex)
if exp, got := uintptr(pageIndex<<mem.PageShift), page.Address(); got != exp {
t.Errorf("expected page (%d, index: %d) call to Address() to return %x; got %x", page, pageIndex, exp, got)
}
}
}
func TestPageFromAddress(t *testing.T) {
specs := []struct {
input uintptr
expPage Page
}{
{0, Page(0)},
{4095, Page(0)},
{4096, Page(1)},
{4123, Page(1)},
}
for specIndex, spec := range specs {
if got := PageFromAddress(spec.input); got != spec.expPage {
t.Errorf("[spec %d] expected returned page to be %v; got %v", specIndex, spec.expPage, got)
}
}
}