[squeak-dev] The Trunk: System-eem.975.mcz

commits at source.squeak.org commits at source.squeak.org
Tue Nov 14 19:23:08 UTC 2017


Eliot Miranda uploaded a new version of System to project The Trunk:
http://source.squeak.org/trunk/System-eem.975.mcz

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

Name: System-eem.975
Author: eem
Time: 14 November 2017, 11:22:51.118839 am
UUID: d8e00134-ca31-43fb-8558-8bf9a15c7aba
Ancestors: System-tpr.974

Add the ability to set a pragma preference stored in a class or global variable by analysing the getter, obviating the need for a setter.

Improve the class comment for PragmaPreference and mention this feature.

=============== Diff against System-tpr.974 ===============

Item was changed:
  Preference subclass: #PragmaPreference
  	instanceVariableNames: 'provider getter setter'
  	classVariableNames: ''
  	poolDictionaries: ''
  	category: 'System-Preferences'!
  
+ !PragmaPreference commentStamp: 'eem 11/14/2017 11:20' prior: 0!
+ Differs from superclass by redirecting all queries to a preference provider that defines its preference via a class-side preference method marked with a pragma.  For example, evaluate
+ 	self systemNavigation browseAllCallsOn: #preference:categoryList:description:type:
+ 
+ Each preference method getter can be accompanied by a setter that assigns to the preference whose value the getter answers.  If the getter is of the form
+ 	^SomeGlobalOrClassVar ifNil: [...]
+ then the framework is smart enough to figure out the SomeGlobalOrClassVar from the getter and no setter method is required.!
- !PragmaPreference commentStamp: 'ar 3/9/2009 21:27' prior: 0!
- Differs from superclass by redirecting all queries to preference provider.!

Item was added:
+ ----- Method: PragmaPreference>>attemptToSetValueFromGetter: (in category 'value') -----
+ attemptToSetValueFromGetter: aValue
+ 	"Attempt to set the value of the preference from the getter method, answering if the attempt was successful.
+ 	 Do so by seeing if the method is of the form
+ 		^ClassVar ifNil: [...]
+ 	 by analysing its bytecode, and if so, extracting the class (or global) var and setting its value."
+ 	| getterMethod getterBytecodes getterBytecodeNames
+ 	  constant comparison branchTuple distance followingpc
+ 	  classVar |
+ 	getterMethod := provider class compiledMethodAt: getter ifAbsent: [^false].
+ 	getterBytecodes := getterMethod abstractBytecodeMessagesAndPCs.
+ 	getterBytecodeNames := getterBytecodes collect: [:tuple| tuple first selector].
+ 	((getterBytecodeNames beginsWith: #(pushLiteralVariable: doDup #pushConstant: send:super:numArgs: jump:if:))
+ 	 and: [getterBytecodeNames last == #methodReturnTop
+ 	 and: [(constant := getterBytecodes third first) arguments first == nil
+ 	 and: [(comparison := getterBytecodes fourth first) arguments first == #==
+ 	 and: [branchTuple := getterBytecodes fifth.
+ 			followingpc := getterBytecodes sixth last.
+ 			distance := branchTuple first arguments first.
+ 			"i.e. does the branch jump to the return?"
+ 			distance + followingpc = getterBytecodes last second]]]]) ifFalse:
+ 		[^false].
+ 	classVar := getterBytecodes first first arguments first.
+ 	classVar value: aValue.
+ 	^true!

Item was changed:
  ----- Method: PragmaPreference>>rawValue: (in category 'value') -----
  rawValue: aValue
  	"set the value as indicated, with no side effects"
+ 	[provider perform: setter with: aValue]
+ 		on: MessageNotUnderstood
+ 		do: [:ex|
+ 			(self attemptToSetValueFromGetter: aValue) ifFalse:
+ 				[ex pass]]!
- 	provider perform: setter with: aValue!



More information about the Squeak-dev mailing list