Add mmap, munmap, mremap and brk syscalls
This commit is contained in:
parent
852903de20
commit
ea00690e68
@ -17,12 +17,19 @@ extern ssize_t occlum_write(int fd, const void* buf, size_t size);
|
|||||||
extern ssize_t occlum_readv(int fd, struct iovec* iov, int count);
|
extern ssize_t occlum_readv(int fd, struct iovec* iov, int count);
|
||||||
extern ssize_t occlum_writev(int fd, const struct iovec* iov, int count);
|
extern ssize_t occlum_writev(int fd, const struct iovec* iov, int count);
|
||||||
extern off_t occlum_lseek(int fd, off_t offset, int whence);
|
extern off_t occlum_lseek(int fd, off_t offset, int whence);
|
||||||
|
|
||||||
extern int occlum_spawn(int* child_pid, const char* path,
|
extern int occlum_spawn(int* child_pid, const char* path,
|
||||||
const char** argv,
|
const char** argv,
|
||||||
const char** envp);
|
const char** envp);
|
||||||
extern int occlum_wait4(int child_pid, int* status, int options/*, struct rusage* rusage*/);
|
extern int occlum_wait4(int child_pid, int* status, int options/*, struct rusage* rusage*/);
|
||||||
extern unsigned int occlum_getpid(void);
|
extern unsigned int occlum_getpid(void);
|
||||||
extern void occlum_exit(int status);
|
extern void occlum_exit(int status);
|
||||||
|
|
||||||
|
extern void *occlum_mmap(void *addr, size_t length, int prot, int flags, int fd, off_t offset);
|
||||||
|
extern int occlum_munmap(void *addr, size_t length);
|
||||||
|
extern void *occlum_mremap(void *old_address, size_t old_size, size_t new_size, int flags, void *new_address);
|
||||||
|
extern void* occlum_brk(void* addr);
|
||||||
|
|
||||||
extern int occlum_unknown(int num);
|
extern int occlum_unknown(int num);
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
|
@ -1,6 +1,8 @@
|
|||||||
use prelude::*;
|
use prelude::*;
|
||||||
use {std, file, file_table, fs, process};
|
use {std, file, file_table, fs, process, vm};
|
||||||
use std::ffi::{CStr, CString};
|
use std::ffi::{CStr, CString};
|
||||||
|
use fs::{off_t};
|
||||||
|
use vm::{VMAreaFlags, VMResizeOptions};
|
||||||
// Use the internal syscall wrappers from sgx_tstd
|
// Use the internal syscall wrappers from sgx_tstd
|
||||||
//use std::libc_fs as fs;
|
//use std::libc_fs as fs;
|
||||||
//use std::libc_io as io;
|
//use std::libc_io as io;
|
||||||
@ -158,6 +160,80 @@ pub fn do_lseek(fd: c_int, offset: off_t, whence: c_int) -> Result<off_t, Error>
|
|||||||
fs::do_lseek(fd, seek_from)
|
fs::do_lseek(fd, seek_from)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn do_mmap(addr: *const c_void, size: size_t, prot: c_int,
|
||||||
|
flags: c_int, fd: c_int, offset: off_t)
|
||||||
|
-> Result<*const c_void, Error>
|
||||||
|
{
|
||||||
|
let addr = addr as usize;
|
||||||
|
let size = size as usize;
|
||||||
|
let flags = VMAreaFlags(prot as u32);
|
||||||
|
vm::do_mmap(addr, size, flags).map(|ret_addr| ret_addr as *const c_void)
|
||||||
|
}
|
||||||
|
|
||||||
|
fn do_munmap(addr: *const c_void, size: size_t) -> Result<(), Error> {
|
||||||
|
let addr = addr as usize;
|
||||||
|
let size = size as usize;
|
||||||
|
vm::do_munmap(addr, size)
|
||||||
|
}
|
||||||
|
|
||||||
|
fn do_mremap(old_addr: *const c_void, old_size: size_t,
|
||||||
|
new_size: size_t, flags: c_int, new_addr: *const c_void)
|
||||||
|
-> Result<*const c_void, Error>
|
||||||
|
{
|
||||||
|
let old_addr = old_addr as usize;
|
||||||
|
let old_size = old_size as usize;
|
||||||
|
let mut options = VMResizeOptions::new(new_size)?;
|
||||||
|
// TODO: handle flags and new_addr
|
||||||
|
vm::do_mremap(old_addr, old_size, &options)
|
||||||
|
.map(|ret_addr| ret_addr as *const c_void)
|
||||||
|
}
|
||||||
|
|
||||||
|
fn do_brk(new_brk_addr: *const c_void) -> Result<*const c_void, Error> {
|
||||||
|
let new_brk_addr = new_brk_addr as usize;
|
||||||
|
vm::do_brk(new_brk_addr).map(|ret_brk_addr| ret_brk_addr as *const c_void)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
const MAP_FAILED : *const c_void = ((-1) as i64) as *const c_void;
|
||||||
|
|
||||||
|
#[no_mangle]
|
||||||
|
pub extern "C" fn occlum_mmap(addr: *const c_void, length: size_t, prot: c_int,
|
||||||
|
flags: c_int, fd: c_int, offset: off_t)
|
||||||
|
-> *const c_void
|
||||||
|
{
|
||||||
|
match do_mmap(addr, length, prot, flags, fd, offset) {
|
||||||
|
Ok(ret_addr) => { ret_addr },
|
||||||
|
Err(e) => { MAP_FAILED }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[no_mangle]
|
||||||
|
pub extern "C" fn occlum_munmap(addr: *const c_void, length: size_t) -> c_int {
|
||||||
|
match do_munmap(addr, length) {
|
||||||
|
Ok(()) => { 0 },
|
||||||
|
Err(e) => { -1 }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[no_mangle]
|
||||||
|
pub extern "C" fn occlum_mremap(old_addr: *const c_void, old_size: size_t,
|
||||||
|
new_size: size_t, flags: c_int,
|
||||||
|
new_addr: *const c_void)
|
||||||
|
-> *const c_void
|
||||||
|
{
|
||||||
|
match do_mremap(old_addr, old_size, new_size, flags, new_addr) {
|
||||||
|
Ok(ret_addr) => { ret_addr },
|
||||||
|
Err(e) => { MAP_FAILED }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[no_mangle]
|
||||||
|
pub extern "C" fn occlum_brk(addr: *const c_void) -> *const c_void {
|
||||||
|
match do_brk(addr) {
|
||||||
|
Ok(ret_addr) => { ret_addr },
|
||||||
|
Err(e) => { MAP_FAILED }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#[no_mangle]
|
#[no_mangle]
|
||||||
pub extern "C" fn occlum_open(path_buf: * const c_char, flags: c_int, mode: c_int) -> c_int {
|
pub extern "C" fn occlum_open(path_buf: * const c_char, flags: c_int, mode: c_int) -> c_int {
|
||||||
|
@ -4,7 +4,7 @@
|
|||||||
#define DECL_SYSCALL_ARG(_type, _name, _arg) \
|
#define DECL_SYSCALL_ARG(_type, _name, _arg) \
|
||||||
_type _name = (_type) (_arg)
|
_type _name = (_type) (_arg)
|
||||||
|
|
||||||
long dispatch_syscall(int num, long arg0, long arg1, long arg2, long arg3, long arg4) {
|
long dispatch_syscall(int num, long arg0, long arg1, long arg2, long arg3, long arg4, long arg5) {
|
||||||
long ret = 0;
|
long ret = 0;
|
||||||
|
|
||||||
switch (num) {
|
switch (num) {
|
||||||
@ -81,10 +81,39 @@ long dispatch_syscall(int num, long arg0, long arg1, long arg2, long arg3, long
|
|||||||
ret = occlum_getpid();
|
ret = occlum_getpid();
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
case SYS_mmap: {
|
||||||
|
DECL_SYSCALL_ARG(void*, addr, arg0);
|
||||||
|
DECL_SYSCALL_ARG(size_t, length, arg1);
|
||||||
|
DECL_SYSCALL_ARG(int, prot, arg2);
|
||||||
|
DECL_SYSCALL_ARG(int, flags, arg3);
|
||||||
|
DECL_SYSCALL_ARG(int, fd, arg4);
|
||||||
|
DECL_SYSCALL_ARG(off_t, offset, arg5);
|
||||||
|
ret = (long) occlum_mmap(addr, length, prot, flags, fd, offset);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case SYS_munmap: {
|
||||||
|
DECL_SYSCALL_ARG(void*, addr, arg0);
|
||||||
|
DECL_SYSCALL_ARG(size_t, length, arg1);
|
||||||
|
ret = occlum_munmap(addr, length);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case SYS_mremap: {
|
||||||
|
DECL_SYSCALL_ARG(void*, old_addr, arg0);
|
||||||
|
DECL_SYSCALL_ARG(size_t, old_size, arg1);
|
||||||
|
DECL_SYSCALL_ARG(size_t, new_size, arg2);
|
||||||
|
DECL_SYSCALL_ARG(int, flags, arg3);
|
||||||
|
DECL_SYSCALL_ARG(void*, new_addr, arg4);
|
||||||
|
ret = (long) occlum_mremap(old_addr, old_size, new_size, flags, new_addr);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case SYS_brk: {
|
||||||
|
DECL_SYSCALL_ARG(void*, addr, arg0);
|
||||||
|
ret = (long) occlum_brk(addr);
|
||||||
|
break;
|
||||||
|
}
|
||||||
default:
|
default:
|
||||||
ret = occlum_unknown(num);
|
ret = occlum_unknown(num);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
@ -1,5 +1,8 @@
|
|||||||
use prelude::*;
|
use prelude::*;
|
||||||
use std::{fmt};
|
use std::{fmt};
|
||||||
|
use file_table::{FileDesc};
|
||||||
|
use fs::{off_t};
|
||||||
|
use process::{Process, ProcessRef, get_current};
|
||||||
|
|
||||||
// TODO: Rename VMSpace to VMUniverse
|
// TODO: Rename VMSpace to VMUniverse
|
||||||
|
|
||||||
@ -13,8 +16,43 @@ mod process_vm;
|
|||||||
pub use self::vm_range::{VMRange, VMRangeTrait};
|
pub use self::vm_range::{VMRange, VMRangeTrait};
|
||||||
pub use self::process_vm::{ProcessVM};
|
pub use self::process_vm::{ProcessVM};
|
||||||
|
|
||||||
pub const PAGE_SIZE : usize = 4096;
|
// TODO: separate proc and flags
|
||||||
|
// TODO: accept fd and offset
|
||||||
|
pub fn do_mmap(addr: usize, size: usize, flags: VMAreaFlags)
|
||||||
|
-> Result<usize, Error>
|
||||||
|
{
|
||||||
|
let current_ref = get_current();
|
||||||
|
let mut current_process = current_ref.lock().unwrap();
|
||||||
|
let current_vm = current_process.get_vm_mut();
|
||||||
|
current_vm.mmap(addr, size, flags)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn do_munmap(addr: usize, size: usize) -> Result<(), Error> {
|
||||||
|
let current_ref = get_current();
|
||||||
|
let mut current_process = current_ref.lock().unwrap();
|
||||||
|
let current_vm = current_process.get_vm_mut();
|
||||||
|
current_vm.munmap(addr, size)
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO: accept flags
|
||||||
|
pub fn do_mremap(old_addr: usize, old_size: usize, options: &VMResizeOptions)
|
||||||
|
-> Result<usize, Error>
|
||||||
|
{
|
||||||
|
let current_ref = get_current();
|
||||||
|
let mut current_process = current_ref.lock().unwrap();
|
||||||
|
let current_vm = current_process.get_vm_mut();
|
||||||
|
current_vm.mremap(old_addr, old_size, options)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn do_brk(addr: usize) -> Result<usize, Error> {
|
||||||
|
let current_ref = get_current();
|
||||||
|
let mut current_process = current_ref.lock().unwrap();
|
||||||
|
let current_vm = current_process.get_vm_mut();
|
||||||
|
current_vm.brk(addr)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
pub const PAGE_SIZE : usize = 4096;
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub struct VMSpace {
|
pub struct VMSpace {
|
||||||
|
@ -145,6 +145,7 @@ impl ProcessVM {
|
|||||||
self.get_stack_vma().get_end()
|
self.get_stack_vma().get_end()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TODO: override the mmaping of already mmaped range
|
||||||
pub fn mmap(&mut self, addr: usize, size: usize, flags: VMAreaFlags)
|
pub fn mmap(&mut self, addr: usize, size: usize, flags: VMAreaFlags)
|
||||||
-> Result<usize, Error>
|
-> Result<usize, Error>
|
||||||
{
|
{
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
CUR_DIR := $(shell dirname $(realpath $(lastword $(MAKEFILE_LIST))))
|
CUR_DIR := $(shell dirname $(realpath $(lastword $(MAKEFILE_LIST))))
|
||||||
PROJECT_DIR := $(realpath $(CUR_DIR)/../)
|
PROJECT_DIR := $(realpath $(CUR_DIR)/../)
|
||||||
|
|
||||||
TEST_SUITES := empty hello_world
|
TEST_SUITES := empty hello_world malloc
|
||||||
BUILD_TEST_SUITES := $(TEST_SUITES:%=%)
|
BUILD_TEST_SUITES := $(TEST_SUITES:%=%)
|
||||||
RUN_TEST_SUITES := $(TEST_SUITES:%=run-%)
|
RUN_TEST_SUITES := $(TEST_SUITES:%=run-%)
|
||||||
CLEAN_TEST_SUITES := $(TEST_SUITES:%=clean-%)
|
CLEAN_TEST_SUITES := $(TEST_SUITES:%=clean-%)
|
||||||
|
4
test/malloc/Makefile
Normal file
4
test/malloc/Makefile
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
include ../test_common.mk
|
||||||
|
|
||||||
|
EXTRA_C_FLAGS :=
|
||||||
|
EXTRA_LINK_FLAGS :=
|
16
test/malloc/main.c
Normal file
16
test/malloc/main.c
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
#include <stdlib.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
|
#define MAX_SIZE (1*1024*1024)
|
||||||
|
#define MIN_SIZE 8
|
||||||
|
|
||||||
|
int main(void) {
|
||||||
|
printf("Testing malloc and free...\n");
|
||||||
|
for (size_t buf_size = MIN_SIZE; buf_size <= MAX_SIZE; buf_size *= 4) {
|
||||||
|
printf("buf_size = %lu\n", buf_size);
|
||||||
|
void* buf = malloc(buf_size);
|
||||||
|
free(buf);
|
||||||
|
}
|
||||||
|
printf("Done.\n");
|
||||||
|
return 0;
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user