@@ -35,6 +35,7 @@ public class DBApiLayer extends DB {
3535 static final boolean D = Boolean .getBoolean ( "DEBUG.DB" );
3636 /** The maximum number of cursors allowed */
3737 static final int NUM_CURSORS_BEFORE_KILL = 100 ;
38+ static final int NUM_CURSORS_PER_BATCH = 20000 ;
3839
3940 // --- show
4041
@@ -182,16 +183,23 @@ public WriteResult remove( DBObject o , com.mongodb.WriteConcern concern )
182183
183184 void _cleanCursors ()
184185 throws MongoException {
185- if ( _deadCursorIds .size () == 0 )
186- return ;
187186
188- if ( _deadCursorIds .size () % 20 != 0 && _deadCursorIds .size () < NUM_CURSORS_BEFORE_KILL )
189- return ;
187+ List <Long > l = null ;
188+
189+ synchronized ( _deadCursorIdsLock ){
190+ int sz = _deadCursorIds .size ();
190191
191- List <Long > l = _deadCursorIds ;
192- _deadCursorIds = new Vector <Long >();
192+ if ( _deadCursorIds .size () == 0 )
193+ return ;
194+
195+ if ( sz % 20 != 0 && sz < NUM_CURSORS_BEFORE_KILL )
196+ return ;
197+
198+ l = _deadCursorIds ;
199+ _deadCursorIds = new Vector <Long >();
200+ }
193201
194- Bytes .LOGGER .info ( "trying to kill cursors : " + l .size () );
202+ Bytes .LOGGER .info ( "going to kill cursors : " + l .size () );
195203
196204 try {
197205 killCursors ( l );
@@ -210,10 +218,23 @@ void killCursors( List<Long> all )
210218 OutMessage om = OutMessage .get ( 2007 );
211219 om .writeInt ( 0 ); // reserved
212220
213- om .writeInt ( all .size () );
221+ om .writeInt ( Math . min ( NUM_CURSORS_PER_BATCH , all .size () ) );
214222
223+ int soFar = 0 ;
224+ int totalSoFar = 0 ;
215225 for (Long l : all ) {
216226 om .writeLong (l );
227+
228+ totalSoFar ++;
229+ soFar ++;
230+
231+ if ( soFar >= NUM_CURSORS_PER_BATCH ){
232+ _connector .say ( _db , om ,com .mongodb .WriteConcern .NONE );
233+ om = OutMessage .get ( 2007 );
234+ om .writeInt ( 0 ); // reserved
235+ om .writeInt ( Math .min ( NUM_CURSORS_PER_BATCH , all .size () - totalSoFar ) );
236+ soFar = 0 ;
237+ }
217238 }
218239
219240 _connector .say ( _db , om ,com .mongodb .WriteConcern .NONE );
@@ -364,8 +385,11 @@ public String toString(){
364385 }
365386
366387 protected void finalize () throws Throwable {
367- if ( _curResult != null && _curResult .cursor () > 0 )
368- _deadCursorIds .add ( _curResult .cursor () );
388+ if ( _curResult != null && _curResult .cursor () != 0 ){
389+ synchronized ( _deadCursorIdsLock ){
390+ _deadCursorIds .add ( _curResult .cursor () );
391+ }
392+ }
369393 super .finalize ();
370394 }
371395
@@ -398,7 +422,9 @@ List<Integer> getSizes(){
398422 final String _rootPlusDot ;
399423 final DBConnector _connector ;
400424 final Map <String ,MyCollection > _collections = Collections .synchronizedMap ( new HashMap <String ,MyCollection >() );
401- List <Long > _deadCursorIds = new Vector <Long >();
425+
426+ final String _deadCursorIdsLock = "DBApiLayer-_deadCursorIdsLock-" + Math .random ();
427+ List <Long > _deadCursorIds = new LinkedList <Long >();
402428
403429 static final List <DBObject > EMPTY = Collections .unmodifiableList ( new LinkedList <DBObject >() );
404430}
0 commit comments