This is the mail archive of the
mailing list for the glibc project.
Re: Friendlier EPERM - Request for input
On Sun, Jan 20, 2013 at 04:00:46PM -0800, Eric W. Biederman wrote:
> Let me propose a different mechanism for getting this to user space
> that gives you a save/restore ability.
> When a system call returns with an error we return the error code
> in one register and leave the rest of the registers that calling
> conventions allow us to stomp unchanged.
> On i386 (probabaly our most constraint architecture) that gives us
> 4 32bit registers or 16 bytes/characters to play with.
On i386, there are no extra registers. All of them are
syscall-preserved. This cannot be changed. On some other archs you
have registers free, but it's very arch-specific.
> Returning either an exteneded error number or a short
> string in those extra bytes should be very doable, and largely
> backwards compatible.
> Then in userspace for those applications who care you can
> have a "struct exteneded_error" that holds the extra information.
How would you propose getting them from registers into a struct the
caller can see? If the syscall wrapper in libc does this, then the
exact same signal handler issue arises again: it will get clobbered if
a syscall is made in a signal handler. If the syscall wrapper in libc
isn't what does it, then the only other way would be to write inline
asm syscalls into the caller. This is obviously hideous.
> To use that information I expect you want something like:
> char *explain_error(int (*failed_func)(...), int errno, struct extended_error *error);
> Where explain_error could possibly deduce things even if there
> is no side channel information in the kernel. (i.e. You got EPERM
> because the permissions are 0700 and you don't own the file.)
> Having the core information returned in registers (that are saved by
> signal handling) and having a structure of a fixed size that you can
> save and restore should help.
As I have explained above, this does not work for multiple reasons.