• Duoming Zhou's avatar
    ax25: fix UAF bugs of net_device caused by rebinding operation · feef318c
    Duoming Zhou authored
    The ax25_kill_by_device() will set s->ax25_dev = NULL and
    call ax25_disconnect() to change states of ax25_cb and
    sock, if we call ax25_bind() before ax25_kill_by_device().
    
    However, if we call ax25_bind() again between the window of
    ax25_kill_by_device() and ax25_dev_device_down(), the values
    and states changed by ax25_kill_by_device() will be reassigned.
    
    Finally, ax25_dev_device_down() will deallocate net_device.
    If we dereference net_device in syscall functions such as
    ax25_release(), ax25_sendmsg(), ax25_getsockopt(), ax25_getname()
    and ax25_info_show(), a UAF bug will occur.
    
    One of the possible race conditions is shown below:
    
          (USE)                   |      (FREE)
    ax25_bind()                   |
                                  |  ax25_kill_by_device()
    ax25_bind()                   |
    ax25_connect()                |    ...
                                  |  ax25_dev_device_down()
                                  |    ...
                                  |    dev_put_track(dev, ...) //FREE
    ax25_release()                |    ...
      ax25_send_control()         |
        alloc_skb()      //USE    |
    
    the corresponding fail log is shown below:
    ===============================================================
    BUG: KASAN: use-after-free in ax25_send_control+0x43/0x210
    ...
    Call Trace:
      ...
      ax25_send_control+0x43/0x210
      ax25_release+0x2db/0x3b0
      __sock_release+0x6d/0x120
      sock_close+0xf/0x20
      __fput+0x11f/0x420
      ...
    Allocated by task 1283:
      ...
      __kasan_kmalloc+0x81/0xa0
      alloc_netdev_mqs+0x5a/0x680
      mkiss_open+0x6c/0x380
      tty_ldisc_open+0x55/0x90
      ...
    Freed by task 1969:
      ...
      kfree+0xa3/0x2c0
      device_release+0x54/0xe0
      kobject_put+0xa5/0x120
      tty_ldisc_kill+0x3e/0x80
      ...
    
    In order to fix these UAF bugs caused by rebinding operation,
    this patch adds dev_hold_track() into ax25_bind() and
    corresponding dev_put_track() into ax25_kill_by_device().
    Signed-off-by: default avatarDuoming Zhou <duoming@zju.edu.cn>
    Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
    feef318c
af_ax25.c 44.1 KB