aboutsummaryrefslogtreecommitdiffstats
path: root/executor/snapshot.h
diff options
context:
space:
mode:
authorDmitry Vyukov <dvyukov@google.com>2024-08-14 17:46:34 +0200
committerDmitry Vyukov <dvyukov@google.com>2024-08-16 09:31:43 +0000
commitc3a6603be2cc031a8f2fa69e757e04a4ce647080 (patch)
tree863f68e6614951e732460b4725dd114fcedcfb7b /executor/snapshot.h
parent5340a9ab4c1ab7801ad1055041dec2c2ff50a254 (diff)
executor: protect kcov/output regions with pkeys
Protect KCOV regions with pkeys if they are available. Protect output region with pkeys in snapshot mode. Snapshot mode is especially sensitive to output buffer corruption since its location is not randomized.
Diffstat (limited to 'executor/snapshot.h')
-rw-r--r--executor/snapshot.h9
1 files changed, 9 insertions, 0 deletions
diff --git a/executor/snapshot.h b/executor/snapshot.h
index 5479a162f..ce3e355b0 100644
--- a/executor/snapshot.h
+++ b/executor/snapshot.h
@@ -87,6 +87,11 @@ static void FindIvshmemDevices()
input, static_cast<uint64>(rpc::Const::MaxInputSize));
debug("mapped shmem output at at %p/%llu\n",
output, static_cast<uint64>(rpc::Const::MaxOutputSize));
+#if GOOS_linux
+ if (pkeys_enabled && pkey_mprotect(output, static_cast<uint64>(rpc::Const::MaxOutputSize),
+ PROT_READ | PROT_WRITE, RESERVED_PKEY))
+ exitf("failed to pkey_mprotect output buffer");
+#endif
}
close(res2);
}
@@ -175,6 +180,8 @@ static void TouchMemory(void* ptr, size_t size)
#if SYZ_EXECUTOR_USES_FORK_SERVER
static void SnapshotPrepareParent()
{
+ // This allows access to the output region.
+ CoverAccessScope scope(nullptr);
TouchMemory((char*)output_data + output_size - kOutputPopulate, kOutputPopulate);
// Notify SnapshotStart that we finished prefaulting memory in the parent.
output_data->completed = 1;
@@ -188,6 +195,7 @@ static void SnapshotPrepareParent()
static void SnapshotStart()
{
debug("SnapshotStart\n");
+ CoverAccessScope scope(nullptr);
// Prefault as much memory as we can before the snapshot is taken.
// Also pre-create some threads and let them block.
// This is intended to make execution after each snapshot restore faster,
@@ -241,6 +249,7 @@ static void SnapshotStart()
NORETURN static void SnapshotDone(bool failed)
{
debug("SnapshotDone\n");
+ CoverAccessScope scope(nullptr);
uint32 num_calls = output_data->num_calls.load(std::memory_order_relaxed);
auto data = finish_output(output_data, 0, 0, num_calls, 0, 0, failed ? kFailStatus : 0, nullptr);
ivs.hdr->output_offset = data.data() - reinterpret_cast<volatile uint8_t*>(ivs.hdr);