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

Bug#965091: glibc: setgroups: Bad address [2.31/x32, regression from 2.30]



[H.J. Lu Cc'ed as author of what looks like the problematic commit]

On Wed, 15 Jul 2020 23:47:27 +0200 (CEST) Thorsten Glaser <t.glaser@tarent.de> wrote:
> Some more analysis:
> 
> We enter libc from openssh code with the correct values in rsi and rdi:
> 
> 
> (gdb) u
> => 0x56560e45 <main+12661>:     call   0x5655d0b0 <setgroups@plt>
> (gdb) info r
> rax            0xfffe              65534
> rbx            0x5663a000          1449369600
> rcx            0x0                 0
> rdx            0x0                 0
> rsi            0xffffd2e0          4294955744
> rdi            0x1                 1
> rbp            0x56641b50          1449401168
> rsp            0xffffd260          4294955616
> r8             0x0                 0
> r9             0x0                 0
> r10            0xf7a88888          4155017352
> r11            0x246               582
> r12            0x565d71d1          1448964561
> r13            0x3                 3
> r14            0xe2cc              58060
> r15            0x5663c730          1449379632
> rip            0x56560e45          1448480325
> eflags         0x282               [ SF IF ]
> cs             0x33                51
> ss             0x2b                43
> ds             0x2b                43
> es             0x2b                43
> fs             0x0                 0
> gs             0x0                 0
> 
> 
> Inside glibc, there’s an indirect call:
> 
> 
> => 0xf79949f4 <__GI_setgroups+100>:     call   rax
> rax            0xf7833500          4152571136
> => 0xf7833500 <__nptl_setxid>:  push   r15
> 
> 
> Some time in __nptl_setxid later, here’s the bug:
> 
> 
> 1162    in allocatestack.c
> rax            0xf77ca840          4152141888
> rbx            0xffffd230          4294955568
> rcx            0x0                 0
> rdx            0x1                 1
> rsi            0xffffd2e0          4294955744
> rdi            0xf77ca840          4152141888
> rbp            0xf77ca840          4152141888
> rsp            0xffffd1d0          4294955472
> r8             0x0                 0
> r9             0x0                 0
> r10            0xf77caac0          4152142528
> r11            0x246               582
> r12            0xf784a360          4152664928
> r13            0xf784a360          4152664928

Looks like df76ff3a446a787a95cf74cb15c285464d73a93d broke this upstream
(x32: Properly pass long to syscall [BZ #25810]).

setgroups uses INLINE_SETXID_SYSCALL, which in turn passes its
arguments through the various id fields in xid_command. Unfortunately,
those are `long int`, and so, when the `const gid_t *list` argument
gets later passed through INTERNAL_SYSCALL_NCS, it's treated as an
integer argument and thus sign-extended, despite actually being a
pointer. I think xid_command's id fields need to become __kernel_ulong
or equivalent, with ARGIFY happening inside INLINE_SETXID_SYSCALL when
it still knows what the types are.

Jess


Reply to: