Merge tag 'dmaengine-5.11-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/vkoul...
[linux-2.6-microblaze.git] / fs / gfs2 / aops.c
index d4af283..cc4f987 100644 (file)
@@ -77,7 +77,7 @@ static int gfs2_get_block_noalloc(struct inode *inode, sector_t lblock,
        if (error)
                return error;
        if (!buffer_mapped(bh_result))
-               return -EIO;
+               return -ENODATA;
        return 0;
 }
 
@@ -91,22 +91,13 @@ static int gfs2_writepage(struct page *page, struct writeback_control *wbc)
        struct inode *inode = page->mapping->host;
        struct gfs2_inode *ip = GFS2_I(inode);
        struct gfs2_sbd *sdp = GFS2_SB(inode);
-       loff_t i_size = i_size_read(inode);
-       pgoff_t end_index = i_size >> PAGE_SHIFT;
-       unsigned offset;
+       struct iomap_writepage_ctx wpc = { };
 
        if (gfs2_assert_withdraw(sdp, gfs2_glock_is_held_excl(ip->i_gl)))
                goto out;
        if (current->journal_info)
                goto redirty;
-       /* Is the page fully outside i_size? (truncate in progress) */
-       offset = i_size & (PAGE_SIZE-1);
-       if (page->index > end_index || (page->index == end_index && !offset)) {
-               page->mapping->a_ops->invalidatepage(page, 0, PAGE_SIZE);
-               goto out;
-       }
-
-       return nobh_writepage(page, gfs2_get_block_noalloc, wbc);
+       return iomap_writepage(page, wbc, &wpc, &gfs2_writeback_ops);
 
 redirty:
        redirty_page_for_writepage(wbc, page);
@@ -115,11 +106,16 @@ out:
        return 0;
 }
 
-/* This is the same as calling block_write_full_page, but it also
+/**
+ * gfs2_write_jdata_page - gfs2 jdata-specific version of block_write_full_page
+ * @page: The page to write
+ * @wbc: The writeback control
+ *
+ * This is the same as calling block_write_full_page, but it also
  * writes pages outside of i_size
  */
-static int gfs2_write_full_page(struct page *page, get_block_t *get_block,
-                               struct writeback_control *wbc)
+static int gfs2_write_jdata_page(struct page *page,
+                                struct writeback_control *wbc)
 {
        struct inode * const inode = page->mapping->host;
        loff_t i_size = i_size_read(inode);
@@ -137,7 +133,7 @@ static int gfs2_write_full_page(struct page *page, get_block_t *get_block,
        if (page->index == end_index && offset)
                zero_user_segment(page, offset, PAGE_SIZE);
 
-       return __block_write_full_page(inode, page, get_block, wbc,
+       return __block_write_full_page(inode, page, gfs2_get_block_noalloc, wbc,
                                       end_buffer_async_write);
 }
 
@@ -166,7 +162,7 @@ static int __gfs2_jdata_writepage(struct page *page, struct writeback_control *w
                }
                gfs2_page_add_databufs(ip, page, 0, sdp->sd_vfs->s_blocksize);
        }
-       return gfs2_write_full_page(page, gfs2_get_block_noalloc, wbc);
+       return gfs2_write_jdata_page(page, wbc);
 }
 
 /**
@@ -208,7 +204,8 @@ static int gfs2_writepages(struct address_space *mapping,
                           struct writeback_control *wbc)
 {
        struct gfs2_sbd *sdp = gfs2_mapping2sbd(mapping);
-       int ret = mpage_writepages(mapping, wbc, gfs2_get_block_noalloc);
+       struct iomap_writepage_ctx wpc = { };
+       int ret;
 
        /*
         * Even if we didn't write any pages here, we might still be holding
@@ -216,9 +213,9 @@ static int gfs2_writepages(struct address_space *mapping,
         * want balance_dirty_pages() to loop indefinitely trying to write out
         * pages held in the ail that it can't find.
         */
+       ret = iomap_writepages(mapping, wbc, &wpc, &gfs2_writeback_ops);
        if (ret == 0)
                set_bit(SDF_FORCE_AIL_FLUSH, &sdp->sd_flags);
-
        return ret;
 }
 
@@ -470,12 +467,13 @@ static int stuffed_readpage(struct gfs2_inode *ip, struct page *page)
 
 static int __gfs2_readpage(void *file, struct page *page)
 {
-       struct gfs2_inode *ip = GFS2_I(page->mapping->host);
-       struct gfs2_sbd *sdp = GFS2_SB(page->mapping->host);
+       struct inode *inode = page->mapping->host;
+       struct gfs2_inode *ip = GFS2_I(inode);
+       struct gfs2_sbd *sdp = GFS2_SB(inode);
        int error;
 
-       if (i_blocksize(page->mapping->host) == PAGE_SIZE &&
-           !page_has_buffers(page)) {
+       if (!gfs2_is_jdata(ip) ||
+           (i_blocksize(inode) == PAGE_SIZE && !page_has_buffers(page))) {
                error = iomap_readpage(page, &gfs2_iomap_ops);
        } else if (gfs2_is_stuffed(ip)) {
                error = stuffed_readpage(ip, page);
@@ -563,8 +561,12 @@ static void gfs2_readahead(struct readahead_control *rac)
        struct inode *inode = rac->mapping->host;
        struct gfs2_inode *ip = GFS2_I(inode);
 
-       if (!gfs2_is_stuffed(ip))
+       if (gfs2_is_stuffed(ip))
+               ;
+       else if (gfs2_is_jdata(ip))
                mpage_readahead(rac, gfs2_block_map);
+       else
+               iomap_readahead(rac, &gfs2_iomap_ops);
 }
 
 /**
@@ -621,7 +623,8 @@ out:
  
 static int jdata_set_page_dirty(struct page *page)
 {
-       SetPageChecked(page);
+       if (current->journal_info)
+               SetPageChecked(page);
        return __set_page_dirty_buffers(page);
 }
 
@@ -663,8 +666,11 @@ static void gfs2_discard(struct gfs2_sbd *sdp, struct buffer_head *bh)
        if (bd) {
                if (!list_empty(&bd->bd_list) && !buffer_pinned(bh))
                        list_del_init(&bd->bd_list);
-               else
+               else {
+                       spin_lock(&sdp->sd_ail_lock);
                        gfs2_remove_from_journal(bh, REMOVE_JDATA);
+                       spin_unlock(&sdp->sd_ail_lock);
+               }
        }
        bh->b_bdev = NULL;
        clear_buffer_mapped(bh);
@@ -736,7 +742,6 @@ int gfs2_releasepage(struct page *page, gfp_t gfp_mask)
         */
 
        gfs2_log_lock(sdp);
-       spin_lock(&sdp->sd_ail_lock);
        head = bh = page_buffers(page);
        do {
                if (atomic_read(&bh->b_count))
@@ -748,7 +753,6 @@ int gfs2_releasepage(struct page *page, gfp_t gfp_mask)
                        goto cannot_release;
                bh = bh->b_this_page;
        } while(bh != head);
-       spin_unlock(&sdp->sd_ail_lock);
 
        head = bh = page_buffers(page);
        do {
@@ -774,7 +778,6 @@ int gfs2_releasepage(struct page *page, gfp_t gfp_mask)
        return try_to_free_buffers(page);
 
 cannot_release:
-       spin_unlock(&sdp->sd_ail_lock);
        gfs2_log_unlock(sdp);
        return 0;
 }
@@ -784,12 +787,13 @@ static const struct address_space_operations gfs2_aops = {
        .writepages = gfs2_writepages,
        .readpage = gfs2_readpage,
        .readahead = gfs2_readahead,
+       .set_page_dirty = iomap_set_page_dirty,
+       .releasepage = iomap_releasepage,
+       .invalidatepage = iomap_invalidatepage,
        .bmap = gfs2_bmap,
-       .invalidatepage = gfs2_invalidatepage,
-       .releasepage = gfs2_releasepage,
        .direct_IO = noop_direct_IO,
-       .migratepage = buffer_migrate_page,
-       .is_partially_uptodate = block_is_partially_uptodate,
+       .migratepage = iomap_migrate_page,
+       .is_partially_uptodate = iomap_is_partially_uptodate,
        .error_remove_page = generic_error_remove_page,
 };