| CVE |
Vendors |
Products |
Updated |
CVSS v3.1 |
| In the Linux kernel, the following vulnerability has been resolved:
fbdev: vfb: defer cleanup until the last reference
FBIOGETCMAP takes a shallow snapshot of info->cmap and performs the
usercopy after dropping info->lock. vfb_remove() frees the colormap
immediately after unregistering the framebuffer, even when an open file
still holds a reference to fb_info. A concurrent driver unbind can
therefore free the colormap while the ioctl copies it to userspace.
KASAN reports:
BUG: KASAN: slab-use-after-free in _copy_to_user
Read of size 512 by task poc/125
_copy_to_user (./include/linux/instrumented.h:129 ./include/linux/uaccess.h:201 lib/usercopy.c:24)
fb_cmap_to_user (./include/linux/uaccess.h:230 drivers/video/fbdev/core/fbcmap.c:211)
do_fb_ioctl (drivers/video/fbdev/core/fb_chrdev.c:114)
Allocated by task 1:
fb_alloc_cmap_gfp (./include/linux/slab.h:973 ./include/linux/slab.h:1290 drivers/video/fbdev/core/fbcmap.c:108)
vfb_probe (drivers/video/fbdev/vfb.c:459)
Freed by task 124:
fb_dealloc_cmap (drivers/video/fbdev/core/fbcmap.c:151)
vfb_remove (drivers/video/fbdev/vfb.c:489)
unregister_framebuffer() drops the registration reference, and fbdev calls
fb_destroy after the last put_fb_info(). Move the registered framebuffer's
cleanup into an fb_destroy callback so its colormap and screen buffer stay
alive until all file references have been released. |
| In the Linux kernel, the following vulnerability has been resolved:
idpf: disable DIM work before freeing q_vectors
idpf never drains the Tx/Rx DIM works before freeing the memory they
live in. tx_dim and rx_dim are embedded in struct idpf_q_vector, they
are queued from the NAPI poll via net_dim(), and idpf_vport_intr_rel()
ends with kfree(rsrc->q_vectors). Nothing in the driver cancels them.
idpf_tx_dim_work() and idpf_rx_dim_work() then run on freed memory:
idpf_vport_intr_write_itr() writes the ITR register through
q_vector->intr_reg.tx_itr / rx_itr, void __iomem pointers loaded out of
the freed q_vector. No configuration is needed to get there --
IDPF_ITR_IS_DYNAMIC() is defined as (itr_mode) and idpf_vport_alloc()
initialises both modes to IDPF_ITR_DYNAMIC.
Draining after idpf_vport_intr_napi_dis_all() is not enough on its own.
idpf_net_dim() is called from inside the
"if (napi_complete_done(napi, work_done))" branch of the poll, and
napi_complete_done() has already cleared NAPIF_STATE_SCHED by then.
napi_disable_locked() waits only while (val & (NAPIF_STATE_SCHED |
NAPIF_STATE_NPSVC)), so napi_disable() can return while the poll tail is
still queueing the work, and a plain cancel_work_sync() would be
re-armed behind the drain.
Use disable_work_sync(): schedule_work() on a work with a non-zero
disable count is dropped by clear_pending_if_disabled() before
__queue_work() is reached.
Move idpf_init_dim() to idpf_vport_intr_alloc() so the works are
initialised on every path that can reach the drain -- the three
"goto intr_deinit" sites between idpf_vport_intr_init() and
idpf_vport_intr_ena() get there without the enable side having run.
Nothing re-enables them: rsrc->q_vectors is freed on every exit from
idpf_vport_open() and on every idpf_vport_stop(), so the count dies with
the object.
It is a race, not a deterministic failure -- net_dim() only schedules
once DIM_NEVENTS events have accumulated and the profile index changes.
A KASAN ifup/ifdown loop under load is the way to see it. |
| In the Linux kernel, the following vulnerability has been resolved:
mac802154: fix use-after-free of sdata via queued RX frames
The RX softirq producer ieee802154_subif_frame() queues received beacon
and MAC-command frames onto local->rx_beacon_list / rx_mac_cmd_list and
schedules a process-context worker, storing a raw mac_pkt->sdata (and
skb->dev == sdata->dev) with neither a reference nor any locking:
- the lists have no lock: the softirq producer list_add_tail()s while the
mac_wq worker list_del()s, so sibling interfaces on the same phy corrupt
the list;
- the workers dereference the interface after it may have been freed.
mac802154_rx_mac_cmd_worker() touches mac_pkt->sdata directly, and
mac802154_rx_beacon_worker() -> mac802154_process_beacon() dereferences
skb->dev (== sdata->dev). Removing an interface frees its sdata
(netdev_priv) while a queued frame still points at it, so a later worker
run is a use-after-free.
Reproduced under KASAN by flooding a victim interface with MAC command
frames and removing it (the beacon path is the same class via skb->dev):
BUG: KASAN: slab-use-after-free in mac802154_rx_mac_cmd_worker+0x463/0x630 [mac802154]
Read of size 4 at addr ffff888002f9ea18 by task kworker/u8:1/31
Workqueue: phy0-mac-cmds mac802154_rx_mac_cmd_worker [mac802154]
Call Trace:
mac802154_rx_mac_cmd_worker+0x463/0x630 [mac802154]
process_one_work+0x611/0xe80
worker_thread+0x52e/0xdc0
kthread+0x30c/0x630
ret_from_fork+0x2fd/0x3e0
Fix both lists together:
- add local->rx_lock and take it around every list access: the softirq
producer (plain spin_lock, softirq context) and the workers and flush
(spin_lock_bh, process context);
- pin the interface for the lifetime of a queued frame with
netdev_hold()/netdev_put(), so the worker can safely dereference sdata /
skb->dev even while the interface is being removed;
- dequeue under the lock at the head and loop-drain the whole list in the
workers (they previously processed one frame per run and relied on a
later enqueue to drain the rest);
- drop not-yet-started frames of an interface before it is unregistered,
from ieee802154_if_remove() (after the RCU grace period) and from the
ieee802154_remove_interfaces() loop -- the latter is the whole-phy
teardown path, which does not go through ieee802154_if_remove().
An in-flight worker that already dequeued a frame keeps its own netdev
reference; unregister_netdevice() then waits it out in netdev_run_todo(),
which runs at rtnl_unlock() (rtnl released) and after the interface has
been closed, so it does not pin rtnl. A worker blocked in an association
TX only delays that one interface's unregister (the usual "waiting for %s
to become free"), it does not hold rtnl. netdev_hold() is used for this
reason instead of a cancel_work_sync() under rtnl, which would block on
the worker's unbounded MLME TX wait via ieee802154_sync_queue().
The mac-command worker additionally skips processing for a stopped
interface (ieee802154_sdata_running()), avoiding a needless association
response during teardown. |
| In the Linux kernel, the following vulnerability has been resolved:
hwmon: (gpio-fan) Fix use-after-free in alarm work
fan_alarm_irq_handler() queues fan_data->alarm_work, but nothing
cancels it. fan_alarm_notify() dereferences fan_data and its hwmon
device. On unbind, devres frees the interrupt, which only waits for
the handler itself, and then releases the hwmon device and fan_data,
so a pending fan_alarm_notify() can run after those frees.
Replace INIT_WORK() with devm_work_autocancel(), registered before
devm_request_irq(). The devres cleanup then frees the interrupt
first, so no new work can be queued, and cancels the work while
fan_data and the hwmon device are still alive.
This issue was found by an in-house static analysis tool. |
| In the Linux kernel, the following vulnerability has been resolved:
bnxt_en: Don't free the live ring's TPA state on queue restart failure
bnxt_queue_mem_alloc() shallow copies the live RX ring into the clone:
memcpy(clone, rxr, sizeof(*rxr));
the code currently clears pointers that the clone owns (such as
rx_agg_bmap), but rx_tpa and rx_tpa_idx_map are left pointing at memory
of the live ring that was cloned.
If an allocation failure happens later and the err_free_tpa_info label
is taken, the live ring's memory can be freed while still in use.
Fix this by initializing the clone's pointers to NULL to prevent live
ring state from being freed inadvertently. |
| In the Linux kernel, the following vulnerability has been resolved:
wifi: ath9k_htc: don't store usb_device_id
usb_device_id is not guaranteed to live longer than probe due to presence
of dynamic ID. All information apart from driver_data can be easily
retrieved from usb_device, so just store driver_data. |
| In the Linux kernel, the following vulnerability has been resolved:
thunderbolt: Keep XDomain reference during the lifetime of a service
This is needed because we release the service ID in tb_service_release()
and the ID array is owned by the parent XDomain. |
| In the Linux kernel, the following vulnerability has been resolved:
thunderbolt: Set tb->root_switch to NULL when domain is stopped
Similarly what we do with the firmware connection manager. This makes
tb_xdp_handle_request() return error to the remote host. However, we
need to make sure we keep the uuid alive so that we can reply until the
whole domain is released. |
| In the Linux kernel, the following vulnerability has been resolved:
thermal/drivers/tegra/soctherma: Switch to devm cooling device registration
Use devm_thermal_of_cooling_device_register() to simplify resource
management and avoid manual cleanup in error paths.
As a side effect this change has the benefit of solving an existing
issue. Before, the function tegra_soctherm_remove() only called
debugfs_remove_recursive() and never called thermal_cooling_device_unregister()
for any of the cooling devices registered here.
After the driver removal, the thermal framework's cdev list would
still hold references to thermal_cooling_device objects whose devdata
pointer (ts) pointed to memory already freed by the platform device's
devm cleanup.
With this change, the cooling device is unregistered when the driver
is removed, thus fixing the issue above. |
| In the Linux kernel, the following vulnerability has been resolved:
ACPICA: Fix use-after-free in acpi_ds_terminate_control_method()
Fix use-after-free issue in acpi_ds_terminate_control_method() by
clearing references to method locals and arguments. |
| In the Linux kernel, the following vulnerability has been resolved:
ACPICA: Add validation for node in acpi_ns_build_normalized_path()
Add validation for node in acpi_ns_build_normalized_path()
to prevent use-after-free vulnerabilities. |
| In the Linux kernel, the following vulnerability has been resolved:
dpaa2-switch: fix handling of NAPI on the remove path
All the NAPI instances for a DPSW device are attached to the first
switch port's net_device but shared by all ports. The NAPI instances get
disabled only once the last port goes down.
This causes an issue on the .remove() path where each port is
unregistered and freed one at a time, causing the NAPI instances to be
deleted even though they are not disabled.
In order to avoid this, split up the unregister_netdev() calls from the
free_netdev() so that we make sure all ports go down before we attempt
a deletion of NAPI instances. Also, make the netif_napi_del() explicit
as it is on the .probe() path. |
| In the Linux kernel, the following vulnerability has been resolved:
drm/amdkfd: fix UAF race in destroy_queue_cpsch
wait_on_destroy_queue() drops locks to wait for queue resume, allowing
a concurrent destroy to free the queue. Use is_being_destroyed flag to
serialize destruction. |
| In the Linux kernel, the following vulnerability has been resolved:
HID: hidpp: fix potential UAF in hidpp_connect_event()
If input_register_device() fails, we call input_free_device(), but keep
stale pointer to the old device in hidpp->input, which could potentially
lead to UAF. Fix that by resetting it to NULL before returning from
hidpp_connect_event(). |
| In the Linux kernel, the following vulnerability has been resolved:
net: au1000: move free_irq out of the close-time spinlocked section
au1000_close() calls free_irq() while aup->lock is still held with
spin_lock_irqsave(). free_irq() can sleep because it takes the IRQ
descriptor request mutex, so it does not belong inside the close-time
spinlocked section.
This was found by our static analysis tool and then confirmed by manual
review of the in-tree au1000_close() .ndo_stop path. The reviewed path
keeps aup->lock held across the MAC reset, queue stop and
free_irq(dev->irq, dev).
A directed runtime validation kept that ndo_stop carrier and the same
free_irq(dev->irq, dev) operation under the driver lock. Lockdep reported
"BUG: sleeping function called from invalid context" and "Invalid wait
context" while free_irq() was taking desc->request_mutex, with
au1000_close() and free_irq() on the stack.
Drop aup->lock before freeing the IRQ. The protected close-time work still
stops the device and queue before IRQ teardown, but the sleepable IRQ core
path now runs outside the spinlocked section. |
| In the Linux kernel, the following vulnerability has been resolved:
btrfs: fix use-after-free on reloc root after error in insert_dirty_subvol()
If during relocation we fail in insert_dirty_subvol() because
btrfs_update_reloc_root() returned an error, we will leave a root's
reloc_root field pointing to a reloc root that was freed instead of NULL,
resulting later in a use-after-free, or double free attempt during
unmount.
The sequence of steps is this:
1) During relocation the call to btrfs_update_reloc_root() in
insert_dirty_subvol() fails, so insert_dirty_subvol() returns the
error to merge_reloc_root() without adding the root to the list
rc->dirty_subvol_roots;
2) Then merge_reloc_root() aborts the current transaction because
insert_dirty_subvol() returned an error;
3) Up the call chain, merge_reloc_roots() gets the error, adds the
reloc root for root X to the local reloc_roots list and jumps to the
'out' label, where it calls free_reloc_roots() to free all the reloc
roots in the local reloc_roots list. This frees the reloc root for
root X;
4) We go up the call chain to relocate_block_group() which calls
clean_dirty_subvols() to go over dirty roots and set their
->reloc_root field to NULL, but root X is not in the dirty_subvol_roots
list, so its ->reloc_root still points to a reloc root;
5) Relocation finishes, with an error and a transaction abort, but the
->reloc_root field for root X still points to the reloc root that was
freed in step 3;
6) When unmounting the fs we end up calling:
btrfs_free_fs_roots()
btrfs_drop_and_free_fs_root()
--> calls btrfs_put_root() against root X's ->reloc_root
which is not NULL and points to the already freed
reloc root in step 4 above
Resulting in a use-after-free to a double free attempt.
Syzbot reported this with the following dmesg/syslog:
[ 106.004389][ T5339] BTRFS error (device loop0 state A): Transaction aborted (error -5)
[ 106.014266][ T5339] BTRFS: error (device loop0 state A) in merge_reloc_root:1655: errno=-5 IO failure
[ 106.021891][ T1061] BTRFS error (device loop0 state A): error while writing out transaction: -5
[ 106.026964][ T1061] BTRFS warning (device loop0 state A): Skipping commit of aborted transaction.
[ 106.033807][ T5340] BTRFS error (device loop0 state A): bdev /dev/loop0 errs: wr 3, rd 0, flush 0, corrupt 0, gen 0
[ 106.039265][ T1061] BTRFS: error (device loop0 state A) in cleanup_transaction:2067: errno=-5 IO failure
[ 106.044382][ T5339] BTRFS info (device loop0 state EA): forced readonly
[ 106.074329][ T5339] BTRFS: error (device loop0 state EA) in merge_reloc_roots:1887: errno=-5 IO failure
[ 106.081004][ T5356] BTRFS info (device loop0 state EA): scrub: started on devid 1
[ 106.085611][ T5339] BTRFS info (device loop0 state EA): balance: ended with status: -30
[ 106.089517][ T5356] BTRFS info (device loop0 state EA): scrub: not finished on devid 1 with status: -30
[ 106.662365][ T5338] BTRFS info (device loop0 state EA): last unmount of filesystem 3a375e4e-b156-4d76-a2ad-16e198ce1409
[ 106.682946][ T5338] ==================================================================
[ 106.686574][ T5338] BUG: KASAN: slab-use-after-free in btrfs_put_root+0x2f/0x250
[ 106.690090][ T5338] Write of size 4 at addr ffff88803f978630 by task syz.0.0/5338
[ 106.693173][ T5338]
[ 106.694279][ T5338] CPU: 0 UID: 0 PID: 5338 Comm: syz.0.0 Not tainted syzkaller #0 PREEMPT(full)
[ 106.694293][ T5338] Hardware name: QEMU Standard PC (Q35 + ICH9, 2009), BIOS 1.16.3-debian-1.16.3-2 04/01/2014
[ 106.694300][ T5338] Call Trace:
[ 106.694308][ T5338] <TASK>
[ 106.694314][ T5338] dump_stack_lvl+0xe8/0x150
[ 106.694331][ T5338] print_address_description+0x55/0x1e0
[ 106.694343][ T5338] ? btrfs_put_root+0x2f/0x250
[ 106.694358][ T5338] print_report+0x58/0x70
[ 106.
---truncated--- |
| In the Linux kernel, the following vulnerability has been resolved:
smb/client: flush dirty data before punching a hole
Punching a hole after a large buffered write may leave the range
reported as data. Reproduce it with:
xfs_io -f \
-c "pwrite -b 3m -S 0x61 0 3m" \
-c "fpunch 1m 1m" \
-c "seek -h 0" \
-c "seek -d 1m" \
/mnt/test/repro
Punching 1 MiB at offset 1 MiB should produce:
0 1 MiB 2 MiB 3 MiB
| DATA | HOLE | DATA | EOF
Instead, the entire file is reported as data. SEEK_HOLE(0) returns EOF,
and SEEK_DATA(1M) returns 1M.
This happens because a dirty folio spanning the punched range can be
written back after the punch and refill the hole.
Fix this by flushing and waiting for dirty data in the punched range
before invalidating the page cache and issuing FSCTL_SET_ZERO_DATA.
The xfstests generic/539 pass against Samba/ksmbd with this change. |
| In the Linux kernel, the following vulnerability has been resolved:
vhost-scsi: flush backend after device ioctls
vhost-scsi translates guest response descriptors into userspace iovecs
when commands are submitted. Target-core completes those commands
asynchronously, so VHOST_SET_MEM_TABLE can replace the memory table while
an in-flight command still retains response iovecs translated through the
old table.
If the old mapping is reused after VHOST_SET_MEM_TABLE returns, command
completion can write the response to an unrelated userspace object.
Flush the vhost-scsi backend after vhost_dev_ioctl() handles a device
ioctl. This waits for in-flight commands that can still use the old
response iovecs before the ioctl returns. |
| In the Linux kernel, the following vulnerability has been resolved:
usb: dwc3: gadget: Fix use-after-free in dwc3_gadget_free_endpoints due to race condition
In dwc3_gadget_init_endpoint, &dep->nostream_work is bound with
dwc3_nostream_work, and dwc3_gadget_endpoint_stream_event can queue
this delayed work on system_percpu_wq when a DEPEVT_STREAM_NOSTREAM
event is received.
If we remove the gadget, dwc3_gadget_free_endpoints makes cleanup and
the memory allocated for dep with kzalloc() is released by kfree(dep),
while the delayed work mentioned above may still be pending or
running. The sequence of operations that may lead to a UAF bug is as
follows:
CPU0 CPU1
| dwc3_thread_interrupt
| dwc3_endpoint_interrupt
| dwc3_gadget_endpoint_stream_event
| queue_delayed_work(system_percpu_wq,
| &dep->nostream_work)
dwc3_gadget_free_endpoints |
dwc3_free_trb_pool(dep) |
list_del(&dep->endpoint.ep_list) |
dwc3_debugfs_remove_endpoint_dir(dep) |
kfree(dep) |
// dep is freed |
| dwc3_nostream_work
| // use dep (use-after-free)
Fix it by canceling the delayed work before kfree(dep) in
dwc3_gadget_free_endpoints. |
| In the Linux kernel, the following vulnerability has been resolved:
iommufd: Fix UAF in selftest IOPF reporting
IOMMUFD selftest TRIGGER_IOPF borrows an attach handle from
group->pasid_array without synchronizing against PASID detach,
then a concurrent iommu_report_device_fault() can dereference
that borrowed handle's domain pointer after the detach erases
the handle and frees the backing struct iommufd_attach_handle.
TRIGGER_IOPF then dereferences the freed handle, causing a UAF.
Fix by adding a iopf_rwsem in mock_dev to follow the expected design
of a real driver. Hold its read side across the whole
iommu_report_device_fault() call, and its write side around every
path that attaches, detaches, or replaces a device domain.
This can block new reports and drains in-flight reports before an old
attach handle or the IOPF fault parameter can be removed.
Also take the write side while registering a mock device, since
it can invoke the mock driver's default-domain attach callback. |