[Date Prev][Date Next] [Thread Prev][Thread Next] [Date Index] [Thread Index]

Re: unowned processes and who controls them (was: Re: passwd entry for uid -1



Oystein Viggen <oysteivi@tihlde.org> writes:

> What do you mean with *completely unmodified* here?  Do you mean that if
> I would compile bsd-ftpd today, it would be able to use your capability
> service out of the box in two years without changing any source or even
> recompiling? (provided the library APIs and ABIs are stable, and that
> somebody actually wrote that capability thing, of course).

Exactly, it just needs to link dynamically to glibc, and glibc abi
needs to be stable.

> The current implementation in bsd-ftpd, and I think most ftpds, is that
> you run the daemon with full root access, fork() at logins, and when
> somebody has successfully authenticated themselves, "their" server
> process will seteuid() to the user, keeping 0 as the saved id.

I'm thinking of anonymous ftp service only. In my book, changing the
effective uid but keeping a root real uid is *NOT* to "drop
privileges". I'm comparing with hacks like having a www-server start
with root privileges, bind port 80, and then change the *real* uid to
nobody. Like the "permenently change uid" option in Roxen.

With a decent capabilities feature like we're discussing here, you
would run an anonymous ftp server with the special capability of
making connections with port 20 as the source port, and *no* special
privileges besides that. In particular, the process should not run
with the capability of reading all users' private files. That's one
thing you can't do on a traditional unix. I'm not sure if you can do
that with linux' capabilities.

> When the server needs to open port 20, it will seteuid(0), ...

Using seteuid requires root privileges (real uid = 0). So that's out
of the question for a hurd process running with an empty set of uids.

> Capabilities handle this nicely, can keep a clear effective set most
> of the time and have only the capability for opening low ports in
> your permitted set, copying it to the effective set when needed.

I see. If I understand you correctly, capabilities in linux only apply
to root processes. You can run a process as root but with most
capabilites stripped away, and switch back and forth between root euid
and the euid of your choice (assuming you have enough capabilities to
call seteuid).

That's not at all how I think about capabilities. A "capability" is
the abaility to do certain things on the system. When logged on on the
Hurd, by default you have the capability of authenticating as a
certain user (this is represented as a port right to the auth-server).
And when you apply this capability to proc and filesystem servers, you
get all capabilities of that user, like reading and writing certain
files, controlling certain other processes, etc.

When you drop that capability, you drop ordinary unix access control,
so if you need to do things to the system at all, you need smaller
capabilites for the things you need to be able to to, like the "listen
on port 21" and "connect from port 20" capabilities.

The good thing about this approach is that you don't need to be root
to use it. Of course, if only root can bind low port, you need some
cooperation with root to get to the example capabilities above. But
there are other capabilities that you already have that you may want
to delegate.

For instance, you could run a shell server that allows anybody to get
a shell on your system, but with capabilities stripped down so that
the only parts of the filesystem the shell processes can get to is
certain files or directories in your $HOME. And you don't need any
root access to set that up.

> I guess it is possible to make setxuid(), socket(), open(), and most
> other functions in glibc understand and make use of this capability
> service.  This would at least work for dynamically linked libraries, but
> I believe it would be a quite intrusive to libc, and I have not made my
> mind up yet as to whether I really like it...

You wouldn't actually have to hack glibc, you could simply use
LD_PRELOAD to override certain functions in it. But then it's not
really simple anymore.

/Niels



Reply to: