<feed xmlns='http://www.w3.org/2005/Atom'>
<title>kernel/linux.git/fs/btrfs/zstd.c, branch v6.18.22</title>
<subtitle>Linux kernel stable tree (mirror)</subtitle>
<id>https://git.radix-linux.su/kernel/linux.git/atom?h=v6.18.22</id>
<link rel='self' href='https://git.radix-linux.su/kernel/linux.git/atom?h=v6.18.22'/>
<link rel='alternate' type='text/html' href='https://git.radix-linux.su/kernel/linux.git/'/>
<updated>2025-09-23T06:49:26+00:00</updated>
<entry>
<title>btrfs: add unlikely annotations to branches leading to EIO</title>
<updated>2025-09-23T06:49:26+00:00</updated>
<author>
<name>David Sterba</name>
<email>dsterba@suse.com</email>
</author>
<published>2025-09-17T17:53:55+00:00</published>
<link rel='alternate' type='text/html' href='https://git.radix-linux.su/kernel/linux.git/commit/?id=cc53bd2085c8fa7b199a9a8e10e634b62a6d3fa8'/>
<id>urn:sha1:cc53bd2085c8fa7b199a9a8e10e634b62a6d3fa8</id>
<content type='text'>
The unlikely() annotation is a static prediction hint that compiler may
use to reorder code out of hot path. We use it elsewhere (namely
tree-checker.c) for error branches that almost never happen, where
EIO is one of them.

Reviewed-by: Filipe Manana &lt;fdmanana@suse.com&gt;
Signed-off-by: David Sterba &lt;dsterba@suse.com&gt;
</content>
</entry>
<entry>
<title>btrfs: prepare zstd to support bs &gt; ps cases</title>
<updated>2025-09-23T06:49:24+00:00</updated>
<author>
<name>Qu Wenruo</name>
<email>wqu@suse.com</email>
</author>
<published>2025-09-08T06:58:16+00:00</published>
<link rel='alternate' type='text/html' href='https://git.radix-linux.su/kernel/linux.git/commit/?id=a6452b85b3e55aafceb84c25784f25f63ba620b0'/>
<id>urn:sha1:a6452b85b3e55aafceb84c25784f25f63ba620b0</id>
<content type='text'>
This involves converting the following functions to use proper folio
sizes/shifts:

- zstd_compress_folios()
- zstd_decompress_bio()

The function zstd_decompress() is already using block size correctly
without using page size, thus it needs no modification.

And since zstd compression is calling kmap_local_folio(), the existing
code cannot handle large folios with HIGHMEM, as kmap_local_folio()
requires us to handle one page range each time.

I do not really think it's worth to spend time on some feature that will
be deprecated eventually.  So here just add an extra explicit rejection
for bs &gt; ps with HIGHMEM feature enabled kernels.

Signed-off-by: Qu Wenruo &lt;wqu@suse.com&gt;
Reviewed-by: David Sterba &lt;dsterba@suse.com&gt;
Signed-off-by: David Sterba &lt;dsterba@suse.com&gt;
</content>
</entry>
<entry>
<title>btrfs: prepare compression folio alloc/free for bs &gt; ps cases</title>
<updated>2025-09-23T06:49:24+00:00</updated>
<author>
<name>Qu Wenruo</name>
<email>wqu@suse.com</email>
</author>
<published>2025-09-08T06:37:57+00:00</published>
<link rel='alternate' type='text/html' href='https://git.radix-linux.su/kernel/linux.git/commit/?id=c2ffb1ec1a7cfc754c1d2fe66d317f0aa4c0f1e6'/>
<id>urn:sha1:c2ffb1ec1a7cfc754c1d2fe66d317f0aa4c0f1e6</id>
<content type='text'>
This includes the following preparation for bs &gt; ps cases:

- Always alloc/free the folio directly if bs &gt; ps
  This adds a new @fs_info parameter for btrfs_alloc_compr_folio(), thus
  affecting all compression algorithms.

  For btrfs_free_compr_folio() it needs no parameter for now, as we can
  use the folio size to skip the caching part.

  For now the change is just to passing a @fs_info into the function,
  all the folio size assumption is still based on page size.

- Properly zero the last folio in compress_file_range()
  Since the compressed folios can be larger than a page, we need to
  properly zero the whole folio.

- Use correct folio size for btrfs_add_compressed_bio_folios()
  Instead of page size, use the correct folio size.

- Use correct folio size/shift for btrfs_compress_filemap_get_folio()
  As we are not only using simple page sized folios anymore.

- Use correct folio size for btrfs_decompress()
  There is an ASSERT() making sure the decompressed range is no larger
  than a page, which will be triggered for bs &gt; ps cases.

- Skip readahead for compressed pages
  Similar to subpage cases.

- Make btrfs_alloc_folio_array() to accept a new @order parameter

- Add a helper to calculate the minimal folio size

All those changes should not affect the existing bs &lt;= ps handling.

Signed-off-by: Qu Wenruo &lt;wqu@suse.com&gt;
Reviewed-by: David Sterba &lt;dsterba@suse.com&gt;
Signed-off-by: David Sterba &lt;dsterba@suse.com&gt;
</content>
</entry>
<entry>
<title>btrfs: reduce compression workspace buffer space to block size</title>
<updated>2025-09-23T06:49:16+00:00</updated>
<author>
<name>Qu Wenruo</name>
<email>wqu@suse.com</email>
</author>
<published>2025-08-14T01:14:48+00:00</published>
<link rel='alternate' type='text/html' href='https://git.radix-linux.su/kernel/linux.git/commit/?id=74e8f002b772686408d62e420d9f70a4bcb1c2c4'/>
<id>urn:sha1:74e8f002b772686408d62e420d9f70a4bcb1c2c4</id>
<content type='text'>
Currently the compression workspace buffer size is always based on
PAGE_SIZE, but btrfs has support subpage sized block size for some time.

This means for one-shot compression algorithm like lzo, we're wasting
quite some memory if the block size is smaller than page size, as the
LZO only works on one block (thus one-shot).

On 64K page sized systems with 4K block size, it means we only need at
most 8K buffer space for lzo, but in reality we're allocating 64K
buffer.

So to reduce the memory usage, change all workspace buffer to base its
size based on block size other than page size.

Signed-off-by: Qu Wenruo &lt;wqu@suse.com&gt;
Reviewed-by: David Sterba &lt;dsterba@suse.com&gt;
Signed-off-by: David Sterba &lt;dsterba@suse.com&gt;
</content>
</entry>
<entry>
<title>btrfs: rename btrfs_compress_op to btrfs_compress_levels</title>
<updated>2025-09-23T06:49:16+00:00</updated>
<author>
<name>Qu Wenruo</name>
<email>wqu@suse.com</email>
</author>
<published>2025-08-14T01:05:23+00:00</published>
<link rel='alternate' type='text/html' href='https://git.radix-linux.su/kernel/linux.git/commit/?id=0d0b80929eff93e7e0323060899d04905b8e6de9'/>
<id>urn:sha1:0d0b80929eff93e7e0323060899d04905b8e6de9</id>
<content type='text'>
Since all workspace managers are per-fs, there is no need nor no way to
store them inside btrfs_compress_op::wsm anymore.

With that said, we can do the following modifications:

- Remove zstd_workspace_mananger::ops
  Zstd always grab the global btrfs_compress_op[].
- Remove btrfs_compress_op::wsm member
- Rename btrfs_compress_op to btrfs_compress_levels

This should make it more clear that btrfs_compress_levels structures are
only to indicate the levels of each compress algorithm.

Signed-off-by: Qu Wenruo &lt;wqu@suse.com&gt;
Reviewed-by: David Sterba &lt;dsterba@suse.com&gt;
Signed-off-by: David Sterba &lt;dsterba@suse.com&gt;
</content>
</entry>
<entry>
<title>btrfs: cleanup the per-module compression workspace managers</title>
<updated>2025-09-23T06:49:16+00:00</updated>
<author>
<name>Qu Wenruo</name>
<email>wqu@suse.com</email>
</author>
<published>2025-08-14T00:59:58+00:00</published>
<link rel='alternate' type='text/html' href='https://git.radix-linux.su/kernel/linux.git/commit/?id=9c8f4cf45651b8f07bd06df443871d526dc53cea'/>
<id>urn:sha1:9c8f4cf45651b8f07bd06df443871d526dc53cea</id>
<content type='text'>
Since all workspaces are handled by the per-fs workspace managers, we
can safely remove the old per-module managers.

Signed-off-by: Qu Wenruo &lt;wqu@suse.com&gt;
Reviewed-by: David Sterba &lt;dsterba@suse.com&gt;
Signed-off-by: David Sterba &lt;dsterba@suse.com&gt;
</content>
</entry>
<entry>
<title>btrfs: migrate to use per-fs workspace manager</title>
<updated>2025-09-23T06:49:15+00:00</updated>
<author>
<name>Qu Wenruo</name>
<email>wqu@suse.com</email>
</author>
<published>2025-08-14T00:19:50+00:00</published>
<link rel='alternate' type='text/html' href='https://git.radix-linux.su/kernel/linux.git/commit/?id=856d46c31343169a566f44035c4c74b2f0842438'/>
<id>urn:sha1:856d46c31343169a566f44035c4c74b2f0842438</id>
<content type='text'>
There are several interfaces involved for each algorithm:

- alloc workspace
  All algorithms allocate a workspace without the need for workspace
  manager.
  So no change needs to be done.

- get workspace
  This involves checking the workspace manager to find a free one, and
  if not, allocate a new one.

  For none and lzo, they share the same generic btrfs_get_workspace()
  helper, only needs to update that function to use the per-fs manager.

  For zlib it uses a wrapper around btrfs_get_workspace(), so no special
  work needed.

  For zstd, update zstd_find_workspace() and zstd_get_workspace() to
  utilize the per-fs manager.

- put workspace
  For none/zlib/lzo they share the same btrfs_put_workspace(), update
  that function to use the per-fs manager.

  For zstd, it's zstd_put_workspace(), the same update.

- zstd specific timer
  This is the timer to reclaim workspace, change it to grab the per-fs
  workspace manager instead.

Now all workspace are managed by the per-fs manager.

Signed-off-by: Qu Wenruo &lt;wqu@suse.com&gt;
Reviewed-by: David Sterba &lt;dsterba@suse.com&gt;
Signed-off-by: David Sterba &lt;dsterba@suse.com&gt;
</content>
</entry>
<entry>
<title>btrfs: add workspace manager initialization for zstd</title>
<updated>2025-09-23T06:49:15+00:00</updated>
<author>
<name>Qu Wenruo</name>
<email>wqu@suse.com</email>
</author>
<published>2025-08-13T05:35:20+00:00</published>
<link rel='alternate' type='text/html' href='https://git.radix-linux.su/kernel/linux.git/commit/?id=330f02b136a8c2e025548683c265fc2be844614c'/>
<id>urn:sha1:330f02b136a8c2e025548683c265fc2be844614c</id>
<content type='text'>
This involves:

- Add zstd_alloc_workspace_manager() and zstd_free_workspace_manager()
  Those two functions will accept an fs_info pointer, and alloc/free
  fs_info-&gt;compr_wsm[BTRFS_COMPRESS_ZSTD] pointer.

- Add btrfs_alloc_compress_wsm() and btrfs_free_compress_wsm()
  Those are helpers allocating the workspace managers for all
  algorithms.
  For now only zstd is supported, and the timing is a little unusual,
  the btrfs_alloc_compress_wsm() should only be called after the
  sectorsize being initialized.

  Meanwhile btrfs_free_fs_info_compress() is called in
  btrfs_free_fs_info().

- Move the definition of btrfs_compression_type to "fs.h"
  The reason is that "compression.h" has already included "fs.h", thus
  we can not just include "compression.h" to get the definition of
  BTRFS_NR_COMPRESS_TYPES to define fs_info::compr_wsm[].

For now the per-fs zstd workspace manager won't really have any effect,
and all compression is still going through the global workspace manager.

Signed-off-by: Qu Wenruo &lt;wqu@suse.com&gt;
Reviewed-by: David Sterba &lt;dsterba@suse.com&gt;
Signed-off-by: David Sterba &lt;dsterba@suse.com&gt;
</content>
</entry>
<entry>
<title>btrfs: add an fs_info parameter for compression workspace manager</title>
<updated>2025-09-23T06:49:15+00:00</updated>
<author>
<name>Qu Wenruo</name>
<email>wqu@suse.com</email>
</author>
<published>2025-08-13T05:03:38+00:00</published>
<link rel='alternate' type='text/html' href='https://git.radix-linux.su/kernel/linux.git/commit/?id=2c5cca03c1738e1342cbe57671d463f275c00623'/>
<id>urn:sha1:2c5cca03c1738e1342cbe57671d463f275c00623</id>
<content type='text'>
[BACKGROUND]
Currently btrfs shares workspaces and their managers for all filesystems,
this is mostly fine as all those workspaces are using page size based
buffers, and btrfs only support block size (bs) &lt;= page size (ps).

This means even if bs &lt; ps, we at most waste some buffer space in the
workspace, but everything will still work fine.

The problem here is that is limiting our support for bs &gt; ps cases.

As now a workspace now may need larger buffer to handle bs &gt; ps cases,
but since the pool has no way to distinguish different workspaces, a
regular workspace (which is still using buffer size based on ps) can be
passed to a btrfs whose bs &gt; ps.

In that case the buffer is not large enough, and will cause various
problems.

[ENHANCEMENT]
To prepare for the per-fs workspace migration, add an fs_info parameter
to all workspace related functions.

For now this new fs_info parameter is not yet utilized.

Signed-off-by: Qu Wenruo &lt;wqu@suse.com&gt;
Reviewed-by: David Sterba &lt;dsterba@suse.com&gt;
Signed-off-by: David Sterba &lt;dsterba@suse.com&gt;
</content>
</entry>
<entry>
<title>btrfs: use blocksize to check if compression is making things larger</title>
<updated>2025-09-22T08:54:31+00:00</updated>
<author>
<name>Qu Wenruo</name>
<email>wqu@suse.com</email>
</author>
<published>2025-08-11T00:13:42+00:00</published>
<link rel='alternate' type='text/html' href='https://git.radix-linux.su/kernel/linux.git/commit/?id=0a6dcd42353b96ab4a74796aed1541591de5890c'/>
<id>urn:sha1:0a6dcd42353b96ab4a74796aed1541591de5890c</id>
<content type='text'>
[BEHAVIOR DIFFERENCE BETWEEN COMPRESSION ALGOS]
Currently LZO compression algorithm will check if we're making the
compressed data larger after compressing more than 2 blocks.

But zlib and zstd do the same checks after compressing more than 8192
bytes.

This is not a big deal, but since we're already supporting larger block
size (e.g. 64K block size if page size is also 64K), this check is not
suitable for all block sizes.

For example, if our page and block size are both 16KiB, and after the
first block compressed using zlib, the resulted compressed data is
slightly  larger than 16KiB, we will immediately abort the compression.

This makes zstd and zlib compression algorithms to behave slightly
different from LZO, which only aborts after compressing two blocks.

[ENHANCEMENT]
To unify the behavior, only abort the compression after compressing at
least two blocks.

Reviewed-by: Anand Jain &lt;anand.jain@oracle.com&gt;
Signed-off-by: Qu Wenruo &lt;wqu@suse.com&gt;
Reviewed-by: David Sterba &lt;dsterba@suse.com&gt;
Signed-off-by: David Sterba &lt;dsterba@suse.com&gt;
</content>
</entry>
</feed>
