[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Initial target(s) for libmob (was Re: Improving object mobility within t
Carl Fredrik Hammar
Initial target(s) for libmob (was Re: Improving object mobility within the Hurd)
Fri, 29 May 2009 16:18:55 +0200
I was going to refute your suggestion of ioctl handlers, but in arguing
about it back and forth with myself, I ended up agreeing with you. ;-)
As such this mail became a good bit longer than intended, feel free to
just skim through most of this first part.
I will answer the rest of your mail seperatly.
On Thu, May 21, 2009 at 06:44:59PM +0200, olafBuddenhagen@gmx.net wrote:
> > > These stubs are individual for every ioctl: to support a new type of
> > > device, new stubs need to be added to libc -- which is obviously
> > > painful. Would be nice to have a mechanism that loads the stubs
> > > dynamically from some external source.
> > Yes, but transforming ioctls to RPCs seems totally independent of the
> > server.
> No, not really. The more I think about it, the more I'm convinced that
> it is actually inherently bound to the server.
> ioctl()s are always specific to a particular device class, and thus the
> server(s) implementing (or proxying) it. It makes perfect sense for a
> server implementing a specific device, also to provide the ioctl
> wrappers necessary to access it.
I agree that ioctls are device specific, but not that they are specific
to the server. If the client makes use of an ioctl, then it must be
aware of the device class as well. A header must be provided that
defines macros for the ioctl numbers, it does not seem unreasonable to
also provide a module with the corresponding handlers at the same time.
Investigating ioctls a bit closer it seems that glibc already provides
some provisions to register additional handlers. I think its possible to
do everything needed from a linked object file by simply linking to it,
i.e. without any function calls.
(Curiously there is a hurd_register_ioctl_handler function declared to
do this at runtime as well, but it does not actually seem to be defined
The only real problem here is that we are required to link the application
with the specific handler library. A step that isn't needed on other
OSes. Rather it should be enough to link with glibc, and for easy
extensibility no change to glibc should be required to add new ioctls.
This means glibc has to dynamically link with an ioctl handler module.
Which leaves the question of how to find it.
Broadly speaking there are only two options; either the device specifies
it or a system service does. The system service can be quite mundane,
as my original suggestion of simply loading a library based on the device
class name. Note that the name would have to be encoded into the ioctl
number, or looked up in a file e.g. /etc/ioctltab, otherwise glibc would
need to be hacked in order to add new device classes. It could also be
a more sophisticated system server, possibly giving out handlers using
libmob as in your suggestion.
Lets look at this from the perspective of a non-root user who wants to
provide a device of a new device class. This is the sort of thing the
Hurd is all about. ;-)
In the system case, the user would need to override the system service,
which could be as simple as exporting LD_LIBRARY_PATH, or pretty nasty
if the ioctl module must be looked up in a file or a server, which
would involve a chroot if there are no other provisions for overriding
In the device case, the user would need to make sure libmob can determine
that the module can be trusted, e.g. by defining LD_LIBRARY_PATH, or
twiddle with the file permissions, or whatever we decide.
At this point it is at least clear that we can rule out the system
case with name look up, as it would definitely be more complicated to
override it. And the other two cases are either tied or the device case
is superior, depending on how libmob determines trust.
One issue with encoding the handler module name in the ioctl is that
it requires changing the current numbering convention. (At least if
we want more than a single letter.) I believe the numbering should be
changed anyway, as it's currently over-complicated. But breaking glibc
ABI over ioctls is a hard pill to swallow...
Another interesting issue is ioctl clashes, i.e. that two distinct ioctls
share the same number but differ in semantics and possibly parameters
and their types.
Clashes are inherently bad. Sending an ioctl to a device that supports a
clashing ioctl will at best confuse the client, and at worst make it make
it segfault. Perhaps the latter is preventable, by somehow inspecting
the process' memory mapping or handling the signal, but I'm pretty sure
the confusion is unavoidable.
However, that they should be avoided does not necessarily mean they will
be avoided. And if we let users provide their own ioctls, it is likely
it will happen at some point. Such a situation should be fixed, but such
a situation might not be discovered immediately, and fixes takes time.
This leaves us with how to handle the interim period.
Currently, glibc seems to assume that there are no clashes, it just uses
the first handler it finds that claims to handle a particular ioctl.
In the system case, it will mean that one of the ioctls is always
preferred over the other. If a user overrides the system, then the
other ioctl will always be preferred. In the end neither client or
server has any control.
In the device case, the ioctl handler from the first device used will
be used. Still not an ideal situation, but chances are better that
the client wishes to use the ioctl of a device it has actually tried
to use. Though, it will fail if it first tries a device that implements
a clashing ioctl and then use one that implements the wanted ioctl.
It also can never use more than one of the clashing ioctls.
The only way to handle clashes is they would be on other OSes would be
to keep distinct ioctl handlers for each file descriptor. This would
make use of proper mobile objects, and not just the same code loading
mechanism. Though the objects would be trivial, and only used as function
This would require changing how ioctl are handled in glibc, but I believe
the end result would be simpler and less reliant on linker magic, such
as the use of symbol lists.
It seems both variants of device supplied ioctl handlers are superior
to system supplied ioctl handlers. And we would start by implementing
the first variant in any case, so the final decision to implement FD
specific handlers can be postponed.
> In fact, I believe now that this is an ideal initial target for the
> mobility framework: while it won't employ all aspects of the framework,
> it is simple, well-defined, and obviously useful. Much better than
> aiming at moving targets like sound or networking; or even trying to
> design the framework on a purely theoretical ground, without
> implementing any actual use cases at all...
After looking more closely at the problem, I agree that this is a good
initial use-case. It would mainly exercise the code loading mechanism,
and if we go for the FD specific handles, also the object system's
method dispatch. Notably, authority verification isn't needed for this
and there is no need for transparency.
However, I also want to get a thesis out of this and I don't think server
loaded ioctl handlers would be enough on their own.
My initial use-case so far has been to use mobile objects for
optimization, i.e. to use a local copy of an object to avoid RPCs in a
transparent fashion. Though the idea was that the mobility framework
would handle general issues faced with mobile objects.
Though optimization might not be worth the extra complications involved
it would be interesting to find out what kind of speed up we can get.
It's also nice in that the requirements for security and transparency
are probably higher than use-cases that would require mobility. Thus
mechanisms used for optimization can safely be used by other use-cases
without much further analysis. So even if we do not use mobile objects
for pure optimization, we still get useful mechanisms as a side-effect.
As such I have been considering refocusing my thesis solely on the
optimization use-case. However, it would be hard to fit ioctls in
to this. Though I guess I could state that the long term goal is a
general mobility framework, but that I choose to focus on two immediate
use-cases. Or I could just implement ioctls and then simply not mention
it in my thesis.
However, I would like to finish my thesis before the next opportunity
to hand it in for review, which is September 2. So I'm mostly worried
that implementing ioctls will keep me from completing it on time.
(Though, there will be other opportunities of course.)
I will think on it further and discuss it with my supervisor. In the
mean time, what do you think of it?
> BTW, I meant to ask for a while now, but always forgot: do you have any
> problems with IRC? I think it would be very useful if you could join one
> of the GSoC IRC meetings, or simply try to catch me on IRC at another
> time -- I'm sure many of these things are much easier to discuss
Mostly because of unfamiliarity with IRC. Though I did use it a brief
time about a year ago for a university group project. It seems it was
on freenode, because it seems my nick is registered there, though I have
forgotten my password. :-(
In any case I'll start lurking while I'm working on my thesis. And I'll
try to make it to today's meeting.