static int blk_ioctl_discard(struct block_device *bdev, blk_mode_t mode,
                unsigned long arg)
  {
 -      uint64_t range[2];
 -      uint64_t start, len, end;
 +      unsigned int bs_mask = bdev_logical_block_size(bdev) - 1;
-       struct inode *inode = bdev->bd_inode;
 +      uint64_t range[2], start, len, end;
 +      struct bio *prev = NULL, *bio;
 +      sector_t sector, nr_sects;
 +      struct blk_plug plug;
        int err;
  
        if (!(mode & BLK_OPEN_WRITE))
        err = truncate_bdev_range(bdev, mode, start, start + len - 1);
        if (err)
                goto fail;
 -      err = blkdev_issue_discard(bdev, start >> 9, len >> 9, GFP_KERNEL);
 +
 +      sector = start >> SECTOR_SHIFT;
 +      nr_sects = len >> SECTOR_SHIFT;
 +
 +      blk_start_plug(&plug);
 +      while (1) {
 +              if (fatal_signal_pending(current)) {
 +                      if (prev)
 +                              bio_await_chain(prev);
 +                      err = -EINTR;
 +                      goto out_unplug;
 +              }
 +              bio = blk_alloc_discard_bio(bdev, §or, &nr_sects,
 +                              GFP_KERNEL);
 +              if (!bio)
 +                      break;
 +              prev = bio_chain_and_submit(prev, bio);
 +      }
 +      if (prev) {
 +              err = submit_bio_wait(prev);
 +              if (err == -EOPNOTSUPP)
 +                      err = 0;
 +              bio_put(prev);
 +      }
 +out_unplug:
 +      blk_finish_plug(&plug);
  fail:
-       filemap_invalidate_unlock(inode->i_mapping);
+       filemap_invalidate_unlock(bdev->bd_mapping);
        return err;
  }
  
 
                            struct btrfs_super_block *sb, int max_mirrors)
  {
        struct btrfs_fs_info *fs_info = device->fs_info;
-       struct address_space *mapping = device->bdev->bd_inode->i_mapping;
+       struct address_space *mapping = device->bdev->bd_mapping;
        SHASH_DESC_ON_STACK(shash, fs_info->csum_shash);
        int i;
 -      int errors = 0;
        int ret;
        u64 bytenr, bytenr_orig;
  
                    device->commit_total_bytes)
                        break;
  
-               folio = filemap_get_folio(device->bdev->bd_inode->i_mapping,
 -              page = find_get_page(device->bdev->bd_mapping,
 -                                   bytenr >> PAGE_SHIFT);
 -              if (!page) {
 -                      errors++;
 -                      if (i == 0)
 -                              primary_failed = true;
++              folio = filemap_get_folio(device->bdev->bd_mapping,
 +                                        bytenr >> PAGE_SHIFT);
 +              /* If the folio has been removed, then we know it completed. */
 +              if (IS_ERR(folio))
                        continue;
 -              }
 -              /* Page is submitted locked and unlocked once the IO completes */
 -              wait_on_page_locked(page);
 -              if (PageError(page)) {
 -                      errors++;
 -                      if (i == 0)
 -                              primary_failed = true;
 -              }
 -
 -              /* Drop our reference */
 -              put_page(page);
 +              ASSERT(folio_order(folio) == 0);
  
 -              /* Drop the reference from the writing run */
 -              put_page(page);
 +              /* Folio will be unlocked once the write completes. */
 +              folio_wait_locked(folio);
 +              folio_put(folio);
        }
  
 -      /* log error, force error return */
 +      errors += atomic_read(&device->sb_write_errors);
 +      if (errors >= BTRFS_SUPER_PRIMARY_WRITE_ERROR)
 +              primary_failed = true;
        if (primary_failed) {
                btrfs_err(device->fs_info, "error writing primary super block to device %llu",
                          device->devid);