'From Cuis 1.0 of 6 March 2009 [latest update: #123] on 6 March 2009 at 1:05:55 pm'!

!Debugger methodsFor: 'code pane' stamp: 'jmv 3/6/2009 11:49'!
pcRange
	"Answer the indices in the source code for the method corresponding to 
	the selected context's program counter value."

	| i pc end |
	(selectingPC and: [contextStackIndex ~= 0])
		ifFalse: [^1 to: 0].
	sourceMap ifNil:
		[sourceMap _ theMethodNode sourceMap.
		tempNames _ theMethodNode tempNames].
	(sourceMap size = 0 or: [ self selectedContext isDead ]) ifTrue: [^1 to: 0].
	Smalltalk at: #RBProgramNode ifPresent:[:nodeClass|
		(theMethodNode isKindOf: nodeClass) ifTrue: [
			pc _ contextStackIndex = 1
				ifTrue: [self selectedContext pc]
				ifFalse: [self selectedContext previousPc].
			i _ sourceMap findLast:[:pcRange | pcRange key <= pc].
			i = 0 ifTrue:[^ 1 to: 0].
			^ (sourceMap at: i) value
		].
	].
	pc_ self selectedContext pc -
		(("externalInterrupt" true and: [contextStackIndex=1])
			ifTrue: [1]
			ifFalse: [2]).
	i _ sourceMap indexForInserting: (Association key: pc value: nil).
	i < 1 ifTrue: [^1 to: 0].
	i > sourceMap size
		ifTrue:
			[end _ sourceMap inject: 0 into:
				[:prev :this | prev max: this value last].
			^ end+1 to: end].
	^(sourceMap at: i) value! !


!MethodNode methodsFor: 'code generation' stamp: 'jmv 3/6/2009 11:50'!
generate: trailer 
	"The receiver is the root of a parse tree. Answer a CompiledMethod. The
	argument, trailer, is the references to the source code that is stored with 
	every CompiledMethod."

	| blkSize nLits stack strm nArgs method |
	self generate: trailer ifQuick: 
		[:m |  method _ m.
		^ method].
	nArgs _ arguments size.
	blkSize _ block sizeForEvaluatedValue: encoder.
	literals _ encoder allLiterals.
	(nLits _ literals size) > 255
		ifTrue: [^self error: 'Too many literals referenced'].
	method _ CompiledMethod	"Dummy to allocate right size"
				newBytes: blkSize
				trailerBytes: trailer 
				nArgs: nArgs
				nTemps: encoder maxTemp
				nStack: 0
				nLits: nLits
				primitive: primitive.
	strm _ ReadWriteStream with: method.
	strm position: method initialPC - 1.
	stack _ ParseStack new init.
	block emitForEvaluatedValue: stack on: strm.
	stack position ~= 1 ifTrue: [^self error: 'Compiler stack
discrepancy'].
	strm position ~= (method size - trailer size) 
		ifTrue: [^self error: 'Compiler code size discrepancy'].
	method needsFrameSize: stack size.
	1 to: nLits do: [:lit | method literalAt: lit put: (literals at: lit)].
	^ method! !

!MethodNode methodsFor: 'code generation' stamp: 'jmv 3/6/2009 11:50'!
generateNative: trailer 
	"The receiver is the root of a parse tree. Answer a CompiledMethod. The
	argument, trailer, is the references to the source code that is stored with 
	every CompiledMethod."

	| blkSize nLits stack strm nArgs method |
	self generate: trailer ifQuick: 
		[:m |  method _ m.
		^ method].
	nArgs _ arguments size.
	blkSize _ block sizeForEvaluatedValue: encoder.
	literals _ encoder allLiterals.
	(nLits _ literals size) > 255
		ifTrue: [^self error: 'Too many literals referenced'].
	method _ CompiledMethod	"Dummy to allocate right size"
				newBytes: blkSize
				trailerBytes: trailer 
				nArgs: nArgs
				nTemps: encoder maxTemp
				nStack: 0
				nLits: nLits
				primitive: primitive.
	strm _ ReadWriteStream with: method.
	strm position: method initialPC - 1.
	stack _ ParseStack new init.
	block emitForEvaluatedValue: stack on: strm.
	stack position ~= 1 ifTrue: [^self error: 'Compiler stack
discrepancy'].
	strm position ~= (method size - trailer size) 
		ifTrue: [^self error: 'Compiler code size discrepancy'].
	method needsFrameSize: stack size.
	1 to: nLits do: [:lit | method literalAt: lit put: (literals at: lit)].
	^ method! !


!ProcessBrowser methodsFor: 'stack list' stamp: 'jmv 3/6/2009 11:50'!
pcRange
	"Answer the indices in the source code for the method corresponding to  
	the selected context's program counter value."
	| i methodNode pc end |
	methodText isEmptyOrNil
		ifTrue: [^ 1 to: 0].
	sourceMap == nil
		ifTrue: [self selectedClass == #unknown
				ifTrue: [^ 1 to: 0].
			[[methodNode _ self selectedClass compilerClass new
						parse: methodText
						in: self selectedClass
						notifying: self ]
				on: Warning
				do: [:ex | 
					methodText _ ('(syntax error) ' , ex description , String cr , methodText) asText.
					ex return]]
				on: Error
				do: [:ex | 
					methodText _ ('(parse error) ' , ex description , String cr , methodText) asText.
					ex return].
			methodNode
				ifNil: [sourceMap _ nil.
					^ 1 to: 0].
			sourceMap _ methodNode sourceMap].
	(sourceMap size = 0 or: [ selectedContext isDead ])
		ifTrue: [^ 1 to: 0].
	pc _ selectedContext pc.
	pc _ pc - 2.
	i _ sourceMap
				indexForInserting: (Association key: pc value: nil).
	i < 1
		ifTrue: [^ 1 to: 0].
	i > sourceMap size
		ifTrue: [end _ sourceMap
						inject: 0
						into: [:prev :this | prev max: this value last].
			^ end + 1 to: end].
	^ (sourceMap at: i) value! !

CompiledMethod removeSelector: #cacheTempNames:!
CompiledMethod removeSelector: #setTempNamesIfCached:!
