[Ocfs2-tools-devel] [PATCH 8/9] ocfs2-tools: add xattr support in fsck.ocfs2
Joel Becker
Joel.Becker at oracle.com
Fri Dec 19 14:54:57 PST 2008
On Fri, Dec 19, 2008 at 05:42:05PM +0800, Tiger Yang wrote:
> This patch will check all extended attributes related with each inode,
> It will check xattr extent tree in index block and xattr's value tree,
> mark all xattr block/cluster as used.
>
<snip>
> +static errcode_t check_xattr(o2fsck_state *ost,
> + struct ocfs2_dinode *di,
> + struct ocfs2_xattr_header *xh,
> + int *changed)
> +{
> + int i;
> + struct extent_info ei = {0, };
> + errcode_t ret = 0;
> +
> + for (i = 0 ; i < xh->xh_count; i++) {
> + int change = 0;
> + struct ocfs2_xattr_entry *xe = &xh->xh_entries[i];
> +
> + if (!ocfs2_xattr_is_local(xe)) {
> + struct ocfs2_xattr_value_root *xv =
> + (struct ocfs2_xattr_value_root *)
> + ((void *)xh + xe->xe_name_offset +
> + OCFS2_XATTR_SIZE(xe->xe_name_len));
> + struct ocfs2_extent_list *el = &xv->xr_list;
> + ret = check_el(ost, &ei, di, el, 1, &change);
> + if (ret)
> + return ret;
> + if (change)
> + *changed = 1;
> + }
> + }
> +
> + return ret;
> +}
I would think this should check the fields of ocfs2_xattr_header
and correct them if necessary. Ignore the checksum fields. But
xh_count, xh_free_start, and xh_name_value_len certainly can be
out-of-bounds and corrected.
Similarly, when walking the entries, xe_name_offset and
xe_name_len can be checked and fixed. I wonder, too, if xe_name_hash
can be checked and fixed - I bet it can.
> +static errcode_t ocfs2_check_xattr_buckets(o2fsck_state *ost,
> + struct ocfs2_dinode *di,
> + uint64_t blkno,
> + uint32_t clusters)
> +{
> + int i;
> + errcode_t ret = 0;
> + char *bucket = NULL;
> + struct ocfs2_xattr_header *xh;
> + int blk_per_bucket = ocfs2_blocks_per_xattr_bucket(ost->ost_fs);
> + uint32_t bpc = ocfs2_xattr_buckets_per_cluster(ost->ost_fs);
> + uint32_t num_buckets = clusters * bpc;
> +
> + ret = ocfs2_malloc_blocks(ost->ost_fs->fs_io, blk_per_bucket, &bucket);
> + if (ret) {
> + com_err(whoami, ret, "while allocating room to read bucket "
> + "of xattr data");
> + goto out;
> + }
> +
> + for (i = 0; i < num_buckets; i++, blkno += blk_per_bucket) {
> + int changed = 0;
> +
> + ret = io_read_block(ost->ost_fs->fs_io, blkno,
> + blk_per_bucket, bucket);
> + if (ret) {
> + com_err(whoami, ret, "while reading blocks of xattr "
> + "bucket");
> + goto out;
> + }
> +
> + xh = (struct ocfs2_xattr_header *)bucket;
> + ocfs2_swap_xattr_header(xh);
> + ocfs2_swap_xattr_entries_to_cpu(xh);
> + /*
> + * The real bucket num in this series of blocks is stored
> + * in the 1st bucket.
> + */
> + if (i == 0)
> + num_buckets = xh->xh_num_buckets;
The number of buckets can be checked and fixed, as well.
> + ret = check_xattr(ost, di, xh, &changed);
> + if (ret)
> + break;
> + if (changed) {
> + ocfs2_swap_xattr_entries_from_cpu(xh);
> + ocfs2_swap_xattr_header(xh);
> + io_write_block(ost->ost_fs->fs_io, blkno,
> + blk_per_bucket, bucket);
> + }
Right here, you'll break the checksum, because you don't
calculate it.
> +static errcode_t o2fsck_check_xattr_block(o2fsck_state *ost,
> + struct ocfs2_dinode *di)
> +{
> + errcode_t ret;
> + char *blk = NULL;
> + struct ocfs2_xattr_block *xb = NULL;
> + int changed = 0;
> +
> + ret = ocfs2_malloc_block(ost->ost_fs->fs_io, &blk);
> + if (ret) {
> + com_err(whoami, ret, "while allocating room to read block "
> + "of xattr.");
> + return ret;
> + }
> +
> + ret = ocfs2_read_xattr_block(ost->ost_fs, di->i_xattr_loc, blk);
> + if (ret) {
> + com_err(whoami, ret, "while reading externel block of xattr.");
> + return ret;
> + }
> +
> + xb = (struct ocfs2_xattr_block *)blk;
Check and fix the fields of the xattr block here.
Basically, this fsck patch validates the xattr tree structures,
but not the xattr fields themselves. I think we should have that for
this to be ready to go.
Joel
--
"Win95 file and print sharing are for relatively friendly nets."
- Paul Leach, Microsoft
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker at oracle.com
Phone: (650) 506-8127
More information about the Ocfs2-tools-devel
mailing list