Index: buffer/bufmgr.c
===================================================================
RCS file: /projects/cvsroot/pgsql/src/backend/storage/buffer/bufmgr.c,v
retrieving revision 1.182
diff -d -c -r1.182 bufmgr.c
*** buffer/bufmgr.c	24 Nov 2004 02:56:17 -0000	1.182
--- buffer/bufmgr.c	12 Dec 2004 21:53:10 -0000
***************
*** 681,686 ****
--- 681,687 ----
  {
  	BufferDesc **dirty_buffers;
  	BufferTag  *buftags;
+     int         maxdirty;
  	int			num_buffer_dirty;
  	int			i;
  
***************
*** 688,717 ****
  	if (percent == 0 || maxpages == 0)
  		return 0;
  
  	/*
  	 * Get a list of all currently dirty buffers and how many there are.
  	 * We do not flush buffers that get dirtied after we started. They
  	 * have to wait until the next checkpoint.
  	 */
! 	dirty_buffers = (BufferDesc **) palloc(NBuffers * sizeof(BufferDesc *));
! 	buftags = (BufferTag *) palloc(NBuffers * sizeof(BufferTag));
  
  	LWLockAcquire(BufMgrLock, LW_EXCLUSIVE);
- 	num_buffer_dirty = StrategyDirtyBufferList(dirty_buffers, buftags,
- 											   NBuffers);
  
! 	/*
! 	 * If called by the background writer, we are usually asked to only
! 	 * write out some portion of dirty buffers now, to prevent the IO
! 	 * storm at checkpoint time.
! 	 */
! 	if (percent > 0)
! 	{
! 		Assert(percent <= 100);
! 		num_buffer_dirty = (num_buffer_dirty * percent + 99) / 100;
! 	}
! 	if (maxpages > 0 && num_buffer_dirty > maxpages)
! 		num_buffer_dirty = maxpages;
  
  	/* Make sure we can handle the pin inside the loop */
  	ResourceOwnerEnlargeBuffers(CurrentResourceOwner);
--- 689,720 ----
  	if (percent == 0 || maxpages == 0)
  		return 0;
  
+     /* Set number of buffers we will clean at LRUs of buffer lists 
+      * If no limits set, then clean the whole of shared_buffers
+      */
+ 	if (maxpages > 0)
+     	maxdirty = maxpages;
+     else {
+     	if (percent > 0) {
+        		Assert(percent <= 100);
+         	maxdirty = (NBuffers * percent + 99) / 100;
+         }
+         else
+         	maxdirty = NBuffers;
+     }
+ 
  	/*
  	 * Get a list of all currently dirty buffers and how many there are.
  	 * We do not flush buffers that get dirtied after we started. They
  	 * have to wait until the next checkpoint.
  	 */
! 	dirty_buffers = (BufferDesc **) palloc(maxdirty * sizeof(BufferDesc *));
! 	buftags = (BufferTag *) palloc(maxdirty * sizeof(BufferTag));
  
  	LWLockAcquire(BufMgrLock, LW_EXCLUSIVE);
  
!    	num_buffer_dirty = StrategyDirtyBufferList(dirty_buffers, buftags,
! 											   maxdirty);
  
  	/* Make sure we can handle the pin inside the loop */
  	ResourceOwnerEnlargeBuffers(CurrentResourceOwner);
Index: buffer/freelist.c
===================================================================
RCS file: /projects/cvsroot/pgsql/src/backend/storage/buffer/freelist.c,v
retrieving revision 1.48
diff -d -c -r1.48 freelist.c
*** buffer/freelist.c	16 Sep 2004 16:58:31 -0000	1.48
--- buffer/freelist.c	12 Dec 2004 21:53:11 -0000
***************
*** 735,741 ****
   * StrategyDirtyBufferList
   *
   * Returns a list of dirty buffers, in priority order for writing.
-  * Note that the caller may choose not to write them all.
   *
   * The caller must beware of the possibility that a buffer is no longer dirty,
   * or even contains a different page, by the time he reaches it.  If it no
--- 735,740 ----
***************
*** 755,760 ****
--- 754,760 ----
  	int			cdb_id_t2;
  	int			buf_id;
  	BufferDesc *buf;
+ 	int			i;
  
  	/*
  	 * Traverse the T1 and T2 list LRU to MRU in "parallel" and add all
***************
*** 765,771 ****
  	cdb_id_t1 = StrategyControl->listHead[STRAT_LIST_T1];
  	cdb_id_t2 = StrategyControl->listHead[STRAT_LIST_T2];
  
! 	while (cdb_id_t1 >= 0 || cdb_id_t2 >= 0)
  	{
  		if (cdb_id_t1 >= 0)
  		{
--- 765,771 ----
  	cdb_id_t1 = StrategyControl->listHead[STRAT_LIST_T1];
  	cdb_id_t2 = StrategyControl->listHead[STRAT_LIST_T2];
  
! 	for (i = 0; i < max_buffers; i++)
  	{
  		if (cdb_id_t1 >= 0)
  		{
***************
*** 779,786 ****
  					buffers[num_buffer_dirty] = buf;
  					buftags[num_buffer_dirty] = buf->tag;
  					num_buffer_dirty++;
- 					if (num_buffer_dirty >= max_buffers)
- 						break;
  				}
  			}
  
--- 779,784 ----
***************
*** 799,806 ****
  					buffers[num_buffer_dirty] = buf;
  					buftags[num_buffer_dirty] = buf->tag;
  					num_buffer_dirty++;
- 					if (num_buffer_dirty >= max_buffers)
- 						break;
  				}
  			}
  
--- 797,802 ----
