From c95837a6c131fbdf820db352a97d54fcbcbde6c0 Mon Sep 17 00:00:00 2001 From: Wiktor Garbacz Date: Thu, 11 Nov 2021 06:10:12 -0800 Subject: [PATCH] Check and limit seccomp policy length. PiperOrigin-RevId: 409129756 Change-Id: Ib9937495966f545fb980eba04393db640af2325f --- sandboxed_api/sandbox2/client.cc | 3 +++ sandboxed_api/sandbox2/policybuilder.cc | 6 ++++++ sandboxed_api/sandbox2/policybuilder.h | 3 +++ 3 files changed, 12 insertions(+) diff --git a/sandboxed_api/sandbox2/client.cc b/sandboxed_api/sandbox2/client.cc index 63d118a..5ed3ee8 100644 --- a/sandboxed_api/sandbox2/client.cc +++ b/sandboxed_api/sandbox2/client.cc @@ -200,6 +200,9 @@ void Client::ApplyPolicyAndBecomeTracee() { "setting PR_SET_KEEPCAPS flag"); sock_fprog prog; + SAPI_RAW_CHECK(policy_.size() / sizeof(sock_filter) <= + std::numeric_limits::max(), + "seccomp policy too long"); prog.len = static_cast(policy_.size() / sizeof(sock_filter)); prog.filter = reinterpret_cast(&policy_.front()); diff --git a/sandboxed_api/sandbox2/policybuilder.cc b/sandboxed_api/sandbox2/policybuilder.cc index c0830b2..202dd06 100644 --- a/sandboxed_api/sandbox2/policybuilder.cc +++ b/sandboxed_api/sandbox2/policybuilder.cc @@ -786,6 +786,12 @@ std::vector PolicyBuilder::ResolveBpfFunc(BpfFunc f) { absl::StatusOr> PolicyBuilder::TryBuild() { auto output = absl::WrapUnique(new Policy()); + if (user_policy_.size() > kMaxUserPolicyLength) { + return absl::FailedPreconditionError( + absl::StrCat("User syscall policy is to long (", user_policy_.size(), + " > ", kMaxUserPolicyLength, ").")); + } + if (!last_status_.ok()) { return last_status_; } diff --git a/sandboxed_api/sandbox2/policybuilder.h b/sandboxed_api/sandbox2/policybuilder.h index 8a697be..b9f8c28 100644 --- a/sandboxed_api/sandbox2/policybuilder.h +++ b/sandboxed_api/sandbox2/policybuilder.h @@ -99,6 +99,9 @@ class PolicyBuilder final { }; static constexpr absl::string_view kDefaultHostname = "sandbox2"; + // Seccomp takes a 16-bit filter length, so the limit would be 64k. + // We set it lower so that there is for sure some room for the default policy. + static constexpr size_t kMaxUserPolicyLength = 30000; using BpfInitializer = std::initializer_list; using BpfFunc = const std::function(bpf_labels&)>&;