Marcel Taeumel uploaded a new version of FFI-Kernel to project FFI: http://source.squeak.org/FFI/FFI-Kernel-mt.212.mcz
==================== Summary ====================
Name: FFI-Kernel-mt.212 Author: mt Time: 18 August 2021, 12:03:05.687133 pm UUID: 5bf6ded7-5f9b-de41-8c03-aeacd2620940 Ancestors: FFI-Kernel-mt.211
Fixes issue with updating alias-to-atomic types through #noticeModificationOf:.
Speeds up image startUp on platform changes.
Complements FFI-Tests-mt.62.
=============== Diff against FFI-Kernel-mt.211 ===============
Item was added: + ----- Method: ExternalAtomicType>>newReferentClass: (in category 'private') ----- + newReferentClass: classOrNil + "If I am an alias-to-atomic type, fetch the current spec from my referentClass." + + (referentClass := classOrNil) + ifNotNil: [ "my class has been changed - update my compiledSpec" + compiledSpec := referentClass compiledSpec. + byteAlignment := referentClass byteAlignment].!
Item was removed: - ----- Method: ExternalStructure class>>platformChangedFrom:to: (in category 'system startup') ----- - platformChangedFrom: lastPlatform to: currentPlatform - "The system is coming up on a new platform. Compile all field specs and install them in the respective struct types. Also re-generate all struct-field accessors if necessary." - - self defineAllFields.!
Item was removed: - ----- Method: ExternalType class>>checkTypeIntegrity (in category 'housekeeping') ----- - checkTypeIntegrity - " - self initialize. - self checkTypeIntegrity. - " - #(atomicTypesDo: atomic structTypesDo: struct pointerTypesDo: pointer arrayTypesDo: array typeAliasTypesDo: alias) - groupsDo: [:enumerator :label | - Transcript showln: ('Checking integrity of {1} types ...' format: { label }). - self perform: enumerator with: [:type | - type compiledSpec ifNil: [Transcript showln: '...', type typeName, ' has invalid compiledSpec!!']. - type byteAlignment ifNil: [Transcript showln: '...', type typeName, ' has invalid byteAlignment!!']]].!
Item was added: + ----- Method: ExternalType class>>initializeArrayTypes (in category 'class initialization') ----- + initializeArrayTypes + "Private. Initialize all array types that have an atomic-or-pointer type as their content type. Other array types will be updated through #initializeStructureTypes because of how #defineAllFields work with its callback to ExternalType class >> #noticeModificationOf:." + + self allArrayTypesDo: [:arrayType | + (arrayType contentType isAtomic or: [arrayType contentType isPointerType]) ifTrue: [ + arrayType newContentType: arrayType contentType]].!
Item was changed: ----- Method: ExternalType class>>initializeAtomicTypeCodes (in category 'class initialization') ----- initializeAtomicTypeCodes "ExternalType initializeAtomicTypeCodes"
+ FFIConstants initialize. "Init appropriate type codes for current plugin version." + AtomicTypeCodes := OrderedDictionary newFrom: { #'void' -> FFITypeVoid. #'bool' -> FFITypeBool. #'uint8_t' -> FFITypeUnsignedInt8. #'int8_t' -> FFITypeSignedInt8. #'uint16_t' -> FFITypeUnsignedInt16. #'int16_t' -> FFITypeSignedInt16. #'uint32_t' -> FFITypeUnsignedInt32. #'int32_t' -> FFITypeSignedInt32. #'uint64_t' -> FFITypeUnsignedInt64. #'int64_t' -> FFITypeSignedInt64. #'uchar8_t' -> FFITypeUnsignedChar8. #'char8_t' -> FFITypeSignedChar8. #'uchar16_t' -> FFITypeUnsignedChar16. #'char16_t' -> FFITypeSignedChar16. #'uchar32_t' -> FFITypeUnsignedChar32. #'char32_t' -> FFITypeSignedChar32. #'float' -> FFITypeSingleFloat. #'double' -> FFITypeDoubleFloat}. "We must now update the names of all known atomic types." AtomicTypes ifNotNil: [ AtomicTypes keys do: [:oldName | | type newName | type := AtomicTypes at: oldName. newName := AtomicTypeCodes keyAtValue: type atomicType. (AtomicTypes includesKey: newName) ifFalse: [ "Only store new names. Do not support name swap." AtomicTypes removeKey: oldName. AtomicTypes at: newName put: type. type setAtomicTypeName: newName]]].!
Item was changed: ----- Method: ExternalType class>>initializeAtomicTypes (in category 'class initialization') ----- initializeAtomicTypes + "Private. (Re-)initialize all atomic types. Preserves object identity of all involved types. If the amount of types changed, use #resetAllAtomicTypes instead. Needs atomic-type codes to be initialized already." - "(Re-)initialize all atomic types. Preserves object identity of all involved types. If the amount of types changed, use #resetAllAtomicTypes instead. Needs atomic-type codes to be initialized already."
self assert: [AtomicTypeCodes notNil]. self assert: [AtomicTypeCodes notEmpty]. self basicInitializeAtomicTypes. self invalidateAtomicTypes. ExternalAtomicType initializeAtomicTypes. ExternalAtomicType initializeAtomicTypeCompanions. self initializeAtomicSends.!
Item was added: + ----- Method: ExternalType class>>initializeFast (in category 'class initialization') ----- + initializeFast + "Faster than #initialize. Update all atomic types for platform-specifc byte size and alignment. Also update struct and array types when they change due to changed atomics. NOTE THAT this cannot be used when atomic-type codes have changed!!" + + ExternalAtomicType initializeAtomicTypes. + self initializeArrayTypes. + ExternalStructure defineAllChangedFields.!
Item was changed: ----- Method: ExternalType class>>initializeStructureTypes (in category 'class initialization') ----- initializeStructureTypes "(Re-)initialize all structure types and all array types. Preserves object identity of all involved types. If the amount of types changed, use #resetAllStructureTypes instead."
self basicInitializeStructureTypes. self invalidateStructureTypes. "1) Initialize all array types that have an atomic-or-pointer type as their content type." + self initializeArrayTypes. - self allArrayTypesDo: [:arrayType | - (arrayType contentType isAtomic or: [arrayType contentType isPointerType]) ifTrue: [ - arrayType newContentType: arrayType contentType]]. + "2) Trigger #noticeModificationOf: callback to actually initialize all structure types. Since we invalidated all types, we cannot use #defineAllChangedFields. We rely on the #noticeModificationOf: callback." - "2) Trigger #noticeModificationOf: callback to actually initialize all structure types." ExternalStructure defineAllFields.
"Finally do some garbage collection." self cleanupUnusedTypes.!
Item was changed: ----- Method: ExternalType class>>invalidateAtomicTypes (in category 'class initialization') ----- invalidateAtomicTypes + "Invalidate all pure atomic types. Do not invalidate alias-to-atomic types here. See #invalidateStructureTypes." self atomicTypesDo: [:atomicType | atomicType "asNonPointerType" invalidate. atomicType asPointerType invalidate].!
Item was changed: ----- Method: ExternalType class>>invalidateStructureTypes (in category 'class initialization') ----- invalidateStructureTypes
+ self typeAliasTypesDo: [:type | type isAtomic ifTrue: [ + type "asNonPointerType" invalidate. + type asPointerType invalidate]]. + self allStructTypesDo:[:structType | structType "asNonPointerType" invalidate. structType asPointerType invalidate]. self allArrayTypesDo: [:arrayType | arrayType "asNonPointerType" invalidate. arrayType asPointerType invalidate].!
Item was changed: ----- Method: ExternalType class>>platformChangedFrom:to: (in category 'system startup') ----- platformChangedFrom: lastPlatform to: currentPlatform "Byte size or byte alignment for atomic types might be different on the new platform." + lastPlatform pluginVersion = currentPlatform pluginVersion + ifTrue: [self initializeFast] + ifFalse: [self initialize "Slower but necessary for new type codes"]. - "0) For a different FFI plugin version, type-codes might have changed." - lastPlatform pluginVersion ~= currentPlatform pluginVersion ifTrue: [ - FFIConstants initialize. - self initializeAtomicTypeCodes]. - - "1) Update all atomic types for platform-specifc byte size and alignment." - self initializeAtomicTypes. + self flag: #todo. "mt: Update all critical aliases for atomic types, i.e., intptr_t, uintptr_t. But what about 'c_long' between 64-bit platforms?!!" + "lastPlatform wordSize ~= currentPlatform wordSize + ifTrue: [self recompileAllLibraryFunctions]."! - "2) Discard all compiled specs for all structure types." - self initializeStructureTypes. - - "3) Update all critical aliases for atomic types, i.e., intptr_t, uintptr_t. But what about 'c_long' between 64-bit platforms?!!" - lastPlatform wordSize ~= currentPlatform wordSize - ifTrue: [self recompileAllLibraryFunctions].!
Item was changed: ----- Method: FFIPlatformDescription class>>startUp: (in category 'system startup') ----- startUp: resuming "Notify all FFI classes about platform changes."
resuming ifTrue: [ LastPlatform in: [:lastPlatform | self newCurrent in: [:currentPlatform | lastPlatform = currentPlatform ifTrue: [ self flag: #discuss. "mt: Maybe add #platformResuming?" + ExternalAddress allBeNull ] - ExternalAddress allBeNull. - ExternalType cleanupUnusedTypes ] ifFalse: [ LastPlatform := currentPlatform. "Update now. See #current." + { ExternalAddress. ExternalType. ExternalPool. ExternalLibrary } - { ExternalAddress. ExternalType. ExternalStructure. ExternalPool. ExternalLibrary } do: [:cls | cls platformChangedFrom: lastPlatform to: currentPlatform] ]]]. self checkFFIOnStartUp ifTrue: [self checkFFI]].!
packages@lists.squeakfoundation.org