Diff
Not logged in

Differences From Artifact [09d09ef7ad]:

To Artifact [959b2bcc77]:


131
132
133
134
135
136
137

138
139
140
141
142
143
144
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145







+







static void	LockBucket(Cache *cachePtr, int bucket);
static void	UnlockBucket(Cache *cachePtr, int bucket);
static void	PutBlocks(Cache *cachePtr, int bucket, int numMove);
static int	GetBlocks(Cache *cachePtr, int bucket);
static Block *	Ptr2Block(char *ptr);
static char *	Block2Ptr(Block *blockPtr, int bucket, unsigned int reqSize);
static void	MoveObjs(Cache *fromPtr, Cache *toPtr, int numMove);
static void	PutObjs(Cache *fromPtr, int numMove);

/*
 * Local variables defined in this file and initialized at startup.
 */

static Tcl_Mutex *listLockPtr;
static Tcl_Mutex *objLockPtr;
267
268
269
270
271
272
273
274
275

276
277
278
279
280
281
282
283
268
269
270
271
272
273
274


275

276
277
278
279
280
281
282







-
-
+
-







    }

    /*
     * Flush objs.
     */

    if (cachePtr->numObjects > 0) {
	Tcl_MutexLock(objLockPtr);
	MoveObjs(cachePtr, sharedPtr, cachePtr->numObjects);
	PutObjs(cachePtr, cachePtr->numObjects);
	Tcl_MutexUnlock(objLockPtr);
    }

    /*
     * Remove from pool list.
     */

    Tcl_MutexLock(listLockPtr);
628
629
630
631
632
633
634
635
636

637
638
639
640
641
642
643
644
627
628
629
630
631
632
633


634

635
636
637
638
639
640
641







-
-
+
-








    /*
     * If the number of free objects has exceeded the high water mark, move
     * some blocks to the shared list.
     */

    if (cachePtr->numObjects > NOBJHIGH) {
	Tcl_MutexLock(objLockPtr);
	MoveObjs(cachePtr, sharedPtr, NOBJALLOC);
	PutObjs(cachePtr, NOBJALLOC);
	Tcl_MutexUnlock(objLockPtr);
    }
}

/*
 *----------------------------------------------------------------------
 *
 * Tcl_GetMemoryInfo --
731
732
733
734
735
736
737






















































738
739
740
741
742
743
744
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795







+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+







     * Move all objects as a block - they are already linked to each other, we
     * just have to update the first and last.
     */

    objPtr->internalRep.twoPtrValue.ptr1 = toPtr->firstObjPtr;
    toPtr->firstObjPtr = fromFirstObjPtr;
}

/*
 *----------------------------------------------------------------------
 *
 * PutObjs --
 *
 *	Move Tcl_Obj's from thread cache to shared cache.
 *
 * Results:
 *	None.
 *
 * Side effects:
 *	None.
 *
 *----------------------------------------------------------------------
 */

static void
PutObjs(
    Cache *fromPtr,
    int numMove)
{
    int keep = fromPtr->numObjects - numMove;
    Tcl_Obj *firstPtr, *lastPtr;

    fromPtr->numObjects = keep;
    firstPtr = fromPtr->firstObjPtr;
    if (keep == 0) {
	fromPtr->firstObjPtr = NULL;
    } else {
	do {
	    lastPtr = firstPtr;
	    firstPtr = firstPtr->internalRep.twoPtrValue.ptr1;
	} while (--keep > 0);
	lastPtr->internalRep.twoPtrValue.ptr1 = NULL;
    }

    /* TODO: We could avoid this walk to lastPtr if we kept a lastPtr field */
    lastPtr = firstPtr;
    while (lastPtr->internalRep.twoPtrValue.ptr1) {
	lastPtr = lastPtr->internalRep.twoPtrValue.ptr1;
    }
    
    /*
     * Move all objects as a block - they are already linked to each other, we
     * just have to update the first and last.
     */

    Tcl_MutexLock(objLockPtr);
    lastPtr->internalRep.twoPtrValue.ptr1 = sharedPtr->firstObjPtr;
    sharedPtr->firstObjPtr = firstPtr;
    sharedPtr->numObjects += numMove;
    Tcl_MutexUnlock(objLockPtr);
}

/*
 *----------------------------------------------------------------------
 *
 * Block2Ptr, Ptr2Block --
 *
 *	Convert between internal blocks and user pointers.
844
845
846
847
848
849
850






851
852
853
854















855
856

857
858

859
860


861
862
863

864



865
866
867
868
869
870
871
895
896
897
898
899
900
901
902
903
904
905
906
907




908
909
910
911
912
913
914
915
916
917
918
919
920
921
922


923
924
925
926


927
928
929
930

931

932
933
934
935
936
937
938
939
940
941







+
+
+
+
+
+
-
-
-
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
-
-
+


+
-
-
+
+


-
+
-
+
+
+








static void
PutBlocks(
    Cache *cachePtr,
    int bucket,
    int numMove)
{
    /*
     * We have numFree.  Want to shed numMove. So compute how many
     * Blocks to keep.
     */

    int keep = cachePtr->buckets[bucket].numFree - numMove;
    register Block *lastPtr, *firstPtr;
    register int n = numMove;

    /*
    Block *lastPtr, *firstPtr;

    cachePtr->buckets[bucket].numFree = keep;
    firstPtr = cachePtr->buckets[bucket].firstPtr;
    if (keep == 0) {
	cachePtr->buckets[bucket].firstPtr = NULL;
    } else {
	do {
	    lastPtr = firstPtr;
	    firstPtr = firstPtr->nextBlock;
	} while (--keep > 0);
	lastPtr->nextBlock = NULL;
    }

    /* 
     * Before acquiring the lock, walk the block list to find the last block
     * to be moved.
     * firstPtr now points to the first Block to return to shared.
     */

    /* TODO: We could avoid this walk to lastPtr if we kept a lastPtr field */
    firstPtr = lastPtr = cachePtr->buckets[bucket].firstPtr;
    while (--n > 0) {
    lastPtr = firstPtr;
    while (lastPtr->nextBlock) {
	lastPtr = lastPtr->nextBlock;
    }
    cachePtr->buckets[bucket].firstPtr = lastPtr->nextBlock;

    cachePtr->buckets[bucket].numFree -= numMove;
    /*
     * lastPtr now points to the last Block to return to shared.
     */

    /*
     * Aquire the lock and place the list of blocks at the front of the shared
     * cache bucket.
     */

    LockBucket(cachePtr, bucket);