Eliot Miranda uploaded a new version of SystemReporter to project The Trunk:
http://source.squeak.org/trunk/SystemReporter-eem.47.mcz
==================== Summary ====================
Name: SystemReporter-eem.47
Author: eem
Time: 12 January 2021, 3:42:22.819678 pm
UUID: 440e979a-59dd-4593-8ada-75bc330a6583
Ancestors: SystemReporter-eem.46
Add event tracing mask, VM ticker stats, mixed arithmetic flag, and separate marking time.
=============== Diff against SystemReporter-eem.46 ===============
Item was changed:
----- Method: SystemReporter>>reportVMParameters: (in category 'reporting') -----
reportVMParameters: aStream
| vmParameters isStack isCog isSpur |
self header: 'Virtual Machine Parameters' on: aStream.
vmParameters := Smalltalk vm getVMParameters.
isStack := (vmParameters at: 42 ifAbsent: [0]) ~= 0. "42 = number of stack pages available"
isCog := isStack and: [(vmParameters at: 46) ~= 0]. "46 is machine code zone size"
isSpur := isStack and: [(vmParameters at: 41) anyMask: 2r10000]. "41 is imageFormatVersion for the VM; bit 16 is the Spur bit"
(isSpur
ifFalse:
[#( 1 'size of old space'
2 'size of young+old space'
3 'size of memory'
4 'allocationCount'
5 'allocations between GCs'
6 'survivor count tenuring threshold')]
ifTrue:
[#( 1 'size of old space'
2 'used bytes in new space (used eden + used past space)'
3 'size of heap')]),
#( 7 'full GCs since startup'
8 'total milliseconds in full GCs since startup'),
(isSpur
ifFalse: [#( 9 'incremental GCs since startup'
10 'total milliseconds in incremental GCs since startup'
11 'tenures of surving objects since startup'),
{12 to: 19. 'specific to the translating VM'}]
ifTrue: [#( 9 'scavenging GCs since startup'
10 'total milliseconds in scavenging GCs since startup'
+ 11 'tenures of surving objects since startup'
+ 12 'event trace mask (for debugging input events)'
+ 13 'VM ticker start microseconds (Croquet/QwaqVM)'
+ 14 'VM ticker count (Croquet/QwaqVM)'
+ 15 'VM ticker call count (Croquet/QwaqVM)'
+ 16 'total microseconds in idle since startup'
- 11 'tenures of surving objects since startup'),
- {12 to: 15. 'reserved for future use'},
- #( 16 'total microseconds in idle since startup'
17 'proportion of code zone available for use (Sista VMs only; read-write)'
18 'total milliseconds in full GC compaction since startup (a portion of parameter 8)'
19 'scavenge threshold; the effective size of eden')]),
#( 20 'utc microseconds at startup (if non-zero)'
21 'root/remembered table size (occupancy)'
22 'root/remembered table overflows since startup'
23 'bytes of extra memory to reserve for VM buffers, plugins, etc.'
24 'free memory threshold above which object memory will be shrunk'
25 'memory headroom when growing object memory'),
(isStack
ifFalse:
[#( 26 'interruptChecksEveryNms - force an ioProcessEvents every N milliseconds, in case the image is not calling getNextEvent often')]
ifTrue:
[#( 26 'heartbeat period (ms; see #58)')]),
(isSpur
ifFalse:
[#( 27 'number of times mark loop iterated for current IGC/FGC includes ALL marking'
28 'number of times sweep loop iterated for current IGC/FGC'
29 'number of times make forward loop iterated for current IGC/FGC'
30 'number of times compact move loop iterated for current IGC/FGC')]
ifTrue: [#()]),
#( 31 'number of grow memory requests'
32 'number of shrink memory requests'),
(isSpur
ifFalse:
[#( 33 'number of root table entries used for current IGC/FGC'
34 'number of allocations done before current IGC/FGC'
35 'number of survivor objects after current IGC/FGC'
36 'millisecond clock when current IGC/FGC completed'
37 'number of marked objects for Roots of the world, not including Root Table entries for current IGC/FGC'
38 'milliseconds taken by current IGC'
39 'Number of finalization signals for Weak Objects pending when current IGC/FGC completed')]
ifTrue:
[#( 33 'number of root table entries at last scavenge'
35 'number of survivor objects at last scavenge (if non-zero)'
36 'millisecond clock when current scavenge completed'
38 'milliseconds taken by current scavenge'
39 'Number of finalization signals for Weak Objects pending when current SGC/FGC completed')]),
#( 40 'VM word size - 4 or 8'),
(isStack
ifTrue:
[#(
41 'imageFormatVersion for the VM'
42 'number of stack pages available'
43 'desired number of stack pages (stored in image file header, max 65535)'
44 'size of eden, in bytes'
45 'desired size of eden, in bytes (stored in image file header)'
46 'machine code zone size, in bytes (0 in Stack VM)'
47 'desired machine code zone size (0 => default 1Mb to 2Mb depending on processor)'),
{ 48. 'Persistent image header flags\ bit 0: implies Process has threadId as its 4th inst var\ bit 1: if set, methods that are interpreted will have the flag bit set in their header\ bit 2: if set, implies preempting a process does not put it to the back of its run queue\ bit 3: if set, implies the GUI should run on the first thread and event queues should not be accessed from other threads\ bit 4: if set, implies the new finalization scheme where WeakArrays are queued\ bit 5: if set, implies wheel events will be delivered as such and not mapped to arrow key events\ bit 6: if set, implies arithmetic primitives will fail if given arguments of different types (float vs int)\ bit 7: if set, causes times delivered from file primitives to be in UTC rather than local time.' withCRs },
#( 49 'max size the image promises to grow the external semaphore table to'),
(isSpur
ifFalse:
[{ 50 to: 51. 'reserved for VM parameters that persist in the image (such as size of eden above)'.
52 to: 56. 'specific to Spur' }]
ifTrue:
[{ 50 to: 51. 'reserved for VM parameters that persist in the image (such as size of eden above)' },
#( 52 'root/remembered table capacity'
53 'number of old space segments'
54 'total free old space'
55 'ratio of growth and image size at or above which a GC will be performed post scavenge')]),
#( 56 'number of process switches since startup'
57 'number of ioProcessEvents calls since startup'
58 'number of forceInterruptCheck calls since startup'
59 'number of check event calls since startup'
60 'number of stack page overflows since startup'
61 'number of stack page divorces since startup'
62 'compiled code compactions since startup'),
(isCog
ifFalse:
[#()]
ifTrue:
[#( 63 'total milliseconds in compiled code compactions since startup'
64 'the number of methods that currently have jitted machine-code')]),
{ 65. 'Cog feature flags\ bit 0: set if the VM supports MULTIPLE_BYTECODE_SETS.\ bit 1: set if the VM supports read-only objects (IMMUTABILITY).\ bit 2: set if the VM has an ITIMER_HEARTBEAT\ bit 3: set if the VM supports cross-platform BIT_IDENTICAL_FLOATING_POINT arithmetic' withCRs.
66. 'the byte size of a stack page'.},
(isSpur
ifFalse:
[{ 67 to: 69. 'reserved for more Cog-related info' }]
ifTrue:
[#( 67 'the maximum allowed size of old space (if zero there is no limit)'
68 'the average number of live stack pages when scanned by scavenge/gc/become'
69 'the maximum number of live stack pages when scanned by scavenge/gc/become')]),
#( 70 'the vmProxyMajorVersion (the interpreterProxy VM_MAJOR_VERSION)'
+ 71 'the vmProxyMinorVersion (the interpreterProxy VM_MINOR_VERSION)'),
+ (isSpur
+ ifFalse: [#()]
+ ifTrue:
+ [#( 72 'milliseconds spent marking since startup'
+ 73 'reserved for more Spur-related info'
+ 74 'reserved for more Spur-related info'
+ 75 'do mixed arithmetic; if false binary arithmetic primitives will fail unless receiver and argument are of the same type')])]
- 71 'the vmProxyMinorVersion (the interpreterProxy VM_MINOR_VERSION)')]
ifFalse:
[#()])
pairsDo: [:idx :desc | | value values |
aStream nextPut: $#.
idx isInteger
ifTrue:
[value := vmParameters at: idx.
aStream
print: idx; tab: (idx < 10 ifTrue: [2] ifFalse: [1]);
nextPutAll: ((value isInteger and: [idx ~= 41])
ifTrue: [(desc includesSubstring: 'bit 0:')
ifTrue: [value printStringBase: 2 nDigits: value highBit]
ifFalse: [value asStringWithCommas]]
ifFalse: [value printString])]
ifFalse:
[value := vmParameters at: idx first.
aStream print: idx first; next: 2 put: $.; print: idx last; tab.
values := idx collect: [:i| vmParameters at: i].
values asSet size = 1
ifTrue: [aStream print: value]
ifFalse: [values do: [:v| aStream print: v] separatedBy: [aStream nextPutAll: ', ']]].
aStream tab; nextPutAll: desc; cr]!
Marcel Taeumel uploaded a new version of Morphic to project The Trunk:
http://source.squeak.org/trunk/Morphic-mt.1716.mcz
==================== Summary ====================
Name: Morphic-mt.1716
Author: mt
Time: 12 January 2021, 2:52:47.977356 pm
UUID: 93f95f53-4457-5e4c-a157-5cbf89aa7328
Ancestors: Morphic-mt.1715
Fixes a bug in resize grips (having #rigid targets) that are placed within layouted (usually #shrinkWrap) owners.
This makes all grips in resizable dialogs finally work as expected. I still consider this a #workaround to be improved.
=============== Diff against Morphic-mt.1715 ===============
Item was changed:
----- Method: BorderedMorph>>doFastWindowReframe: (in category 'resize handling') -----
doFastWindowReframe: ptName
+ | newBounds delta |
- | newBounds |
"For fast display, only higlight the rectangle during loop"
newBounds := self bounds newRectButtonPressedDo: [:f |
f
withSideOrCorner: ptName
setToPoint: (self pointFromWorld: Sensor cursorPoint)
minExtent: self minimumExtent].
+ delta := newBounds origin - self bounds origin.
self bounds: newBounds.
+ self flag: #workaround. "mt: Due to a layout-specific 'let us start in the top-left corner of a layout cell'-behavior, we have to go up the owner chain and propagate the delta. See Morph >> #layoutInBounds:positioning: and there section 1.2."
+ self allOwnersDo: [:owner |
+ owner layoutPolicy ifNotNil: [owner topLeft: owner topLeft + delta]].
^newBounds.!
Item was changed:
----- Method: BottomLeftGripMorph>>apply: (in category 'target resize') -----
apply: delta
| oldBounds |
oldBounds := self target bounds.
self target
+ bounds: (oldBounds origin + (delta x @ 0) corner: oldBounds corner + (0 @ delta y)).
+ self flag: #workaround. "mt: Due to a layout-specific 'let us start in the top-left corner of a layout cell'-behavior, we have to go up the owner chain and propagate the delta. See Morph >> #layoutInBounds:positioning: and there section 1.2."
+ self target allOwnersDo: [:owner |
+ owner layoutPolicy ifNotNil: [owner left: owner left + delta x]].!
- bounds: (oldBounds origin + (delta x @ 0) corner: oldBounds corner + (0 @ delta y))!
Item was changed:
----- Method: LeftGripMorph>>apply: (in category 'target resize') -----
apply: delta
| oldBounds |
oldBounds := self target bounds.
self target
+ bounds: (oldBounds origin + (delta x @ 0) corner: oldBounds corner).
+ self flag: #workaround. "mt: Due to a layout-specific 'let us start in the top-left corner of a layout cell'-behavior, we have to go up the owner chain and propagate the delta. See Morph >> #layoutInBounds:positioning: and there section 1.2."
+ self target allOwnersDo: [:owner |
+ owner layoutPolicy ifNotNil: [owner left: owner left + delta x]].!
- bounds: (oldBounds origin + (delta x @ 0) corner: oldBounds corner)!
Item was changed:
----- Method: TopGripMorph>>apply: (in category 'target resize') -----
apply: delta
| oldBounds |
oldBounds := self target bounds.
self target
+ bounds: (oldBounds origin + (0 @ delta y) corner: oldBounds corner).
+ self flag: #workaround. "mt: Due to a layout-specific 'let us start in the top-left corner of a layout cell'-behavior, we have to go up the owner chain and propagate the delta. See Morph >> #layoutInBounds:positioning: and there section 1.2."
+ self target allOwnersDo: [:owner |
+ owner layoutPolicy ifNotNil: [owner top: owner top + delta y]].!
- bounds: (oldBounds origin + (0 @ delta y) corner: oldBounds corner)!
Item was changed:
----- Method: TopLeftGripMorph>>apply: (in category 'target resize') -----
apply: delta
| oldBounds |
oldBounds := self target bounds.
self target
+ bounds: (oldBounds origin + delta corner: oldBounds corner).
+ self flag: #workaround. "mt: Due to a layout-specific 'let us start in the top-left corner of a layout cell'-behavior, we have to go up the owner chain and propagate the delta. See Morph >> #layoutInBounds:positioning: and there section 1.2."
+ self target allOwnersDo: [:owner |
+ owner layoutPolicy ifNotNil: [owner topLeft: owner topLeft + delta]].!
- bounds: (oldBounds origin + delta corner: oldBounds corner)!
Item was changed:
----- Method: TopRightGripMorph>>apply: (in category 'target resize') -----
apply: delta
| oldBounds |
oldBounds := self target bounds.
self target
+ bounds: (oldBounds origin + (0@delta y) corner: oldBounds corner + (delta x @ 0)).
+ self flag: #workaround. "mt: Due to a layout-specific 'let us start in the top-left corner of a layout cell'-behavior, we have to go up the owner chain and propagate the delta. See Morph >> #layoutInBounds:positioning: and there section 1.2."
+ self target allOwnersDo: [:owner |
+ owner layoutPolicy ifNotNil: [owner top: owner top + delta y]].!
- bounds: (oldBounds origin + (0@delta y) corner: oldBounds corner + (delta x @ 0))!
Marcel Taeumel uploaded a new version of Morphic to project The Trunk:
http://source.squeak.org/trunk/Morphic-mt.1715.mcz
==================== Summary ====================
Name: Morphic-mt.1715
Author: mt
Time: 12 January 2021, 2:04:07.252356 pm
UUID: 2641645d-9048-f44f-b6ea-2cd85e2c7ff0
Ancestors: Morphic-mt.1714
Fixes the issue where a dialog with flexible contents was not fully visible in small worlds. Thanks to Chris (cbc) for pointing this out!
(Note that I think that we need a better way for this combination of #fullBounds, #extent:, and #translatedToBeWithin: to make sure that a morph is visible in the world. May be also useful for other windows. Not sure about this variation with #center: though.)
=============== Diff against Morphic-mt.1714 ===============
Item was changed:
----- Method: DialogWindow>>moveToHand (in category 'position') -----
moveToHand
+ self moveToHand: self currentHand.!
- self moveToHand: self activeHand.!
Item was changed:
----- Method: DialogWindow>>moveToPreferredPosition (in category 'initialization') -----
moveToPreferredPosition
+ "Moves the dialog window to its preferred position, which can be a point on the screen or a named widget in the dialog's central pane. Ensure that the dialog is fully visible in the world. Also see #positionOverWidgetNamed:."
+
+ | visibleArea decorationOffset |
+ self fullBounds. "Compute new layout to have updated bounds."
+ visibleArea := self currentWorld visibleClearArea.
+ decorationOffset := self extent - self paneMorph extent.
+ self paneMorph extent:
+ (self paneMorph extent min: visibleArea extent - decorationOffset).
+ self fullBounds. "Compute new layout to have updated bounds."
self center:
(preferredPosition isPoint
ifTrue: [ preferredPosition ]
ifFalse: [ self center + self currentHand position - preferredPosition center ]).
+ self bounds:
+ (self bounds translatedToBeWithin: visibleArea).!
- self bounds: (self bounds translatedToBeWithin: self currentWorld visibleClearArea)!
Marcel Taeumel uploaded a new version of Morphic to project The Trunk:
http://source.squeak.org/trunk/Morphic-mt.1714.mcz
==================== Summary ====================
Name: Morphic-mt.1714
Author: mt
Time: 11 January 2021, 5:39:09.729446 pm
UUID: e843c65c-8522-4544-84e8-4d21a8ca197e
Ancestors: Morphic-mt.1713
Minor fix in dialog to not hide the world's docking bar.
=============== Diff against Morphic-mt.1713 ===============
Item was changed:
----- Method: DialogWindow>>moveToPreferredPosition (in category 'initialization') -----
moveToPreferredPosition
self center:
(preferredPosition isPoint
ifTrue: [ preferredPosition ]
ifFalse: [ self center + self currentHand position - preferredPosition center ]).
+ self bounds: (self bounds translatedToBeWithin: self currentWorld visibleClearArea)!
- self bounds: (self bounds translatedToBeWithin: self currentWorld bounds)!
David T. Lewis uploaded a new version of System to project The Trunk:
http://source.squeak.org/trunk/System-dtl.1210.mcz
==================== Summary ====================
Name: System-dtl.1210
Author: dtl
Time: 6 January 2021, 4:59:31.092128 pm
UUID: a704d749-4986-46f9-aa2f-faa8bb4ea5e1
Ancestors: System-eem.1207
Provide vmParameterAt:ifAbsent: to handle primitive failure on reading VM parameters.
Supply default parameter values to mock possibly missing elements in the parameters array.
=============== Diff against System-eem.1207 ===============
Item was changed:
----- Method: SmalltalkImage>>isRunningCog (in category 'system attributes') -----
isRunningCog
"Answers if we're running on a Cog VM (JIT or StackInterpreter)"
+ ^(self vmParameterAt: 42 ifAbsent: nil)
- ^(self vmParameterAt: 42)
ifNil: [false]
ifNotNil: [:numStackPages| numStackPages > 0]!
Item was changed:
----- Method: SmalltalkImage>>isRunningCogit (in category 'system attributes') -----
isRunningCogit
"Answers if we're running on the Cog JIT"
+ ^(self vmParameterAt: 46 ifAbsent: nil)
- ^(self vmParameterAt: 46)
ifNil: [false]
ifNotNil: [:machineCodeZoneSize| machineCodeZoneSize > 0]!
Item was changed:
----- Method: SmalltalkImage>>lowSpaceThreshold (in category 'memory space') -----
lowSpaceThreshold
"Answer the low space threshold. When the amount of free memory (after garbage collection)
falls below this limit, the system is in serious danger of completely exhausting memory and
crashing. This limit should be made high enough to allow the user open a debugger to diagnose
a problem or to save the image. In a stack-based VM such as Cog contexts for activations in
the stack zone will have to be created as the debugger opens, requiring additional headroom."
| slotsForDebugger slotsForContextsOnStackPages |
slotsForDebugger := 65536. "Arbitrary guess"
slotsForContextsOnStackPages :=
+ (self vmParameterAt: 42 ifAbsent: nil)
- (self vmParameterAt: 42)
ifNil: [0]
ifNotNil:
[:numStackPages| | headerSize numActivationsPerPage maxContextSize |
numActivationsPerPage := 40. "Design goal of the Cog & Stack VMs"
headerSize := 8 / self wordSize. "64-bits for Spur"
maxContextSize := thisContext class instSize + CompiledMethod fullFrameSize + headerSize.
numStackPages * numActivationsPerPage * maxContextSize].
^slotsForDebugger + slotsForContextsOnStackPages * self wordSize!
Item was changed:
----- Method: SmalltalkImage>>maxExternalSemaphores (in category 'vm parameters') -----
maxExternalSemaphores
+ "The size of table where external semaphores are registered. Only in Cog,
+ other VMs are expected to answer nil if present in the parameters array."
+ ^self vmParameterAt: 49 ifAbsent: nil!
- "The size of table where external semaphores are registered. Only in Cog"
- self isRunningCog ifFalse: [^nil].
- ^self vmParameterAt: 49!
Item was changed:
----- Method: SmalltalkImage>>maxExternalSemaphores: (in category 'vm parameters') -----
maxExternalSemaphores: aSize
"Changes the size of table where external semaphores are registered.
The size can only grow, and will always be the next power of two larger than the parameter.
Setting this at any time other than start-up can potentially lose requests.
i.e. during the realloc new storage is allocated,
the old contents are copied and then pointers are switched.
Requests occurring during copying won't be seen if they occur to indices already copied.
The intended use is to set the table to some adequate maximum at start-up"
- self isRunningCog ifFalse: [^0].
"The vm-header field is a short, maximum 64k entries. Well, on most platforms anyways "
(aSize < 0 or: [aSize > 16rFFFF]) ifTrue: [^self error: 'maxExternalSemaphores: is limited to 16rFFFF'].
+ ^[self vmParameterAt: 49 put: aSize] on: Error do: [0].!
- ^self vmParameterAt: 49 put: aSize!
Item was changed:
----- Method: SmalltalkImage>>processPreemptionYields (in category 'system attributes') -----
processPreemptionYields
"Answer whether the VM causes a process to yield on process preemption,
i.e. to put a preempted process at the back of its run queue. If the parameter
is unavailable (non-Cog VMs) or bit 2 (4) is 0 then preemption yields."
+ ^((self vmParameterAt: 48 ifAbsent: [^true]) allMask: 4) not
+ !
- ^(([self vmParameterAt: 48]
- on: Error
- do: [:ex| ^true]) allMask: 4) not!
Item was changed:
----- Method: SmalltalkImage>>sendMouseWheelEvents (in category 'system attributes') -----
sendMouseWheelEvents
"The Cog VM can be instructed to deliver mouse wheel events as mouse wheel events.
By default mouse wheel events are mapped to arrow events.
This flag persists across snapshots, stored in the image header."
+ ^(self vmParameterAt: 48 ifAbsent: 0) anyMask: 32!
- ^(self vmParameterAt: 48) anyMask: 32!
Item was changed:
----- Method: SmalltalkImage>>supportsMultipleBytecodeSets (in category 'system attributes') -----
supportsMultipleBytecodeSets
"Answer whether the VM supports multiple bytecodeSets."
"SmalltalkImage current supportsMultipleBytecodeSets"
+ ^(self vmParameterAt: 65 ifAbsent: nil)
- ^(self vmParameterAt: 65)
ifNil: [false]
ifNotNil:
[:param| "In older VMs this is a boolean answering the vm-internal MULTIPLE_BYTECODE_SETS define"
param isInteger "In newer VMs it is a set of integer flags, bit 0 of which is the vm-internal MULTIPLE_BYTECODE_SETS define"
ifTrue: [param anyMask: 1]
ifFalse: [param]]!
Item was changed:
----- Method: SmalltalkImage>>supportsQueueingFinalization (in category 'system attributes') -----
supportsQueueingFinalization
"Answer whether the VM queues individual weak arrays for finalization, instead
of signalling the finalization semaphore once for all arrays and having the
WeakRegistry mechanism finalize all weak arrays, whether they need to or not."
"SmalltalkImage current supportsQueueingFinalization"
+ ^(self vmParameterAt: 48 ifAbsent: 0) anyMask: 16!
- ^(self vmParameterAt: 48) anyMask: 16!
Item was changed:
----- Method: SmalltalkImage>>supportsQueueingFinalization: (in category 'system attributes') -----
supportsQueueingFinalization: aBoolean
"Determine whether the VM queues individual weak arrays for finalization, instead
of signalling the finalization semaphore once for all arrays and having the
WeakRegistry mechanism finalize all weak arrays, whether they need to or not.
This flag persists across snapshots, stored in the image header."
"SmalltalkImage current supportsQueueingFinalization: true"
+ self vmParameterAt: 48 put: ((self vmParameterAt: 48 ifAbsent: [^false]) bitClear: 16) + (aBoolean ifTrue: [16] ifFalse: [0])!
- self vmParameterAt: 48 put: ((self vmParameterAt: 48) bitClear: 16) + (aBoolean ifTrue: [16] ifFalse: [0])!
Item was changed:
----- Method: SmalltalkImage>>supportsReadOnlyObjects (in category 'system attributes') -----
supportsReadOnlyObjects
"Answer whether the VM observes the per-object read-only flag and consequently aborts
writes to inst vars of, and fails primitives that attempt to modify, read-only objects."
"SmalltalkImage current supportsReadOnlyObjects"
+ ^(self vmParameterAt: 65 ifAbsent: nil)
- ^(self vmParameterAt: 65)
ifNil: [false]
ifNotNil:
[:param| "In older VMs this is a boolean answering the vm-internal MULTIPLE_BYTECODE_SETS define"
param isInteger "In newer VMs it is a set of integer flags, bit 1 of which is the vm-internal IMMUTABILITY define"
ifTrue: [param anyMask: 2]
ifFalse: [false]]!
Item was added:
+ ----- Method: SmalltalkImage>>vmParameterAt:ifAbsent: (in category 'vm parameters') -----
+ vmParameterAt: parameterIndex ifAbsent: defaultValueOrBlock
+ "Answer a VM parameter or defaultValueOrBlock value if out of range."
+ ^ [self vmParameterAt: parameterIndex]
+ on: Error
+ do: [defaultValueOrBlock value]!
Item was changed:
----- Method: SmalltalkImage>>wordSize (in category 'image') -----
wordSize
"Answer the size in bytes of an object pointer or word in the object memory.
The value does not change for a given image, but may be modified by a SystemTracer
when converting the image to another format. The value is cached in WordSize to
avoid the performance overhead of repeatedly consulting the VM."
"Smalltalk wordSize"
+ ^ WordSize ifNil: [WordSize := self vmParameterAt: 40 ifAbsent: 4]!
- ^ WordSize ifNil: [WordSize := [self vmParameterAt: 40] on: Error do: [4]]!
Marcel Taeumel uploaded a new version of Tools to project The Trunk:
http://source.squeak.org/trunk/Tools-mt.1023.mcz
==================== Summary ====================
Name: Tools-mt.1023
Author: mt
Time: 6 January 2021, 11:12:15.085417 am
UUID: cc33f893-f9b4-2047-a2f9-b085897e017f
Ancestors: Tools-eem.1022
Improve robustness against erroneous menu builders.
=============== Diff against Tools-eem.1022 ===============
Item was changed:
----- Method: Model>>buildMenu:withBuilders:shifted: (in category '*Tools-pluggable menus') -----
buildMenu: aMenu withBuilders: builders shifted: aBoolean
+ " We let every builder modify the menu. Skip erroneous builders silently.
- " We let every builder modify the menu.
The builder should indicate whether to abort by returning nil."
| menu |
menu := aMenu.
builders do: [:builder |
+ menu := [self perform: builder method selector withEnoughArguments: { menu . aBoolean }]
+ ifError: [:msg | Transcript showln: 'Menu builder failed: ', msg. menu].
- menu := self perform: builder method selector withEnoughArguments: { menu . aBoolean }.
menu ifNil: [^ aMenu]].
^ menu
!