On 07/25/2017 10:43 AM, ag0aep6g wrote:
On 07/25/2017 04:32 PM, Shachar Shemesh wrote:
And, indeed, the code calling "read" shouldn't be able to do that as @safe. Read itself, however, is trusted (because, let's face it, if you cannot trust the kernel, you're screwed anyways).

That's not how `@trusted` works. The point of `@trusted` is to allow unsafe features in the implementation. The interface must be just as safe as with `@safe`.

`read` doesn't have a safe interface. `read` is safe as long as long as you pass good arguments. When you pass bad arguments, `read` will break your stuff. A `@trusted` function must always be safe, no matter the arguments.

About http://man7.org/linux/man-pages/man2/read.2.html, there's just a bit of wrapping necessary:

nothrow @trusted @nogc
ssize_t read(int fd, ubyte[] buf)
{
    return read(fd, buf.ptr, buf.length);
}

(btw void[] doesn't work)

The point being that a safe D program needs to guarantee memory will not be corrupted, and there's no way for the type system to ensure that in the Posix read() call the buffer and the length are coordinated.

Certain systems (such as the static checker used at Microsoft - it's fairly well known, there are a couple of papers on it, forgot the name) require annotations in the function signature to indicate the coordination, e.g.:

ssize_t read(int fd, void *buf, @islengthof(buf) size_t count);

Then the type checker can verify upon each call that indeed count is the right size of buf.

A suite of safe wrappers on OS primitives might be useful.


Andrei

Reply via email to