Skip to content

tinywl: Fix null deference due to race condition

Alexander Orzechowski requested to merge Nefsen402/wlroots:tinywl-sigsegv into master

scene_output can be null if the following events happen:

  1. New frame scheduled for output (due to the frame being damaged possibly)
  2. Output is destroyed/disabled
  3. events.frame callback is triggered

Tinywl in step 3 will try to send NULL as an output into wlr_scene_output_commit triggering SIGSEGV.

Core was generated by `./build/tinywl/tinywl -s ../kitty/linux-package/bin/kitty'.
Program terminated with signal SIGSEGV, Segmentation fault.

warning: Section `.reg-xstate/283097' in core file too small.
0  0x00007fab670552a2 in wlr_scene_output_commit (scene_output=0x0)
--Type <RET> for more, q to quit, c to continue without paging--
    at ../types/scene/wlr_scene.c:1089

warning: Source file is more recent than executable.
1089		struct wlr_output *output = scene_output->output;
[Current thread is 1 (Thread 0x7fab662ee040 (LWP 283097))]
(gdb) bt full
0  0x00007fab670552a2 in wlr_scene_output_commit (scene_output=0x0)
    at ../types/scene/wlr_scene.c:1089
        output = 0x55e6402fadb0
        renderer = 0x7ffd3cce3470
        __PRETTY_FUNCTION__ = "wlr_scene_output_commit"
        scanout = 64
        needs_frame = 97
        damage = 
          {extents = {x1 = 1020146384, y1 = 32765, x2 = 1729008992, y2 = 32683}, data = 0x55e640ea99d0}
        scene_buffer = 0x55e641050fb0
        scene_buffer_tmp = 0x55e64060bbd8
        nrects = 21990
        rects = 0x7fab66fb0d25
        tr_width = 1020146288
        tr_height = 32765
        transform = 21990
        frame_damage = 
          {extents = {x1 = 1020146352, y1 = 32765, x2 = 1090229680, y2 = 21990}, data = 0x7ffd3cce32c0}
1  0x000055e6402f7530 in output_frame (listener=0x55e640fba880, data=0x55e640fb9310)
    at ../tinywl/tinywl.c:542
        output = 0x55e640fba860
        scene = 0x55e640ea99d0
        scene_output = 0x0
        now = {tv_sec = 94447422814768, tv_nsec = 94447422462912}
2  0x00007fab670953bd in wlr_signal_emit_safe (signal=0x55e640fb9490, data=0x55e640fb9310)
    at ../util/signal.c:29
        pos = 0x55e640fba880
        l = 0x55e640fba880
        cursor = 
          {link = {prev = 0x55e640fba880, next = 0x7ffd3cce3370}, notify = 0x7fab67095307 <handle_noop>}
        end = 
          {link = {prev = 0x7ffd3cce3350, next = 0x55e640fb9490}, notify = 0x7fab67095307 <handle_noop>}
3  0x00007fab67050bc4 in wlr_output_send_frame (output=0x55e640fb9310)
    at ../types/output/output.c:797
4  0x00007fab67050c08 in schedule_frame_handle_idle_timer (data=0x55e640fb9310)
    at ../types/output/output.c:805
        output = 0x55e640fb9310
5  0x00007fab66fb00db in wl_event_loop_dispatch_idle () at /usr/lib/libwayland-server.so.0
6  0x00007fab66fb0239 in wl_event_loop_dispatch () at /usr/lib/libwayland-server.so.0
7  0x00007fab66fadd37 in wl_display_run () at /usr/lib/libwayland-server.so.0
8  0x000055e6402f81f4 in main (argc=3, argv=0x7ffd3cce3948) at ../tinywl/tinywl.c:903
Edited by Alexander Orzechowski

Merge request reports