Commit c7bfaff4 authored by Linus Torvalds's avatar Linus Torvalds
Browse files
Pull udf and ext2 updates from Jan Kara:
 "A few udf and ext2 fixes and cleanups"

* tag 'fs_for_v6.17-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/jack/linux-fs:
  udf: Verify partition map count
  udf: stop using write_cache_pages
  ext2: Handle fiemap on empty files to prevent EINVAL
parents 1edaac34 1a112016
Loading
Loading
Loading
Loading
+11 −1
Original line number Diff line number Diff line
@@ -895,9 +895,19 @@ int ext2_fiemap(struct inode *inode, struct fiemap_extent_info *fieinfo,
		u64 start, u64 len)
{
	int ret;
	loff_t i_size;

	inode_lock(inode);
	len = min_t(u64, len, i_size_read(inode));
	i_size = i_size_read(inode);
	/*
	 * iomap_fiemap() returns EINVAL for 0 length. Make sure we don't trim
	 * length to 0 but still trim the range as much as possible since
	 * ext2_get_blocks() iterates unmapped space block by block which is
	 * slow.
	 */
	if (i_size == 0)
		i_size = 1;
	len = min_t(u64, len, i_size);
	ret = iomap_fiemap(inode, fieinfo, start, len, &ext2_iomap_ops);
	inode_unlock(inode);

+16 −12
Original line number Diff line number Diff line
@@ -181,19 +181,23 @@ static void udf_write_failed(struct address_space *mapping, loff_t to)
	}
}

static int udf_adinicb_writepage(struct folio *folio,
				 struct writeback_control *wbc, void *data)
static int udf_adinicb_writepages(struct address_space *mapping,
		      struct writeback_control *wbc)
{
	struct inode *inode = folio->mapping->host;
	struct inode *inode = mapping->host;
	struct udf_inode_info *iinfo = UDF_I(inode);
	struct folio *folio = NULL;
	int error = 0;

	while ((folio = writeback_iter(mapping, wbc, folio, &error))) {
		BUG_ON(!folio_test_locked(folio));
		BUG_ON(folio->index != 0);
	memcpy_from_file_folio(iinfo->i_data + iinfo->i_lenEAttr, folio, 0,
		       i_size_read(inode));
		memcpy_from_file_folio(iinfo->i_data + iinfo->i_lenEAttr, folio,
				0, i_size_read(inode));
		folio_unlock(folio);
	mark_inode_dirty(inode);
	}

	mark_inode_dirty(inode);
	return 0;
}

@@ -203,9 +207,9 @@ static int udf_writepages(struct address_space *mapping,
	struct inode *inode = mapping->host;
	struct udf_inode_info *iinfo = UDF_I(inode);

	if (iinfo->i_alloc_type != ICBTAG_FLAG_AD_IN_ICB)
	if (iinfo->i_alloc_type == ICBTAG_FLAG_AD_IN_ICB)
		return udf_adinicb_writepages(mapping, wbc);
	return mpage_writepages(mapping, wbc, udf_get_block_wb);
	return write_cache_pages(mapping, wbc, udf_adinicb_writepage, NULL);
}

static void udf_adinicb_read_folio(struct folio *folio)
+11 −2
Original line number Diff line number Diff line
@@ -1440,7 +1440,7 @@ static int udf_load_logicalvol(struct super_block *sb, sector_t block,
	struct genericPartitionMap *gpm;
	uint16_t ident;
	struct buffer_head *bh;
	unsigned int table_len;
	unsigned int table_len, part_map_count;
	int ret;

	bh = udf_read_tagged(sb, block, block, &ident);
@@ -1461,7 +1461,16 @@ static int udf_load_logicalvol(struct super_block *sb, sector_t block,
					   "logical volume");
	if (ret)
		goto out_bh;
	ret = udf_sb_alloc_partition_maps(sb, le32_to_cpu(lvd->numPartitionMaps));

	part_map_count = le32_to_cpu(lvd->numPartitionMaps);
	if (part_map_count > table_len / sizeof(struct genericPartitionMap1)) {
		udf_err(sb, "error loading logical volume descriptor: "
			"Too many partition maps (%u > %u)\n", part_map_count,
			table_len / (unsigned)sizeof(struct genericPartitionMap1));
		ret = -EIO;
		goto out_bh;
	}
	ret = udf_sb_alloc_partition_maps(sb, part_map_count);
	if (ret)
		goto out_bh;