Why don't the safe file I/O operations panic when /proc/self/mem is opened for writing?
I understand why they don't want to make all of File I/O unsafe just for edge cases like this, but shouldn't this be handled at runtime?
Because you could just do the Rust equivalent of system("dd of=/proc/myprocess/mem ...") instead, so it would be security theater. Memory safety just isn't a part of the default Unix model.
Note the emphasis on "default" above; you can use the Linux sandboxing features such as seccomp-bpf to build a sandbox which is truly memory-safe, closing this hole. The OS is in charge of the features it exposes, and Rust can't do much about that.
Note also that the existence of totally_safe_transmute doesn't mean that Rust's memory safety features are pointless. Empirically, memory-safe programming languages result in far fewer memory safety vulnerabilities, because they make exploitation way harder.
Okay but why doesn’t Rust set up an LLM to analyze all output of the process and if it determines that the process is trying to communicate to the outside world that it intends to do something memory unsafe it pani
I've considered proposing this before, but presumably it's a cat and mouse game. Can the Rust stdlib reliably detect writes to /proc/mem in the face of links and raw FDs? And it probably should be reliable, because nobody writes to /proc/mem by accident.
And even then, it doesn't help with whole-system security when every program in every other language on your system, including safe ones like Java and Python, have the same capability. (Although if I'm wrong that there's no precedence for languages attempting to block this, I'd love to see the prior art.)
It’s not just /proc/sys/mem. One could also modify executable files and cause all manner of other mayhem. At the end of they, if you have access to all ambient privileges available to your process, you can use them. Trying to specifically block memory safety violations would be a bit odd.
Not if they’re not running or if you replace them outright. So you can rename a garbage file over your main executable, exec yourself, and segfault. Is that memory unsafety?
How about ptracing yourself?
How about undervolting your CPU such that it malfunctions?
How about running your program off a FUSE filesystem that changes the contents out from under it?
How about editing the raw block device you’re running from?
How about modifying /dev/mem on older systems that allow that?
This particular rabbit hole is extremely deep, and I don’t think it’s practical to address it for real short of making a real security model for what running code may and may not to do the rest of the world. (I think doing that is an extremely worthwhile endeavor, but disallowing opening specific files won’t be part of it.)
In case anyone else was wondering if this was an acronym for an aphorism (like YAGNI), this is an error code (error text busy). And 'text' refers to the executable
Rust is not a sandbox language like JS. It only catches accidental programming errors, and it's improbable that someone would write a hack via /proc/self/mem by mistake.
> Also, what if you really want do access this and it panics?
That's the easy part, you'd provide some OS-specific API for getting this file handle, call it `std::os::fs::proc()` or thereabouts, and make it an `unsafe` function. The "hard to do" is the bigger problem, because if you're providing an unsafe alternative then you'd like to plug all the holes in the safe interface, which AFAIK is non-trivial.
Note the emphasis on "default" above; you can use the Linux sandboxing features such as seccomp-bpf to build a sandbox which is truly memory-safe, closing this hole. The OS is in charge of the features it exposes, and Rust can't do much about that.
Note also that the existence of totally_safe_transmute doesn't mean that Rust's memory safety features are pointless. Empirically, memory-safe programming languages result in far fewer memory safety vulnerabilities, because they make exploitation way harder.