From patchwork Sun Nov 10 15:27:52 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Jens Axboe X-Patchwork-Id: 13869944 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from kanga.kvack.org (kanga.kvack.org [205.233.56.17]) by smtp.lore.kernel.org (Postfix) with ESMTP id 896E7D12D43 for ; Sun, 10 Nov 2024 15:29:17 +0000 (UTC) Received: by kanga.kvack.org (Postfix) id 111416B009F; Sun, 10 Nov 2024 10:29:17 -0500 (EST) Received: by kanga.kvack.org (Postfix, from userid 40) id 0C04F6B00A8; Sun, 10 Nov 2024 10:29:17 -0500 (EST) X-Delivered-To: int-list-linux-mm@kvack.org Received: by kanga.kvack.org (Postfix, from userid 63042) id EA37F6B00A6; Sun, 10 Nov 2024 10:29:16 -0500 (EST) X-Delivered-To: linux-mm@kvack.org Received: from relay.hostedemail.com (smtprelay0015.hostedemail.com [216.40.44.15]) by kanga.kvack.org (Postfix) with ESMTP id CC82A6B009F for ; Sun, 10 Nov 2024 10:29:16 -0500 (EST) Received: from smtpin23.hostedemail.com (a10.router.float.18 [10.200.18.1]) by unirelay04.hostedemail.com (Postfix) with ESMTP id 8BE071A0CF9 for ; Sun, 10 Nov 2024 15:29:16 +0000 (UTC) X-FDA: 82770567936.23.EA38116 Received: from mail-pg1-f176.google.com (mail-pg1-f176.google.com [209.85.215.176]) by imf22.hostedemail.com (Postfix) with ESMTP id A2FBDC0018 for ; Sun, 10 Nov 2024 15:28:25 +0000 (UTC) Authentication-Results: imf22.hostedemail.com; dkim=pass header.d=kernel-dk.20230601.gappssmtp.com header.s=20230601 header.b=YQCnes3F; dmarc=none; spf=pass (imf22.hostedemail.com: domain of axboe@kernel.dk designates 209.85.215.176 as permitted sender) smtp.mailfrom=axboe@kernel.dk ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=hostedemail.com; s=arc-20220608; t=1731252468; h=from:from:sender:reply-to:subject:subject:date:date: message-id:message-id:to:to:cc:cc:mime-version:mime-version: content-type:content-transfer-encoding:content-transfer-encoding: in-reply-to:references:dkim-signature; bh=WMc2BZOwmLfUUNk6EhelpeJQ4f3KdM89SU9iONc3Ots=; b=MSvWymHX4CmfwuHUQSR4BYmpwOJ9mRqL1xKBi45F6JQI4JW5wlDFKTtB0EYunUL9Gczra5 YrPDEZ0YMlSv2zM+KhIkvIQC3dGHKSRDxTwHApTWmsgytqVHE0XQpceYBpMyBCT43xE6lK AH6VENjejShSmBZzLaadaR77psnxTa0= ARC-Authentication-Results: i=1; imf22.hostedemail.com; dkim=pass header.d=kernel-dk.20230601.gappssmtp.com header.s=20230601 header.b=YQCnes3F; dmarc=none; spf=pass (imf22.hostedemail.com: domain of axboe@kernel.dk designates 209.85.215.176 as permitted sender) smtp.mailfrom=axboe@kernel.dk ARC-Seal: i=1; s=arc-20220608; d=hostedemail.com; t=1731252468; a=rsa-sha256; cv=none; b=jrT9DMHqStPTProbEe1HK+zbLY3e3/ufHPxr2nKxnrdVn3csHtzQtUT/kJc2/G4p/9VCid T4354l5ptngZ0XAycKSz0CgHBPksSVFamd7Z8Yas0Z18Tv1IXI3JBP0Y3GU7NRDC4MlqBk cR+zRtCzRuh04oaKrVew8d+u4mdMeoI= Received: by mail-pg1-f176.google.com with SMTP id 41be03b00d2f7-7ee6edc47abso2523292a12.3 for ; Sun, 10 Nov 2024 07:29:14 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=kernel-dk.20230601.gappssmtp.com; s=20230601; t=1731252553; x=1731857353; darn=kvack.org; h=content-transfer-encoding:mime-version:message-id:date:subject:cc :to:from:from:to:cc:subject:date:message-id:reply-to; bh=WMc2BZOwmLfUUNk6EhelpeJQ4f3KdM89SU9iONc3Ots=; b=YQCnes3FnjBoQkuH0gPTgDvK2g1/Kx6u9VGS1CgWQW4+pSIjYpzis96n9HDXJPEWgo TZloagRqF4a+B+5OiUWu6z+wuj/IpcARwKlH2KH7Q+2bDgIsjuzkuZLyCUfoq1z4eguN buk56LOYb9pI7e/IjKW+htGNOW9/kwJPi6sJHwrRyIMWHPI6itxPS+6+7CtH9mm+rTXi A+R19z8rVHmNH6PckKoPLkrJrft5GKParpzTagkCFxJ87J9y6tuT7BDDyFzwoMRv1fVd e0/Dl0Aqv6/tViJfAP1m5J7QbPONTmUjAjcRbdqiRPtgaHfId6M8S4RKvAG5wrzxVXFh WP/g== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1731252553; x=1731857353; h=content-transfer-encoding:mime-version:message-id:date:subject:cc :to:from:x-gm-message-state:from:to:cc:subject:date:message-id :reply-to; bh=WMc2BZOwmLfUUNk6EhelpeJQ4f3KdM89SU9iONc3Ots=; b=r/56ab8kiifdv/YAkX7I6RQUagRYpvrwWQ/PNU0u5f6yO4X3QwkcyeUFQ2qmWvje17 n2iHxG3XrKFnuGdazAImSylWCMvb1O2hDmBKEEuceT8P+SHnPp0kqlGIZbI00rtUrLiO C3TRys04krdDWEHL3A6A4mIe0DM+Jqgph7iTi851yNh2iPpOHhK9hzeSiiMovJBK7jom J4pfpzDHWjbFB/pd9vyWnUQMl/ech5kUeCXh+k4kXgrUbBtF072RcdvCKzgbNWgix3xl SZdYVX6S2exZb9ICLZJMUd5TNhjCMwH7gg51HMCzvR/Jf2r0osv+xXB7vi+PyhY+93yC sDPw== X-Gm-Message-State: AOJu0YxwjhSrSTAX3zeIqwvgptbMy14vg0WMNavbPz0SDvi0pajkVr1J IVJihWWCb1Ma21ZcW7Sd3qlLTx66cDjO8JrBgttVYv2Yk9Yde8NY/YBaeXjbOw3tM2RbwVuuK2o ChWA= X-Google-Smtp-Source: AGHT+IETALI0TZNk7iFvxtwupHcZ8wUtsRKgb47lHuBSuGblNAkHhnyAIoKBozbdHkor69Q0lPYHHA== X-Received: by 2002:a17:90b:2e42:b0:2e2:d175:5f8d with SMTP id 98e67ed59e1d1-2e9b1713587mr14936527a91.10.1731252552713; Sun, 10 Nov 2024 07:29:12 -0800 (PST) Received: from localhost.localdomain ([198.8.77.157]) by smtp.gmail.com with ESMTPSA id 98e67ed59e1d1-2e99a5f935dsm9940973a91.35.2024.11.10.07.29.11 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Sun, 10 Nov 2024 07:29:11 -0800 (PST) From: Jens Axboe To: linux-mm@kvack.org, linux-fsdevel@vger.kernel.org Cc: hannes@cmpxchg.org, clm@meta.com, linux-kernel@vger.kernel.org, willy@infradead.org Subject: [PATCHSET v2 0/15] Uncached buffered IO Date: Sun, 10 Nov 2024 08:27:52 -0700 Message-ID: <20241110152906.1747545-1-axboe@kernel.dk> X-Mailer: git-send-email 2.45.2 MIME-Version: 1.0 X-Rspam-User: X-Rspamd-Server: rspam03 X-Rspamd-Queue-Id: A2FBDC0018 X-Stat-Signature: s8h7zctrmitkdmsyh9my3hht959ee6w4 X-HE-Tag: 1731252505-326759 X-HE-Meta: U2FsdGVkX19Bymt22Z4+9KSyvyMg4BFmdJFkH8bEMr0htKE1MN+dUmi/uSkpq7mR/q8OsdffkeXtHSkxXZJsTVb7FDHqDgg5oPvnoQgXJphlYICu23eCEIqyxd0nhhaHN59lA0pyyNWWz44UjBnXScbVkHx1Au6Pwe++YMiDWQcWJcfwuF4W7oMKC5aEXAsBDoLx+aB8px7ShFBrw1HKIqmm3ZLCj0oYlY08RHacaqbSKgw6uNQBA2grVnNpuKRsySYlTaUGQS31ZyMX3PPGc9Gj73XEb5vtAX/uek1ZDBl4KiuNT3CJdkG0ba9YiWUVPi6DGcD1oj5BuY05/p2L8iRGJnw7qbtEwTkMMUcfA3IAiefcKo6+IQt+CWlUgLI7PWPtP5VzKf8BH6oSgkn+tq4EqGySAQ7OoZ4/R2sKoDJo6dPLS2Gxe13wgCBExSAEooykcNeqBvFO3Xh5jMdHDIllourt7hZrLg7FtTaqWsCIeJXxDmPnVTCugTUBRfitkaePEuswkni9l6lCwjce6/yUBRs8gdtok9s+uwUoffII6NXx2K35MM4uIDM6PkHpwY/c1AhsUzcnpyfZuoKw+xQ49ACtNKOn847LbWRWYZif7txjFwJDMJLwSDJ/HN6yATx2VOY+rXuAujFknXt7VlE4ttsmaLkfa+C1r44GDPBoVSviVWsdB0eRHndA5ypP3shhalC3GEYnisk+GnikZiPtk9h2aGjKaHqK2bPN5h0s7i7d9ShQdu+edoeIy+Tv0Q67zy89BK+RPyKs+ckDNIdzt2jejFQYMdkkVAX0avFmcwP0TolYA9WnXtlVah82vhWTCWd7hVsklFOeYDazuivDFlqTl6gztojAefLGJ3eYSBlPcRebkJZOGyHS3gKmE0TJ6oHL/M9zoFN+8pdQyCFVvhrbEivOI9vm+Ab6N5EPnGfxoXEYjZspgxSkecbPoZcOf05uXHBmz0PHRYY jrogky/X mPstNDsbmbCvfkp5k/XCQeSe+fxLa1YI2oPtDKROzxGFpDOiYhlKsRup0MV72eLjw8Rqy3K2DNUR1gWNM+EYwF4ruOtJzmp5n14EZ561mPBL+b+ST96j+M1JzOIOFxJgKzdE2gDLmDzFPyOg99XhpHuQfnS/xcvUJVQK9GEVLjePTXpgCb/2jYEsaoXuuCPUE0wDiHcsMv+CzHG1ExJIxfIq7ozvMXOf7h96YZ9BXwLsh079DxAp974BTiTWjveYBB+jGvwzWlQKdVEcIBcbpZjvAWgaXFxildneMx8g946Xyg2BgkJbLS0X7QO2l4wie0IpJDGpJz6mL1wKnH9JrsqDBfKVxUKrqa0dOuXHDbSMml7Y= X-Bogosity: Ham, tests=bogofilter, spamicity=0.000000, version=1.2.4 Sender: owner-linux-mm@kvack.org Precedence: bulk X-Loop: owner-majordomo@kvack.org List-ID: List-Subscribe: List-Unsubscribe: Hi, 5 years ago I posted patches adding support for RWF_UNCACHED, as a way to do buffered IO that isn't page cache persistent. The approach back then was to have private pages for IO, and then get rid of them once IO was done. But that then runs into all the issues that O_DIRECT has, in terms of synchronizing with the page cache. So here's a new approach to the same concent, but using the page cache as synchronization. That makes RWF_UNCACHED less special, in that it's just page cache IO, except it prunes the ranges once IO is completed. Why do this, you may ask? The tldr is that device speeds are only getting faster, while reclaim is not. Doing normal buffered IO can be very unpredictable, and suck up a lot of resources on the reclaim side. This leads people to use O_DIRECT as a work-around, which has its own set of restrictions in terms of size, offset, and length of IO. It's also inherently synchronous, and now you need async IO as well. While the latter isn't necessarily a big problem as we have good options available there, it also should not be a requirement when all you want to do is read or write some data without caching. Even on desktop type systems, a normal NVMe device can fill the entire page cache in seconds. On the big system I used for testing, there's a lot more RAM, but also a lot more devices. As can be seen in some of the results in the following patches, you can still fill RAM in seconds even when there's 1TB of it. Hence this problem isn't solely a "big hyperscaler system" issue, it's common across the board. Common for both reads and writes with RWF_UNCACHED is that they use the page cache for IO. Reads work just like a normal buffered read would, with the only exception being that the touched ranges will get pruned after data has been copied. For writes, the ranges will get writeback kicked off before the syscall returns, and then writeback completion will prune the range. Hence writes aren't synchronous, and it's easy to pipeline writes using RWF_UNCACHED. File systems need to support this. The patches add support for the generic filemap helpers, and for iomap. Then ext4 and XFS are marked as supporting it. The amount of code here is really trivial, and the only reason the fs opt-in is necessary is to have an RWF_UNCACHED IO return -EOPNOTSUPP just in case the fs doesn't use either the generic paths or iomap. Adding "support" to other file systems should be trivial, most of the time just a one-liner adding FOP_UNCACHED to the fop_flags in the file_operations struct. Performance results are in patch 7 for reads and patch 10 for writes, with the tldr being that I see about a 65% improvement in performance for both, with fully predictable IO times. CPU reduction is substantial as well, with no kswapd activity at all for reclaim when using uncached IO. Using it from applications is trivial - just set RWF_UNCACHED for the read or write, using pwritev2(2) or preadv2(2). For io_uring, same thing, just set RWF_UNCACHED in sqe->rw_flags for a buffered read/write operation. And that's it. The goal with this patchset was to make it less special than before. I think if you look at the diffstat you'll agree that this is the case. Patches 1..6 are just prep patches, and should have no functional changes at all. Patch 7 adds support for the filemap path for RWF_UNCACHED reads, patch 10 adds support for filemap RWF_UNCACHED writes, and patches 12..15 adds ext4 and xfs/iomap support iomap. Git tree available here: https://git.kernel.dk/cgit/linux/log/?h=buffered-uncached.5 fs/ext4/ext4.h | 1 + fs/ext4/file.c | 2 +- fs/ext4/inline.c | 7 ++- fs/ext4/inode.c | 18 ++++++- fs/ext4/page-io.c | 28 ++++++----- fs/iomap/buffered-io.c | 15 +++++- fs/xfs/xfs_aops.c | 7 ++- fs/xfs/xfs_file.c | 4 +- include/linux/fs.h | 10 +++- include/linux/iomap.h | 4 +- include/linux/page-flags.h | 5 ++ include/linux/pagemap.h | 34 +++++++++++++ include/trace/events/mmflags.h | 3 +- include/uapi/linux/fs.h | 6 ++- mm/filemap.c | 90 ++++++++++++++++++++++++++++------ mm/readahead.c | 22 +++++++-- mm/swap.c | 2 + mm/truncate.c | 9 ++-- 18 files changed, 218 insertions(+), 49 deletions(-) Since v1 - Move iocb->ki_flags checking into filemap_create_folio() - Use __folio_set_uncached() when marking a folio as uncached right after creation - Shuffle patches around to not have a bisection issue - Combine some patches - Add FGP_UNCACHED folio get flag. If set, newly created folios will get marked as uncached. - Add foliop_uncached to be able to pass whether this is an uncached folio creation or not into ->write_begin(). Fixes the issue of uncached writes pruning existing ranges. Not the prettiest, but the prospect of changing ->write_begin() is daunting. I did go that route but it's a lot of churn. Have the patch and the scars. - Ensure that both ext4 and xfs punt to their workqueue handling writeback completion for uncached writebacks, as we need workqueue context to prune ranges. - Add generic_uncached_write() helper to make it easy for file systems to prune the ranges. - Add folio_end_uncached() writeback completion helper, and also check in_task() in there. Can trigger if the fs needs hints on punting to a safe context for this completion, but normal writeback races with us and starts writeback on a range that includes uncached folios. - Rebase on current master