Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 110ba908 authored by Joel Becker's avatar Joel Becker Committed by Mark Fasheh
Browse files

ocfs2: Respond to on-disk corruption in the extent map code.



The extent map code has long noticed when the on-disk extent information
is corrupt.  However, so far it has only returned an error.  We should
take the filesystem read-only, as it is corrupt.

Signed-off-by: default avatarJoel Becker <joel.becker@oracle.com>
Signed-off-by: default avatarMark Fasheh <mark.fasheh@oracle.com>
parent 93cc9ac4
Loading
Loading
Loading
Loading
+36 −2
Original line number Diff line number Diff line
@@ -181,6 +181,12 @@ static int ocfs2_extent_map_find_leaf(struct inode *inode,
			ret = -EBADR;
			if (rec_end > OCFS2_I(inode)->ip_clusters) {
				mlog_errno(ret);
				ocfs2_error(inode->i_sb,
					    "Extent %d at e_blkno %"MLFu64" of inode %"MLFu64" goes past ip_clusters of %u\n",
					    i,
					    le64_to_cpu(rec->e_blkno),
					    OCFS2_I(inode)->ip_blkno,
					    OCFS2_I(inode)->ip_clusters);
				goto out_free;
			}

@@ -226,6 +232,12 @@ static int ocfs2_extent_map_find_leaf(struct inode *inode,
			ret = -EBADR;
			if (blkno) {
				mlog_errno(ret);
				ocfs2_error(inode->i_sb,
					    "Multiple extents for (cpos = %u, clusters = %u) on inode %"MLFu64"; e_blkno %"MLFu64" and rec %d at e_blkno %"MLFu64"\n",
					    cpos, clusters,
					    OCFS2_I(inode)->ip_blkno,
					    blkno, i,
					    le64_to_cpu(rec->e_blkno));
				goto out_free;
			}

@@ -238,6 +250,10 @@ static int ocfs2_extent_map_find_leaf(struct inode *inode,
		 */
		ret = -EBADR;
		if (!blkno) {
			ocfs2_error(inode->i_sb,
				    "No record found for (cpos = %u, clusters = %u) on inode %"MLFu64"\n",
				    cpos, clusters,
				    OCFS2_I(inode)->ip_blkno);
			mlog_errno(ret);
			goto out_free;
		}
@@ -266,6 +282,20 @@ static int ocfs2_extent_map_find_leaf(struct inode *inode,

	for (i = 0; i < le16_to_cpu(el->l_next_free_rec); i++) {
		rec = &el->l_recs[i];

		if ((le32_to_cpu(rec->e_cpos) + le32_to_cpu(rec->e_clusters)) >
		    OCFS2_I(inode)->ip_clusters) {
			ret = -EBADR;
			mlog_errno(ret);
			ocfs2_error(inode->i_sb,
				    "Extent %d at e_blkno %"MLFu64" of inode %"MLFu64" goes past ip_clusters of %u\n",
				    i,
				    le64_to_cpu(rec->e_blkno),
				    OCFS2_I(inode)->ip_blkno,
				    OCFS2_I(inode)->ip_clusters);
			return ret;
		}

		ret = ocfs2_extent_map_insert(inode, rec,
					      le16_to_cpu(el->l_tree_depth));
		if (ret) {
@@ -526,6 +556,10 @@ static int ocfs2_extent_map_insert(struct inode *inode,
		    OCFS2_I(inode)->ip_map.em_clusters) {
			ret = -EBADR;
			mlog_errno(ret);
			ocfs2_error(inode->i_sb,
				    "Zero e_clusters on non-tail extent record at e_blkno %"MLFu64" on inode %"MLFu64"\n",
				    le64_to_cpu(rec->e_blkno),
				    OCFS2_I(inode)->ip_blkno);
			return ret;
		}