I’ve been pondering a project for about a year now, and I may be ready to finally start coding the beast. The basic idea is you run a process in a jail where it’s completely isolated from the system, except where you let it interact.
The interface is of course through syscalls like open() and connect(). The jail would let you set up a sort of ACL per-process of what syscalls it can make and which it can’t. Think ZoneAlarm, only we’re talking everything, not just network access. But that’s not the real kicker.
This all happens in userspace, and doesn’t require root access.
My idea is to code a preload library that captures all of the important system calls, like open(), connect(), bind(), etc. Some daemon will run on the user’s desktop, and every system call will be sent over a socket to that daemon. Upon receiving the call, the daemon will look in its access tables and send back a message to “proceed” or “fail with this errno.” The daemon may even ask the user in realtime if the call should succeed.
I started coding a Gtk# frontend but stopped after realizing that the network protocol for this baby is going to suck.
Even more challenging will be keeping the process completely jailed. All a process needs to do is unset LD_PRELOAD and spawn another copy of itself and it’s home free. So I’ll need to capture things like setenv() and look for other mechanisms for setting LD_PRELOAD for new processes and make sure that the library remains in that variable and in the front. In short, finding loopholes around it will be relatively simple. Some harmless program may even clobber LD_PRELOAD to perform some similar trick. So that will be another fun aspect of this project.
Perhaps more challenging would be allowing the daemon to alter the call arguments. While powerful, there is simply no good way to represent a void* over a socket.
But if it works… think about it. Your desktop environment could be started with this library preloaded, and then every process started from the desktop could be controlled.
The applications of this go far beyond security. You could deny your web browser access to your sound card to suppress those cute little songs and noises some sites like to play. You could deny all processes access to some directory unless you authenticate to the daemon. (Not exactly real security, but a fine deterrent against unskilled relatives.)
But we’ll see what happens…
And how would you prevent the program from removing the preload hooks, remapping the preload library readwrite and change it’s code, calling the kernel directly w/o going through libc etc.?
You wouldn’t easily be able to prevent code specifically designed to bypass the library. It’s more intended to provide a quick preview of the system and to secure programs that are well-intended (e.g. your web browser) but that you want more control over.
Kind of like a Mac, eh?
Not really like a Mac, no. I don’t recall seeing any Mac that can prompt you for permission whenever any program wants access to a file in a certain directory, for example. The control is much more fine-grained.
it’s called chroot … see the man page
@bill, chroot is only a filesystem jail. This project (in its currently-existing form) allows jailing of, for example, network resources as well, so that each DNS lookup or connection attempt by the process must be authorized by the user.