[Vm-dev] VM Maker: Cog-eem.71.mcz

commits at source.squeak.org commits at source.squeak.org
Thu Sep 5 21:13:39 UTC 2013


Eliot Miranda uploaded a new version of Cog to project VM Maker:
http://source.squeak.org/VMMaker/Cog-eem.71.mcz

==================== Summary ====================

Name: Cog-eem.71
Author: eem
Time: 5 September 2013, 2:13:26.665 pm
UUID: 4bd9ed8f-2b14-41c1-b6c3-4bb86633e92c
Ancestors: Cog-eem.70

Add asserts to the Spur bootstrap that ed me to realize the image I
am using has an invalid specialObjectsArray.  GIGO ;-).

Change the Spur bootstrap launch to use linear search on method
lookup (because nothing's been rehashed yet).

The bootstrap now gets to the first instantiation.

Needs VMMaker.oscog-eem.349.

=============== Diff against Cog-eem.70 ===============

Item was changed:
  Object subclass: #SpurBootstrap
+ 	instanceVariableNames: 'oldHeap newHeap map reverseMap classToIndex oldInterpreter lastClassTablePage'
- 	instanceVariableNames: 'oldHeap newHeap map reverseMap classToIndex oldInterpreter pastClassTable'
  	classVariableNames: ''
  	poolDictionaries: 'VMObjectIndices'
  	category: 'Cog-Bootstrapping'!
  
  !SpurBootstrap commentStamp: 'eem 9/2/2013 13:26' prior: 0!
  SpurBootstrap bootstraps an image in CogMemoryManager format from a Squeak V3 + closures format.
  
  e.g.
  	(SpurBootstrap32 new on: '/Users/eliot/Cog/startreader.image')
  		transform;
  		launch
  
  Instance Variables
  	classToIndex:		<Dictionary>
  	map:		<Dictionary>
  	newHeap:		<CogMemoryManager>
  	oldHeap:		<NewObjectMemory>
  	oldInterpreter:		<StackInterpreterSimulator>
  
  classToIndex
  	- oldClass to new classIndex map
  
  map
  	- oldObject to newObject map
  
  newHeap
  	- the output, bootstrapped image
  
  oldHeap
  	- the input, image
  
  oldInterpreter
  	- the interpreter associated with oldHeap, needed for a hack to grab WeakArray
  !

Item was changed:
  ----- Method: SpurBootstrap>>allocateClassTable (in category 'bootstrap') -----
  allocateClassTable
  	"Allocate the root of the classTable plus enough pages to accomodate all classes in
  	 the classToIndex map.  Don;t fill in the entries yet; the classes have yet to be cloned."
  	| tableRootSize tableRoot page maxSize numPages |
  	tableRootSize := self classTableSize / newHeap classTablePageSize.
  	tableRoot := newHeap
  					allocateSlots: tableRootSize
  					format: newHeap arrayFormat
  					classIndex: newHeap arrayClassIndexPun.
  	self assert: (newHeap numSlotsOf: tableRoot) = tableRootSize.
  	self assert: (newHeap formatOf: tableRoot) = newHeap arrayFormat.
  	self assert: (newHeap classIndexOf: tableRoot) = newHeap arrayClassIndexPun.
  	newHeap nilFieldsOf: tableRoot.
  	"first page is strong"
  	page := newHeap
  					allocateSlots: newHeap classTablePageSize
  					format: newHeap arrayFormat
  					classIndex: newHeap arrayClassIndexPun.
  	self assert: (newHeap numSlotsOf: page) = newHeap classTablePageSize.
  	self assert: (newHeap formatOf: tableRoot) = newHeap arrayFormat.
  	self assert: (newHeap classIndexOf: tableRoot) = newHeap arrayClassIndexPun.
+ 	self assert: (newHeap objectAfter: tableRoot limit: newHeap freeStart) = page..
+ 	lastClassTablePage := page.
- 	self assert: (newHeap objectAfter: tableRoot limit: newHeap freeStart) = page.
  	newHeap nilFieldsOf: page.
  	newHeap storePointer: 0 ofObject: tableRoot withValue: page.
  	newHeap classTableRootObj: tableRoot.
  	maxSize := classToIndex inject: 0 into: [:a :b| a max: b].
  	numPages := (maxSize + newHeap classTableMinorIndexMask / newHeap classTablePageSize) truncated.
  	2 to: numPages do:
  		[:i|
  		page := newHeap
  					allocateSlots: newHeap classTablePageSize
  					format: newHeap weakArrayFormat
  					classIndex: newHeap weakArrayClassIndexPun.
  		self assert: (newHeap numSlotsOf: page) = newHeap classTablePageSize.
  		self assert: (newHeap formatOf: page) = newHeap weakArrayFormat.
  		self assert: (newHeap classIndexOf: page) = newHeap weakArrayClassIndexPun.
  		newHeap nilFieldsOf: page.
  		newHeap storePointer: i - 1 ofObject: tableRoot withValue: page.
+ 		self assert: (newHeap objectAfter: (newHeap fetchPointer: i - 2 ofObject: tableRoot)  limit: newHeap freeStart) = page.
+ 		lastClassTablePage := page]!
- 		self assert: (newHeap objectAfter: (newHeap fetchPointer: i - 2 ofObject: tableRoot)  limit: newHeap freeStart) = page].
- 	pastClassTable := newHeap freeStart.!

Item was changed:
  ----- Method: SpurBootstrap>>buildClassMap (in category 'bootstrap') -----
  buildClassMap
  	"enumerate all objects asking isBehavior:?  (class == Metaclass or class class == Metaclass) doesn't work for Newspeak"
  	"Build a map from all classes in oldHeap to a class index.
  	 ONLY DEALS WITH CLASSES THAT HAVE INSTANCES!!!! (can walk superclass chain?  Can walk subclasses set? Can ask class == Metaclass or class class == Metaclass class?)"
  	| classes classTableIndex |
  	self defineKnownClassIndices.
  	classes := classToIndex keys asSet.
+ 	classTableIndex := classToIndex inject: 0 into: [:a :b| a max: b].
- 	classTableIndex := newHeap classTablePageSize.
  	oldHeap allObjectsDo:
  		[:oldObj| | oldClass |
  		 oldClass := oldHeap fetchClassOfNonImm: oldObj.
+ 		 self assert: (oldHeap isPointersNonImm: oldClass).
  		 (classes includes: oldClass) ifFalse:
  			[classes add: oldClass.
  			 classToIndex at: oldClass put: (classTableIndex := classTableIndex + 1)]]!

Item was changed:
  ----- Method: SpurBootstrap>>defineKnownClassIndices (in category 'class indices') -----
  defineKnownClassIndices
  	"The classTable is laid out
  		- to make it easy to map immediates to classes; the tag pattern of an immediate is its class index.
  		  hence there are two entries for SmallInteger
  		- to assign small indices to well-known classes such as Array, Message et al
  		- to leave plenty of room for new known classes; hence the first page contains only well-known classes
  		- to enable overlaps and avoid conflicts with indices in the specialObjectsArray (?really? eem)
  		- to provide a WeakArray pun for the pages of the table itself so that these do not show up as instances of WeakArray"
  	| classMethodContext classBlockClosure classMessage "no api method for these" |
  	classMessage := oldHeap splObj: (VMObjectIndices bindingOf: #ClassMessage) value.
  	classMethodContext := oldHeap splObj: (VMObjectIndices bindingOf: #ClassMethodContext) value.
  	classBlockClosure := oldHeap splObj: (VMObjectIndices bindingOf: #ClassBlockClosure) value.
+ 	"c.f. CogMemoryManager class>>intializeCompactClassIndices".
+ 	classToIndex keysDo:
+ 		[:oldClass|
+ 		self assert: (oldInterpreter addressCouldBeClassObj: oldClass)].
- 	"c.f. CogMemoryManager class>>intializeCompactClassIndices"
  	classToIndex
  		at: oldHeap classSmallInteger put: 1; "N.B. must fill-in index 3 manually"
  		at: oldHeap classCharacter put: 2;
  		"at: oldHeap classSmallInteger put: 3" "N.B. must fill-in index 3 manually"
  		"leave room for up to 15 tagged classes"
  		"leave room for up to 16 puns"
  		at: oldHeap classLargeNegativeInteger put: 32;
  		at: oldHeap classLargePositiveInteger put: 33;
  		at: oldHeap classFloat put: 34;
  
  		at: "oldHeap" classMessage put: 35;
  		at: "oldHeap" classMethodContext put: 36;
  		at: "oldHeap" classBlockClosure put: 37;
  
  		at: oldHeap classSemaphore put: 48;
  		at: oldHeap classMutex put: 49;
  
  		at: oldHeap classByteArray put: 50;
  		at: oldHeap classArray put: 51;
  		at: oldHeap classString put: 52;
  		at: oldHeap classBitmap put: 53;
  		at: oldHeap classPoint put: 54;
  
  		at: oldHeap classExternalAddress put: 128;
  		at: oldHeap classExternalData put: 129;
  		at: oldHeap classExternalFunction put: 130;
  		at: oldHeap classExternalLibrary put: 131;
  		at: oldHeap classExternalStructure put: 132;
  		at: oldHeap classAlien put: 133;
+ 		at: oldHeap classUnsafeAlien put: 134.
+ 	classToIndex keysDo:
+ 		[:oldClass|
+ 		self assert: (oldInterpreter addressCouldBeClassObj: oldClass)]!
- 		at: oldHeap classUnsafeAlien put: 133!

Item was changed:
  ----- Method: SpurBootstrap>>fillInClassTable (in category 'bootstrap') -----
  fillInClassTable
  	| firstPage classWeakArray |
  	classToIndex keysAndValuesDo:
  		[:oldClass :index| | newClass page |
  		newClass := map at: oldClass.
+ 		self assert: (newHeap isPointersNonImm: newClass).
  		newHeap setHashBitsOf: newClass to: index.
  		page := newHeap
  					fetchPointer: index >> newHeap classTableMajorIndexShift
  					ofObject: newHeap classTableRootObj.
  		newHeap
  			storePointer: (index bitAnd: newHeap classTableMinorIndexMask)
  			ofObject: page
+ 			withValue: newClass.
+ 		self assert: (newHeap classAtIndex: index) = newClass].
- 			withValue: newClass].
  	firstPage := newHeap
  					fetchPointer: 0
  					ofObject: newHeap classTableRootObj.
  	classWeakArray := classToIndex keys detect:
  							[:oldClass|
  							(oldHeap instSpecOfClass: oldClass) = 4
  							and: [oldInterpreter classNameOf: oldClass Is: 'WeakArray']].
  	newHeap
  		storePointer: 1
  			ofObject: firstPage
  				withValue: (map at: oldHeap classSmallInteger);
  		storePointer: 2
  			ofObject: firstPage
  				withValue: (map at: oldHeap classCharacter);
  		storePointer: 3
  			ofObject: firstPage
  				withValue: (map at: oldHeap classSmallInteger);
  		storePointer: newHeap arrayClassIndexPun
  			ofObject: firstPage
  				withValue: (map at: oldHeap classArray);
  		storePointer: newHeap weakArrayClassIndexPun
  			ofObject: firstPage
  				withValue: (map at: classWeakArray)!

Item was changed:
  ----- Method: SpurBootstrap>>launch (in category 'testing') -----
  launch
  	| sim |
  	sim := StackInterpreterSimulator onObjectMemory: newHeap.
  	newHeap coInterpreter: sim.
  	sim initializeInterpreter: 0.
+ 	sim
+ 		ensureDebugAtEachStepBlock;
+ 		instVarNamed: 'printBytecodeAtEachStep' put: true;
+ 		instVarNamed: 'methodDictLinearSearchLimit' put: SmallInteger maxVal. "for now"
  	sim run!

Item was changed:
  ----- Method: SpurBootstrap>>validate (in category 'bootstrap') -----
  validate
+ 	| p n duplicates maxClassIndex |
+ 	self assert: (reverseMap at: newHeap specialObjectsOop) = oldHeap specialObjectsOop.
+ 	self assert: (map at: oldHeap specialObjectsOop) = newHeap specialObjectsOop.
+ 	self assert: (reverseMap at: newHeap classTableRootObj ifAbsent: []) isNil.
+ 
+ 	duplicates := { 3. newHeap arrayClassIndexPun. newHeap weakArrayClassIndexPun }.
+ 	maxClassIndex := classToIndex inject: 0 into: [:a :b| a max: b].
+ 	self assert: ((0 to: maxClassIndex) select:
+ 					[:idx| | classObj |
+ 					(classObj := newHeap classAtIndex: idx) ~= newHeap nilObject
+ 					and: [(newHeap classIndexOf: classObj) = (newHeap hashBitsOf: classObj)]]) isEmpty.
+ 	0 to: maxClassIndex do:
+ 		[:index| | classObj |
+ 		(classObj := newHeap classAtIndex: index) = newHeap nilObject
+ 			ifTrue:
+ 				[self assert: (classToIndex keyAtValue: index ifAbsent: []) isNil]
+ 			ifFalse:
+ 				[self assert: (newHeap classIndexOf: classObj) ~= (newHeap hashBitsOf: classObj).
+ 				(duplicates includes: index) ifFalse:
+ 					[self assert: (newHeap hashBitsOf: classObj) = index]]].
+ 	classToIndex keysAndValuesDo:
+ 		[:oldClass :idx|
+ 		self assert: (newHeap hashBitsOf: (map at: oldClass)) = idx. 
+ 		self assert: oldClass = (reverseMap at: (newHeap classAtIndex: idx))].
+ 	n := 0.
- 	| p i |
- 	i := 0.
  	newHeap allObjectsDo:
  		[:o|
+ 		(o <= newHeap trueObject
+ 		 or: [o > lastClassTablePage]) ifTrue:
+ 			[self assert: (reverseMap includesKey: o).
+ 			 self assert: (newHeap fetchClassOfNonImm: o) = (map at: (oldHeap fetchClassOfNonImm: (reverseMap at: o)))].
+ 		n := n + 1.
+ 		p := o].
- 		o >= pastClassTable ifTrue:
- 			[self assert: (reverseMap includesKey: o)].
- 		i := i + 1. p := o].
  	p class.
+ 	self assert: (n between: map size and: map size + 5) "+ 5 is room for classTable"!
- 	self assert: (i between: map size and: map size + 5) "+ 5 is room for classTable"!



More information about the Vm-dev mailing list