[squeak-dev] The Trunk: Tools-mt.1087.mcz

commits at source.squeak.org commits at source.squeak.org
Wed Dec 15 15:52:02 UTC 2021


Marcel Taeumel uploaded a new version of Tools to project The Trunk:
http://source.squeak.org/trunk/Tools-mt.1087.mcz

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

Name: Tools-mt.1087
Author: mt
Time: 15 December 2021, 4:52:00.953892 pm
UUID: 627887b0-5064-ab43-b7ac-60b329a8b606
Ancestors: Tools-mt.1086

Tweak BlockClosureInspector to show all the closured stuff including temps from the outer context and inst-vars from the current receiver. Adds some caching to make it faster. Support cache invalidation only for changing the #receiver field. Not sure whether it makes sense to support changing the outerContext as well...

=============== Diff against Tools-mt.1086 ===============

Item was changed:
  Inspector subclass: #BlockClosureInspector
+ 	instanceVariableNames: 'debuggerMap tempVarNames instVarNames'
- 	instanceVariableNames: ''
  	classVariableNames: ''
  	poolDictionaries: ''
  	category: 'Tools-Inspector'!

Item was added:
+ ----- Method: BlockClosureInspector>>debuggerMap (in category 'private') -----
+ debuggerMap
+ 
+ 	^ debuggerMap ifNil: [debuggerMap := self object method debuggerMap]!

Item was changed:
  ----- Method: BlockClosureInspector>>hasBindingOf: (in category 'user interface - styling') -----
  hasBindingOf: aString
  	
  	self object method literalsDo: [:literal |
  		(literal isVariableBinding and: [literal key = aString])
  			ifTrue: [^ true]].
+ 		
+ 	(self tempVarNames includes: aString) ifTrue: [^ true].
+ 	(self instVarNames includes: aString) ifTrue: [^ true].
+ 	
+ 	^ false!
- 	^ self object outerContext tempNames includes: aString!

Item was added:
+ ----- Method: BlockClosureInspector>>instVarNames (in category 'private') -----
+ instVarNames
+ 
+ 	^ instVarNames ifNil: [instVarNames := (self object receiver perform: #class "avoid inlining; support proxies") allInstVarNames]!

Item was added:
+ ----- Method: BlockClosureInspector>>replaceSelectionValue: (in category 'selection') -----
+ replaceSelectionValue: anObject
+ 
+ 	| success |
+ 	(success := super replaceSelectionValue: anObject) ifTrue: [
+ 		self selectedField key = #receiver
+ 			ifTrue: [instVarNames := nil]].
+ 	^ success!

Item was changed:
  ----- Method: BlockClosureInspector>>streamBindingsOn: (in category 'fields - streaming') -----
  streamBindingsOn: aStream
  	
+ 	| compiledCode instNames tempNames |
- 	| compiledCode tempNames |
  	self flag: #decompile. "mt: Use #to: and #do: instead of #to:do: to avoid inlining to preserve bindings in enumeration block for later decompilation. See InspectorField."
+ 
+ 	(1 to: (instNames := self instVarNames) size) do: [:index |
+ 		aStream nextPut: ((self newFieldForType: #instVar key: index)
+ 				name: ('[[[{1}]]]' format: {instNames at: index});
+ 				valueGetter: [:closure | closure receiver instVarAt: index];
+ 				valueSetter: [:closure :value | closure receiver instVarAt: index put: value];
+ 				yourself)].
+ 	
+ 	tempNames := self tempVarNames.
+ 	"No need to show closured bindings from outerContext. The important temps are already covered in the indexed fields below."
+ 	(1 to: tempNames size - self object basicSize) do: [:index |
+ 		aStream nextPut: ((self newFieldForType: #tempVar key: index)
+ 				name: ('[[{1}]]' format: {tempNames at: index});
+ 				valueGetter: [:closure | closure outerContext tempAt: index];
+ 				valueSetter: [:closure :value | closure outerContext tempAt: index put: value];
+ 				yourself)].
+ 			
  	(1 to: (compiledCode := self object method) numLiterals) do: [:index |
  		| literal |
  		literal := compiledCode literalAt: index.
  		literal isVariableBinding ifTrue: [ 		
  			aStream nextPut: ((self newFieldForType: #tempVar key: index)
  				name: ('[{1}]' format: {literal key});
  				valueGetter: [:closure | (closure method literalAt: index) value];
  				valueSetter: [:closure :value | (closure method literalAt: index) value: value];
  				yourself)]].
+ 
- 	
- 	tempNames := self object outerContext tempNames.
- 	"No need to show closured bindings from outerContext. The important temps are already covered in the indexed fields below."
- 	"(1 to: tempNames size - self object basicSize) do: [:index |
- 		aStream nextPut: ((self newFieldForType: #tempVar key: index)
- 				name: ('[{1}]' format: {tempNames at: index});
- 				valueGetter: [:closure | closure outerContext tempAt: index];
- 				valueSetter: [:closure :value | closure outerContext tempAt: index put: value];
- 				yourself)]."
- 			
  	(1 to: self object basicSize) do: [:index |
  		aStream nextPut: ((self newFieldForType: #tempVar key: index)
  				name: ('[{1}]' format: {tempNames at: index + tempNames size - self object basicSize});
  				valueGetter: [:closure | closure basicAt: index];
  				valueSetter: [:closure :value | closure basicAt: index put: value];
  				yourself)].
  			
  		
  "See commentary in #doItReceiver. No need to expose the closured 'self' here because there is already the #receiver instVar.
  
  fieldReceiver
  	^ (self newFieldForType: #tempVar key: #receiver)
  		name: '[self]';
  		valueGetter: [:obj | obj receiver];
  		valueSetter: [:obj :value | obj receiver: value];
  		yourself
  "!

Item was added:
+ ----- Method: BlockClosureInspector>>tempVarNames (in category 'private') -----
+ tempVarNames
+ 
+ 	^ tempVarNames ifNil: [tempVarNames := self debuggerMap tempNamesForContext: self object outerContext]!



More information about the Squeak-dev mailing list