| 1 | #include "mem/tests/test_internal.h" |
| 2 | #include <mem/address_range.h> |
| 3 | |
| 4 | ADDRESS_RANGE_DECLARE(vas_test_map, .flags = ADDRESS_RANGE_DYNAMIC, |
| 5 | .size = PAGE_2MB, .align = PAGE_SIZE); |
| 6 | |
| 7 | TEST_DECLARE_SMOKE(vas, reserve_query_free) { |
| 8 | const vaddr_t base = 0x700000000000ULL; |
| 9 | struct vas *vas = vas_create(base, limit: base + PAGE_1GB); |
| 10 | TEST_ASSERT_NONNULL(vas); |
| 11 | |
| 12 | size_t sizes[] = {PAGE_SIZE, 64 * 1024, PAGE_2MB}; |
| 13 | vaddr_t addresses[TEST_ARRAY_LEN(sizes)]; |
| 14 | for (size_t i = 0; i < TEST_ARRAY_LEN(sizes); i++) { |
| 15 | addresses[i] = vas_alloc(vas, size: sizes[i], PAGE_SIZE); |
| 16 | TEST_ASSERT_NE(addresses[i], 0); |
| 17 | TEST_ASSERT(vas_vaddr_is_allocated(vas, addresses[i])); |
| 18 | TEST_ASSERT(vas_vaddr_is_allocated(vas, addresses[i] + sizes[i] - 1)); |
| 19 | } |
| 20 | |
| 21 | for (size_t i = 0; i < TEST_ARRAY_LEN(sizes); i++) { |
| 22 | vas_free(vas, addr: addresses[i], size: sizes[i]); |
| 23 | TEST_ASSERT_FALSE(vas_vaddr_is_allocated(vas, addresses[i])); |
| 24 | } |
| 25 | |
| 26 | TEST_ASSERT(vas_destroy(vas)); |
| 27 | return TEST_SUCCESS; |
| 28 | } |
| 29 | |
| 30 | TEST_DECLARE_SMOKE(vas, map_unaligned_physical_address) { |
| 31 | struct vas *vas = vas_from(ar: &ADDRESS_RANGE(vas_test_map)); |
| 32 | TEST_ASSERT_NONNULL(vas); |
| 33 | paddr_t phys = pmm_alloc_pages(2); |
| 34 | TEST_ASSERT_NE(phys, 0); |
| 35 | void *mapped = |
| 36 | vas_map(vas, paddr: phys + 37, PAGE_SIZE, PAGE_WRITE, vflags: VMM_FLAG_NONE); |
| 37 | |
| 38 | TEST_ASSERT_NONNULL(mapped); |
| 39 | vaddr_t base = (vaddr_t) mapped - 37; |
| 40 | |
| 41 | TEST_ASSERT_EQ(base & (PAGE_SIZE - 1), 0); |
| 42 | TEST_ASSERT_EQ(vmm_get_phys((vaddr_t) mapped, VMM_FLAG_NONE), phys + 37); |
| 43 | TEST_ASSERT(vas_vaddr_is_allocated(vas, base + 2 * PAGE_SIZE - 1)); |
| 44 | |
| 45 | ((uint8_t *) mapped)[PAGE_SIZE - 1] = 0x57; |
| 46 | TEST_ASSERT_EQ(((uint8_t *) hhdm_paddr_to_ptr(phys))[PAGE_SIZE + 36], 0x57); |
| 47 | vaddr_t next = vas_alloc(vas, PAGE_SIZE, PAGE_SIZE); |
| 48 | |
| 49 | TEST_ASSERT_EQ(next, base + 2 * PAGE_SIZE); |
| 50 | vas_unmap(vas, vaddr: mapped, PAGE_SIZE); |
| 51 | |
| 52 | TEST_ASSERT_FALSE(vas_vaddr_is_allocated(vas, base)); |
| 53 | TEST_ASSERT_EQ(vmm_get_phys(base, VMM_FLAG_NONE), PADDR_MAX); |
| 54 | TEST_ASSERT_EQ(vmm_get_phys(base + PAGE_SIZE, VMM_FLAG_NONE), PADDR_MAX); |
| 55 | vas_free(vas, addr: next, PAGE_SIZE); |
| 56 | pmm_free_pages(addr: phys, count: 2); |
| 57 | TEST_ASSERT(vas_destroy(vas)); |
| 58 | |
| 59 | return TEST_SUCCESS; |
| 60 | } |
| 61 | |