An explanation of the exploit (not by me) is at
<https://news.ycombinator.com/item?id=16762794>:

    My speculation on the race condition fixed in the patch:

        The while loop in `main` calls `play_beep` multiple times. Each call
        to `play_beep` opens the `--device` and sets the global
        `console_fd`, and then sets the global `console_type` based on the
        `ioctl(EVIOCGSND)` error, before calling `do_beep`.

        This normally prevents the user from writing to arbitrary files with
        `--device`, because without the `ioctl(EVIOCGSND)` succeeding,
        `do_beep` with `BEEP_TYPE_CONSOLE` only does a (harmless?)
        `ioctl(KIOCSOUND)`, not a `write` with the `struct input_event`.
        However, the signal handler calls `do_beep` directly using the
        globals set by `play_beep`...

        So I image that with something along the lines of `beep
        --device=./symlink-to-tty ... --new ...`, you can rewrite the
        symlink to point to an arbitrary file during the first `play_beep`,
        and then race the open/ioctl in the second `play_beep` with the
        signal handler such that `do_beep` gets called with `console_fd`
        pointing to your arbitrary file, and with `console_type` still set
        to `BEEP_TYPE_EVDEV`, resulting in a `write` to your arbitrary file.

        Exploiting that for privesc would require control over the `struct
        input_event` for the `write`... `handle_signal` calls `do_beep` with
        a fixed `freq` of 0, so all of the initialized fields are set to
        fixed values... However, there's an unitialized `struct timeval` at
        the beginning of the `struct input_event`, and it's allocated on the
        stack...

        Seems like a curious security vulnerability, I'll assume the debian
        security team must have a working PoC in order to actually call it
        out as a local privesc vulnerability... I'd love to see the actual
        PoC eventually :)

Reply via email to