jD91mZM2 6 lat temu
rodzic
commit
face6f07f3

+ 1 - 0
Cargo.lock

@@ -247,6 +247,7 @@ dependencies = [
  "ralloc 1.0.0",
  "redox_syscall 0.1.40 (registry+https://github.com/rust-lang/crates.io-index)",
  "sc 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)",
+ "spin 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)",
 ]
 
 [[package]]

+ 6 - 0
include/bits/sys/mman.h

@@ -0,0 +1,6 @@
+#ifndef _BITS_SYS_MMAN_H
+#define _BITS_SYS_MMAN_H
+
+#define MAP_FAILED ((void *) -1)
+
+#endif

+ 5 - 1
include/limits.h

@@ -1,7 +1,11 @@
 #define MB_LEN_MAX 4 // unicode
 
 #define CHAR_BIT __CHAR_BIT__
-#define CHAR_MAX __CHAR_MAX__
+#ifdef __CHAR_MAX__
+# define CHAR_MAX __CHAR_MAX__
+#else
+# define CHAR_MAX 0xFF
+#endif
 #define CHAR_MIN 0
 #define INT_MAX __INT_MAX__
 #define INT_MIN (-INT_MAX - 1)

+ 2 - 0
include/stddef.h

@@ -10,4 +10,6 @@ typedef int32_t wchar_t;
 
 typedef unsigned long long size_t;
 
+#define offsetof(type, member) __builtin_offsetof(type, member)
+
 #endif /* _STDDEF_H */

+ 1 - 0
src/fcntl/src/linux.rs

@@ -10,3 +10,4 @@ pub const O_APPEND: c_int = 0o2000;
 pub const O_CLOEXEC: c_int = 0o2_000_000;
 pub const O_DIRECTORY: c_int = 0o200_000;
 pub const O_EXCL: c_int = 0o200;
+pub const O_NONBLOCK: c_int = 0o4000;

+ 1 - 0
src/platform/Cargo.toml

@@ -13,3 +13,4 @@ sc = "0.2"
 
 [target.'cfg(target_os = "redox")'.dependencies]
 redox_syscall = "0.1"
+spin = "0.4"

+ 6 - 3
src/platform/src/lib.rs

@@ -6,13 +6,16 @@
 #[cfg_attr(target_os = "redox", macro_use)]
 extern crate alloc;
 
-#[cfg(all(not(feature = "no_std"), target_os = "linux"))]
+#[cfg(target_os = "linux")]
 #[macro_use]
 extern crate sc;
 
-#[cfg(all(not(feature = "no_std"), target_os = "redox"))]
+#[cfg(target_os = "redox")]
 extern crate syscall;
 
+#[cfg(target_os = "redox")]
+extern crate spin;
+
 pub use allocator::*;
 
 #[cfg(not(feature = "ralloc"))]
@@ -38,7 +41,7 @@ pub mod types;
 
 pub use rawfile::RawFile;
 
-use alloc::Vec;
+use alloc::vec::Vec;
 use core::{fmt, ptr};
 
 use types::*;

+ 15 - 0
src/platform/src/linux/mod.rs

@@ -284,6 +284,21 @@ pub fn mkfifo(path: *const c_char, mode: mode_t) -> c_int {
     e(unsafe { syscall!(MKNODAT, AT_FDCWD, path, mode, 0) }) as c_int
 }
 
+pub unsafe fn mmap(
+    addr: *mut c_void,
+    len: usize,
+    prot: c_int,
+    flags: c_int,
+    fildes: c_int,
+    off: off_t,
+) -> *mut c_void {
+    e(syscall!(MMAP, addr, len, prot, flags, fildes, off)) as *mut c_void
+}
+
+pub unsafe fn munmap(addr: *mut c_void, len: usize) -> c_int {
+    e(syscall!(MUNMAP, addr, len)) as c_int
+}
+
 pub fn nanosleep(rqtp: *const timespec, rmtp: *mut timespec) -> c_int {
     e(unsafe { syscall!(NANOSLEEP, rqtp, rmtp) }) as c_int
 }

+ 47 - 3
src/platform/src/redox/mod.rs

@@ -1,9 +1,9 @@
 //! sys/socket implementation, following http://pubs.opengroup.org/onlinepubs/009696699/basedefs/sys/socket.h.html
 
+use alloc::btree_map::BTreeMap;
 use core::fmt::Write;
-use core::mem;
-use core::ptr;
-use core::slice;
+use core::{mem, ptr, slice};
+use spin::{Once, Mutex, MutexGuard};
 use syscall::data::Stat as redox_stat;
 use syscall::data::TimeSpec as redox_timespec;
 use syscall::flag::*;
@@ -13,10 +13,17 @@ use types::*;
 use *;
 
 const EINVAL: c_int = 22;
+const MAP_ANON: c_int = 1;
 
 #[thread_local]
 static mut SIG_HANDLER: Option<extern "C" fn(c_int)> = None;
 
+static ANONYMOUS_MAPS: Once<Mutex<BTreeMap<usize, usize>>> = Once::new();
+
+fn anonymous_maps() -> MutexGuard<'static, BTreeMap<usize, usize>> {
+    ANONYMOUS_MAPS.call_once(|| Mutex::new(BTreeMap::new())).lock()
+}
+
 extern "C" fn sig_handler(sig: usize) {
     if let Some(ref callback) = unsafe { SIG_HANDLER } {
         callback(sig as c_int);
@@ -640,6 +647,43 @@ pub fn mkfifo(path: *const c_char, mode: mode_t) -> c_int {
     }
 }
 
+pub unsafe fn mmap(
+    _addr: *mut c_void,
+    len: usize,
+    _prot: c_int,
+    flags: c_int,
+    fildes: c_int,
+    off: off_t,
+) -> *mut c_void {
+    if flags & MAP_ANON == MAP_ANON {
+        let fd = e(syscall::open("memory:", 0)); // flags don't matter currently
+        if fd == !0 {
+            return !0 as *mut c_void;
+        }
+
+        let addr = e(syscall::fmap(fd, off as usize, len as usize));
+        if addr == !0 {
+            let _ = syscall::close(fd);
+            return !0 as *mut c_void;
+        }
+
+        anonymous_maps().insert(addr as usize, fd);
+        addr as *mut c_void
+    } else {
+        e(syscall::fmap(fildes as usize, off as usize, len as usize)) as *mut c_void
+    }
+}
+
+pub unsafe fn munmap(addr: *mut c_void, _len: usize) -> c_int {
+    if e(syscall::funmap(addr as usize)) == !0 {
+        return !0;
+    }
+    if let Some(fd) = anonymous_maps().remove(&(addr as usize)) {
+        let _ = syscall::close(fd);
+    }
+    0
+}
+
 pub fn nanosleep(rqtp: *const timespec, rmtp: *mut timespec) -> c_int {
     let redox_rqtp = unsafe { redox_timespec::from(&*rqtp) };
     let mut redox_rmtp: redox_timespec;

+ 1 - 0
src/sys_mman/cbindgen.toml

@@ -1,5 +1,6 @@
 sys_includes = ["stdint.h", "sys/types.h"]
 include_guard = "_SYS_MMAN_H"
+trailer = "#include <bits/sys/mman.h>"
 language = "C"
 style = "Tag"
 

+ 6 - 6
src/sys_mman/src/lib.rs

@@ -24,8 +24,8 @@ pub extern "C" fn mlockall(flags: c_int) -> c_int {
     unimplemented!();
 }
 
-// #[no_mangle]
-pub extern "C" fn mmap(
+#[no_mangle]
+pub unsafe extern "C" fn mmap(
     addr: *mut c_void,
     len: usize,
     prot: c_int,
@@ -33,7 +33,7 @@ pub extern "C" fn mmap(
     fildes: c_int,
     off: off_t,
 ) -> *mut c_void {
-    unimplemented!();
+    platform::mmap(addr, len, prot, flags, fildes, off)
 }
 
 // #[no_mangle]
@@ -56,9 +56,9 @@ pub extern "C" fn munlockall() -> c_int {
     unimplemented!();
 }
 
-// #[no_mangle]
-pub extern "C" fn munmap(addr: *mut c_void, len: usize) -> c_int {
-    unimplemented!();
+#[no_mangle]
+pub unsafe extern "C" fn munmap(addr: *mut c_void, len: usize) -> c_int {
+    platform::munmap(addr, len)
 }
 
 // #[no_mangle]

+ 2 - 0
src/sys_mman/src/linux.rs

@@ -7,3 +7,5 @@ pub const PROT_NONE: c_int = 0x0;
 
 pub const MAP_SHARED: c_int = 0x1;
 pub const MAP_PRIVATE: c_int = 0x2;
+pub const MAP_ANON: c_int = 0x20;
+pub const MAP_ANONYMOUS: c_int = MAP_ANON;

+ 10 - 0
src/sys_mman/src/redox.rs

@@ -1 +1,11 @@
+use platform::types::*;
 
+pub const PROT_READ: c_int = 0;
+pub const PROT_WRITE: c_int = 0;
+pub const PROT_EXEC: c_int = 0;
+pub const PROT_NONE: c_int = 0;
+
+pub const MAP_SHARED: c_int = 0;
+pub const MAP_PRIVATE: c_int = 0;
+pub const MAP_ANON: c_int = 1;
+pub const MAP_ANONYMOUS: c_int = MAP_ANON;