On Wed, 21 Feb 2001, Danny wrote:
<snip>
> Item final: I've seen the messages:
>
> cluster_write: can't get pb (page_buf_io.c:1839)
> cluster_write: pb_lookup_pages failed! (page_buf_io.c:1844)
>
> and the process hung. The only out was a reboot, and that filesystem
> refused to be unmounted. ps(1) showed the process status as 'D',
> uninterruptable sleep :-(.
Hi,
Could you please try the following patch against current XFS tree and
report results?
You still need the pagbuf -> pagebuf typo patch you just sent on top of
this to make it compile.
Thanks.
Index: mm/vmscan.c
===================================================================
RCS file: /cvs/linux-2.4-xfs/linux/mm/vmscan.c,v
retrieving revision 1.48
diff -u -r1.48 vmscan.c
--- mm/vmscan.c 2001/02/09 20:44:34 1.48
+++ mm/vmscan.c 2001/02/22 12:22:15
@@ -427,7 +427,7 @@
#define MAX_LAUNDER (4 * (1 << page_cluster))
int page_launder(int gfp_mask, int sync)
{
- int launder_loop, maxscan, cleaned_pages, maxlaunder;
+ int launder_loop, maxscan, cleaned_pages, maxlaunder, can_queue_buffers;
int can_get_io_locks;
struct list_head * page_lru;
struct page * page;
@@ -437,6 +437,7 @@
* buffers to disk) if __GFP_IO is set.
*/
can_get_io_locks = gfp_mask & __GFP_IO;
+ can_queue_buffers = gfp_mask & __GFP_PAGE_IO;
launder_loop = 0;
maxlaunder = 0;
@@ -488,7 +489,7 @@
goto page_active;
/* First time through? Move it to the back of the list
*/
- if (!launder_loop) {
+ if (!launder_loop || !can_get_io_locks) {
list_del(page_lru);
list_add(page_lru, &inactive_dirty_list);
UnlockPage(page);
@@ -618,7 +619,8 @@
* loads, flush out the dirty pages before we have to wait on
* IO.
*/
- if (can_get_io_locks && !launder_loop && free_shortage()) {
+ if ((can_get_io_locks || can_queue_buffers) && !launder_loop
+ && free_shortage()) {
launder_loop = 1;
/* If we cleaned pages, never do synchronous IO. */
if (cleaned_pages)
Index: fs/pagebuf/page_buf.c
===================================================================
RCS file: /cvs/linux-2.4-xfs/linux/fs/pagebuf/page_buf.c,v
retrieving revision 1.56
diff -u -r1.56 page_buf.c
--- fs/pagebuf/page_buf.c 2001/02/21 22:31:45 1.56
+++ fs/pagebuf/page_buf.c 2001/02/22 12:22:46
@@ -497,7 +497,7 @@
*/
if (flags & PBF_MAPPABLE) {
- gfp_mask = GFP_BUFFER;
+ gfp_mask = GFP_PAGE_IO;
} else {
gfp_mask = GFP_HIGHUSER;
}
@@ -1341,7 +1341,7 @@
*/
psync = (pagesync_t *) kmalloc(sizeof(pagesync_t) +
- blk_length * sizeof(struct buffer_head *), GFP_BUFFER);
+ blk_length * sizeof(struct buffer_head *), GFP_PAGE_IO);
/* Ugh - out of memory condition here */
if (psync == NULL)
@@ -1354,7 +1354,7 @@
for (cnt = 0; blk_length > 0;
blk_length--, blk_offset++, pg_offset += sector) {
- bh = kmem_cache_alloc(bh_cachep, SLAB_BUFFER);
+ bh = kmem_cache_alloc(bh_cachep, SLAB_PAGE_IO);
if (bh == NULL){
err = -ENOMEM;
goto error;
Index: fs/pagebuf/page_buf_io.c
===================================================================
RCS file: /cvs/linux-2.4-xfs/linux/fs/pagebuf/page_buf_io.c,v
retrieving revision 1.53
diff -u -r1.53 fs/pagebuf/page_buf_io.c
--- fs/pagebuf/page_buf_io.c 2001/02/21 00:50:22 1.53
+++ fs/pagebuf/page_buf_io.c 2001/02/22 12:23:27
@@ -261,7 +261,7 @@
* since this can be in kswapd's path ...
*/
cpages = kmalloc(CLUSTER_PAGE_LIST_SIZE * sizeof(struct page *),
- GFP_BUFFER);
+ GFP_PAGE_IO);
spin_lock(&pagecache_lock);
_pagebuf_flush(ip, &ip->i_mapping->clean_pages, ioff, cpages);
@@ -1084,7 +1084,7 @@
current->flags |= PF_MEMALLOC;
cpages = kmalloc(CLUSTER_PAGE_LIST_SIZE * sizeof(struct page *),
- GFP_BUFFER);
+ GFP_PAGE_IO);
do_write_full_page++;
Index: include/linux/slab.h
===================================================================
RCS file: /cvs/linux-2.4-xfs/linux/include/linux/slab.h,v
retrieving revision 1.12
diff -u -r1.12 slab.h
--- include/linux/slab.h 2001/01/03 01:43:05 1.12
+++ include/linux/slab.h 2001/02/22 12:25:32
@@ -21,8 +21,9 @@
#define SLAB_KERNEL GFP_KERNEL
#define SLAB_NFS GFP_NFS
#define SLAB_DMA GFP_DMA
+#define SLAB_PAGE_IO GFP_PAGE_IO
-#define SLAB_LEVEL_MASK (__GFP_WAIT|__GFP_HIGH|__GFP_IO)
+#define SLAB_LEVEL_MASK
(__GFP_WAIT|__GFP_HIGH|__GFP_IO|__GFP_PAGE_IO)
#define SLAB_NO_GROW 0x00001000UL /* don't grow a cache */
/* flags to pass to kmem_cache_create().
Index: include/linux/mm.h
===================================================================
RCS file: /cvs/linux-2.4-xfs/linux/include/linux/mm.h,v
retrieving revision 1.48
diff -u -r1.48 mm.h
--- include/linux/mm.h 2001/02/14 23:54:41 1.48
+++ include/linux/mm.h 2001/02/22 12:25:50
@@ -468,8 +468,9 @@
#define __GFP_HIGHMEM 0x0 /* noop */
#endif
#define __GFP_VM 0x20
+#define __GFP_PAGE_IO 0x40
-
+#define GFP_PAGE_IO (__GFP_HIGH | __GFP_WAIT | __GFP_PAGE_IO)
#define GFP_BUFFER (__GFP_HIGH | __GFP_WAIT)
#define GFP_ATOMIC (__GFP_HIGH)
#define GFP_USER ( __GFP_WAIT | __GFP_IO)
|