Merge branch 'upstream' of git://git.linux-mips.org/pub/scm/ralf/upstream-linus
[firefly-linux-kernel-4.4.55.git] / fs / hfs / extent.c
index a67955a0c36f621e8ca935c50f769a4b5023a1e4..e33a0d36a93ebea7183909ff45f523302943b694 100644 (file)
@@ -107,7 +107,7 @@ static u16 hfs_ext_lastblock(struct hfs_extent *ext)
        return be16_to_cpu(ext->block) + be16_to_cpu(ext->count);
 }
 
-static void __hfs_ext_write_extent(struct inode *inode, struct hfs_find_data *fd)
+static int __hfs_ext_write_extent(struct inode *inode, struct hfs_find_data *fd)
 {
        int res;
 
@@ -116,26 +116,31 @@ static void __hfs_ext_write_extent(struct inode *inode, struct hfs_find_data *fd
        res = hfs_brec_find(fd);
        if (HFS_I(inode)->flags & HFS_FLG_EXT_NEW) {
                if (res != -ENOENT)
-                       return;
+                       return res;
                hfs_brec_insert(fd, HFS_I(inode)->cached_extents, sizeof(hfs_extent_rec));
                HFS_I(inode)->flags &= ~(HFS_FLG_EXT_DIRTY|HFS_FLG_EXT_NEW);
        } else {
                if (res)
-                       return;
+                       return res;
                hfs_bnode_write(fd->bnode, HFS_I(inode)->cached_extents, fd->entryoffset, fd->entrylength);
                HFS_I(inode)->flags &= ~HFS_FLG_EXT_DIRTY;
        }
+       return 0;
 }
 
-void hfs_ext_write_extent(struct inode *inode)
+int hfs_ext_write_extent(struct inode *inode)
 {
        struct hfs_find_data fd;
+       int res = 0;
 
        if (HFS_I(inode)->flags & HFS_FLG_EXT_DIRTY) {
-               hfs_find_init(HFS_SB(inode->i_sb)->ext_tree, &fd);
-               __hfs_ext_write_extent(inode, &fd);
+               res = hfs_find_init(HFS_SB(inode->i_sb)->ext_tree, &fd);
+               if (res)
+                       return res;
+               res = __hfs_ext_write_extent(inode, &fd);
                hfs_find_exit(&fd);
        }
+       return res;
 }
 
 static inline int __hfs_ext_read_extent(struct hfs_find_data *fd, struct hfs_extent *extent,
@@ -161,8 +166,11 @@ static inline int __hfs_ext_cache_extent(struct hfs_find_data *fd, struct inode
 {
        int res;
 
-       if (HFS_I(inode)->flags & HFS_FLG_EXT_DIRTY)
-               __hfs_ext_write_extent(inode, fd);
+       if (HFS_I(inode)->flags & HFS_FLG_EXT_DIRTY) {
+               res = __hfs_ext_write_extent(inode, fd);
+               if (res)
+                       return res;
+       }
 
        res = __hfs_ext_read_extent(fd, HFS_I(inode)->cached_extents, inode->i_ino,
                                    block, HFS_IS_RSRC(inode) ? HFS_FK_RSRC : HFS_FK_DATA);
@@ -185,9 +193,11 @@ static int hfs_ext_read_extent(struct inode *inode, u16 block)
            block < HFS_I(inode)->cached_start + HFS_I(inode)->cached_blocks)
                return 0;
 
-       hfs_find_init(HFS_SB(inode->i_sb)->ext_tree, &fd);
-       res = __hfs_ext_cache_extent(&fd, inode, block);
-       hfs_find_exit(&fd);
+       res = hfs_find_init(HFS_SB(inode->i_sb)->ext_tree, &fd);
+       if (!res) {
+               res = __hfs_ext_cache_extent(&fd, inode, block);
+               hfs_find_exit(&fd);
+       }
        return res;
 }
 
@@ -195,11 +205,12 @@ static void hfs_dump_extent(struct hfs_extent *extent)
 {
        int i;
 
-       dprint(DBG_EXTENT, "   ");
+       hfs_dbg(EXTENT, "   ");
        for (i = 0; i < 3; i++)
-               dprint(DBG_EXTENT, " %u:%u", be16_to_cpu(extent[i].block),
-                                be16_to_cpu(extent[i].count));
-       dprint(DBG_EXTENT, "\n");
+               hfs_dbg_cont(EXTENT, " %u:%u",
+                            be16_to_cpu(extent[i].block),
+                            be16_to_cpu(extent[i].count));
+       hfs_dbg_cont(EXTENT, "\n");
 }
 
 static int hfs_add_extent(struct hfs_extent *extent, u16 offset,
@@ -298,7 +309,9 @@ int hfs_free_fork(struct super_block *sb, struct hfs_cat_file *file, int type)
        if (total_blocks == blocks)
                return 0;
 
-       hfs_find_init(HFS_SB(sb)->ext_tree, &fd);
+       res = hfs_find_init(HFS_SB(sb)->ext_tree, &fd);
+       if (res)
+               return res;
        do {
                res = __hfs_ext_read_extent(&fd, extent, cnid, total_blocks, type);
                if (res)
@@ -392,10 +405,10 @@ int hfs_extend_file(struct inode *inode)
                goto out;
        }
 
-       dprint(DBG_EXTENT, "extend %lu: %u,%u\n", inode->i_ino, start, len);
+       hfs_dbg(EXTENT, "extend %lu: %u,%u\n", inode->i_ino, start, len);
        if (HFS_I(inode)->alloc_blocks == HFS_I(inode)->first_blocks) {
                if (!HFS_I(inode)->first_blocks) {
-                       dprint(DBG_EXTENT, "first extents\n");
+                       hfs_dbg(EXTENT, "first extents\n");
                        /* no extents yet */
                        HFS_I(inode)->first_extents[0].block = cpu_to_be16(start);
                        HFS_I(inode)->first_extents[0].count = cpu_to_be16(len);
@@ -437,8 +450,10 @@ out:
        return res;
 
 insert_extent:
-       dprint(DBG_EXTENT, "insert new extent\n");
-       hfs_ext_write_extent(inode);
+       hfs_dbg(EXTENT, "insert new extent\n");
+       res = hfs_ext_write_extent(inode);
+       if (res)
+               goto out;
 
        memset(HFS_I(inode)->cached_extents, 0, sizeof(hfs_extent_rec));
        HFS_I(inode)->cached_extents[0].block = cpu_to_be16(start);
@@ -460,13 +475,13 @@ void hfs_file_truncate(struct inode *inode)
        u32 size;
        int res;
 
-       dprint(DBG_INODE, "truncate: %lu, %Lu -> %Lu\n", inode->i_ino,
-              (long long)HFS_I(inode)->phys_size, inode->i_size);
+       hfs_dbg(INODE, "truncate: %lu, %Lu -> %Lu\n",
+               inode->i_ino, (long long)HFS_I(inode)->phys_size,
+               inode->i_size);
        if (inode->i_size > HFS_I(inode)->phys_size) {
                struct address_space *mapping = inode->i_mapping;
                void *fsdata;
                struct page *page;
-               int res;
 
                /* XXX: Can use generic_cont_expand? */
                size = inode->i_size - 1;
@@ -488,7 +503,12 @@ void hfs_file_truncate(struct inode *inode)
                goto out;
 
        mutex_lock(&HFS_I(inode)->extents_lock);
-       hfs_find_init(HFS_SB(sb)->ext_tree, &fd);
+       res = hfs_find_init(HFS_SB(sb)->ext_tree, &fd);
+       if (res) {
+               mutex_unlock(&HFS_I(inode)->extents_lock);
+               /* XXX: We lack error handling of hfs_file_truncate() */
+               return;
+       }
        while (1) {
                if (alloc_cnt == HFS_I(inode)->first_blocks) {
                        hfs_free_extents(sb, HFS_I(inode)->first_extents,