[Vm-dev] VM Maker: VMMaker.oscog-cb.1003.mcz

commits at source.squeak.org commits at source.squeak.org
Tue Dec 30 12:46:45 UTC 2014


ClementBera uploaded a new version of VMMaker to project VM Maker:
http://source.squeak.org/VMMaker/VMMaker.oscog-cb.1003.mcz

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

Name: VMMaker.oscog-cb.1003
Author: cb
Time: 30 December 2014, 1:41:14.778 pm
UUID: 012766da-2988-46a8-8f32-f8849b1e5324
Ancestors: VMMaker.oscog-eem.1002

Added code for inline primitive comparison.

I now need to test them from the image.

=============== Diff against VMMaker.oscog-eem.1002 ===============

Item was changed:
  ----- Method: StackToRegisterMappingCogit>>genBinaryConstOpVarInlinePrimitive: (in category 'inline primitive generators') -----
  genBinaryConstOpVarInlinePrimitive: prim
  	"Const op var version of binary inline primitives."
  	"SistaV1: 248		11111000 	iiiiiiii		mjjjjjjj		Call Primitive #iiiiiiii + (jjjjjjj * 256) m=1 means inlined primitive, no hard return after execution.
  	 See EncoderForSistaV1's class comment and StackInterpreter>>#binaryInlinePrimitive:"
  	| ra val untaggedVal |
  	(ra := backEnd availableRegisterOrNilFor: self liveRegisters) ifNil:
  		[self ssAllocateRequiredReg:
  			(ra := optStatus isReceiverResultRegLive
  					ifTrue: [Arg0Reg]
  					ifFalse: [ReceiverResultReg])].
  	ra = ReceiverResultReg ifTrue:
  		[optStatus isReceiverResultRegLive: false].
  	self ssTop popToReg: ra.
  	self ssPop: 1.
  	val := self ssTop constant.
  	self ssPop: 1.
  	untaggedVal := val - objectMemory smallIntegerTag.
  	prim caseOf: {
  		"0 through 6, +, -, *, /, //, \\, quo:, SmallInteger op SmallInteger => SmallInteger, no overflow"
  		[0]	->	[self AddCq: untaggedVal R: ra].
  		[1]	->	[self MoveCq: val R: TempReg.
  				 self SubR: ra R: TempReg.
  				 objectRepresentation genAddSmallIntegerTagsTo: TempReg.
  				 self MoveR: TempReg R: ra].
  		[2]	->	[objectRepresentation genRemoveSmallIntegerTagsInScratchReg: ra.
  				 self MoveCq: (objectMemory integerValueOf: val) R: TempReg.
  				 self MulR: TempReg R: ra.
  				 objectRepresentation genAddSmallIntegerTagsTo: ra].
  
  		"2016 through 2019, bitAnd:, bitOr:, bitXor, bitShift:, SmallInteger op SmallInteger => SmallInteger, no overflow"
  
  		"2032	through 2037, >, <, >=, <=. =, ~=, SmallInteger op SmallInteger => Boolean (flags?? then in jump bytecodes if ssTop is a flags value, just generate the instruction!!!!)"
+ 		[32] -> [ self CmpCq: val R: ra.
+ 				self genBinaryInlineComparison: JumpGreater opFalse: JumpLess destReg: ra ].
+ 		[33] -> [ self CmpCq: val R: ra.
+ 				self genBinaryInlineComparison: JumpLess opFalse: JumpGreater destReg: ra ].
+ 		[34] -> [ self CmpCq: val R: ra.
+ 				self genBinaryInlineComparison: JumpGreaterOrEqual opFalse: JumpLessOrEqual destReg: ra ].
+ 		[35] -> [ self CmpCq: val R: ra.
+ 				self genBinaryInlineComparison: JumpLessOrEqual opFalse: JumpGreaterOrEqual destReg: ra ].
+ 		[36] -> [ self CmpCq: val R: ra.
+ 				self genBinaryInlineComparison: JumpZero opFalse: JumpNonZero destReg: ra ].
+ 		[37] -> [ self CmpCq: val R: ra.
+ 				self genBinaryInlineComparison: JumpNonZero opFalse: JumpZero destReg: ra ].
  
  		"2064	through 2068, Pointer Object>>at:, Byte Object>>at:, Short16 Word Object>>at: LongWord32 Object>>at: Quad64Word Object>>at:. obj op 0-rel SmallInteger => oop"
  		[64] ->	[self genConvertSmallIntegerToIntegerInReg: ra.
  				 self MoveCq: val R: TempReg.
  				 self MoveXwr: ra R: TempReg R: ra].
  		[65] ->	[self genConvertSmallIntegerToIntegerInReg: ra.
  				 self MoveCq: val R: TempReg.
  				 self MoveXbr: ra R: TempReg R: ra]
  
  	}
  	otherwise: [^EncounteredUnknownBytecode].
  	self ssPushRegister: ra.
  	^0!

Item was added:
+ ----- Method: StackToRegisterMappingCogit>>genBinaryInlineComparison:opFalse:destReg: (in category 'inline primitive generators') -----
+ genBinaryInlineComparison: opTrue opFalse: opFalse destReg: destReg
+ 	"Inlined comparison. opTrue = jump for true and opFalse = jump for false"
+ 	| nextPC branchDescriptor nExts |	
+ 	nextPC := bytecodePC + 3.
+ 	[branchDescriptor := self generatorAt: (objectMemory fetchByte: nextPC ofObject: methodObj) + (byte0 bitAnd: 256).
+ 	 			nExts := 0.	
+ 	branchDescriptor isExtension] whileTrue:
+ 	[nExts := nExts + 1.
+ 	 		nextPC := nextPC + branchDescriptor numBytes].
+ 	(branchDescriptor isBranchTrue or: [branchDescriptor isBranchFalse])
+ 		ifTrue: [
+ 		"This is the path where the inlined comparison is followed immediatly by a branch"
+ 		| targetBytecodePC postBranchPC |
+ 		targetBytecodePC := nextPC
+ 				+ branchDescriptor numBytes
+ 				+ (self spanFor: branchDescriptor at: nextPC exts: nExts in: methodObj).
+ 		postBranchPC := nextPC + branchDescriptor numBytes.
+ 		self ssPushConstant: objectMemory trueObject. "dummy object"
+ 		self gen: (branchDescriptor isBranchTrue ifTrue: [opTrue] ifFalse: [opFalse])
+ 			operand: (self ensureNonMergeFixupAt: targetBytecodePC - initialPC) asUnsignedInteger.
+ 		self Jump: (self ensureNonMergeFixupAt: postBranchPC - initialPC).
+ 		 ]
+ 		ifFalse: [ 
+ 		"This is the path where the inlined comparison is *not* followed immediatly by a branch"
+ 			| condJump jump |
+ 			condJump := self gen: opTrue operand: 0.
+ 	 		self 
+ 				annotate: (self MoveCw: objectMemory falseObject R: destReg) 
+ 				objRef: objectMemory falseObject.
+ 	 		jump := self Jump: 0.
+ 			condJump jmpTarget: (self 
+ 				annotate: (self MoveCw: objectMemory trueObject R: destReg) 
+ 				objRef: objectMemory trueObject).
+ 			jump jmpTarget: self Label ].
+ 	^ 0!

Item was changed:
  ----- Method: StackToRegisterMappingCogit>>genBinaryVarOpConstInlinePrimitive: (in category 'inline primitive generators') -----
  genBinaryVarOpConstInlinePrimitive: prim
  	"Var op const version of inline binary inline primitives."
  	"SistaV1: 248		11111000 	iiiiiiii		mjjjjjjj		Call Primitive #iiiiiiii + (jjjjjjj * 256) m=1 means inlined primitive, no hard return after execution.
  	 See EncoderForSistaV1's class comment and StackInterpreter>>#binaryInlinePrimitive:"
  	| rr val untaggedVal |
  	(rr := backEnd availableRegisterOrNilFor: self liveRegisters) ifNil:
  		[self ssAllocateRequiredReg:
  			(rr := optStatus isReceiverResultRegLive
  					ifTrue: [Arg0Reg]
  					ifFalse: [ReceiverResultReg])].
  	rr = ReceiverResultReg ifTrue:
  		[optStatus isReceiverResultRegLive: false].
  	val := self ssTop constant.
  	self ssPop: 1.
  	self ssTop popToReg: rr.
  	self ssPop: 1.
  	untaggedVal := val - objectMemory smallIntegerTag.
  	prim caseOf: {
  		"0 through 6, +, -, *, /, //, \\, quo:, SmallInteger op SmallInteger => SmallInteger, no overflow"
  		[0]	->	[self AddCq: untaggedVal R: rr].
  		[1]	->	[self SubCq: untaggedVal R: rr ].
  		[2]	->	[self flag: 'could use MulCq:R'.
  				 objectRepresentation genShiftAwaySmallIntegerTagsInScratchReg: rr.
  				 self MoveCq: (objectMemory integerValueOf: val) R: TempReg.
  				 self MulR: TempReg R: rr.
  				 objectRepresentation genAddSmallIntegerTagsTo: rr].
  
  		"2016 through 2019, bitAnd:, bitOr:, bitXor, bitShift:, SmallInteger op SmallInteger => SmallInteger, no overflow"
  
+ 		"2032	through 2037, >, <, >=, <=. =, ~=, SmallInteger op SmallInteger => Boolean (flags?? then in jump bytecodes if ssTop is a flags value, just generate the instruction!!!!)
+ 		Here the comparison is reversed (cst on the left, reg on the right) so I inverted opTrue and opFalse"
+ 		[32] -> [ self CmpCq: val R: rr.
+ 				self genBinaryInlineComparison: JumpLess opFalse: JumpGreater destReg: rr ].
+ 		[33] -> [ self CmpCq: val R: rr.
+ 				self genBinaryInlineComparison: JumpGreater opFalse: JumpLess destReg: rr ].
+ 		[34] -> [ self CmpCq: val R: rr.
+ 				self genBinaryInlineComparison: JumpLessOrEqual opFalse: JumpGreaterOrEqual destReg: rr ].
+ 		[35] -> [ self CmpCq: val R: rr.
+ 				self genBinaryInlineComparison: JumpGreaterOrEqual opFalse: JumpLessOrEqual destReg: rr ].
+ 		[36] -> [ self CmpCq: val R: rr.
+ 				self genBinaryInlineComparison: JumpNonZero opFalse: JumpZero destReg: rr ].
+ 		[37] -> [ self CmpCq: val R: rr.
+ 				self genBinaryInlineComparison: JumpZero opFalse: JumpNonZero destReg: rr ].
- 		"2032	through 2037, >, <, >=, <=. =, ~=, SmallInteger op SmallInteger => Boolean (flags?? then in jump bytecodes if ssTop is a flags value, just generate the instruction!!!!)"
  
  		"2064	through 2068, Pointer Object>>at:, Byte Object>>at:, Short16 Word Object>>at: LongWord32 Object>>at: Quad64Word Object>>at:. obj op 0-rel SmallInteger => oop"
  		[64] ->	[self genConvertSmallIntegerToIntegerInReg: rr.
  				self MoveCq: val >> 1 R: TempReg.
  				self MoveXwr: TempReg R: rr R: rr ].
  		[65] ->	[self genConvertSmallIntegerToIntegerInReg: rr.
  				self MoveCq: val >> 1 R: TempReg.
  				self MoveXbr: TempReg R: rr R: rr ]
  
  	}
  	otherwise: [^EncounteredUnknownBytecode].
  	self ssPushRegister: rr.
  	^0!

Item was changed:
  ----- Method: StackToRegisterMappingCogit>>genBinaryVarOpVarInlinePrimitive: (in category 'inline primitive generators') -----
  genBinaryVarOpVarInlinePrimitive: prim
  	"Var op var version of binary inline primitives."
  	"SistaV1: 248		11111000 	iiiiiiii		mjjjjjjj		Call Primitive #iiiiiiii + (jjjjjjj * 256) m=1 means inlined primitive, no hard return after execution.
  	 See EncoderForSistaV1's class comment and StackInterpreter>>#binaryInlinePrimitive:"
  	| ra rr |
  	(rr := backEnd availableRegisterOrNilFor: self liveRegisters) ifNil:
  		[self ssAllocateRequiredReg:
  			(rr := optStatus isReceiverResultRegLive
  					ifTrue: [Arg0Reg]
  					ifFalse: [ReceiverResultReg])].
  	(ra := backEnd availableRegisterOrNilFor: (self liveRegisters bitOr: (self registerMaskFor: rr))) ifNil:
  		[self ssAllocateRequiredReg: (ra := Arg1Reg)].
  	(rr = ReceiverResultReg or: [ra = ReceiverResultReg]) ifTrue:
  		[optStatus isReceiverResultRegLive: false].
  	self ssTop popToReg: ra.
  	self ssPop: 1.
  	self ssTop popToReg: rr.
  	self ssPop: 1.
  	prim caseOf: {
  		"0 through 6, +, -, *, /, //, \\, quo:, SmallInteger op SmallInteger => SmallInteger, no overflow"
  		[0]	->	[objectRepresentation genRemoveSmallIntegerTagsInScratchReg: ra.
  				 self AddR: ra R: rr].
  		[1]	->	[self SubR: ra R: rr.
  				 objectRepresentation genAddSmallIntegerTagsTo: rr].
  		[2]	->	[objectRepresentation genRemoveSmallIntegerTagsInScratchReg: rr.
  				 objectRepresentation genShiftAwaySmallIntegerTagsInScratchReg: ra.
  				 self MulR: ra R: rr.
  				 objectRepresentation genAddSmallIntegerTagsTo: rr].
  
  		"2016 through 2019, bitAnd:, bitOr:, bitXor, bitShift:, SmallInteger op SmallInteger => SmallInteger, no overflow"
  
  		"2032	through 2037, >, <, >=, <=. =, ~=, SmallInteger op SmallInteger => Boolean (flags?? then in jump bytecodes if ssTop is a flags value, just generate the instruction!!!!)"
+ 		[32] -> [ self CmpR: rr R: ra.
+ 				self genBinaryInlineComparison: JumpGreater opFalse: JumpLess destReg: rr ].
+ 		[33] -> [ self CmpR: rr R: ra.
+ 				self genBinaryInlineComparison: JumpLess opFalse: JumpGreater destReg: rr ].
+ 		[34] -> [ self CmpR: rr R: ra.
+ 				self genBinaryInlineComparison: JumpGreaterOrEqual opFalse: JumpLessOrEqual destReg: rr ].
+ 		[35] -> [ self CmpR: rr R: ra.
+ 				self genBinaryInlineComparison: JumpLessOrEqual opFalse: JumpGreaterOrEqual destReg: rr ].
+ 		[36] -> [ self CmpR: rr R: ra.
+ 				self genBinaryInlineComparison: JumpZero opFalse: JumpNonZero destReg: rr ].
+ 		[37] -> [ self CmpR: rr R: ra.
+ 				self genBinaryInlineComparison: JumpNonZero opFalse: JumpZero destReg: rr ].
  
  		"2064	through 2068, Pointer Object>>at:, Byte Object>>at:, Short16 Word Object>>at: LongWord32 Object>>at: Quad64Word Object>>at:. obj op 0-rel SmallInteger => oop"
  		[64] ->	[self genConvertSmallIntegerToIntegerInReg: ra.
  				self MoveXwr: ra R: rr R: rr ].
  		[65] ->	[self genConvertSmallIntegerToIntegerInReg: ra.
  				self MoveXbr: ra R: rr R: rr ]
  
  	}
  	otherwise: [^EncounteredUnknownBytecode].
  	self ssPushRegister: rr.
  	^0!



More information about the Vm-dev mailing list