diff options
| author | Yunlk <[email protected]> | 2026-11-06 10:06:02 +0800 |
|---|---|---|
| committer | Rbb666 <[email protected]> | 2026-11-14 17:29:16 +0800 |
| commit | ebf206d823d9267c5534105f1ef8e6cb8d702a8b (patch) | |
| tree | 8718efcfd40a660514c7f9a5d1c1881b49e43ce9 /components/external/SQLite-3.8.1/src/legacy.c | |
| parent | 3c1f755ce0fe23877053ec34b6c8d433fce19543 (diff) | |
sys_poll() and sys_epoll_pwait() size a kernel buffer from a count that comes
straight from the user process:
if (!lwp_user_accessable((void *)fds, nfds * sizeof *fds)) /* wraps */
kfds = (struct pollfd *)kmem_get(nfds * sizeof *kfds); /* wraps */
ret = poll(kfds, nfds, timeout); /* full nfds */
On a 32-bit build nfds = 0x20000001 and sizeof(struct pollfd) = 8 make the
product 0x1_00000008, which wraps to 8. The access check and the allocation then
agree on an 8-byte block, but poll() walks all 536,870,913 entries: do_pollfd()
reads pollfd->fd and writes revents far outside that block. 64-bit builds are not
affected because the product is promoted to 64 bits and the oversized allocation
just fails.
sys_epoll_pwait() has the same shape, and its cnt is a signed int, so a negative
value has to be rejected as well.
Reject the counts that cannot be represented before anything is sized from them,
using the same SIZE_MAX / sizeof(...) form already used for msg_iovlen in
sys_sendmsg/sys_recvmsg.
The guard arithmetic was checked in isolation with 32-bit size_t semantics:
32-bit SIZE_MAX / sizeof(struct pollfd) = 536870911 (0x1FFFFFFF)
nfds 0x1FFFFFFF -> accepted
nfds 0x20000000 -> rejected
nfds 0x20000001 -> wraps to 8 without the guard, rejected with it
epoll cnt -1, 0x15555556 -> rejected, 0 and small values -> accepted
Note: the RT-Smart build itself was NOT compiled locally. lwp.h requires
RT_USING_MUSLLIBC, so an arm-linux-musleabi toolchain is needed and it was not
available here. A CI run on the RT-Smart configuration is required before
merging.
Refs #11925
Diffstat (limited to 'components/external/SQLite-3.8.1/src/legacy.c')
0 files changed, 0 insertions, 0 deletions
