From patchwork Sun Apr 12 08:57:03 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: stijn rutjens X-Patchwork-Id: 11484467 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 33A9B13B2 for ; Sun, 12 Apr 2020 08:58:23 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.kernel.org (Postfix) with ESMTP id 019F720708 for ; Sun, 12 Apr 2020 08:58:22 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="oWRZDqFH" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1725907AbgDLI5S (ORCPT ); Sun, 12 Apr 2020 04:57:18 -0400 Received: from mail-qt1-f182.google.com ([209.85.160.182]:33335 "EHLO mail-qt1-f182.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1725832AbgDLI5S (ORCPT ); Sun, 12 Apr 2020 04:57:18 -0400 Received: by mail-qt1-f182.google.com with SMTP id x2so4993762qtr.0 for ; Sun, 12 Apr 2020 01:57:16 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=mime-version:from:date:message-id:subject:to; bh=6pD3nrZnTMZ7AVuyl49L1slWpdN/MQYroJhleW81+V8=; b=oWRZDqFHpNTdnUH2diNJrhj5eCIkc48TZzFPnpRfpW+au/VSNJMpcb1RxeqbYt97U1 rDxg9JZ45IAqZXwwZTVS1rxq11yLH/3siHEwWfPLtq8z/oa8Jsi+VW3NygpokkYTUQWA cxAuqYLkdESaV7mfGZKomDjZBYuxxbLCZvChwMtTEu5igDHlCtprFSXL4sphDb0H+DlK 6uAi40/4aXXqYCzULTFFM4BkRTniv61l3GjlrNC35zcTj/s/K9GS5lVTgPBHNaKHG7Dt TVK1MSBLWvjg/SdzUOdpbVhEhaRCynWHWXL32cVKmpooR2ckMmv2NrwJ+1lvrvp0LUFb qwsA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:mime-version:from:date:message-id:subject:to; bh=6pD3nrZnTMZ7AVuyl49L1slWpdN/MQYroJhleW81+V8=; b=tEu0JI9kZR23abJMyq/tlBOva4xVDsOme/iWi/OCpAjvGGhVBpA1rz9xCrfm281IqN ZOTBUABR0X0TbigtRMfIJeuAfB4i4/bRJRVk2eJLB6n1W2f8Ox+Cxu0F/TlxLcxVBWp2 Q66w4ULuhNoTcc92ToRBAFOr0sXcHbX2PLiGOwFvj47uZJvfw3k8Ftq2oH8n1MZmZWlG 4jVyG1P9xDdtrdwJbHm9CrM7SsVg2SNsP8vTSArmuKXDKHcV9EMt5pP9PRUbfT4uruBA q7ENjPZNxu3iwespMp+oDTeluvpXrRLKmAkwIM7EtsYtvSykxhr9Pn2VDCQ9CME5P3Th bLpQ== X-Gm-Message-State: AGi0PubWyprucEYXlYOn40MiA27AzW6ZFN20kG4gtFiNtFJQ0cqzvUtA +V3HKQQ/7rUjpDya8zYxcnoPWnTTPWM9EJoyfxV0hB5eTXk= X-Google-Smtp-Source: APiQypI8QXsKaMlqzQLoCbJ+4/GF2UEP11+4w236PXQvdGHC0XRzyRgm8DIchAPNo96Zvv7zmP4or1t+o3ParIPiRC8= X-Received: by 2002:ac8:1b70:: with SMTP id p45mr6656749qtk.258.1586681835206; Sun, 12 Apr 2020 01:57:15 -0700 (PDT) MIME-Version: 1.0 From: stijn rutjens Date: Sun, 12 Apr 2020 10:57:03 +0200 Message-ID: Subject: [PATCH] btrfs: allow setting per extent compression To: linux-btrfs@vger.kernel.org Sender: linux-btrfs-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-btrfs@vger.kernel.org Hi all, As mentioned in https://github.com/kdave/btrfs-progs/issues/184 it would be nice to be able to set the compression level per extent (or file) from the IOCTL interface. I'm not sure how submitting patches to mailing lists works, but I have attached a patch which implements this. Any and all feedback is appreciated. Kind regards, Stijn Rutjens diff --git a/fs/btrfs/file-item.c b/fs/btrfs/file-item.c index bb374042d..e1603e1cf 100644 --- a/fs/btrfs/file-item.c +++ b/fs/btrfs/file-item.c @@ -67,7 +67,7 @@ int btrfs_insert_file_extent(struct btrfs_trans_handle *trans, btrfs_set_file_extent_ram_bytes(leaf, item, ram_bytes); btrfs_set_file_extent_generation(leaf, item, trans->transid); btrfs_set_file_extent_type(leaf, item, BTRFS_FILE_EXTENT_REG); - btrfs_set_file_extent_compression(leaf, item, compression); + btrfs_set_file_extent_compression(leaf, item, compression & 0xF); btrfs_set_file_extent_encryption(leaf, item, encryption); btrfs_set_file_extent_other_encoding(leaf, item, other_encoding); diff --git a/fs/btrfs/inode.c b/fs/btrfs/inode.c index dbc9bcaf5..3285d4bd3 100644 --- a/fs/btrfs/inode.c +++ b/fs/btrfs/inode.c @@ -227,7 +227,7 @@ static int insert_inline_extent(struct btrfs_trans_handle *trans, compressed_size -= cur_size; } btrfs_set_file_extent_compression(leaf, ei, - compress_type); + compress_type & 0XF); } else { page = find_get_page(inode->i_mapping, start >> PAGE_SHIFT); @@ -573,14 +573,31 @@ static noinline int compress_file_range(struct async_chunk *async_chunk) } /* Compression level is applied here and only here */ - ret = btrfs_compress_pages( - compress_type | (fs_info->compress_level << 4), - inode->i_mapping, start, - pages, - &nr_pages, - &total_in, - &total_compressed); - + /* + * Check if the upper bits are set, and if so, + * take them as the compression level. + * the inode compression level takes precendence, if set + */ + if ((compress_type & 0xF) == compress_type) { + ret = btrfs_compress_pages( + compress_type | (fs_info->compress_level << 4), + inode->i_mapping, start, + pages, + &nr_pages, + &total_in, + &total_compressed); + } else { + int compress_level = btrfs_compress_set_level( + compress_type & 0xF, + compress_type>>4); + ret = btrfs_compress_pages( + compress_type | (compress_level << 4), + inode->i_mapping, start, + pages, + &nr_pages, + &total_in, + &total_compressed); + } if (!ret) { unsigned long offset = offset_in_page(total_compressed); struct page *page = pages[nr_pages - 1]; @@ -2362,7 +2379,7 @@ static int insert_reserved_file_extent(struct btrfs_trans_handle *trans, btrfs_set_file_extent_offset(leaf, fi, 0); btrfs_set_file_extent_num_bytes(leaf, fi, num_bytes); btrfs_set_file_extent_ram_bytes(leaf, fi, ram_bytes); - btrfs_set_file_extent_compression(leaf, fi, compression); + btrfs_set_file_extent_compression(leaf, fi, compression & 0xF); btrfs_set_file_extent_encryption(leaf, fi, encryption); btrfs_set_file_extent_other_encoding(leaf, fi, other_encoding); diff --git a/fs/btrfs/ioctl.c b/fs/btrfs/ioctl.c index 0fa1c386d..2a9c1f312 100644 --- a/fs/btrfs/ioctl.c +++ b/fs/btrfs/ioctl.c @@ -1414,7 +1414,11 @@ int btrfs_defrag_file(struct inode *inode, struct file *file, return -EINVAL; if (do_compress) { - if (range->compress_type >= BTRFS_NR_COMPRESS_TYPES) + /* + * The bottom 4 bits of compress_type are for used for the + * compression type, the other bits for the compression level + */ + if ((range->compress_type & 0xF) >= BTRFS_NR_COMPRESS_TYPES) return -EINVAL; if (range->compress_type) compress_type = range->compress_type; @@ -1572,9 +1576,9 @@ int btrfs_defrag_file(struct inode *inode, struct file *file, filemap_flush(inode->i_mapping); } - if (range->compress_type == BTRFS_COMPRESS_LZO) { + if ((range->compress_type & 0xF) == BTRFS_COMPRESS_LZO) { btrfs_set_fs_incompat(fs_info, COMPRESS_LZO); - } else if (range->compress_type == BTRFS_COMPRESS_ZSTD) { + } else if ((range->compress_type & 0xF) == BTRFS_COMPRESS_ZSTD) { btrfs_set_fs_incompat(fs_info, COMPRESS_ZSTD); }