From patchwork Fri Feb 9 17:06:04 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?G=C3=BCnther_Noack?= X-Patchwork-Id: 13551649 Received: from mail-yb1-f202.google.com (mail-yb1-f202.google.com [209.85.219.202]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 830D5745ED for ; Fri, 9 Feb 2024 17:06:18 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=209.85.219.202 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1707498380; cv=none; b=kLbvt1JhqhkeU5iKNah+pvKhBUyvx/zPhZ4hscGxCwUldsDBoAK6IT4b78zi0JYFR/lma76VdoKHcjlfkB7CChUe+olByh0Tbq5DmPCEEKmZTLaIhQewk5DED2FzFvXOwHO0eNtsSnArjM7yG7D4UemIT7Dj7riwm7D0lqTbMo8= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1707498380; c=relaxed/simple; bh=1jX4Fx5t4SwktKfo5+Q87o6SKKur3VTTUs3P/3yVMpw=; h=Date:Message-Id:Mime-Version:Subject:From:To:Cc:Content-Type; b=sKZKtWjnl3OlTsqwkr4fOUDsixyEtJtR/BQ2/+LLvYCvLjyqA9mB04GIZpnAEvUmzDLsA45JkDBSIL0R8cM1SLctDNI/tWJyg6I4esnqLaIr24NHfSHxiIG+BvsqPsORpmnzgA9JIYVYe30zUFagf6AZlzPdGizNsWl795osXCo= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=google.com; spf=pass smtp.mailfrom=flex--gnoack.bounces.google.com; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b=q5oy3ZE5; arc=none smtp.client-ip=209.85.219.202 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=google.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=flex--gnoack.bounces.google.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b="q5oy3ZE5" Received: by mail-yb1-f202.google.com with SMTP id 3f1490d57ef6-dc64b659a9cso2109829276.3 for ; Fri, 09 Feb 2024 09:06:18 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20230601; t=1707498377; x=1708103177; darn=vger.kernel.org; h=content-transfer-encoding:cc:to:from:subject:mime-version :message-id:date:from:to:cc:subject:date:message-id:reply-to; bh=KZw8obsheFmvG9vz8/vpHYuJUv4EkBvPf/qqGkzkm9Y=; b=q5oy3ZE557AtFmbkEraSfonhdUUnbRWeUPhtMTl3Em2m0VdP0aHVOjs5IcYMZI8HRi KKnAByW/VJFTs7eiFwN+2uPBXQOuIC8yGdK9RLPWgyuhnF6M26+jSJHONCmVasrOOrgM aMKNH5iUuQe3CYtxQuFuMQSAFGRGnd7v/3McIFy+68Qv1CpCpVY/HtrVU8TYLHQOi1QN q7tJ/CakN+nbF8rHMVsBbLcAeTZbNLwQIAywcU509+M9AHH8AaX84ovfV58YdNcof3Sd PEYZFmnajB4UXP7ktgNy0R/5i5dRXbMxEq59kuhhqLdOYDiTE9PbJ19tsZBaFAZPdSah E+KA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1707498377; x=1708103177; h=content-transfer-encoding:cc:to:from:subject:mime-version :message-id:date:x-gm-message-state:from:to:cc:subject:date :message-id:reply-to; bh=KZw8obsheFmvG9vz8/vpHYuJUv4EkBvPf/qqGkzkm9Y=; b=lwTL86dlwGBwIhbkmNr+72AsXA4c5QOBJzKfz+DWPZXMlxXkWXqudipjFE1n8Uht7c LH/7kHLI+gBz2xiTXpzvSXUkKYSk/ggCYUNKIB0XBMiy2kiZ5O3MDLvNavzdh0b+6TWX 7dapTL26JINRKTNE+NQs/VKB1/Q0appbmoeOA6WiKtfyhV2Bz8uSGHQ9t2XnpAF7WFeZ ZL3JdKG9qtc5B9ckMFWVr5+QlgFnhZ1fz+Qe7PSaw2GUIAUQkeLhuHKPjsPatSHAGQyY 5HqJ6xbeFHwW884ABC5J+W74McwUUitQSbeeNJRy4s9gV1wO0xSoZNyAERLcn8bKqX7O ZxWw== X-Gm-Message-State: AOJu0YzbrWZ013/nv++TXhb3Dhw39lWhdXhCxuqRcfX72L17hQJlhOY5 BicAyaOGMgdj7n2w/Lk0FCjd3bYF1tiFiB4gbFkLze2rzmXaig95OxoUflx/IBhH6dn5r4Z+8rd P+yz4s5sJwe+T6+3Vtd+bIifhx6OhGzWxhGg8jgQTrEfs2pd9wXXqflqubEi0fWTuQDTGGVYlUO PwjiwQbiGUZDQ66GITWYEmAhlwRh/TkDLAwEipQQWsa5GRaWX3bBpV X-Google-Smtp-Source: AGHT+IHn55JBR6ArMAPPgcy5gYGhWZsA1E+jwGa6Qk+BOhanejIDuSj5KiVN/4YJPWECS2+0BWsE1okf0jk= X-Received: from sport.zrh.corp.google.com ([2a00:79e0:9d:4:3162:977f:c07:bcd8]) (user=gnoack job=sendgmr) by 2002:a05:6902:1022:b0:dc6:207e:e8b1 with SMTP id x2-20020a056902102200b00dc6207ee8b1mr454882ybt.2.1707498377498; Fri, 09 Feb 2024 09:06:17 -0800 (PST) Date: Fri, 9 Feb 2024 18:06:04 +0100 Message-Id: <20240209170612.1638517-1-gnoack@google.com> Precedence: bulk X-Mailing-List: linux-security-module@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: Mime-Version: 1.0 X-Mailer: git-send-email 2.43.0.687.g38aa6559b0-goog Subject: [PATCH v9 0/8] Landlock: IOCTL support From: " =?utf-8?q?G=C3=BCnther_Noack?= " To: linux-security-module@vger.kernel.org, " =?utf-8?q?Micka=C3=ABl_Sala?= =?utf-8?q?=C3=BCn?= " Cc: Jeff Xu , Arnd Bergmann , Jorge Lucangeli Obes , Allen Webb , Dmitry Torokhov , Paul Moore , Konstantin Meskhidze , Matt Bobrowski , linux-fsdevel@vger.kernel.org, " =?utf-8?q?G=C3=BCnther_Noack?= " Hello! These patches add simple ioctl(2) support to Landlock. Objective ~~~~~~~~~ Make ioctl(2) requests restrictable with Landlock, in a way that is useful for real-world applications. Proposed approach ~~~~~~~~~~~~~~~~~ Introduce the LANDLOCK_ACCESS_FS_IOCTL right, which restricts the use of ioctl(2) on file descriptors. We attach IOCTL access rights to opened file descriptors, as we already do for LANDLOCK_ACCESS_FS_TRUNCATE. If LANDLOCK_ACCESS_FS_IOCTL is handled (restricted in the ruleset), the LANDLOCK_ACCESS_FS_IOCTL access right governs the use of all IOCTL commands. We make an exception for the common and known-harmless IOCTL commands FIOCLEX, FIONCLEX, FIONBIO and FIOASYNC. These IOCTL commands are always permitted. Their functionality is already available through fcntl(2). If additionally(!) the access rights LANDLOCK_ACCESS_FS_READ_FILE, LANDLOCK_ACCESS_FS_WRITE_FILE or LANDLOCK_ACCESS_FS_READ_DIR are handled, these access rights also unlock some IOCTL commands which are considered safe for use with files opened in these ways. As soon as these access rights are handled, the affected IOCTL commands can not be permitted through LANDLOCK_ACCESS_FS_IOCTL any more, but only be permitted through the respective more specific access rights. A full list of these access rights is listed below in this cover letter and in the documentation. I believe that this approach works for the majority of use cases, and offers a good trade-off between Landlock API and implementation complexity and flexibility when the feature is used. Current limitations ~~~~~~~~~~~~~~~~~~~ With this patch set, ioctl(2) requests can *not* be filtered based on file type, device number (dev_t) or on the ioctl(2) request number. On the initial RFC patch set [1], we have reached consensus to start with this simpler coarse-grained approach, and build additional IOCTL restriction capabilities on top in subsequent steps. [1] https://lore.kernel.org/linux-security-module/d4f1395c-d2d4-1860-3a02-2a0c023dd761@digikod.net/ Notable implications of this approach ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ * Existing inherited file descriptors stay unaffected when a program enables Landlock. This means in particular that in common scenarios, the terminal's IOCTLs (ioctl_tty(2)) continue to work. * ioctl(2) continues to be available for file descriptors acquired through means other than open(2). Example: Network sockets, memfd_create(2), file descriptors that are already open before the Landlock ruleset is enabled. Examples ~~~~~~~~ Starting a sandboxed shell from $HOME with samples/landlock/sandboxer: LL_FS_RO=/ LL_FS_RW=. ./sandboxer /bin/bash The LANDLOCK_ACCESS_FS_IOCTL right is part of the "read-write" rights here, so we expect that newly opened files outside of $HOME don't work with most IOCTL commands. * "stty" works: It probes terminal properties * "stty , who pointed this out in https://lore.kernel.org/all/f25be6663bcc4608adf630509f045a76@h3c.com/ and Mickaël, who fixed it through #include reordering. * Documentation changes * Reword "IOCTL commands" section a bit * s/permit/allow/ * s/access right/right/, if preceded by LANDLOCK_ACCESS_FS_* * s/IOCTL/FS_IOCTL/ in ASCII table * Update IOCTL grouping documentation in header file * Removed a few of the earlier commits in this patch set, which have already been merged. V8: * Documentation changes * userspace-api/landlock.rst: * Add an extra paragraph about how the IOCTL right combines when used with other access rights. * Explain better the circumstances under which passing of file descriptors between different Landlock domains can happen * limits.h: Add comment to explain public vs internal FS access rights * Add a paragraph in the commit to explain better why the IOCTL right works as it does V7: * in “landlock: Add IOCTL access right”: * Make IOCTL_GROUPS a #define so that static_assert works even on old compilers (bug reported by Intel about PowerPC GCC9 config) * Adapt indentation of IOCTL_GROUPS definition * Add missing dots in kernel-doc comments. * in “landlock: Remove remaining "inline" modifiers in .c files”: * explain reasoning in commit message V6: * Implementation: * Check that only publicly visible access rights can be used when adding a rule (rather than the synthetic ones). Thanks Mickaël for spotting that! * Move all functionality related to IOCTL groups and synthetic access rights into the same place at the top of fs.c * Move kernel doc to the .c file in one instance * Smaller code style issues (upcase IOCTL, vardecl at block start) * Remove inline modifier from functions in .c files * Tests: * use SKIP * Rename 'fd' to dir_fd and file_fd where appropriate * Remove duplicate "ioctl" mentions from test names * Rename "permitted" to "allowed", in ioctl and ftruncate tests * Do not add rules if access is 0, in test helper V5: * Implementation: * move IOCTL group expansion logic into fs.c (implementation suggested by mic) * rename IOCTL_CMD_G* constants to LANDLOCK_ACCESS_FS_IOCTL_GROUP* * fs.c: create ioctl_groups constant * add "const" to some variables * Formatting and docstring fixes (including wrong kernel-doc format) * samples/landlock: fix ABI version and fallback attribute (mic) * Documentation * move header documentation changes into the implementation commit * spell out how FIFREEZE, FITHAW and attribute-manipulation ioctls from fs/ioctl.c are handled * change ABI 4 to ABI 5 in some missing places V4: * use "synthetic" IOCTL access rights, as previously discussed * testing changes * use a large fixture-based test, for more exhaustive coverage, and replace some of the earlier tests with it * rebased on mic-next V3: * always permit the IOCTL commands FIOCLEX, FIONCLEX, FIONBIO, FIOASYNC and FIONREAD, independent of LANDLOCK_ACCESS_FS_IOCTL * increment ABI version in the same commit where the feature is introduced * testing changes * use FIOQSIZE instead of TTY IOCTL commands (FIOQSIZE works with regular files, directories and memfds) * run the memfd test with both Landlock enabled and disabled * add a test for the always-permitted IOCTL commands V2: * rebased on mic-next * added documentation * exercise ioctl(2) in the memfd test * test: Use layout0 for the test --- V1: https://lore.kernel.org/linux-security-module/20230502171755.9788-1-gnoack3000@gmail.com/ V2: https://lore.kernel.org/linux-security-module/20230623144329.136541-1-gnoack@google.com/ V3: https://lore.kernel.org/linux-security-module/20230814172816.3907299-1-gnoack@google.com/ V4: https://lore.kernel.org/linux-security-module/20231103155717.78042-1-gnoack@google.com/ V5: https://lore.kernel.org/linux-security-module/20231117154920.1706371-1-gnoack@google.com/ V6: https://lore.kernel.org/linux-security-module/20231124173026.3257122-1-gnoack@google.com/ V7: https://lore.kernel.org/linux-security-module/20231201143042.3276833-1-gnoack@google.com/ V8: https://lore.kernel.org/linux-security-module/20231208155121.1943775-1-gnoack@google.com/ Günther Noack (8): landlock: Add IOCTL access right selftests/landlock: Test IOCTL support selftests/landlock: Test IOCTL with memfds selftests/landlock: Test ioctl(2) and ftruncate(2) with open(O_PATH) selftests/landlock: Test IOCTLs on named pipes selftests/landlock: Check IOCTL restrictions for named UNIX domain sockets samples/landlock: Add support for LANDLOCK_ACCESS_FS_IOCTL landlock: Document IOCTL support Documentation/userspace-api/landlock.rst | 121 +++- include/uapi/linux/landlock.h | 55 +- samples/landlock/sandboxer.c | 13 +- security/landlock/fs.c | 227 +++++++- security/landlock/fs.h | 3 + security/landlock/limits.h | 11 +- security/landlock/ruleset.h | 2 +- security/landlock/syscalls.c | 19 +- tools/testing/selftests/landlock/base_test.c | 2 +- tools/testing/selftests/landlock/fs_test.c | 559 ++++++++++++++++++- 10 files changed, 963 insertions(+), 49 deletions(-) base-commit: 5b921b7dbe3e0df48a1d947b3813ac9ae18858c1