[Vm-dev] VM Maker: VMMaker.oscog-eem.3034.mcz
Bruce O'Neel
bruce.oneel at pckswarms.ch
Thu Aug 12 20:10:58 UTC 2021
Hi all,
Thanks very much!
With this change I can build ARMv8, Armv6, and x86-64 all on Linux.
This is very very very nice.
And the ARMv8 2 raisedTo: 64 bug is gone but we knew that already.
Thanks again.
cheers
bruce
On 0000-08-17T17:30:28.000+00:34, <commits at source.squeak.org> wrote:
> Eliot Miranda uploaded a new version of VMMaker to project VM Maker:
> source.squeak.org/VMMaker/V... [http://source.squeak.org/VMMaker/VMMaker.oscog-eem.3034.mcz]
>
> ==================== Summary ====================
>
> Name: VMMaker.oscog-eem.3034
> Author: eem
> Time: 12 August 2021, 10:56:19.010201 am
> UUID: 3ea0aaa2-20e4-4c02-b448-c3e708578e16
> Ancestors: VMMaker.oscog-eem.3033
>
> CogARMv8Compiler: Make sure the generated cache flush code flushes the range (startAddress to endAddress], i.e. never flush endAddress, only addresses less than endAddress. Flushing endAddress can cause a segmentation violation if the endAddress is on an empty page.
>
> Have Symbol simulate & for expressions such as
> self cppIf: #__APPLE__ & #__MACH__
> ifFalse: ...
>
> =============== Diff against VMMaker.oscog-eem.3033 ===============
>
> Item was changed:
> ----- Method: CogARMv8Compiler>>generateDCacheFlush (in category 'inline cacheing') -----
> generateDCacheFlush
> "Use the DC instruction to implement ceFlushDCache(void *start, void *end); see flushDCacheFrom:to:.
> If there is a dual mapped zone then clean data via DC_CVAU as address + codeToDataDelta,
> then invalidate data at address via CIVAC."
>
> "D4.4.7 About cache maintenance in AArch64 state D4-2478
>
> Terminology for Clean, Invalidate, and Clean and Invalidate instructions D4-2479
> ...
> - For instructions operating by VA, the following conceptual points are defined: D4-2480
> Point of Unification (PoU)
> The PoU for a PE is the point by which the instruction and data caches and the translation table walks of that
> PE are guaranteed to see the same copy of a memory location. In many cases, the Point of Unification is the
> point in a uniprocessor memory system by which the instruction and data caches and the translation table
> walks have merged.
>
> The PoU for an Inner Shareable shareability domain is the point by which the instruction and data caches
> and the translation table walks of all the PEs in that Inner Shareable shareability domain are guaranteed to
> see the same copy of a memory location. Defining this point permits self-modifying software to ensure future
> instruction fetches are associated with the modified version of the software by using the standard correctness
> policy of:
> 1. Clean data cache entry by address.
> 2. Invalidate instruction cache entry by address.
>
> Example code for cache maintenance instructions D4-2490 - D4-2491"
> self cppIf: #__APPLE__ & #__MACH__
> ifFalse:
> [| mask loop |
> self assert: cogit getCodeToDataDelta ~= 0.
> "Mask is large enough to encompass the method zone and has the correct minimum alignment."
> mask := 1 << (cogit coInterpreter highBit: cogit methodZone zoneEnd) - self dataCacheLineLength.
>
> "Since this is used from C code we must use only caller-saved registers.
> C arg registers 2 & 3 are such a convenient pair of caller-saved registers."
> cogit AndCq: mask R: CArg0Reg R: CArg2Reg. "CArg2Reg = aligned pointer to start of each data cache line"
> cogit AddCq: cogit getCodeToDataDelta R: CArg2Reg R: CArg3Reg.
> loop := cogit Label.
> "see concretizeDataCacheControl"
> cogit gen: DC operand: CArg3Reg operand: DC_CVAU. "clean (flush) address + codeToDataDelta"
> cogit gen: DC operand: CArg2Reg operand: DC_CIVAC. "invalidate address"
> cogit
> AddCq: self dataCacheLineLength R: CArg2Reg;
> AddCq: self dataCacheLineLength R: CArg3Reg;
> CmpR: CArg1Reg R: CArg2Reg;
> + JumpBelow: loop.
> - JumpBelowOrEqual: loop.
> cogit RetN: 0]!
>
> Item was changed:
> ----- Method: CogARMv8Compiler>>generateICacheFlush (in category 'inline cacheing') -----
> generateICacheFlush
> "Use DC VAUC, DSB, IC IVAU, and ISB instructions to implement ceFlushICache(void *start, void *end); see flushICacheFrom:to:.
> One might think that if there is a dual zone then data at address + codeToDataDelta must be cleaned,
> but this isn't the case. All we need to do is clean data at address via DC VAUC and instructions via IC IVAU."
>
> "B2.2.5 Concurrent modification and execution of instructions B2-112
>
> ...to avoid UNPREDICTABLE or CONSTRAINED UNPREDICTABLE behavior, instruction modifications must be explicitly synchronized before they are executed. The required synchronization is as follows:
>
> 1. No PE must be executing an instruction when another PE is modifying that instruction.
>
> 2. To ensure that the modified instructions are observable, a PE that is writing the instructions must issue the following sequence of instructions and operations:
>
> ; Coherency example for data and instruction accesses within the same Inner Shareable domain.
> ; enter this code with <Wt> containing a new 32-bit instruction, to be held in Cacheable space at a location pointed to by Xn.
>
> STR Wt, [Xn]
> DC CVAU, Xn ; Clean data cache by VA to point of unification (PoU)
> DSB ISH ; Ensure visibility of the data cleaned from cache
> IC IVAU, Xn ; Invalidate instruction cache by VA to PoU
> DSB ISH
>
> Note
> - The DC CVAU operation is not required if the area of memory is either Non-cacheable or Write-Through Cacheable.
> - If the contents of physical memory differ between the mappings, changing the mapping of VAs to PAs can cause
> the instructions to be concurrently modified by one PE and executed by another PE. If the modifications affect
> instructions other than those listed as being acceptable for modification, synchronization must be used to avoid
> UNPREDICTABLE or CONSTRAINED UNPREDICTABLE behavior.
>
> 3. In a multiprocessor system, the IC IVAU is broadcast to all PEs within the Inner Shareable domain of the PE running this sequence.
> However, when the modified instructions are observable, each PE that is executing the modified instructions must issue the following
> instruction to ensure execution of the modified instructions:
>
> ISB ; Synchronize fetched instruction stream"
>
> "D4.4.7 About cache maintenance in AArch64 state D4-2478
>
> Terminology for Clean, Invalidate, and Clean and Invalidate instructions D4-2479
> ...
> - For instructions operating by VA, the following conceptual points are defined: D4-2480
> Point of Unification (PoU)
> The PoU for a PE is the point by which the instruction and data caches and the translation table walks of that
> PE are guaranteed to see the same copy of a memory location. In many cases, the Point of Unification is the
> point in a uniprocessor memory system by which the instruction and data caches and the translation table
> walks have merged.
>
> The PoU for an Inner Shareable shareability domain is the point by which the instruction and data caches
> and the translation table walks of all the PEs in that Inner Shareable shareability domain are guaranteed to
> see the same copy of a memory location. Defining this point permits self-modifying software to ensure future
> instruction fetches are associated with the modified version of the software by using the standard correctness
> policy of:
> 1. Clean data cache entry by address.
> 2. Invalidate instruction cache entry by address.
>
> Example code for cache maintenance instructions D4-2490 - D4-2491"
> self cppIf: #__APPLE__ & #__MACH__
> ifFalse:
> [| mask loop |
> "See concretizeCacheControlOp1:CRm:Op2: &
> infocenter.arm.com/help/ind... [http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.100403_0200_00_en/lau1443435580346.html]"
> self dataCacheFlushRequired ifTrue: "CTR_EL0.IDC is zero; must clean data cache to point of unification."
> ["Since this is used from C code we must use only caller-saved registers.
> C arg registers 2 & 3 are as such a convenient pair of caller-saved registers."
> "Mask is large enough to encompass the method zone and has the correct minimum alignment."
> mask := 1 << (cogit coInterpreter highBit: cogit methodZone zoneEnd) - self dataCacheLineLength.
> cogit AndCq: mask R: CArg0Reg R: CArg2Reg. "CArg2Reg = aligned pointer to start of each data cache line"
>
> loop := cogit Label.
> "see concretizeDataCacheControl"
> cogit
> gen: DC operand: CArg2Reg operand: DC_CVAU; "clean (flush) address"
> AddCq: self dataCacheLineLength R: CArg2Reg;
> CmpR: CArg1Reg R: CArg2Reg;
> + JumpBelow: loop].
> - JumpBelowOrEqual: loop].
>
> cogit gen: DSB operand: DSB_ISH operand: DSB_ALL. "Ensure visibility of the data cleaned from cache"
>
> self instructionCacheFlushRequired ifTrue: "CTR_EL0.DIC is zero; must clean instruction cache to point of unification."
> ["Mask is large enough to encompass the method zone and has the correct minimum alignment."
> mask := 1 << (cogit coInterpreter highBit: cogit methodZone zoneEnd) - self instructionCacheLineLength.
> cogit AndCq: mask R: CArg0Reg R: CArg2Reg. "CArg2Reg = aligned pointer to start of each data cache line"
>
> loop := cogit Label.
> "see concretizeDataCacheControl"
> cogit
> gen: IC operand: CArg2Reg operand: IC_IVAU; "clean (flush) address"
> AddCq: self instructionCacheLineLength R: CArg2Reg;
> CmpR: CArg1Reg R: CArg2Reg;
> + JumpBelow: loop.
> - JumpBelowOrEqual: loop.
>
> cogit gen: DSB operand: DSB_ISH operand: DSB_ALL].
>
> cogit
> gen: ISB;
> RetN: 0]!
>
> Item was added:
> + ----- Method: Symbol>>& (in category '*VMMaker-interpreter simulator') -----
> + & aSymbol
> + ^(VMClass valueOfSymbol: self) & (VMClass valueOfSymbol: aSymbol)!
>
> Item was added:
> + ----- Method: VMClass class>>valueOfSymbol: (in category 'simulation') -----
> + valueOfSymbol: value
> + ^(self bindingOf: value)
> + ifNil: [InitializationOptions at: value ifAbsent: [false]]
> + ifNotNil: [:binding| binding value]!
>
> Item was changed:
> ----- Method: VMClass>>cppIf:ifTrue:ifFalse: (in category 'translation support') -----
> cppIf: conditionBlockOrSymbolValue ifTrue: trueExpressionOrBlock ifFalse: falseExpressionOrBlockOrNil
> "When translated, produces #if (condition) #else #endif CPP directives.
> Example usage:
>
> self cppIf: [BytesPerWord = 8]
> ifTrue: [self doSomethingFor64Bit]
> ifFalse: [self doSomethingFor32Bit]
> self cppIf: BytesPerWord = 8
> ifTrue: [self doSomethingFor64Bit]
> ifFalse: [self doSomethingFor32Bit]
> self cppIf: #A_GLOBAL
> ifTrue: [self doSomethingFor64Bit]
> ifFalse: [self doSomethingFor32Bit]"
> <doNotGenerate>
> ^(conditionBlockOrSymbolValue value
> ifNil: [false]
> ifNotNil: [:value|
> value isInteger
> ifTrue: [value ~= 0]
> ifFalse:
> [value isSymbol
> + ifTrue: [self class valueOfSymbol: value]
> - ifTrue: [(self class bindingOf: value)
> - ifNil: [InitializationOptions at: value ifAbsent: [false]]
> - ifNotNil: [:binding| binding value]]
> ifFalse: [value]]])
> ifTrue: trueExpressionOrBlock
> ifFalse: falseExpressionOrBlockOrNil!
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.squeakfoundation.org/pipermail/vm-dev/attachments/20210812/917d6b13/attachment-0001.html>
More information about the Vm-dev
mailing list