#include <j6/errors.h>
#include <j6/types.h>

#include "logger.h"
#include "objects/process.h"
#include "objects/vm_area.h"
#include "syscalls/helpers.h"
#include "vm_space.h"

using namespace obj;

namespace syscalls {

j6_status_t
vma_create(j6_handle_t *self, size_t size, uint32_t flags)
{
    vm_flags f = vm_flags::user_mask & flags;
    if (util::bits::has(f, vm_flags::ring))
        construct_handle<vm_area_ring>(self, size, f);
    else
        construct_handle<vm_area_open>(self, size, f);
    return j6_status_ok;
}

j6_status_t
vma_create_map(j6_handle_t *self, size_t size, uintptr_t base, uint32_t flags)
{
    vm_area *a = nullptr;
    vm_flags f = vm_flags::user_mask & flags;
    if (util::bits::has(f, vm_flags::ring))
        a = construct_handle<vm_area_ring>(self, size, f);
    else
        a = construct_handle<vm_area_open>(self, size, f);

    process::current().space().add(base, a);
    return j6_status_ok;
}

j6_status_t
vma_map(vm_area *self, process *proc, uintptr_t base)
{
    vm_space &space = proc ? proc->space() : process::current().space();
    space.add(base, self);
    return j6_status_ok;
}

j6_status_t
vma_unmap(vm_area *self, process *proc)
{
    vm_space &space = proc ? proc->space() : process::current().space();
    space.remove(self);
    return j6_status_ok;
}

j6_status_t
vma_resize(vm_area *self, size_t *size)
{
    *size = self->resize(*size);
    return j6_status_ok;
}



} // namespace syscalls
