@@ -271,7 +271,7 @@ static int iomap_dio_zero(const struct iomap_iter *iter, struct iomap_dio *dio,
271
271
* clearing the WRITE_THROUGH flag in the dio request.
272
272
*/
273
273
static inline blk_opf_t iomap_dio_bio_opflags (struct iomap_dio * dio ,
274
- const struct iomap * iomap , bool use_fua )
274
+ const struct iomap * iomap , bool use_fua , bool atomic )
275
275
{
276
276
blk_opf_t opflags = REQ_SYNC | REQ_IDLE ;
277
277
@@ -283,6 +283,8 @@ static inline blk_opf_t iomap_dio_bio_opflags(struct iomap_dio *dio,
283
283
opflags |= REQ_FUA ;
284
284
else
285
285
dio -> flags &= ~IOMAP_DIO_WRITE_THROUGH ;
286
+ if (atomic )
287
+ opflags |= REQ_ATOMIC ;
286
288
287
289
return opflags ;
288
290
}
@@ -293,7 +295,8 @@ static loff_t iomap_dio_bio_iter(const struct iomap_iter *iter,
293
295
const struct iomap * iomap = & iter -> iomap ;
294
296
struct inode * inode = iter -> inode ;
295
297
unsigned int fs_block_size = i_blocksize (inode ), pad ;
296
- loff_t length = iomap_length (iter );
298
+ const loff_t length = iomap_length (iter );
299
+ bool atomic = iter -> flags & IOMAP_ATOMIC ;
297
300
loff_t pos = iter -> pos ;
298
301
blk_opf_t bio_opf ;
299
302
struct bio * bio ;
@@ -303,6 +306,9 @@ static loff_t iomap_dio_bio_iter(const struct iomap_iter *iter,
303
306
size_t copied = 0 ;
304
307
size_t orig_count ;
305
308
309
+ if (atomic && length != fs_block_size )
310
+ return - EINVAL ;
311
+
306
312
if ((pos | length ) & (bdev_logical_block_size (iomap -> bdev ) - 1 ) ||
307
313
!bdev_iter_is_aligned (iomap -> bdev , dio -> submit .iter ))
308
314
return - EINVAL ;
@@ -382,7 +388,7 @@ static loff_t iomap_dio_bio_iter(const struct iomap_iter *iter,
382
388
* can set up the page vector appropriately for a ZONE_APPEND
383
389
* operation.
384
390
*/
385
- bio_opf = iomap_dio_bio_opflags (dio , iomap , use_fua );
391
+ bio_opf = iomap_dio_bio_opflags (dio , iomap , use_fua , atomic );
386
392
387
393
nr_pages = bio_iov_vecs_to_alloc (dio -> submit .iter , BIO_MAX_VECS );
388
394
do {
@@ -415,6 +421,17 @@ static loff_t iomap_dio_bio_iter(const struct iomap_iter *iter,
415
421
}
416
422
417
423
n = bio -> bi_iter .bi_size ;
424
+ if (WARN_ON_ONCE (atomic && n != length )) {
425
+ /*
426
+ * This bio should have covered the complete length,
427
+ * which it doesn't, so error. We may need to zero out
428
+ * the tail (complete FS block), similar to when
429
+ * bio_iov_iter_get_pages() returns an error, above.
430
+ */
431
+ ret = - EINVAL ;
432
+ bio_put (bio );
433
+ goto zero_tail ;
434
+ }
418
435
if (dio -> flags & IOMAP_DIO_WRITE ) {
419
436
task_io_account_write (n );
420
437
} else {
@@ -598,6 +615,9 @@ __iomap_dio_rw(struct kiocb *iocb, struct iov_iter *iter,
598
615
if (iocb -> ki_flags & IOCB_NOWAIT )
599
616
iomi .flags |= IOMAP_NOWAIT ;
600
617
618
+ if (iocb -> ki_flags & IOCB_ATOMIC )
619
+ iomi .flags |= IOMAP_ATOMIC ;
620
+
601
621
if (iov_iter_rw (iter ) == READ ) {
602
622
/* reads can always complete inline */
603
623
dio -> flags |= IOMAP_DIO_INLINE_COMP ;
@@ -659,7 +679,17 @@ __iomap_dio_rw(struct kiocb *iocb, struct iov_iter *iter,
659
679
if (ret != - EAGAIN ) {
660
680
trace_iomap_dio_invalidate_fail (inode , iomi .pos ,
661
681
iomi .len );
662
- ret = - ENOTBLK ;
682
+ if (iocb -> ki_flags & IOCB_ATOMIC ) {
683
+ /*
684
+ * folio invalidation failed, maybe
685
+ * this is transient, unlock and see if
686
+ * the caller tries again.
687
+ */
688
+ ret = - EAGAIN ;
689
+ } else {
690
+ /* fall back to buffered write */
691
+ ret = - ENOTBLK ;
692
+ }
663
693
}
664
694
goto out_free_dio ;
665
695
}
0 commit comments