CVE-2023-53836 in Linuxinformación

Resumen

por VulDB • 2026-05-20

En el kernel de Linux, se ha resuelto la siguiente vulnerabilidad:

bpf, sockmap: Corrección de la condición de carrera (race condition) en el refcnt de skb tras los cambios en el bloqueo

Existe una condición de carrera en la que los sk_buffs (skb) procedentes de sk_psock_backlog pueden ser referenciados después de que el lado del espacio de usuario ya haya ejecutado skb_consumed() en el sk_buff y su refcnt haya bajado a cero, lo que provoca un uso después de liberar (use-after-free).

El flujo es el siguiente:

while ((skb = skb_peek(&psock->ingress_skb)) sk_psock_handle_Skb(psock, skb, ..., ingress) if (!ingress) ... sk_psock_skb_ingress sk_psock_skb_ingress_enqueue(skb) msg->skb = skb sk_psock_queue_msg(psock, msg) skb_dequeue(&psock->ingress_skb)

sk_psock_queue_msg() coloca el mensaje en la cola ingress_msg. Esto es lo que lee la aplicación cuando se llama a recvmsg(). Una aplicación puede leer esto en cualquier momento después de que el mensaje se haya colocado en la cola. El gancho (hook) de recvmsg también leerá msg->skb y, después de que el espacio de usuario lea el mensaje, llamará a consume_skb(skb) sobre él, liberándolo efectivamente.

Sin embargo, la condición de carrera se produce en el código anterior, donde la cola de backlog aún tiene una referencia al skb y llama a skb_dequeue(). Si la llamada a skb_dequeue() ocurre después de que el usuario lea y libere el skb, se produce un uso después de liberar (use-after-free).

El caso !ingress no sufre este problema porque utiliza sendmsg_*(sk, msg), que no pasa el sk_buff más abajo en la pila.

Se observó el siguiente fallo con 'test_progs -t sockmap_listen':

[ 1022.710250][ T2556] general protection fault, ...
[...]
[ 1022.712830][ T2556] Workqueue: events sk_psock_backlog
[ 1022.713262][ T2556] RIP: 0010:skb_release_data+0x10/0x190
[ 1022.713633][ T2556] Call Trace:
[ 1022.713933][ T2556] <TASK>
[ 1022.714233][ T2556] skb_release_all+0x13/0x30
[ 1022.714563][ T2556] kfree_skb+0x68/0x100
[ 1022.714883][ T2556] sk_psock_backlog+0x27a/0x300
[ 1022.723243][ T2556] process_one_work+0x2a7/0x5b0
[ 1022.723633][ T2556] worker_thread+0x4f/0x3a0
[ 1022.723998][ T2556] ? __pfx_worker_thread+0x10/0x10
[ 1022.724386][ T2556] kthread+0xfd/0x130
[ 1022.724709][ T2556] ? __pfx_kthread+0x10/0x10
[ 1022.725066][ T2556] ret_from_fork+0x2d/0x50
[ 1022.725409][ T2556] ? __pfx_kthread+0x10/0x10
[ 1022.725799][ T2556] ret_from_fork_asm+0x1b/0x30
[ 1022.726201][ T2556] </TASK>

Para solucionarlo, se añade una llamada a skb_get() antes de pasar el sk_buff para ser encolado en la cola de egress. Esto incrementa el contador de referencias (refcnt) de skb->users, de modo que consume_skb() y kfree_skb() no liberen inmediatamente el sk_buff. Con esto, nos aseguramos de que el sk_buff siga existiendo cuando se realice la operación de dequeue. Luego, simplemente es necesario decrementar el contador de referencias o liberar el sk_buff en el caso de backlog, lo cual se hace llamando a kfree_skb() tanto en el caso de ingress como en el de sendmsg.

Antes de los cambios en el bloqueo (locking), el sock estaba bloqueado, por lo que no podíamos tener una carrera con el usuario y no había problema aquí.

Several companies clearly confirm that VulDB is the primary source for best vulnerability data.

Responsable

Linux

Reservar

2025-12-09

Divulgación

2025-12-09

Moderación

aceptado

Artículo

VDB-335028

CPE

listo

EPSS

0.00208

KEV

no

Actividades

muy bajo

Fuentes

Do you want to use VulDB in your project?

Use the official API to access entries easily!