diff options
author | Nico Weber <thakis@chromium.org> | 2020-09-15 15:44:53 -0400 |
---|---|---|
committer | Andreas Kling <kling@serenityos.org> | 2020-09-15 23:29:51 +0200 |
commit | 62f615f0f40b08d44efc25f727298ef7cefd2216 (patch) | |
tree | fb350db1f96188ccd33628489d07c0b7778fc9d8 /DevTools | |
parent | f0018aca1df36a04e8364dcd39e3013cda54f850 (diff) | |
download | serenity-62f615f0f40b08d44efc25f727298ef7cefd2216.zip |
UsespaceEmulator: Fix minor bugs in recvfrom() interception
* Pass the correct source address for copying tine addr_length.
Previously, this was broken when addr_length was non-nullptr.
* Copy min(sizeof(address), address_length) bytes into address,
instead of sizeof(address), which might be larger than the
user buffer.
* Use sockaddr_storage instead of sockaddr_un. In practice they're
both the same size, but this is what sockaddr_storage is for.
With this (in particular, the first fix), `ue /bin/ntpquery`
actually gets past the recvfrom() call :^)
Diffstat (limited to 'DevTools')
-rw-r--r-- | DevTools/UserspaceEmulator/Emulator.cpp | 11 |
1 files changed, 7 insertions, 4 deletions
diff --git a/DevTools/UserspaceEmulator/Emulator.cpp b/DevTools/UserspaceEmulator/Emulator.cpp index db6c46689a..657a8fa390 100644 --- a/DevTools/UserspaceEmulator/Emulator.cpp +++ b/DevTools/UserspaceEmulator/Emulator.cpp @@ -599,13 +599,16 @@ int Emulator::virt$recvfrom(FlatPtr params_addr) mmu().copy_from_vm(¶ms, params_addr, sizeof(params)); auto buffer = ByteBuffer::create_uninitialized(params.buffer.size); - sockaddr_un address; - if (params.addr) - mmu().copy_from_vm(&address, (FlatPtr)params.addr, sizeof(address)); + if (!params.addr_length && params.addr) + return -EINVAL; socklen_t address_length = 0; if (params.addr_length) - mmu().copy_from_vm(&address_length, (FlatPtr)address_length, sizeof(address_length)); + mmu().copy_from_vm(&address_length, (FlatPtr)params.addr_length, sizeof(address_length)); + + sockaddr_storage address; + if (params.addr) + mmu().copy_from_vm(&address, (FlatPtr)params.addr, min(sizeof(address), (size_t)address_length)); int rc = recvfrom(params.sockfd, buffer.data(), buffer.size(), params.flags, params.addr ? (struct sockaddr*)&address : nullptr, params.addr_length ? &address_length : nullptr); if (rc < 0) |