vpm readability

This commit is contained in:
Mid 2025-07-06 21:20:32 +03:00
parent 2a6a931894
commit 7e506265ce
4 changed files with 50 additions and 35 deletions

View File

@ -17,4 +17,10 @@
#define PAGE_BIT_WRITABLE 2
#define PAGE_BIT_USER 4
#endif
#define PAGE_PRESENT(p) ((p) & (PAGE_BIT_PRESENT))
#define PAGE_SIZE 4096
#define ROUND_UP_POT(i, n) (((i) + ((n) - 1)) & ~((n) - 1))
#endif

View File

@ -21,7 +21,7 @@ uint32_t scheduler_Tick;
void klogs(const char *str);
void klogc(int c);
static void klogp(void *p) {
void klogp(void *p) {
static char hex[16]="0123456789ABCDEF";
uintptr_t i = (uintptr_t) p;

View File

@ -2,49 +2,57 @@
#include"ppm.h"
#include"mem.h"
#include"consts.h"
extern void *_kernel_end;
static void invlpg(uint32_t virtaddr) {
asm volatile("invlpg %0" : : "m"(*(char*)virtaddr) : "memory");
}
void set_temporary_mapping(uint32_t addr) {
static void set_temporary_mapping(uint32_t addr) {
if((addr & 0xFFF) != 0) asm volatile("xchgw %bx, %bx");
*(volatile uint32_t*) 0xFFFFFFF8 = addr | 3;
asm volatile("invlpg 0xFFFFE000" : : : "memory");
}
static uint32_t nextAllocs[2] = {[VPM_KERNEL] = 0, [VPM_USER] = 1 * 1024 * 1024 * 1024};
static uint32_t spaceBoundaries[2] = {[VPM_KERNEL] = 4096, [VPM_USER] = 1 * 1024 * 1024 * 1024};
void vpm_init(uint32_t kernelEnd) {
nextAllocs[VPM_KERNEL] = (kernelEnd + 4095) & ~4095;
//spaceBoundaries[VPM_KERNEL] = (kernelEnd + 4095) & ~4095;
}
/* TODO: Make better. */
uint32_t vpm_find_free(uint32_t addrspace, AllocationOwner owner, size_t lenBytes) {
size_t len = (lenBytes + 4095) / 4096;
/* This is a linear search. Improve? */
uint32_t vpm_find_free(uint32_t addrspace, AllocationOwner owner, size_t len) {
len = ROUND_UP_POT(len, PAGE_SIZE);
uint32_t ret = nextAllocs[owner];
for(size_t i = 0; i < len;) {
uint32_t pdeid = (ret + i * 4096) >> 22;
uint32_t pteid = ((ret + i * 4096) >> 12) & 1023;
set_temporary_mapping(addrspace);
volatile uint32_t *pde = &((volatile uint32_t*) 0xFFFFE000)[pdeid];
if((*pde & 1) == 0) {
i += 4096;
} else {
set_temporary_mapping(*pde & ~0xFFF);
for(uint32_t attempt = spaceBoundaries[owner]; attempt != 0;) {
for(size_t i = 0; i < len;) {
uint32_t pdeid = (attempt + i) >> 22;
uint32_t pteid = ((attempt + i) >> 12) & 1023;
if((((volatile uint32_t*) 0xFFFFE000)[pteid] & 1) == 0) {
i++;
set_temporary_mapping(addrspace);
volatile uint32_t *pde = &((volatile uint32_t*) 0xFFFFE000)[pdeid];
if(!PAGE_PRESENT(*pde)) {
i += PAGE_SIZE * 1024 * 1024; // 4MB
} else {
ret += (i + 1) * 4096;
i = 0;
set_temporary_mapping((*pde) & ~0xFFF);
volatile uint32_t *pte = &((volatile uint32_t*) 0xFFFFE000)[pteid];
if(!PAGE_PRESENT(*pte)) {
i += PAGE_SIZE;
} else {
attempt += i + PAGE_SIZE;
goto try_next;
}
}
}
}
return attempt;
try_next:
}
return ret;
return 0;
}
/* If phys is -1, map to uncontiguous physical pages anywhere, else map contiguous span of physical memory. */
@ -99,8 +107,8 @@ void *vpm_map(uint32_t addrspace, AllocationOwner owner, uint32_t virt, uint32_t
*pte |= 3 | (owner == VPM_USER ? 4 : 0);
if(thisspace == addrspace) {
//~ asm volatile("xchg %bx, %bx");
asm volatile("invlpg %0" : : "m"(*(char*) (virt + i * 4096)) : "memory");
invlpg(virt + i * 4096);
//asm volatile("invlpg %0" : : "m"(*(char*) (virt + i * 4096)) : "memory");
}
}
@ -164,7 +172,8 @@ int vpm_double_map(uint32_t cr3a, uint32_t cr3b, uint32_t *va, uint32_t *vb, uin
*pte = backend | 3 | 4;
if(thisspace == cr3a) {
asm volatile("invlpg %0" : : "m"(*(char*) (*va + i * 4096)) : "memory");
invlpg(*va + i * 4096);
//asm volatile("invlpg %0" : : "m"(*(char*) (*va + i * 4096)) : "memory");
}
}
@ -193,7 +202,8 @@ int vpm_double_map(uint32_t cr3a, uint32_t cr3b, uint32_t *va, uint32_t *vb, uin
*pte = backend | 3 | 4;
if(thisspace == cr3b) {
asm volatile("invlpg %0" : : "m"(*(char*) (*vb + i * 4096)) : "memory");
invlpg(*vb + i * 4096);
//asm volatile("invlpg %0" : : "m"(*(char*) (*vb + i * 4096)) : "memory");
}
}
}
@ -262,7 +272,8 @@ void vpm_unmap(uint32_t cr3, uint32_t virt, size_t len) {
((volatile uint32_t*) 0xFFFFE000)[pteid] = 0;
if(thisspace == cr3) {
asm volatile("invlpg %0" : : "m"(*(char*) (virt + i * 4096)) : "memory");
invlpg(virt + i * 4096);
//asm volatile("invlpg %0" : : "m"(*(char*) (virt + i * 4096)) : "memory");
}
}
}

View File

@ -12,8 +12,6 @@ typedef enum {
VPM_KERNEL, VPM_USER
} AllocationOwner;
void set_temporary_mapping(uint32_t addr);
uint32_t vpm_find_free(uint32_t addrspace, AllocationOwner owner, size_t len);
void *vpm_map(uint32_t cr3, AllocationOwner owner, uint32_t virt, uint32_t phys, size_t len);
uint32_t vpm_create_space();
@ -21,4 +19,4 @@ void vpm_set_space(uint32_t cr3);
uint32_t vpm_get_phys(uint32_t cr3, uint32_t);
void vpm_unmap(uint32_t cr3, uint32_t virt, size_t len);
#endif
#endif