{ "dataType": "CVE_RECORD", "dataVersion": "5.2", "cveMetadata": { "cveId": "CVE-2026-89546", "assignerOrgId": "416baaa9-dc9f-4396-8d5f-8c081fb06d67", "state": "PUBLISHED", "assignerShortName": "Linux", "dateReserved": "2026-09-11T19:38:34.722Z", "datePublished": "2026-09-11T19:44:21.898Z", "dateUpdated": "2026-10-19T08:48:37.920Z" }, "containers": { "cna": { "providerMetadata": { "orgId": "416baaa9-dc9f-4396-8d5f-8c081fb06d67", "shortName": "Linux", "dateUpdated": "2026-10-19T08:48:37.920Z" }, "descriptions": [ { "lang": "en", "value": "In the Linux kernel, the following vulnerability has been resolved:\n\nSUNRPC: close backchannel before destroying callback service\n\nA backchannel receive can complete a request while the NFS callback\nservice is being torn down. xprt_complete_bc_request() removes the\nrequest from bc_pa_list, drops bc_alloc_count, marks the request in use,\nand then asks xprt_enqueue_bc_request() to hand it to the callback\nservice.\n\nIf teardown has already cleared xprt->bc_serv, xprt_enqueue_bc_request()\ncurrently returns without enqueueing or freeing the committed request.\nThe xprt_get() taken on entry is leaked as well. If the producer wins\nthe race before bc_serv is cleared, it can also enqueue onto sv_cb_list\nafter nfs_callback_down() has stopped the callback threads, leaving the\nrequest linked to a svc_serv that is about to be freed.\n\nClose the producer side before callback threads are stopped. Add\nxprt_svc_shutdown_bc() to clear xprt->bc_serv under bc_pa_lock, and call\nit on callback shutdown and callback-start failure before stopping the\nservice threads. Requests that lose the NULL transition in\nxprt_enqueue_bc_request() are released through the normal backchannel\nfree path after balancing bc_slot_count. Finally, drain any remaining\nsv_cb_list requests after the callback threads have stopped and before\nsvc_destroy() frees the service." } ], "metrics": [ { "cvssV3_1": { "version": "3.1", "vectorString": "CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H", "baseScore": 9.8, "baseSeverity": "CRITICAL" }, "scenarios": [ { "lang": "en", "value": "AV:N - The producer is xs_read_stream_call()/rpcrdma_bc_receive_call() handling RPC_CALL messages on the established NFSv4.1+ client TCP or RPC/RDMA transport; a malicious NFS server sends backchannel frames on that connection and reaches the bug without local access.\nAC:L - The attacker controls both sides of the race: they emit backchannel RPC_CALLs on the still-live xprt and force callback teardown via failed session setup, autofs expiry, or unmount, leaving rpc_rqst objects on sv_cb_list when svc_destroy() frees svc_serv.\nPR:N - A remote NFS peer needs no account or capability on the victim; backchannel RPC_CALLs are accepted on the connected NFSv4.1+ transport once a mount or mount attempt exists, with no local privileges at exploit time.\nUI:N - Boot-time, autofs, and Kubernetes NFSv4.1+ mounts are common; after that session exists the attacker drives backchannel traffic and callback teardown without further interactive victim action such as a manual mount.\nS:U - The use-after-free corrupts the in-kernel nfs_callback svc_serv and rpc_rqst objects on the client host and does not cross a VM, IOMMU, or other security-authority boundary.\nC:H - A raced enqueue leaves an in-use rpc_rqst linked into a freed svc_serv (sv_cb_list/sv_pools), and unlocked bc_serv readers can follow that dangling pointer, yielding a kernel-heap use-after-free read primitive.\nI:H - Use-after-free of svc_serv with queued rpc_rqst and svc_pool_wake_idle_thread on dying callback pools enables heap reuse of RPC service control structures, a standard kernel write and control-flow hijack primitive.\nA:H - svc_destroy() of a callback service that still has live backchannel requests, plus dereference of xprt->bc_serv after free, causes kernel oops or panic; the leak path also orphans rpc_rqst objects and xprt references." } ] } ], "affected": [ { "product": "Linux", "vendor": "Linux", "defaultStatus": "unaffected", "repo": "https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git", "programFiles": [ "fs/nfs/callback.c", "include/linux/sunrpc/bc_xprt.h", "net/sunrpc/backchannel_rqst.c" ], "versions": [ { "version": "441244d4273a8037b265fd254dfdaca5fa736ee2", "lessThan": "6debde9e3e6ae21dcca75837b4247b13ca4ea2b8", "status": "affected", "versionType": "git" }, { "version": "441244d4273a8037b265fd254dfdaca5fa736ee2", "lessThan": "3674f780f47d2906b5a0f7199b66973067bdfeca", "status": "affected", "versionType": "git" } ] }, { "product": "Linux", "vendor": "Linux", "defaultStatus": "affected", "repo": "https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git", "programFiles": [ "fs/nfs/callback.c", "include/linux/sunrpc/bc_xprt.h", "net/sunrpc/backchannel_rqst.c" ], "versions": [ { "version": "6.19", "status": "affected" }, { "version": "0", "lessThan": "6.19", "status": "unaffected", "versionType": "semver" }, { "version": "7.2.4", "lessThanOrEqual": "7.2.*", "status": "unaffected", "versionType": "semver" }, { "version": "7.3", "lessThanOrEqual": "*", "status": "unaffected", "versionType": "original_commit_for_fix" } ] } ], "cpeApplicability": [ { "nodes": [ { "operator": "OR", "negate": false, "cpeMatch": [ { "vulnerable": true, "criteria": "cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:*", "versionStartIncluding": "6.19", "versionEndExcluding": "7.2.4" }, { "vulnerable": true, "criteria": "cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:*", "versionStartIncluding": "6.19", "versionEndExcluding": "7.3" } ] } ] } ], "references": [ { "url": "https://git.kernel.org/stable/c/6debde9e3e6ae21dcca75837b4247b13ca4ea2b8" }, { "url": "https://git.kernel.org/stable/c/3674f780f47d2906b5a0f7199b66973067bdfeca" } ], "title": "SUNRPC: close backchannel before destroying callback service", "x_generator": { "engine": "bippy-1.2.0" } } } }