Helper function to safely read a structure from a stream

Let's say we have an OS of a single address space. To maintain stability, we need to enforce memory protection for user applications, for example. disallow the use of the "unsafe" keyword if the user has no accessibility.

Our users should be able to safely read / write arbitrary structures from / to byte streams (e.g. files). Of course, we are talking about structures that do not contain references (otherwise we lose memory safety).

Now I tried to implement a generic read function like this:

#![feature(core)]

use std::io;
use std::mem;
use std::raw;

fn read<T>(reader: &mut io::Read, dest: &mut T) -> io::Result<usize> {
    let slice = raw::Slice{ data:dest, len:mem::size_of::<T>() };
    let buf: &mut [u8] = unsafe { mem::transmute(slice) };
    reader.read(buf)
}

      

The implementation above has a major problem. It allows you to read structures containing links. So how can I fix this?

+3


source to share


1 answer


You can use what is known as a bullet point: a custom unsafe flag with a default value for all types and a negative flag for all links. Since you prohibit all uses unsafe

, the user cannot implement the trait on their own, and therefore there cannot be an implementation of the trait for any referenced type.

Probably, you should also include raw pointers ( *mut

and *const

) in the negative implication ... otherwise the user can deserialize Vec

, or any other "safe" type with internal insecurity.

#![feature(optin_builtin_traits)]

unsafe trait NoInnerRefs {}

impl<'a, T> !NoInnerRefs for &'a T {}
unsafe impl NoInnerRefs for .. {}

struct A(&'static str);

struct B(i32);

fn test<T: NoInnerRefs>(_: T) {
}

fn main() {
    test(B(5));
    test(A("hi"));
}

      



This won't compile:

<anon>:17:5: 17:9 error: the trait `NoInnerRefs` is not implemented for the type `&'static str` [E0277]
<anon>:17     test(A("hi"));
              ^~~~

      

+5


source







All Articles