Hi Jens,

Would you be able to comment please...

Thanks,

Michael

On Sun, Jul 29, 2012 at 8:32 AM, Michael Kerrisk (man-pages)
<mtk.manpa...@gmail.com> wrote:
> [CCing Jens because of the discussion below about IOPRIO_WHO_USER
> below; he may have a comment]
> [CCing Марк, who independently noted the lack of documentation for
> IOPRIO_WHO_PROCESS, who==0 .]
> [CCing Colin McCabe who sent other recent fixes for the ioprio_set.2 page]
>
> On Sat, Dec 17, 2011 at 11:26 PM, Kalle Olavi Niemitalo <k...@iki.fi> wrote:
>> Package: manpages-dev
>> Version: 3.32-0.2
>> Severity: wishlist
>> File: /usr/share/man/man2/ioprio_get.2.gz
>>
>> The ioprio_get(2) manual page describes the meanings of the which
>> and who parameters:
>>
>>> IOPRIO_WHO_PROCESS
>>>        who is a process ID identifying a single process.
>>>
>>> IOPRIO_WHO_PGRP
>>>        who is a process group ID identifying all the members of
>>>        a process group.
>>>
>>> IOPRIO_WHO_USER
>>>        who is a user ID identifying all of the processes that
>>>        have a matching real UID.
>>
>> The manual page should mention that IOPRIO_WHO_PROCESS and
>> IOPRIO_WHO_PGRP also allow who==0.
>
> Yes.
>
>> As implemented in
>> fs/ioprio.c, who==0 means the calling process or its process
>> group.  The ioprio program in util-linux already uses the
>> feature.  This is worth documenting separately because
>> e.g. tcsetpgrp does not treat pgrp==0 in that way.
>
> Agreed, this should be documented since various APIs interpret pgrp==0
> differently. Some (e.g., killpg(2)) are like this syscall, others are
> not.
>
>> For IOPRIO_WHO_USER, the situation is more complex: who==0 means
>> the root user in ioprio_set but the current user (I think the
>> real UID of the calling process) in ioprio_get.  (That
>> inconsistency might even be a bug.)
>
> So, I'm not sure I'm following the kernel code too well here...
> @Jens, your comments would be very welovem.
>
> In ioprio_get() (Linux 3.5 kernel source file fs/ioprio.c), I see the 
> following:
>
>                 case IOPRIO_WHO_USER:
>                         uid = make_kuid(current_user_ns(), who);
>                         if (!who)
>                                 user = current_user();
>                         else
>                                 user = find_user(uid);
>
>                         if (!user)
>                                 break;
>
>                         do_each_thread(g, p) {
>                                 if (!uid_eq(task_uid(p), user->uid))
>                                         continue;
>                                 tmpio = get_task_ioprio(p);
>                                 if (tmpio < 0)
>                                         continue;
>                                 if (ret == -ESRCH)
>                                         ret = tmpio;
>                                 else
>                                         ret = ioprio_best(ret, tmpio);
>                         } while_each_thread(g, p);
>
>                         if (who)
>                                 free_uid(user);
>                         break;
>
> In ioprio_set(), I see:
>
>                 case IOPRIO_WHO_USER:
>                         uid = make_kuid(current_user_ns(), who);
>                         if (!uid_valid(uid))
>                                 break;
>                         if (!who)
>                                 user = current_user();
>                         else
>                                 user = find_user(uid);
>
>                         if (!user)
>                                 break;
>
>                         do_each_thread(g, p) {
>                                 if (!uid_eq(task_uid(p), uid))
>                                         continue;
>                                 ret = set_task_ioprio(p, ioprio);
>                                 if (ret)
>                                         goto free_uid;
>                         } while_each_thread(g, p);
> free_uid:
>                         if (who)
>                                 free_uid(user);
>                         break;
>
> This suggests to me that you are right Kalle, in your interpretation
> of who==0 for the IOPRIO_WHO_USER, since ioprio_get() uses
> current_iser()->uid for its scan while ioprio_get() uses the UID
> returned by make_kuid() (So, to be precise, I think who==0 in this
> case means "the UID of the uer who is thye super user in this user
> namespace"). If that's correct, it does of course need to be
> documented. I'd be happy to get confirmation from Jens on this point.
>
> I suppose that the differing meaning of who==0 for IOPRIO_WHO_USER in
> ioprio_get() versus ioprio_set() is by design. But if so, like you
> Kalle, I agree that it's a design point that is likely to surprise
> users (and surprises here might have security implications). Again,
> I'd like to get input from Jens.
>
> In the meantime, I've applied the patch below to cover the other two cases.
>
> Thanks,
>
> Michael
>
> --- a/man2/ioprio_set.2
> +++ b/man2/ioprio_set.2
> @@ -56,10 +56,16 @@ is interpreted, and has one of the following values:
>  .B IOPRIO_WHO_PROCESS
>  .I who
>  is a process ID or thread ID identifying a single process or thread.
> +If
> +.I who
> +is 0, then operate on the calling thread.
>  .TP
>  .B IOPRIO_WHO_PGRP
>  .I who
>  is a process group ID identifying all the members of a process group.
> +If
> +.I who
> +is 0, then operate on the process group of which the caller is a member.
>  .TP
>  .B IOPRIO_WHO_USER
>  .I who
>
> --
> Michael Kerrisk
> Linux man-pages maintainer; http://www.kernel.org/doc/man-pages/
> Author of "The Linux Programming Interface"; http://man7.org/tlpi/



-- 
Michael Kerrisk
Linux man-pages maintainer; http://www.kernel.org/doc/man-pages/
Author of "The Linux Programming Interface"; http://man7.org/tlpi/


--
To UNSUBSCRIBE, email to debian-bugs-dist-requ...@lists.debian.org
with a subject of "unsubscribe". Trouble? Contact listmas...@lists.debian.org

Reply via email to