Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge tag 'gfs2-v5.8-rc4.fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/gfs2/linux-gfs2

Pull gfs2 fixes from Andreas Gruenbacher:
"Fix gfs2 readahead deadlocks by adding a IOCB_NOIO flag that allows
gfs2 to use the generic fiel read iterator functions without having to
worry about being called back while holding locks".

* tag 'gfs2-v5.8-rc4.fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/gfs2/linux-gfs2:
gfs2: Rework read and page fault locking
fs: Add IOCB_NOIO flag for generic_file_read_iter

+73 -48
+1 -44
fs/gfs2/aops.c
··· 468 468 } 469 469 470 470 471 - /** 472 - * __gfs2_readpage - readpage 473 - * @file: The file to read a page for 474 - * @page: The page to read 475 - * 476 - * This is the core of gfs2's readpage. It's used by the internal file 477 - * reading code as in that case we already hold the glock. Also it's 478 - * called by gfs2_readpage() once the required lock has been granted. 479 - */ 480 - 481 471 static int __gfs2_readpage(void *file, struct page *page) 482 472 { 483 473 struct gfs2_inode *ip = GFS2_I(page->mapping->host); 484 474 struct gfs2_sbd *sdp = GFS2_SB(page->mapping->host); 485 - 486 475 int error; 487 476 488 477 if (i_blocksize(page->mapping->host) == PAGE_SIZE && ··· 494 505 * gfs2_readpage - read a page of a file 495 506 * @file: The file to read 496 507 * @page: The page of the file 497 - * 498 - * This deals with the locking required. We have to unlock and 499 - * relock the page in order to get the locking in the right 500 - * order. 501 508 */ 502 509 503 510 static int gfs2_readpage(struct file *file, struct page *page) 504 511 { 505 - struct address_space *mapping = page->mapping; 506 - struct gfs2_inode *ip = GFS2_I(mapping->host); 507 - struct gfs2_holder gh; 508 - int error; 509 - 510 - unlock_page(page); 511 - gfs2_holder_init(ip->i_gl, LM_ST_SHARED, 0, &gh); 512 - error = gfs2_glock_nq(&gh); 513 - if (unlikely(error)) 514 - goto out; 515 - error = AOP_TRUNCATED_PAGE; 516 - lock_page(page); 517 - if (page->mapping == mapping && !PageUptodate(page)) 518 - error = __gfs2_readpage(file, page); 519 - else 520 - unlock_page(page); 521 - gfs2_glock_dq(&gh); 522 - out: 523 - gfs2_holder_uninit(&gh); 524 - if (error && error != AOP_TRUNCATED_PAGE) 525 - lock_page(page); 526 - return error; 512 + return __gfs2_readpage(file, page); 527 513 } 528 514 529 515 /** ··· 562 598 { 563 599 struct inode *inode = rac->mapping->host; 564 600 struct gfs2_inode *ip = GFS2_I(inode); 565 - struct gfs2_holder gh; 566 601 567 - gfs2_holder_init(ip->i_gl, LM_ST_SHARED, 0, &gh); 568 - if (gfs2_glock_nq(&gh)) 569 - goto out_uninit; 570 602 if (!gfs2_is_stuffed(ip)) 571 603 mpage_readahead(rac, gfs2_block_map); 572 - gfs2_glock_dq(&gh); 573 - out_uninit: 574 - gfs2_holder_uninit(&gh); 575 604 } 576 605 577 606 /**
+50 -2
fs/gfs2/file.c
··· 558 558 return block_page_mkwrite_return(ret); 559 559 } 560 560 561 + static vm_fault_t gfs2_fault(struct vm_fault *vmf) 562 + { 563 + struct inode *inode = file_inode(vmf->vma->vm_file); 564 + struct gfs2_inode *ip = GFS2_I(inode); 565 + struct gfs2_holder gh; 566 + vm_fault_t ret; 567 + int err; 568 + 569 + gfs2_holder_init(ip->i_gl, LM_ST_SHARED, 0, &gh); 570 + err = gfs2_glock_nq(&gh); 571 + if (err) { 572 + ret = block_page_mkwrite_return(err); 573 + goto out_uninit; 574 + } 575 + ret = filemap_fault(vmf); 576 + gfs2_glock_dq(&gh); 577 + out_uninit: 578 + gfs2_holder_uninit(&gh); 579 + return ret; 580 + } 581 + 561 582 static const struct vm_operations_struct gfs2_vm_ops = { 562 - .fault = filemap_fault, 583 + .fault = gfs2_fault, 563 584 .map_pages = filemap_map_pages, 564 585 .page_mkwrite = gfs2_page_mkwrite, 565 586 }; ··· 845 824 846 825 static ssize_t gfs2_file_read_iter(struct kiocb *iocb, struct iov_iter *to) 847 826 { 827 + struct gfs2_inode *ip; 828 + struct gfs2_holder gh; 829 + size_t written = 0; 848 830 ssize_t ret; 849 831 850 832 if (iocb->ki_flags & IOCB_DIRECT) { ··· 856 832 return ret; 857 833 iocb->ki_flags &= ~IOCB_DIRECT; 858 834 } 859 - return generic_file_read_iter(iocb, to); 835 + iocb->ki_flags |= IOCB_NOIO; 836 + ret = generic_file_read_iter(iocb, to); 837 + iocb->ki_flags &= ~IOCB_NOIO; 838 + if (ret >= 0) { 839 + if (!iov_iter_count(to)) 840 + return ret; 841 + written = ret; 842 + } else { 843 + if (ret != -EAGAIN) 844 + return ret; 845 + if (iocb->ki_flags & IOCB_NOWAIT) 846 + return ret; 847 + } 848 + ip = GFS2_I(iocb->ki_filp->f_mapping->host); 849 + gfs2_holder_init(ip->i_gl, LM_ST_SHARED, 0, &gh); 850 + ret = gfs2_glock_nq(&gh); 851 + if (ret) 852 + goto out_uninit; 853 + ret = generic_file_read_iter(iocb, to); 854 + if (ret > 0) 855 + written += ret; 856 + gfs2_glock_dq(&gh); 857 + out_uninit: 858 + gfs2_holder_uninit(&gh); 859 + return written ? written : ret; 860 860 } 861 861 862 862 /**
+1
include/linux/fs.h
··· 315 315 #define IOCB_SYNC (1 << 5) 316 316 #define IOCB_WRITE (1 << 6) 317 317 #define IOCB_NOWAIT (1 << 7) 318 + #define IOCB_NOIO (1 << 9) 318 319 319 320 struct kiocb { 320 321 struct file *ki_filp;
+21 -2
mm/filemap.c
··· 2028 2028 2029 2029 page = find_get_page(mapping, index); 2030 2030 if (!page) { 2031 - if (iocb->ki_flags & IOCB_NOWAIT) 2031 + if (iocb->ki_flags & (IOCB_NOWAIT | IOCB_NOIO)) 2032 2032 goto would_block; 2033 2033 page_cache_sync_readahead(mapping, 2034 2034 ra, filp, ··· 2038 2038 goto no_cached_page; 2039 2039 } 2040 2040 if (PageReadahead(page)) { 2041 + if (iocb->ki_flags & IOCB_NOIO) { 2042 + put_page(page); 2043 + goto out; 2044 + } 2041 2045 page_cache_async_readahead(mapping, 2042 2046 ra, filp, page, 2043 2047 index, last_index - index); ··· 2164 2160 } 2165 2161 2166 2162 readpage: 2163 + if (iocb->ki_flags & IOCB_NOIO) { 2164 + unlock_page(page); 2165 + put_page(page); 2166 + goto would_block; 2167 + } 2167 2168 /* 2168 2169 * A previous I/O error may have been due to temporary 2169 2170 * failures, eg. multipath errors. ··· 2258 2249 * 2259 2250 * This is the "read_iter()" routine for all filesystems 2260 2251 * that can use the page cache directly. 2252 + * 2253 + * The IOCB_NOWAIT flag in iocb->ki_flags indicates that -EAGAIN shall 2254 + * be returned when no data can be read without waiting for I/O requests 2255 + * to complete; it doesn't prevent readahead. 2256 + * 2257 + * The IOCB_NOIO flag in iocb->ki_flags indicates that no new I/O 2258 + * requests shall be made for the read or for readahead. When no data 2259 + * can be read, -EAGAIN shall be returned. When readahead would be 2260 + * triggered, a partial, possibly empty read shall be returned. 2261 + * 2261 2262 * Return: 2262 2263 * * number of bytes copied, even for partial reads 2263 - * * negative error code if nothing was read 2264 + * * negative error code (or 0 if IOCB_NOIO) if nothing was read 2264 2265 */ 2265 2266 ssize_t 2266 2267 generic_file_read_iter(struct kiocb *iocb, struct iov_iter *iter)