{"dataType":"CVE_RECORD","dataVersion":"5.2","cveMetadata":{"cveId":"CVE-2026-80975","assignerOrgId":"416baaa9-dc9f-4396-8d5f-8c081fb06d67","state":"PUBLISHED","assignerShortName":"Linux","dateReserved":"2026-08-26T14:34:25.810Z","datePublished":"2026-09-11T19:42:37.086Z","dateUpdated":"2026-09-13T06:28:39.317Z"},"containers":{"cna":{"providerMetadata":{"orgId":"416baaa9-dc9f-4396-8d5f-8c081fb06d67","shortName":"Linux","dateUpdated":"2026-09-13T06:28:39.317Z"},"descriptions":[{"lang":"en","value":"In the Linux kernel, the following vulnerability has been resolved:\n\nmfd: qnap-mcu: keep the reply buffer alive past a command timeout\n\nqnap_mcu_exec() publishes an on-stack buffer to the receive path:\n\n\tunsigned char rx[QNAP_MCU_RX_BUFFER_SIZE];\n\t...\n\treply->data = rx;\n\treply->length = length;\n\nand qnap_mcu_receive_buf() writes into it from the serdev receive path,\nwhich runs out of flush_to_ldisc() and is not serialized against\nqnap_mcu_exec() at all. bus_lock cannot cover it, because qnap_mcu_exec()\nholds that mutex across wait_for_completion_timeout().\n\nOn a timeout qnap_mcu_exec() returns with reply->data still pointing at\nits own frame. A reply that arrives late, or an unsolicited message from\nthe MCU, is then written into a stack frame that has been left, corrupting\nwhatever runs next on that stack. The same applies when qnap_mcu_write()\nfails, since that path returns without touching the reply state either.\n\nMove the receive buffer into struct qnap_mcu. It is 37 bytes and the\nstructure is devm_kzalloc()ed, so it lives as long as the driver, and a\nlate write lands in memory that is still valid and is reinitialized by the\nnext command. bus_lock keeps commands from sharing it.\n\nThis deliberately does not clear reply->data or reply->length on the\ntimeout path. Doing so races with qnap_mcu_receive_buf(), which reads both\nafter its\n\n\tif (!reply->length)\n\t\treturn size;\n\ncheck: clearing reply->data gives a NULL dereference, and clearing\nreply->length alone removes the reply->received == reply->length exit\ncondition, so the copy loop runs until the uart chunk is consumed and\noverruns the buffer. Leaving both set keeps the write bounded by\nreply->length, which qnap_mcu_exec() has already checked against\nsizeof(mcu->rx)."}],"metrics":[{"cvssV3_1":{"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"},"scenarios":[{"lang":"en","value":"AV:L - The bug is reached only through local qnap_mcu_exec() calls from hwmon/nvmem/LED/input/thermal sysfs on QNAP NAS devices whose MCU is a soldered UART serdev child, not a network protocol or a user-pluggable USB device, so the vector is Local rather than Physical.\nAC:L - This is use-after-return of an on-stack RX buffer published to qnap_mcu_receive_buf(), which runs from flush_to_ldisc() with no lock shared with qnap_mcu_exec(); an attacker issues commands via sysfs, retries at will, and after the 500 ms timeout reply->data still points at their kernel stack so a late or unsolicited MCU chunk writes into that frame.\nPR:L - Fan/temp hwmon attributes are mode 0444 and pwm is 0644, and the EEPROM nvmem is registered with root_only=false (0444), so any unprivileged local user can invoke qnap_mcu_exec() by reading those sysfs files without capabilities or init-namespace root.\nUI:N - Exploitation uses the attacker’s own reads of already-present hwmon and nvmem sysfs; no victim must mount a filesystem, plug in hardware, or otherwise act, and thermal cooling plus input polling can also enter the same path automatically.\nS:U - The use-after-return corrupts the kernel stack of the task or kworker that called qnap_mcu_exec() on the same host; it does not cross a VM, IOMMU, or sandbox boundary into a separate security authority.\nC:H - A late UART write of up to 37 bytes into a returned kernel stack frame is use-after-return memory corruption; the attacker can groom that stack with a follow-up syscall so the overwrite becomes a kernel read primitive, which per UAF guidance is High confidentiality impact.\nI:H - The same write into the abandoned stack can smash return addresses, saved registers, and pointers of the next function on that stack, including after attacker-controlled syscall grooming, yielding control-flow hijack; use-after-return stack corruption is High integrity impact.\nA:H - Writing MCU UART bytes into a kernel stack frame that has already been left corrupts in-use stack state and causes an oops or panic even when not turned into a full exploit, fully denying availability."}]}],"affected":[{"product":"Linux","vendor":"Linux","defaultStatus":"unaffected","repo":"https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git","programFiles":["drivers/mfd/qnap-mcu.c"],"versions":[{"version":"998f70d1806bb718a7565f350283e4a79c8cbb4b","lessThan":"0b6680e306397097a97767447368221fac753809","status":"affected","versionType":"git"},{"version":"998f70d1806bb718a7565f350283e4a79c8cbb4b","lessThan":"8391ee06d08845a0a165b5fe679ba326915166b2","status":"affected","versionType":"git"},{"version":"998f70d1806bb718a7565f350283e4a79c8cbb4b","lessThan":"47504742cea7878ebd1bf1491bbed923df6b90b1","status":"affected","versionType":"git"}]},{"product":"Linux","vendor":"Linux","defaultStatus":"affected","repo":"https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git","programFiles":["drivers/mfd/qnap-mcu.c"],"versions":[{"version":"6.14","status":"affected"},{"version":"0","lessThan":"6.14","status":"unaffected","versionType":"semver"},{"version":"6.18.51","lessThanOrEqual":"6.18.*","status":"unaffected","versionType":"semver"},{"version":"7.2.4","lessThanOrEqual":"7.2.*","status":"unaffected","versionType":"semver"},{"version":"7.3-rc1","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.14","versionEndExcluding":"6.18.51"},{"vulnerable":true,"criteria":"cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:*","versionStartIncluding":"6.14","versionEndExcluding":"7.2.4"},{"vulnerable":true,"criteria":"cpe:2.3:o:linux:linux_kernel:*:*:*:*:*:*:*:*","versionStartIncluding":"6.14","versionEndExcluding":"7.3-rc1"}]}]}],"references":[{"url":"https://git.kernel.org/stable/c/0b6680e306397097a97767447368221fac753809"},{"url":"https://git.kernel.org/stable/c/8391ee06d08845a0a165b5fe679ba326915166b2"},{"url":"https://git.kernel.org/stable/c/47504742cea7878ebd1bf1491bbed923df6b90b1"}],"title":"mfd: qnap-mcu: keep the reply buffer alive past a command timeout","x_generator":{"engine":"bippy-1.2.0"}}}}