void btrfs_delalloc_release_extents(struct btrfs_inode *inode, u64 num_bytes);
 
 int btrfs_delalloc_reserve_metadata(struct btrfs_inode *inode, u64 num_bytes,
-                                   u64 disk_num_bytes);
+                                   u64 disk_num_bytes, bool noflush);
 u64 btrfs_account_ro_block_groups_free_space(struct btrfs_space_info *sinfo);
 int btrfs_error_unpin_extent_range(struct btrfs_fs_info *fs_info,
                                   u64 start, u64 end);
 
 }
 
 int btrfs_delalloc_reserve_metadata(struct btrfs_inode *inode, u64 num_bytes,
-                                   u64 disk_num_bytes)
+                                   u64 disk_num_bytes, bool noflush)
 {
        struct btrfs_root *root = inode->root;
        struct btrfs_fs_info *fs_info = root->fs_info;
         * If we have a transaction open (can happen if we call truncate_block
         * from truncate), then we need FLUSH_LIMIT so we don't deadlock.
         */
-       if (btrfs_is_free_space_inode(inode)) {
+       if (noflush || btrfs_is_free_space_inode(inode)) {
                flush = BTRFS_RESERVE_NO_FLUSH;
        } else {
                if (current->journal_info)
         */
        calc_inode_reservations(fs_info, num_bytes, disk_num_bytes,
                                &meta_reserve, &qgroup_reserve);
-       ret = btrfs_qgroup_reserve_meta_prealloc(root, qgroup_reserve, true);
+       ret = btrfs_qgroup_reserve_meta_prealloc(root, qgroup_reserve, true,
+                                                noflush);
        if (ret)
                return ret;
        ret = btrfs_reserve_metadata_bytes(fs_info, block_rsv, meta_reserve, flush);
        ret = btrfs_check_data_free_space(inode, reserved, start, len);
        if (ret < 0)
                return ret;
-       ret = btrfs_delalloc_reserve_metadata(inode, len, len);
+       ret = btrfs_delalloc_reserve_metadata(inode, len, len, false);
        if (ret < 0) {
                btrfs_free_reserved_data_space(inode, *reserved, start, len);
                extent_changeset_free(*reserved);
 
                WARN_ON(reserve_bytes == 0);
                ret = btrfs_delalloc_reserve_metadata(BTRFS_I(inode),
                                                      reserve_bytes,
-                                                     reserve_bytes);
+                                                     reserve_bytes, false);
                if (ret) {
                        if (!only_release_metadata)
                                btrfs_free_reserved_data_space(BTRFS_I(inode),
 
                        goto out;
                }
        }
-       ret = btrfs_delalloc_reserve_metadata(inode, blocksize, blocksize);
+       ret = btrfs_delalloc_reserve_metadata(inode, blocksize, blocksize, false);
        if (ret < 0) {
                if (!only_release_metadata)
                        btrfs_free_reserved_data_space(inode, data_reserved,
                                         u64 start, u64 len,
                                         unsigned int iomap_flags)
 {
+       const bool nowait = (iomap_flags & IOMAP_NOWAIT);
        struct btrfs_fs_info *fs_info = btrfs_sb(inode->i_sb);
        struct extent_map *em = *map;
        int type;
                struct extent_map *em2;
 
                /* We can NOCOW, so only need to reserve metadata space. */
-               ret = btrfs_delalloc_reserve_metadata(BTRFS_I(inode), len, len);
+               ret = btrfs_delalloc_reserve_metadata(BTRFS_I(inode), len, len,
+                                                     nowait);
                if (ret < 0) {
                        /* Our caller expects us to free the input extent map. */
                        free_extent_map(em);
                        *map = NULL;
                        btrfs_dec_nocow_writers(fs_info, block_start);
+                       if (nowait && (ret == -ENOSPC || ret == -EDQUOT))
+                               ret = -EAGAIN;
                        goto out;
                }
                space_reserved = true;
                free_extent_map(em);
                *map = NULL;
 
-               if (iomap_flags & IOMAP_NOWAIT)
+               if (nowait)
                        return -EAGAIN;
 
                /* We have to COW, so need to reserve metadata and data space. */
        ret = btrfs_qgroup_reserve_data(inode, &data_reserved, start, num_bytes);
        if (ret)
                goto out_free_data_space;
-       ret = btrfs_delalloc_reserve_metadata(inode, num_bytes, disk_num_bytes);
+       ret = btrfs_delalloc_reserve_metadata(inode, num_bytes, disk_num_bytes,
+                                             false);
        if (ret)
                goto out_qgroup_free_data;
 
 
 }
 
 int __btrfs_qgroup_reserve_meta(struct btrfs_root *root, int num_bytes,
-                               enum btrfs_qgroup_rsv_type type, bool enforce)
+                               enum btrfs_qgroup_rsv_type type, bool enforce,
+                               bool noflush)
 {
        int ret;
 
        ret = btrfs_qgroup_reserve_meta(root, num_bytes, type, enforce);
-       if (ret <= 0 && ret != -EDQUOT)
+       if ((ret <= 0 && ret != -EDQUOT) || noflush)
                return ret;
 
        ret = try_flush_qgroup(root);
 
 int btrfs_qgroup_reserve_meta(struct btrfs_root *root, int num_bytes,
                              enum btrfs_qgroup_rsv_type type, bool enforce);
 int __btrfs_qgroup_reserve_meta(struct btrfs_root *root, int num_bytes,
-                               enum btrfs_qgroup_rsv_type type, bool enforce);
+                               enum btrfs_qgroup_rsv_type type, bool enforce,
+                               bool noflush);
 /* Reserve metadata space for pertrans and prealloc type */
 static inline int btrfs_qgroup_reserve_meta_pertrans(struct btrfs_root *root,
                                int num_bytes, bool enforce)
 {
        return __btrfs_qgroup_reserve_meta(root, num_bytes,
-                       BTRFS_QGROUP_RSV_META_PERTRANS, enforce);
+                                          BTRFS_QGROUP_RSV_META_PERTRANS,
+                                          enforce, false);
 }
 static inline int btrfs_qgroup_reserve_meta_prealloc(struct btrfs_root *root,
-                               int num_bytes, bool enforce)
+                                                    int num_bytes, bool enforce,
+                                                    bool noflush)
 {
        return __btrfs_qgroup_reserve_meta(root, num_bytes,
-                       BTRFS_QGROUP_RSV_META_PREALLOC, enforce);
+                                          BTRFS_QGROUP_RSV_META_PREALLOC,
+                                          enforce, noflush);
 }
 
 void __btrfs_qgroup_free_meta(struct btrfs_root *root, int num_bytes,
 
 
                /* Reserve metadata for this range */
                ret = btrfs_delalloc_reserve_metadata(BTRFS_I(inode),
-                                                     clamped_len, clamped_len);
+                                                     clamped_len, clamped_len,
+                                                     false);
                if (ret)
                        goto release_page;
 
 
                /* One for parent inode, two for dir entries */
                qgroup_num_bytes = 3 * fs_info->nodesize;
                ret = btrfs_qgroup_reserve_meta_prealloc(root,
-                               qgroup_num_bytes, true);
+                                                        qgroup_num_bytes, true,
+                                                        false);
                if (ret)
                        return ret;
        }