aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2017-09-28 16:27:23 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2017-09-28 16:27:23 -0400
commit02a2b05395dde2f49e7777b67b51a5fbc6606943 (patch)
tree5d1aceee6e5a987772db092b27c49be67360fdb0
parente49aa15ef6c179f69e5578a271801f31a09e9a3f (diff)
parent5e5c943c1f257c2b3424fc3f8a7b18570152dab3 (diff)
Merge tag 'xfs-4.14-fixes-2' of git://git.kernel.org/pub/scm/fs/xfs/xfs-linux
Pull xfs fixes from Darrick Wong: - fix various problems with the copy-on-write extent maps getting freed at the wrong time - fix printk format specifier problems - report zeroing operation outcomes instead of dropping them on the floor - fix some crashes when dio operations partially fail - fix a race condition between unwritten extent conversion & dio read - fix some incorrect tests in the inode log item processing - correct the delayed allocation space reservations on rmap filesystems - fix some problems checking for dax support * tag 'xfs-4.14-fixes-2' of git://git.kernel.org/pub/scm/fs/xfs/xfs-linux: xfs: revert "xfs: factor rmap btree size into the indlen calculations" xfs: Capture state of the right inode in xfs_iflush_done xfs: perag initialization should only touch m_ag_max_usable for AG 0 xfs: update i_size after unwritten conversion in dio completion iomap_dio_rw: Allocate AIO completion queue before submitting dio xfs: validate bdev support for DAX inode flag xfs: remove redundant re-initialization of total_nr_pages xfs: Output warning message when discard option was enabled even though the device does not support discard xfs: report zeroed or not correctly in xfs_zero_range() xfs: kill meaningless variable 'zero' fs/xfs: Use %pS printk format for direct addresses xfs: evict CoW fork extents when performing finsert/fcollapse xfs: don't unconditionally clear the reflink flag on zero-block files
-rw-r--r--fs/iomap.c14
-rw-r--r--fs/xfs/libxfs/xfs_ag_resv.c12
-rw-r--r--fs/xfs/libxfs/xfs_bmap.c17
-rw-r--r--fs/xfs/xfs_aops.c3
-rw-r--r--fs/xfs/xfs_bmap_util.c14
-rw-r--r--fs/xfs/xfs_buf.c2
-rw-r--r--fs/xfs/xfs_error.c2
-rw-r--r--fs/xfs/xfs_file.c39
-rw-r--r--fs/xfs/xfs_inode.c8
-rw-r--r--fs/xfs/xfs_inode_item.c2
-rw-r--r--fs/xfs/xfs_ioctl.c3
-rw-r--r--fs/xfs/xfs_iomap.c7
-rw-r--r--fs/xfs/xfs_iomap.h2
-rw-r--r--fs/xfs/xfs_pnfs.c2
-rw-r--r--fs/xfs/xfs_super.c10
15 files changed, 81 insertions, 56 deletions
diff --git a/fs/iomap.c b/fs/iomap.c
index 8194d30bdca0..be61cf742b5e 100644
--- a/fs/iomap.c
+++ b/fs/iomap.c
@@ -1009,6 +1009,13 @@ iomap_dio_rw(struct kiocb *iocb, struct iov_iter *iter,
1009 WARN_ON_ONCE(ret); 1009 WARN_ON_ONCE(ret);
1010 ret = 0; 1010 ret = 0;
1011 1011
1012 if (iov_iter_rw(iter) == WRITE && !is_sync_kiocb(iocb) &&
1013 !inode->i_sb->s_dio_done_wq) {
1014 ret = sb_init_dio_done_wq(inode->i_sb);
1015 if (ret < 0)
1016 goto out_free_dio;
1017 }
1018
1012 inode_dio_begin(inode); 1019 inode_dio_begin(inode);
1013 1020
1014 blk_start_plug(&plug); 1021 blk_start_plug(&plug);
@@ -1031,13 +1038,6 @@ iomap_dio_rw(struct kiocb *iocb, struct iov_iter *iter,
1031 if (ret < 0) 1038 if (ret < 0)
1032 iomap_dio_set_error(dio, ret); 1039 iomap_dio_set_error(dio, ret);
1033 1040
1034 if (ret >= 0 && iov_iter_rw(iter) == WRITE && !is_sync_kiocb(iocb) &&
1035 !inode->i_sb->s_dio_done_wq) {
1036 ret = sb_init_dio_done_wq(inode->i_sb);
1037 if (ret < 0)
1038 iomap_dio_set_error(dio, ret);
1039 }
1040
1041 if (!atomic_dec_and_test(&dio->ref)) { 1041 if (!atomic_dec_and_test(&dio->ref)) {
1042 if (!is_sync_kiocb(iocb)) 1042 if (!is_sync_kiocb(iocb))
1043 return -EIOCBQUEUED; 1043 return -EIOCBQUEUED;
diff --git a/fs/xfs/libxfs/xfs_ag_resv.c b/fs/xfs/libxfs/xfs_ag_resv.c
index b008ff3250eb..df3e600835e8 100644
--- a/fs/xfs/libxfs/xfs_ag_resv.c
+++ b/fs/xfs/libxfs/xfs_ag_resv.c
@@ -156,7 +156,8 @@ __xfs_ag_resv_free(
156 trace_xfs_ag_resv_free(pag, type, 0); 156 trace_xfs_ag_resv_free(pag, type, 0);
157 157
158 resv = xfs_perag_resv(pag, type); 158 resv = xfs_perag_resv(pag, type);
159 pag->pag_mount->m_ag_max_usable += resv->ar_asked; 159 if (pag->pag_agno == 0)
160 pag->pag_mount->m_ag_max_usable += resv->ar_asked;
160 /* 161 /*
161 * AGFL blocks are always considered "free", so whatever 162 * AGFL blocks are always considered "free", so whatever
162 * was reserved at mount time must be given back at umount. 163 * was reserved at mount time must be given back at umount.
@@ -216,7 +217,14 @@ __xfs_ag_resv_init(
216 return error; 217 return error;
217 } 218 }
218 219
219 mp->m_ag_max_usable -= ask; 220 /*
221 * Reduce the maximum per-AG allocation length by however much we're
222 * trying to reserve for an AG. Since this is a filesystem-wide
223 * counter, we only make the adjustment for AG 0. This assumes that
224 * there aren't any AGs hungrier for per-AG reservation than AG 0.
225 */
226 if (pag->pag_agno == 0)
227 mp->m_ag_max_usable -= ask;
220 228
221 resv = xfs_perag_resv(pag, type); 229 resv = xfs_perag_resv(pag, type);
222 resv->ar_asked = ask; 230 resv->ar_asked = ask;
diff --git a/fs/xfs/libxfs/xfs_bmap.c b/fs/xfs/libxfs/xfs_bmap.c
index 459f4b4f08fe..044a363119be 100644
--- a/fs/xfs/libxfs/xfs_bmap.c
+++ b/fs/xfs/libxfs/xfs_bmap.c
@@ -49,7 +49,6 @@
49#include "xfs_rmap.h" 49#include "xfs_rmap.h"
50#include "xfs_ag_resv.h" 50#include "xfs_ag_resv.h"
51#include "xfs_refcount.h" 51#include "xfs_refcount.h"
52#include "xfs_rmap_btree.h"
53#include "xfs_icache.h" 52#include "xfs_icache.h"
54 53
55 54
@@ -192,12 +191,8 @@ xfs_bmap_worst_indlen(
192 int maxrecs; /* maximum record count at this level */ 191 int maxrecs; /* maximum record count at this level */
193 xfs_mount_t *mp; /* mount structure */ 192 xfs_mount_t *mp; /* mount structure */
194 xfs_filblks_t rval; /* return value */ 193 xfs_filblks_t rval; /* return value */
195 xfs_filblks_t orig_len;
196 194
197 mp = ip->i_mount; 195 mp = ip->i_mount;
198
199 /* Calculate the worst-case size of the bmbt. */
200 orig_len = len;
201 maxrecs = mp->m_bmap_dmxr[0]; 196 maxrecs = mp->m_bmap_dmxr[0];
202 for (level = 0, rval = 0; 197 for (level = 0, rval = 0;
203 level < XFS_BM_MAXLEVELS(mp, XFS_DATA_FORK); 198 level < XFS_BM_MAXLEVELS(mp, XFS_DATA_FORK);
@@ -205,20 +200,12 @@ xfs_bmap_worst_indlen(
205 len += maxrecs - 1; 200 len += maxrecs - 1;
206 do_div(len, maxrecs); 201 do_div(len, maxrecs);
207 rval += len; 202 rval += len;
208 if (len == 1) { 203 if (len == 1)
209 rval += XFS_BM_MAXLEVELS(mp, XFS_DATA_FORK) - 204 return rval + XFS_BM_MAXLEVELS(mp, XFS_DATA_FORK) -
210 level - 1; 205 level - 1;
211 break;
212 }
213 if (level == 0) 206 if (level == 0)
214 maxrecs = mp->m_bmap_dmxr[1]; 207 maxrecs = mp->m_bmap_dmxr[1];
215 } 208 }
216
217 /* Calculate the worst-case size of the rmapbt. */
218 if (xfs_sb_version_hasrmapbt(&mp->m_sb))
219 rval += 1 + xfs_rmapbt_calc_size(mp, orig_len) +
220 mp->m_rmap_maxlevels;
221
222 return rval; 209 return rval;
223} 210}
224 211
diff --git a/fs/xfs/xfs_aops.c b/fs/xfs/xfs_aops.c
index 29172609f2a3..f18e5932aec4 100644
--- a/fs/xfs/xfs_aops.c
+++ b/fs/xfs/xfs_aops.c
@@ -343,7 +343,8 @@ xfs_end_io(
343 error = xfs_reflink_end_cow(ip, offset, size); 343 error = xfs_reflink_end_cow(ip, offset, size);
344 break; 344 break;
345 case XFS_IO_UNWRITTEN: 345 case XFS_IO_UNWRITTEN:
346 error = xfs_iomap_write_unwritten(ip, offset, size); 346 /* writeback should never update isize */
347 error = xfs_iomap_write_unwritten(ip, offset, size, false);
347 break; 348 break;
348 default: 349 default:
349 ASSERT(!xfs_ioend_is_append(ioend) || ioend->io_append_trans); 350 ASSERT(!xfs_ioend_is_append(ioend) || ioend->io_append_trans);
diff --git a/fs/xfs/xfs_bmap_util.c b/fs/xfs/xfs_bmap_util.c
index cd9a5400ba4f..bc6c6e10a969 100644
--- a/fs/xfs/xfs_bmap_util.c
+++ b/fs/xfs/xfs_bmap_util.c
@@ -1459,7 +1459,19 @@ xfs_shift_file_space(
1459 return error; 1459 return error;
1460 1460
1461 /* 1461 /*
1462 * The extent shiting code works on extent granularity. So, if 1462 * Clean out anything hanging around in the cow fork now that
1463 * we've flushed all the dirty data out to disk to avoid having
1464 * CoW extents at the wrong offsets.
1465 */
1466 if (xfs_is_reflink_inode(ip)) {
1467 error = xfs_reflink_cancel_cow_range(ip, offset, NULLFILEOFF,
1468 true);
1469 if (error)
1470 return error;
1471 }
1472
1473 /*
1474 * The extent shifting code works on extent granularity. So, if
1463 * stop_fsb is not the starting block of extent, we need to split 1475 * stop_fsb is not the starting block of extent, we need to split
1464 * the extent at stop_fsb. 1476 * the extent at stop_fsb.
1465 */ 1477 */
diff --git a/fs/xfs/xfs_buf.c b/fs/xfs/xfs_buf.c
index da14658da310..2f97c12ca75e 100644
--- a/fs/xfs/xfs_buf.c
+++ b/fs/xfs/xfs_buf.c
@@ -1258,8 +1258,6 @@ xfs_buf_ioapply_map(
1258 int size; 1258 int size;
1259 int offset; 1259 int offset;
1260 1260
1261 total_nr_pages = bp->b_page_count;
1262
1263 /* skip the pages in the buffer before the start offset */ 1261 /* skip the pages in the buffer before the start offset */
1264 page_index = 0; 1262 page_index = 0;
1265 offset = *buf_offset; 1263 offset = *buf_offset;
diff --git a/fs/xfs/xfs_error.c b/fs/xfs/xfs_error.c
index bd786a9ac2c3..eaf86f55b7f2 100644
--- a/fs/xfs/xfs_error.c
+++ b/fs/xfs/xfs_error.c
@@ -347,7 +347,7 @@ xfs_verifier_error(
347{ 347{
348 struct xfs_mount *mp = bp->b_target->bt_mount; 348 struct xfs_mount *mp = bp->b_target->bt_mount;
349 349
350 xfs_alert(mp, "Metadata %s detected at %pF, %s block 0x%llx", 350 xfs_alert(mp, "Metadata %s detected at %pS, %s block 0x%llx",
351 bp->b_error == -EFSBADCRC ? "CRC error" : "corruption", 351 bp->b_error == -EFSBADCRC ? "CRC error" : "corruption",
352 __return_address, bp->b_ops->name, bp->b_bn); 352 __return_address, bp->b_ops->name, bp->b_bn);
353 353
diff --git a/fs/xfs/xfs_file.c b/fs/xfs/xfs_file.c
index ebdd0bd2b261..309e26c9dddb 100644
--- a/fs/xfs/xfs_file.c
+++ b/fs/xfs/xfs_file.c
@@ -58,7 +58,7 @@ xfs_zero_range(
58 xfs_off_t count, 58 xfs_off_t count,
59 bool *did_zero) 59 bool *did_zero)
60{ 60{
61 return iomap_zero_range(VFS_I(ip), pos, count, NULL, &xfs_iomap_ops); 61 return iomap_zero_range(VFS_I(ip), pos, count, did_zero, &xfs_iomap_ops);
62} 62}
63 63
64int 64int
@@ -377,8 +377,6 @@ restart:
377 */ 377 */
378 spin_lock(&ip->i_flags_lock); 378 spin_lock(&ip->i_flags_lock);
379 if (iocb->ki_pos > i_size_read(inode)) { 379 if (iocb->ki_pos > i_size_read(inode)) {
380 bool zero = false;
381
382 spin_unlock(&ip->i_flags_lock); 380 spin_unlock(&ip->i_flags_lock);
383 if (!drained_dio) { 381 if (!drained_dio) {
384 if (*iolock == XFS_IOLOCK_SHARED) { 382 if (*iolock == XFS_IOLOCK_SHARED) {
@@ -399,7 +397,7 @@ restart:
399 drained_dio = true; 397 drained_dio = true;
400 goto restart; 398 goto restart;
401 } 399 }
402 error = xfs_zero_eof(ip, iocb->ki_pos, i_size_read(inode), &zero); 400 error = xfs_zero_eof(ip, iocb->ki_pos, i_size_read(inode), NULL);
403 if (error) 401 if (error)
404 return error; 402 return error;
405 } else 403 } else
@@ -436,7 +434,6 @@ xfs_dio_write_end_io(
436 struct inode *inode = file_inode(iocb->ki_filp); 434 struct inode *inode = file_inode(iocb->ki_filp);
437 struct xfs_inode *ip = XFS_I(inode); 435 struct xfs_inode *ip = XFS_I(inode);
438 loff_t offset = iocb->ki_pos; 436 loff_t offset = iocb->ki_pos;
439 bool update_size = false;
440 int error = 0; 437 int error = 0;
441 438
442 trace_xfs_end_io_direct_write(ip, offset, size); 439 trace_xfs_end_io_direct_write(ip, offset, size);
@@ -447,6 +444,21 @@ xfs_dio_write_end_io(
447 if (size <= 0) 444 if (size <= 0)
448 return size; 445 return size;
449 446
447 if (flags & IOMAP_DIO_COW) {
448 error = xfs_reflink_end_cow(ip, offset, size);
449 if (error)
450 return error;
451 }
452
453 /*
454 * Unwritten conversion updates the in-core isize after extent
455 * conversion but before updating the on-disk size. Updating isize any
456 * earlier allows a racing dio read to find unwritten extents before
457 * they are converted.
458 */
459 if (flags & IOMAP_DIO_UNWRITTEN)
460 return xfs_iomap_write_unwritten(ip, offset, size, true);
461
450 /* 462 /*
451 * We need to update the in-core inode size here so that we don't end up 463 * We need to update the in-core inode size here so that we don't end up
452 * with the on-disk inode size being outside the in-core inode size. We 464 * with the on-disk inode size being outside the in-core inode size. We
@@ -461,20 +473,11 @@ xfs_dio_write_end_io(
461 spin_lock(&ip->i_flags_lock); 473 spin_lock(&ip->i_flags_lock);
462 if (offset + size > i_size_read(inode)) { 474 if (offset + size > i_size_read(inode)) {
463 i_size_write(inode, offset + size); 475 i_size_write(inode, offset + size);
464 update_size = true; 476 spin_unlock(&ip->i_flags_lock);
465 }
466 spin_unlock(&ip->i_flags_lock);
467
468 if (flags & IOMAP_DIO_COW) {
469 error = xfs_reflink_end_cow(ip, offset, size);
470 if (error)
471 return error;
472 }
473
474 if (flags & IOMAP_DIO_UNWRITTEN)
475 error = xfs_iomap_write_unwritten(ip, offset, size);
476 else if (update_size)
477 error = xfs_setfilesize(ip, offset, size); 477 error = xfs_setfilesize(ip, offset, size);
478 } else {
479 spin_unlock(&ip->i_flags_lock);
480 }
478 481
479 return error; 482 return error;
480} 483}
diff --git a/fs/xfs/xfs_inode.c b/fs/xfs/xfs_inode.c
index 5599dda4727a..4ec5b7f45401 100644
--- a/fs/xfs/xfs_inode.c
+++ b/fs/xfs/xfs_inode.c
@@ -1624,10 +1624,12 @@ xfs_itruncate_extents(
1624 goto out; 1624 goto out;
1625 1625
1626 /* 1626 /*
1627 * Clear the reflink flag if we truncated everything. 1627 * Clear the reflink flag if there are no data fork blocks and
1628 * there are no extents staged in the cow fork.
1628 */ 1629 */
1629 if (ip->i_d.di_nblocks == 0 && xfs_is_reflink_inode(ip)) { 1630 if (xfs_is_reflink_inode(ip) && ip->i_cnextents == 0) {
1630 ip->i_d.di_flags2 &= ~XFS_DIFLAG2_REFLINK; 1631 if (ip->i_d.di_nblocks == 0)
1632 ip->i_d.di_flags2 &= ~XFS_DIFLAG2_REFLINK;
1631 xfs_inode_clear_cowblocks_tag(ip); 1633 xfs_inode_clear_cowblocks_tag(ip);
1632 } 1634 }
1633 1635
diff --git a/fs/xfs/xfs_inode_item.c b/fs/xfs/xfs_inode_item.c
index 6d0f74ec31e8..a705f34b58fa 100644
--- a/fs/xfs/xfs_inode_item.c
+++ b/fs/xfs/xfs_inode_item.c
@@ -745,7 +745,7 @@ xfs_iflush_done(
745 */ 745 */
746 iip = INODE_ITEM(blip); 746 iip = INODE_ITEM(blip);
747 if ((iip->ili_logged && blip->li_lsn == iip->ili_flush_lsn) || 747 if ((iip->ili_logged && blip->li_lsn == iip->ili_flush_lsn) ||
748 lip->li_flags & XFS_LI_FAILED) 748 (blip->li_flags & XFS_LI_FAILED))
749 need_ail++; 749 need_ail++;
750 750
751 blip = next; 751 blip = next;
diff --git a/fs/xfs/xfs_ioctl.c b/fs/xfs/xfs_ioctl.c
index 5049e8ab6e30..aa75389be8cf 100644
--- a/fs/xfs/xfs_ioctl.c
+++ b/fs/xfs/xfs_ioctl.c
@@ -1088,6 +1088,7 @@ xfs_ioctl_setattr_dax_invalidate(
1088 int *join_flags) 1088 int *join_flags)
1089{ 1089{
1090 struct inode *inode = VFS_I(ip); 1090 struct inode *inode = VFS_I(ip);
1091 struct super_block *sb = inode->i_sb;
1091 int error; 1092 int error;
1092 1093
1093 *join_flags = 0; 1094 *join_flags = 0;
@@ -1100,7 +1101,7 @@ xfs_ioctl_setattr_dax_invalidate(
1100 if (fa->fsx_xflags & FS_XFLAG_DAX) { 1101 if (fa->fsx_xflags & FS_XFLAG_DAX) {
1101 if (!(S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode))) 1102 if (!(S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode)))
1102 return -EINVAL; 1103 return -EINVAL;
1103 if (ip->i_mount->m_sb.sb_blocksize != PAGE_SIZE) 1104 if (bdev_dax_supported(sb, sb->s_blocksize) < 0)
1104 return -EINVAL; 1105 return -EINVAL;
1105 } 1106 }
1106 1107
diff --git a/fs/xfs/xfs_iomap.c b/fs/xfs/xfs_iomap.c
index a1909bc064e9..f179bdf1644d 100644
--- a/fs/xfs/xfs_iomap.c
+++ b/fs/xfs/xfs_iomap.c
@@ -829,7 +829,8 @@ int
829xfs_iomap_write_unwritten( 829xfs_iomap_write_unwritten(
830 xfs_inode_t *ip, 830 xfs_inode_t *ip,
831 xfs_off_t offset, 831 xfs_off_t offset,
832 xfs_off_t count) 832 xfs_off_t count,
833 bool update_isize)
833{ 834{
834 xfs_mount_t *mp = ip->i_mount; 835 xfs_mount_t *mp = ip->i_mount;
835 xfs_fileoff_t offset_fsb; 836 xfs_fileoff_t offset_fsb;
@@ -840,6 +841,7 @@ xfs_iomap_write_unwritten(
840 xfs_trans_t *tp; 841 xfs_trans_t *tp;
841 xfs_bmbt_irec_t imap; 842 xfs_bmbt_irec_t imap;
842 struct xfs_defer_ops dfops; 843 struct xfs_defer_ops dfops;
844 struct inode *inode = VFS_I(ip);
843 xfs_fsize_t i_size; 845 xfs_fsize_t i_size;
844 uint resblks; 846 uint resblks;
845 int error; 847 int error;
@@ -899,7 +901,8 @@ xfs_iomap_write_unwritten(
899 i_size = XFS_FSB_TO_B(mp, offset_fsb + count_fsb); 901 i_size = XFS_FSB_TO_B(mp, offset_fsb + count_fsb);
900 if (i_size > offset + count) 902 if (i_size > offset + count)
901 i_size = offset + count; 903 i_size = offset + count;
902 904 if (update_isize && i_size > i_size_read(inode))
905 i_size_write(inode, i_size);
903 i_size = xfs_new_eof(ip, i_size); 906 i_size = xfs_new_eof(ip, i_size);
904 if (i_size) { 907 if (i_size) {
905 ip->i_d.di_size = i_size; 908 ip->i_d.di_size = i_size;
diff --git a/fs/xfs/xfs_iomap.h b/fs/xfs/xfs_iomap.h
index 00db3ecea084..ee535065c5d0 100644
--- a/fs/xfs/xfs_iomap.h
+++ b/fs/xfs/xfs_iomap.h
@@ -27,7 +27,7 @@ int xfs_iomap_write_direct(struct xfs_inode *, xfs_off_t, size_t,
27 struct xfs_bmbt_irec *, int); 27 struct xfs_bmbt_irec *, int);
28int xfs_iomap_write_allocate(struct xfs_inode *, int, xfs_off_t, 28int xfs_iomap_write_allocate(struct xfs_inode *, int, xfs_off_t,
29 struct xfs_bmbt_irec *); 29 struct xfs_bmbt_irec *);
30int xfs_iomap_write_unwritten(struct xfs_inode *, xfs_off_t, xfs_off_t); 30int xfs_iomap_write_unwritten(struct xfs_inode *, xfs_off_t, xfs_off_t, bool);
31 31
32void xfs_bmbt_to_iomap(struct xfs_inode *, struct iomap *, 32void xfs_bmbt_to_iomap(struct xfs_inode *, struct iomap *,
33 struct xfs_bmbt_irec *); 33 struct xfs_bmbt_irec *);
diff --git a/fs/xfs/xfs_pnfs.c b/fs/xfs/xfs_pnfs.c
index 2f2dc3c09ad0..4246876df7b7 100644
--- a/fs/xfs/xfs_pnfs.c
+++ b/fs/xfs/xfs_pnfs.c
@@ -274,7 +274,7 @@ xfs_fs_commit_blocks(
274 (end - 1) >> PAGE_SHIFT); 274 (end - 1) >> PAGE_SHIFT);
275 WARN_ON_ONCE(error); 275 WARN_ON_ONCE(error);
276 276
277 error = xfs_iomap_write_unwritten(ip, start, length); 277 error = xfs_iomap_write_unwritten(ip, start, length, false);
278 if (error) 278 if (error)
279 goto out_drop_iolock; 279 goto out_drop_iolock;
280 } 280 }
diff --git a/fs/xfs/xfs_super.c b/fs/xfs/xfs_super.c
index c996f4ae4a5f..584cf2d573ba 100644
--- a/fs/xfs/xfs_super.c
+++ b/fs/xfs/xfs_super.c
@@ -1654,6 +1654,16 @@ xfs_fs_fill_super(
1654 "DAX and reflink have not been tested together!"); 1654 "DAX and reflink have not been tested together!");
1655 } 1655 }
1656 1656
1657 if (mp->m_flags & XFS_MOUNT_DISCARD) {
1658 struct request_queue *q = bdev_get_queue(sb->s_bdev);
1659
1660 if (!blk_queue_discard(q)) {
1661 xfs_warn(mp, "mounting with \"discard\" option, but "
1662 "the device does not support discard");
1663 mp->m_flags &= ~XFS_MOUNT_DISCARD;
1664 }
1665 }
1666
1657 if (xfs_sb_version_hasrmapbt(&mp->m_sb)) { 1667 if (xfs_sb_version_hasrmapbt(&mp->m_sb)) {
1658 if (mp->m_sb.sb_rblocks) { 1668 if (mp->m_sb.sb_rblocks) {
1659 xfs_alert(mp, 1669 xfs_alert(mp,