2006-05-01 18:02:12

by Jeff Dike

[permalink] [raw]
Subject: Re: [uml-devel] [RFC] PATCH 3/4 - Time virtualization : PTRACE_SYSCALL_MASK

On Sat, Apr 29, 2006 at 10:49:07AM +0200, Heiko Carstens wrote:
> IMHO this is way too complicated. Introducing a ptrace call that returns
> the number of syscalls and forcing user space to pass a complete bitmask
> is much easier. Also the semantics are much easier to understand.

This sounds more complicated than what we are proposing.

This would make the process care about the number of system calls
implemented by the kernel, which is something that doesn't even come
up in the normal case with the current interface. You only care about
it if you get a -EINVAL and want to figure out exactly why.

>From a practical point of view, you would want code that looks like
this:
n = nsyscalls();
mask = malloc((n + 7)/8);
if(mask == NULL)
return;

/* Zero mask, set bits, call ptrace */

free(mask);

rather than code like this:

int mask[(BIGGEST_SYSCALL_I_CARE_ABOUT + 7) / 8];

/* Zero mask, set bits, call ptrace */

That doesn't seem like an improvement to me.

The second case would be more complicated if it wanted to figure out
what the problem was if ptrace returned -EINVAL. However, some users
won't care, so that complexity is optional. For example, UML will
already know by other means what system calls are implemented on the
host, so it won't bother looking at the mask in the case of a
failure. I'm not sure what the right thing for strace is.

> In addition your proposal would already introduce a rather complicated
> interface to figure out how many syscalls the kernel has. I'm sure this
> will be (mis)used sooner or later.

How? And, if so, why is that a problem?

There are already complicated ways to figure out what system calls the
kernel has, and I don't recall them causing problems.

Jeff


2006-05-02 06:57:59

by Heiko Carstens

[permalink] [raw]
Subject: Re: [uml-devel] [RFC] PATCH 3/4 - Time virtualization : PTRACE_SYSCALL_MASK

> This sounds more complicated than what we are proposing.
>
> This would make the process care about the number of system calls
> implemented by the kernel, which is something that doesn't even come
> up in the normal case with the current interface. You only care about
> it if you get a -EINVAL and want to figure out exactly why.
>
> From a practical point of view, you would want code that looks like
> this:

Yes.

[1]
> n = nsyscalls();
> mask = malloc((n + 7)/8);
> if(mask == NULL)
> return;
>
> /* Zero mask, set bits, call ptrace */
>
> free(mask);
>

[2]
> rather than code like this:
>
> int mask[(BIGGEST_SYSCALL_I_CARE_ABOUT + 7) / 8];
>
> /* Zero mask, set bits, call ptrace */


> That doesn't seem like an improvement to me.
>
> The second case would be more complicated if it wanted to figure out
> what the problem was if ptrace returned -EINVAL. However, some users

That is actually my point. If you're checking for errors you will end up
first doing [2] and later on doing something like [1] anyway...

> > In addition your proposal would already introduce a rather complicated
> > interface to figure out how many syscalls the kernel has. I'm sure this
> > will be (mis)used sooner or later.
>
> How? And, if so, why is that a problem?

>From the proposal:

<snip>
> Semantics:
>
> in both cases, the mask is first zero-extended to the right (for syscalls not
> known to userspace), bits for syscall not known to the kernel are checked and
> the call fails if any of them is 1, and in the failure case E2BIG or
> EOVERFLOW is returned (I want to avoid EINVAL and ENOSYS to avoid confusion)
> and the part of the mask known to the kernel is 0-ed.
<snip>

So you just need to pass a large enough bitmask with all ones and the kernel
will put zeroes in the bitmask up to the bit number NR_sycalls - 1.
Counting the zeroes should work...