IPC resilience
This commit is contained in:
@@ -100,6 +100,16 @@ SharedMemory::map(Handle handle, size_t size)
|
||||
close_handle(handle);
|
||||
return out;
|
||||
}
|
||||
#if defined __linux__
|
||||
// The sender keeps its descriptor: without these seals, it could change
|
||||
// the bytes while they are being read, or shrink them away into SIGBUS.
|
||||
const int required = F_SEAL_SHRINK | F_SEAL_WRITE;
|
||||
const int seals = fcntl(int(handle), F_GET_SEALS);
|
||||
if (seals < 0 || (seals & required) != required) {
|
||||
close_handle(handle);
|
||||
return out;
|
||||
}
|
||||
#endif
|
||||
void *p = mmap(nullptr, size, PROT_READ, MAP_SHARED, int(handle), 0);
|
||||
if (p == MAP_FAILED) {
|
||||
close_handle(handle);
|
||||
|
||||
@@ -66,6 +66,11 @@ test_shared_memory()
|
||||
void *writable =
|
||||
mmap(nullptr, 4096, PROT_WRITE, MAP_SHARED, int(owner.handle()), 0);
|
||||
CHECK(writable == MAP_FAILED);
|
||||
|
||||
const int unsealed = memfd_create("unsealed", MFD_CLOEXEC);
|
||||
CHECK(unsealed >= 0 && ftruncate(unsealed, 4096) == 0);
|
||||
CHECK(!dawn::ipc::SharedMemory::map(unsealed, 4096).ok());
|
||||
CHECK(!handle_is_open(unsealed));
|
||||
#endif
|
||||
auto reader =
|
||||
dawn::ipc::SharedMemory::map(duplicate_handle(owner.handle()), 4096);
|
||||
|
||||
Reference in New Issue
Block a user