[Vm-dev] VM Maker: VMMaker.oscog-eem.1950.mcz
commits at source.squeak.org
commits at source.squeak.org
Wed Sep 7 13:33:30 UTC 2016
Eliot Miranda uploaded a new version of VMMaker to project VM Maker:
http://source.squeak.org/VMMaker/VMMaker.oscog-eem.1950.mcz
==================== Summary ====================
Name: VMMaker.oscog-eem.1950
Author: eem
Time: 7 September 2016, 3:31:10.027268 pm
UUID: b4089b49-1494-49d2-8966-57cba5c92194
Ancestors: VMMaker.oscog-rsf.1949
Fix Roni's callback fix for the Cogit.
Add MoveRA32 and MoveA32R support for Sista on x64.
=============== Diff against VMMaker.oscog-rsf.1949 ===============
Item was changed:
SharedPool subclass: #CogRTLOpcodes
instanceVariableNames: ''
+ classVariableNames: 'AddCqR AddCwR AddRR AddRdRd AlignmentNops AndCqR AndCqRR AndCwR AndRR ArithmeticShiftRightCqR ArithmeticShiftRightRR Call CallFull CmpC32R CmpCqR CmpCwR CmpRR CmpRdRd ConvertRRd DivRdRd Fill32 FirstJump FirstShortJump Jump JumpAbove JumpAboveOrEqual JumpBelow JumpBelowOrEqual JumpCarry JumpFPEqual JumpFPGreater JumpFPGreaterOrEqual JumpFPLess JumpFPLessOrEqual JumpFPNotEqual JumpFPOrdered JumpFPUnordered JumpFull JumpGreater JumpGreaterOrEqual JumpLess JumpLessOrEqual JumpLong JumpLongNonZero JumpLongZero JumpNegative JumpNoCarry JumpNoOverflow JumpNonNegative JumpNonZero JumpOverflow JumpR JumpZero Label LastJump LastRTLCode Literal LoadEffectiveAddressMwrR LoadEffectiveAddressXowrR LogicalShiftLeftCqR LogicalShiftLeftRR LogicalShiftRightCqR LogicalShiftRightRR MoveA32R MoveAbR MoveAwR MoveC32R MoveC64R MoveCqR MoveCwR MoveM16rR MoveM32rR MoveM64rRd MoveMbrR MoveMwrR MoveRA32 MoveRAb MoveRAw MoveRM16r MoveRM32r MoveRMbr MoveRMwr MoveRR MoveRRd MoveRX16rR MoveRX32rR MoveRXbrR MoveRXowr MoveRXwrR MoveRdM64r MoveRdR MoveRdRd MoveX16rRR MoveX32rRR MoveXbrRR MoveXowrR MoveXwrRR MulRdRd NegateR Nop OrCqR OrCwR OrRR PopR PrefetchAw PushCq PushCw PushR RetN RotateLeftCqR RotateRightCqR SqrtRd Stop SubCqR SubCwR SubRR SubRdRd TstCqR XorCqR XorCwR XorRR'
- classVariableNames: 'AddCqR AddCwR AddRR AddRdRd AlignmentNops AndCqR AndCqRR AndCwR AndRR ArithmeticShiftRightCqR ArithmeticShiftRightRR Call CallFull CmpC32R CmpCqR CmpCwR CmpRR CmpRdRd ConvertRRd DivRdRd Fill32 FirstJump FirstShortJump Jump JumpAbove JumpAboveOrEqual JumpBelow JumpBelowOrEqual JumpCarry JumpFPEqual JumpFPGreater JumpFPGreaterOrEqual JumpFPLess JumpFPLessOrEqual JumpFPNotEqual JumpFPOrdered JumpFPUnordered JumpFull JumpGreater JumpGreaterOrEqual JumpLess JumpLessOrEqual JumpLong JumpLongNonZero JumpLongZero JumpNegative JumpNoCarry JumpNoOverflow JumpNonNegative JumpNonZero JumpOverflow JumpR JumpZero Label LastJump LastRTLCode Literal LoadEffectiveAddressMwrR LoadEffectiveAddressXowrR LogicalShiftLeftCqR LogicalShiftLeftRR LogicalShiftRightCqR LogicalShiftRightRR MoveAbR MoveAwR MoveC32R MoveC64R MoveCqR MoveCwR MoveM16rR MoveM32rR MoveM64rRd MoveMbrR MoveMwrR MoveRAb MoveRAw MoveRM16r MoveRM32r MoveRMbr MoveRMwr MoveRR MoveRRd MoveRX16rR MoveRX32rR MoveRXbrR MoveRXowr MoveRXwrR MoveRdM64r MoveRdR MoveRdRd MoveX16rRR MoveX32rRR MoveXbrRR MoveXowrR MoveXwrRR MulRdRd NegateR Nop OrCqR OrCwR OrRR PopR PrefetchAw PushCq PushCw PushR RetN RotateLeftCqR RotateRightCqR SqrtRd Stop SubCqR SubCwR SubRR SubRdRd TstCqR XorCqR XorCwR XorRR'
poolDictionaries: ''
category: 'VMMaker-JIT'!
!CogRTLOpcodes commentStamp: 'eem 12/26/2015 14:00' prior: 0!
I am a pool for the Register-Transfer-Language to which Cog compiles. I define unique integer values for all RTL opcodes. See CogAbstractInstruction for instances of instructions with the opcodes that I define.!
Item was changed:
----- Method: CogRTLOpcodes class>>initialize (in category 'class initialization') -----
initialize
"Abstract opcodes are a compound of a one word operation specifier and zero or more operand type specifiers.
The assembler is in Cogit protocol abstract instructions and uses `at&t' syntax, assigning to the register on the
right. e.g. MoveRR is the Move opcode with two register operand specifiers and defines a move register to
register instruction from operand 0 to operand 1. The word and register size is assumed to be either 32-bits
on a 32-bit architecture or 64-bits on a 64-bit architecture. The abstract machine is mostly a 2 address machine
with the odd three address instruction added to better exploit RISCs.
(self initialize)
The operand specifiers are
R - general purpose register
Rd - double-precision floating-point register
Cq - a `quick' constant that can be encoded in the minimum space possible.
Cw - a constant with word size where word is the default operand size for the Smalltalk VM, 32-bits
for a 32-bit VM, 64-bits for a 64-bit VM. The generated constant must occupy the default number
of bits. This allows e.g. a garbage collector to update the value without invalidating the code.
C32 - a constant with 32 bit size. The generated constant must occupy 32 bits.
C64 - a constant with 64 bit size. The generated constant must occupy 64 bits.
+ Aw - memory word (32-bits for a 32-bit VM, 64-bits for a 64-bit VM) at an absolute address
- Aw - memory word at an absolute address
Ab - memory byte at an absolute address
+ A32 - memory 32-bit halfword at an absolute address
Mwr - memory word whose address is at a constant offset from an address in a register
Mbr - memory byte whose address is at a constant offset from an address in a register (zero-extended on read)
M16r - memory 16-bit halfword whose address is at a constant offset from an address in a register
M32r - memory 32-bit halfword whose address is at a constant offset from an address in a register
M64r - memory 64-bit doubleword whose address is at a constant offset from an address in a register
Xbr - memory byte whose address is r * byte size away from an address in a register
X16r - memory 16-bit halfword whose address is r * (2 bytes size) away from an address in a register
X32r - memory 32-bit halfword whose address is r * (4 bytes size) away from an address in a register
Xwr - memory word whose address is r * word size away from an address in a register
Xowr - memory word whose address is o + (r * word size) away from an address in a register (scaled indexed)
An alternative would be to decouple opcodes from operands, e.g.
Move := 1. Add := 2. Sub := 3...
RegisterOperand := 1. ConstantQuickOperand := 2. ConstantWordOperand := 3...
But not all combinations make sense and even fewer are used so we stick with the simple compound approach.
The assumption is that comparison and arithmetic instructions set condition codes and that move instructions
leave the condition codes unaffected. In particular LoadEffectiveAddressMwrR does not set condition codes
although it can be used to do arithmetic. On processors such as MIPS this distinction is invalid; there are no
condition codes. So the backend is allowed to collapse operation, branch pairs to internal instruciton definitions
(see sender and implementors of noteFollowingConditionalBranch:).
Not all of the definitions in opcodeDefinitions below are implemented. In particular we do not implement the
XowrR scaled index addressing mode since it requires 4 operands.
Not all instructions make sense on all architectures. MoveRRd and MoveRdR aqre meaningful only on 64-bit machines.
Note that there are no generic division instructions defined, but a processor may define some.
Branch/Call ranges. Jump[Cond] can be generated as short as possible. Call/Jump[Cond]Long must be generated
in the same number of bytes irrespective of displacement since their targets may be updated, but they need only
span 16Mb, the maximum size of the code zone. This allows e.g. ARM to use single-word call and jump instructions
for most calls and jumps. CallFull/JumpFull must also be generated in the same number of bytes irrespective of
displacement for the same reason, but they must be able to span the full (32-bit or 64-bit) address space because
they are used to call code in the C runtime, which may be distant from the code zone. CallFull/JumpFull are allowed
to use the cResultRegister as a scratch if required (e.g. on x64 where there is no direct 64-bit call or jump).
Byte reads. If the concrete compiler class answers true to byteReadsZeroExtend then byte reads must zero-extend
the byte read into the destination register. If not, the other bits of the register should be left undisturbed and the
Cogit will add an instruction to zero the register as required. Under no circumstances should byte reads sign-extend.
16-bit (and on 64-bits, 32-bit) reads. These /are/ expected to always zero-extend."
| opcodeNames refs |
opcodeNames := #("Noops & Pseudo Ops"
Label
Literal "a word-sized literal"
AlignmentNops
Fill32 "output four byte's worth of bytes with operand 0"
Nop
"Control"
Call "call within the code zone"
CallFull "call anywhere within the full address space"
RetN
JumpR "Not a regular jump, i.e. not pc dependent."
Stop "Halt the processor"
"N.B. Jumps are contiguous. Long and Full jumps are contigiuous within them. See FirstJump et al below"
JumpFull "Jump anywhere within the address space"
JumpLong "Jump anywhere within the 16mb code zone."
JumpLongZero "a.k.a. JumpLongEqual"
JumpLongNonZero "a.k.a. JumpLongNotEqual"
Jump "short jumps; can be encoded in as few bytes as possible; will not be disturbed by GC or relocation."
JumpZero "a.k.a. JumpEqual"
JumpNonZero "a.k.a. JumpNotEqual"
JumpNegative
JumpNonNegative
JumpOverflow
JumpNoOverflow
JumpCarry
JumpNoCarry
JumpLess "signed"
JumpGreaterOrEqual
JumpGreater
JumpLessOrEqual
JumpBelow "unsigned"
JumpAboveOrEqual
JumpAbove
JumpBelowOrEqual
JumpFPEqual
JumpFPNotEqual
JumpFPLess
JumpFPLessOrEqual
JumpFPGreater
JumpFPGreaterOrEqual
JumpFPOrdered
JumpFPUnordered
"Data Movement; destination is always last operand"
MoveRR
+ MoveAwR MoveA32R
+ MoveRAw MoveRA32
- MoveAwR
- MoveRAw
MoveAbR
MoveRAb
MoveMwrR MoveRMwr MoveXwrRR MoveRXwrR MoveXowrR MoveRXowr
MoveM16rR MoveRM16r MoveX16rRR MoveRX16rR
MoveM32rR MoveRM32r MoveX32rRR MoveRX32rR
MoveMbrR MoveRMbr MoveXbrRR MoveRXbrR
MoveCqR MoveCwR MoveC32R MoveC64R
MoveRRd MoveRdR MoveRdRd MoveM64rRd MoveRdM64r
PopR PushR PushCq PushCw
PrefetchAw
"Arithmetic; destination is always last operand except Cmp; CmpXR is SubRX with no update of result"
LoadEffectiveAddressMwrR LoadEffectiveAddressXowrR "Variants of add/multiply"
NegateR "2's complement negation"
ArithmeticShiftRightCqR ArithmeticShiftRightRR
LogicalShiftRightCqR LogicalShiftRightRR
LogicalShiftLeftCqR LogicalShiftLeftRR
RotateLeftCqR RotateRightCqR
CmpRR AddRR SubRR AndRR OrRR XorRR
CmpCqR AddCqR SubCqR AndCqR OrCqR TstCqR XorCqR
CmpCwR CmpC32R AddCwR SubCwR AndCwR OrCwR XorCwR
AndCqRR "Three address ops for RISCs; feel free to add and extend"
CmpRdRd AddRdRd SubRdRd MulRdRd DivRdRd SqrtRd
"Conversion"
ConvertRRd
LastRTLCode).
"Magic auto declaration. Add to the classPool any new variables and nuke any obsolete ones, and assign values"
"Find the variables directly referenced by this method"
refs := (thisContext method literals select: [:l| l isVariableBinding and: [classPool includesKey: l key]]) collect:
[:ea| ea key].
"Move to Undeclared any opcodes in classPool not in opcodes or this method."
(classPool keys reject: [:k| (opcodeNames includes: k) or: [refs includes: k]]) do:
[:k|
Undeclared declare: k from: classPool].
"Declare as class variables and number elements of opcodeArray above"
opcodeNames withIndexDo:
[:classVarName :value|
self classPool
declare: classVarName from: Undeclared;
at: classVarName put: value].
"For CogAbstractInstruction>>isJump etc..."
FirstJump := JumpFull.
LastJump := JumpFPUnordered.
FirstShortJump := Jump.
"And now initialize the backends; they add their own opcodes and hence these must be reinitialized."
(Smalltalk classNamed: #CogAbstractInstruction) ifNotNil:
[:cogAbstractInstruction| cogAbstractInstruction allSubclasses do: [:sc| sc initialize]]!
Item was changed:
----- Method: CogX64Compiler>>computeMaximumSize (in category 'generate machine code') -----
(excessive size, no diff calculated)
Item was added:
+ ----- Method: CogX64Compiler>>concretizeMoveA32R (in category 'generate machine code') -----
+ concretizeMoveA32R
+ "Will get inlined into concretizeAt: switch."
+ <inline: true>
+ | addressOperand reg offset |
+ addressOperand := operands at: 0.
+ (self isAnInstruction: (cogit cCoerceSimple: addressOperand to: #'AbstractInstruction *')) ifTrue:
+ [addressOperand := (cogit cCoerceSimple: addressOperand to: #'AbstractInstruction *') address].
+ reg := operands at: 1.
+ reg = RAX
+ ifTrue: [offset := 0]
+ ifFalse:
+ [machineCode
+ at: 0 put: (self rexR: 0 x: 0 b: reg);
+ at: 1 put: 16r90 + (reg \\ 8).
+ offset := 2].
+ machineCode
+ at: 0 + offset put: 16rA1;
+ at: 1 + offset put: (addressOperand bitAnd: 16rFF);
+ at: 2 + offset put: (addressOperand >> 8 bitAnd: 16rFF);
+ at: 3 + offset put: (addressOperand >> 16 bitAnd: 16rFF);
+ at: 4 + offset put: (addressOperand >> 24 bitAnd: 16rFF);
+ at: 5 + offset put: (addressOperand >> 32 bitAnd: 16rFF);
+ at: 6 + offset put: (addressOperand >> 40 bitAnd: 16rFF);
+ at: 7 + offset put: (addressOperand >> 48 bitAnd: 16rFF);
+ at: 8 + offset put: (addressOperand >> 56 bitAnd: 16rFF).
+ reg = RAX ifTrue:
+ [^machineCodeSize := 9].
+ machineCode
+ at: 11 put: (machineCode at: 0);
+ at: 12 put: (machineCode at: 1).
+ ^machineCodeSize := 13!
Item was added:
+ ----- Method: CogX64Compiler>>concretizeMoveRA32 (in category 'generate machine code') -----
+ concretizeMoveRA32
+ "Will get inlined into concretizeAt: switch."
+ <inline: true>
+ | addressOperand reg offset |
+ reg := operands at: 0.
+ addressOperand := operands at: 1.
+ (self isAnInstruction: (cogit cCoerceSimple: addressOperand to: #'AbstractInstruction *')) ifTrue:
+ [addressOperand := (cogit cCoerceSimple: addressOperand to: #'AbstractInstruction *') address].
+ reg = RAX
+ ifTrue: [offset := 0]
+ ifFalse:
+ [machineCode
+ at: 0 put: (self rexR: 0 x: 0 b: reg);
+ at: 1 put: 16r90 + (reg \\ 8).
+ offset := 2].
+ machineCode
+ at: 0 + offset put: 16rA3;
+ at: 1 + offset put: (addressOperand bitAnd: 16rFF);
+ at: 2 + offset put: (addressOperand >> 8 bitAnd: 16rFF);
+ at: 3 + offset put: (addressOperand >> 16 bitAnd: 16rFF);
+ at: 4 + offset put: (addressOperand >> 24 bitAnd: 16rFF);
+ at: 5 + offset put: (addressOperand >> 32 bitAnd: 16rFF);
+ at: 6 + offset put: (addressOperand >> 40 bitAnd: 16rFF);
+ at: 7 + offset put: (addressOperand >> 48 bitAnd: 16rFF);
+ at: 8 + offset put: (addressOperand >> 56 bitAnd: 16rFF).
+ reg = RAX ifTrue:
+ [^machineCodeSize := 9].
+ machineCode
+ at: 11 put: (machineCode at: 0);
+ at: 12 put: (machineCode at: 1).
+ ^machineCodeSize := 13!
Item was changed:
----- Method: CogX64Compiler>>dispatchConcretize (in category 'generate machine code') -----
dispatchConcretize
"Attempt to generate concrete machine code for the instruction at address.
This is the inner dispatch of concretizeAt: actualAddress which exists only
to get around the branch size limits in the SqueakV3 (blue book derived)
bytecode set."
<returnTypeC: #void>
opcode caseOf: {
"Noops & Pseudo Ops"
[Label] -> [^self concretizeLabel].
[AlignmentNops] -> [^self concretizeAlignmentNops].
[Fill32] -> [^self concretizeFill32].
[Nop] -> [^self concretizeNop].
"Specific Control/Data Movement"
[CDQ] -> [^self concretizeCDQ].
[IDIVR] -> [^self concretizeIDIVR].
[IMULRR] -> [^self concretizeMulRR].
"[CPUID] -> [^self concretizeCPUID]."
"[CMPXCHGAwR] -> [^self concretizeCMPXCHGAwR]."
"[CMPXCHGMwrR] -> [^self concretizeCMPXCHGMwrR]."
"[LFENCE] -> [^self concretizeFENCE: 5]."
"[MFENCE] -> [^self concretizeFENCE: 6].
[SFENCE] -> [^self concretizeFENCE: 7]."
"[LOCK] -> [^self concretizeLOCK]."
"[XCHGAwR] -> [^self concretizeXCHGAwR]."
"[XCHGMwrR] -> [^self concretizeXCHGMwrR]."
[XCHGRR] -> [^self concretizeXCHGRR].
"Control"
[Call] -> [^self concretizeCall].
[CallFull] -> [^self concretizeCallFull].
[JumpR] -> [^self concretizeJumpR].
[JumpFull] -> [^self concretizeJumpFull].
[JumpLong] -> [^self concretizeJumpLong].
[JumpLongZero] -> [^self concretizeConditionalJump: 16r4].
[JumpLongNonZero] -> [^self concretizeConditionalJump: 16r5].
[Jump] -> [^self concretizeJump].
"Table B-1 Intel® 64 and IA-32 Architectures Software Developer's Manual Volume 1: Basic Architecture"
[JumpZero] -> [^self concretizeConditionalJump: 16r4].
[JumpNonZero] -> [^self concretizeConditionalJump: 16r5].
[JumpNegative] -> [^self concretizeConditionalJump: 16r8].
[JumpNonNegative] -> [^self concretizeConditionalJump: 16r9].
[JumpOverflow] -> [^self concretizeConditionalJump: 16r0].
[JumpNoOverflow] -> [^self concretizeConditionalJump: 16r1].
[JumpCarry] -> [^self concretizeConditionalJump: 16r2].
[JumpNoCarry] -> [^self concretizeConditionalJump: 16r3].
[JumpLess] -> [^self concretizeConditionalJump: 16rC].
[JumpGreaterOrEqual] -> [^self concretizeConditionalJump: 16rD].
[JumpGreater] -> [^self concretizeConditionalJump: 16rF].
[JumpLessOrEqual] -> [^self concretizeConditionalJump: 16rE].
[JumpBelow] -> [^self concretizeConditionalJump: 16r2].
[JumpAboveOrEqual] -> [^self concretizeConditionalJump: 16r3].
[JumpAbove] -> [^self concretizeConditionalJump: 16r7].
[JumpBelowOrEqual] -> [^self concretizeConditionalJump: 16r6].
[JumpFPEqual] -> [^self concretizeConditionalJump: 16r4].
[JumpFPNotEqual] -> [^self concretizeConditionalJump: 16r5].
[JumpFPLess] -> [^self concretizeConditionalJump: 16r2].
[JumpFPGreaterOrEqual] -> [^self concretizeConditionalJump: 16r3].
[JumpFPGreater] -> [^self concretizeConditionalJump: 16r7].
[JumpFPLessOrEqual] -> [^self concretizeConditionalJump: 16r6].
[JumpFPOrdered] -> [^self concretizeConditionalJump: 16rB].
[JumpFPUnordered] -> [^self concretizeConditionalJump: 16rA].
[RetN] -> [^self concretizeRetN].
[Stop] -> [^self concretizeStop].
"Arithmetic"
[AddCqR] -> [^self concretizeArithCqRWithRO: 0 raxOpcode: 15r05].
[AddCwR] -> [^self concretizeArithCwR: 16r03].
[AddRR] -> [^self concretizeOpRR: 16r03].
[AddRdRd] -> [^self concretizeSEE2OpRdRd: 16r58].
[AndCqR] -> [^self concretizeArithCqRWithRO: 4 raxOpcode: 16r25].
[AndCwR] -> [^self concretizeArithCwR: 16r23].
[AndRR] -> [^self concretizeOpRR: 16r23].
[TstCqR] -> [^self concretizeTstCqR].
[CmpCqR] -> [^self concretizeArithCqRWithRO: 7 raxOpcode: 16r3D].
[CmpCwR] -> [^self concretizeArithCwR: 16r39].
[CmpC32R] -> [^self concretizeCmpC32R].
[CmpRR] -> [^self concretizeReverseOpRR: 16r39].
[CmpRdRd] -> [^self concretizeCmpRdRd].
[DivRdRd] -> [^self concretizeSEE2OpRdRd: 16r5E].
[MulRdRd] -> [^self concretizeSEE2OpRdRd: 16r59].
[OrCqR] -> [^self concretizeArithCqRWithRO: 1 raxOpcode: 16r0D].
[OrCwR] -> [^self concretizeArithCwR: 16r0B].
[OrRR] -> [^self concretizeOpRR: 16r0B].
[SubCqR] -> [^self concretizeArithCqRWithRO: 5 raxOpcode: 16r2D].
[SubCwR] -> [^self concretizeArithCwR: 16r2B].
[SubRR] -> [^self concretizeOpRR: 16r2B].
[SubRdRd] -> [^self concretizeSEE2OpRdRd: 16r5C].
[SqrtRd] -> [^self concretizeSqrtRd].
[XorCwR] -> [^self concretizeArithCwR: 16r33].
[XorRR] -> [^self concretizeOpRR: 16r33].
[NegateR] -> [^self concretizeNegateR].
[LoadEffectiveAddressMwrR] -> [^self concretizeLoadEffectiveAddressMwrR].
[RotateLeftCqR] -> [^self concretizeShiftCqRegOpcode: 0].
[RotateRightCqR] -> [^self concretizeShiftCqRegOpcode: 1].
[ArithmeticShiftRightCqR] -> [^self concretizeShiftCqRegOpcode: 7].
[LogicalShiftRightCqR] -> [^self concretizeShiftCqRegOpcode: 5].
[LogicalShiftLeftCqR] -> [^self concretizeShiftCqRegOpcode: 4].
[ArithmeticShiftRightRR] -> [^self concretizeShiftRegRegOpcode: 7].
[LogicalShiftLeftRR] -> [^self concretizeShiftRegRegOpcode: 4].
"Data Movement"
[MoveCqR] -> [^self concretizeMoveCqR].
[MoveCwR] -> [^self concretizeMoveCwR].
[MoveC32R] -> [^self concretizeMoveC32R].
[MoveRR] -> [^self concretizeReverseOpRR: 16r89].
[MoveAwR] -> [^self concretizeMoveAwR].
+ [MoveA32R] -> [^self concretizeMoveA32R].
[MoveRAw] -> [^self concretizeMoveRAw].
+ [MoveRA32] -> [^self concretizeMoveRA32].
[MoveAbR] -> [^self concretizeMoveAbR].
[MoveRAb] -> [^self concretizeMoveRAb].
[MoveMbrR] -> [^self concretizeMoveMbrR].
[MoveRMbr] -> [^self concretizeMoveRMbr].
[MoveM16rR] -> [^self concretizeMoveM16rR].
[MoveRM16r] -> [^self concretizeMoveRM16r].
[MoveM64rRd] -> [^self concretizeMoveM64rRd].
[MoveMwrR] -> [^self concretizeMoveMwrR].
[MoveXbrRR] -> [^self concretizeMoveXbrRR].
[MoveRXbrR] -> [^self concretizeMoveRXbrR].
[MoveXwrRR] -> [^self concretizeMoveXwrRR].
[MoveRXwrR] -> [^self concretizeMoveRXwrR].
[MoveX32rRR] -> [^self concretizeMoveX32rRR].
[MoveRX32rR] -> [^self concretizeMoveRX32rR].
[MoveRMwr] -> [^self concretizeMoveRMwr].
[MoveRdM64r] -> [^self concretizeMoveRdM64r].
[MoveRdR] -> [^self concretizeMoveRdR].
[MoveRRd] -> [^self concretizeMoveRRd].
[PopR] -> [^self concretizePopR].
[PushR] -> [^self concretizePushR].
[PushCq] -> [^self concretizePushCq].
[PushCw] -> [^self concretizePushCw].
[PrefetchAw] -> [^self concretizePrefetchAw].
"Conversion"
[ConvertRRd] -> [^self concretizeConvertRRd] }!
Item was added:
+ ----- Method: Cogit>>MoveA32:R: (in category 'abstract instructions') -----
+ MoveA32: address R: reg
+ <inline: true>
+ <returnTypeC: #'AbstractInstruction *'>
+ ^self gen: (objectMemory wordSize = 8
+ ifTrue: [MoveA32R]
+ ifFalse: [MoveAwR])
+ literal: address
+ operand: reg!
Item was added:
+ ----- Method: Cogit>>MoveR:A32: (in category 'abstract instructions') -----
+ MoveR: reg A32: address
+ <inline: true>
+ <returnTypeC: #'AbstractInstruction *'>
+ ^self gen: (objectMemory wordSize = 8
+ ifTrue: [MoveRA32]
+ ifFalse: [MoveRAw])
+ operand: reg
+ literal: address!
Item was changed:
----- Method: SistaCogit>>genExecutionCountLogicInto:counterReg: (in category 'bytecode generator support') -----
genExecutionCountLogicInto: binaryBlock counterReg: counterReg
<var: #countTripped type: #'AbstractInstruction *'>
<inline: true>
| counterAddress countTripped |
counterAddress := counters + ((self sizeof: #sqInt) * counterIndex).
- self flag: 'will need to use MoveAw32:R: if 64 bits'.
self assert: objectMemory wordSize = CounterBytes.
+ self MoveA32: counterAddress R: counterReg.
- self MoveAw: counterAddress R: counterReg.
self SubCq: 16r10000 R: counterReg. "Count executed"
"If counter trips simply abort the comparison continuing to the following
branch *without* writing back. A double decrement will not trip the second time."
countTripped := self JumpCarry: 0.
+ self MoveR: counterReg A32: counterAddress. "write back"
- self MoveR: counterReg Aw: counterAddress. "write back"
binaryBlock value: counterAddress value: countTripped!
Item was changed:
----- Method: SistaCogit>>genFallsThroughCountLogicCounterReg:counterAddress: (in category 'bytecode generator support') -----
genFallsThroughCountLogicCounterReg: counterReg counterAddress: counterAddress
<inline: true>
"Gen this when the branch has not been taken and forwarders have been followed."
self SubCq: 1 R: counterReg. "Count untaken"
+ self MoveR: counterReg A32: counterAddress. "write back"!
- self MoveR: counterReg Aw: counterAddress. "write back"!
Item was changed:
----- Method: StackInterpreter>>returnAs:ThroughCallback:Context: (in category 'callback support') -----
returnAs: returnTypeOop ThroughCallback: vmCallbackContext Context: callbackMethodContext
"callbackMethodContext is an activation of invokeCallback:[stack:registers:jmpbuf:].
Its sender is the VM's state prior to the callback. Reestablish that state (via longjmp),
and mark callbackMethodContext as dead."
<export: true>
<var: #vmCallbackContext type: #'VMCallbackContext *'>
| calloutMethodContext theFP thePage |
<var: #theFP type: #'char *'>
<var: #thePage type: #'StackPage *'>
((self isIntegerObject: returnTypeOop)
and: [self isLiveContext: callbackMethodContext]) ifFalse:
[^false].
calloutMethodContext := self externalInstVar: SenderIndex ofContext: callbackMethodContext.
(self isLiveContext: calloutMethodContext) ifFalse:
[^false].
"We're about to leave this stack page; must save the current frame's instructionPointer."
self push: instructionPointer.
self externalWriteBackHeadFramePointers.
"Mark callbackMethodContext as dead; the common case is that it is the current frame.
We go the extra mile for the debugger."
(self isSingleContext: callbackMethodContext)
ifTrue: [self markContextAsDead: callbackMethodContext]
ifFalse:
[theFP := self frameOfMarriedContext: callbackMethodContext.
framePointer = theFP "common case"
ifTrue:
[(self isBaseFrame: theFP)
ifTrue: [stackPages freeStackPage: stackPage]
ifFalse: "calloutMethodContext is immediately below on the same page. Make it current."
[instructionPointer := (self frameCallerSavedIP: framePointer) asUnsignedInteger.
stackPointer := framePointer + (self frameStackedReceiverOffset: framePointer) + objectMemory wordSize.
framePointer := self frameCallerFP: framePointer.
+ self setMethod: (self frameMethodObject: framePointer).
- self setMethod: (self frameMethod: framePointer).
self restoreCStackStateForCallbackContext: vmCallbackContext.
"N.B. siglongjmp is defines as _longjmp on non-win32 platforms.
This matches the use of _setjmp in ia32abicc.c."
self siglong: vmCallbackContext trampoline jmp: (self integerValueOf: returnTypeOop).
^true]]
ifFalse:
[self externalDivorceFrame: theFP andContext: callbackMethodContext.
self markContextAsDead: callbackMethodContext]].
"Make the calloutMethodContext the active frame. The case where calloutMethodContext
is immediately below callbackMethodContext on the same page is handled above."
(self isStillMarriedContext: calloutMethodContext)
ifTrue:
[theFP := self frameOfMarriedContext: calloutMethodContext.
thePage := stackPages stackPageFor: theFP.
"findSPOf:on: points to the word beneath the instructionPointer, but
there is no instructionPointer on the top frame of the current page."
self assert: thePage ~= stackPage.
stackPointer := (self findSPOf: theFP on: thePage) - objectMemory wordSize.
framePointer := theFP]
ifFalse:
[thePage := self makeBaseFrameFor: calloutMethodContext.
framePointer := thePage headFP.
stackPointer := thePage headSP].
instructionPointer := self popStack.
self setMethod: (objectMemory fetchPointer: MethodIndex ofObject: calloutMethodContext).
self setStackPageAndLimit: thePage.
self restoreCStackStateForCallbackContext: vmCallbackContext.
"N.B. siglongjmp is defines as _longjmp on non-win32 platforms.
This matches the use of _setjmp in ia32abicc.c."
self siglong: vmCallbackContext trampoline jmp: (self integerValueOf: returnTypeOop).
"NOTREACHED"
^true!
More information about the Vm-dev
mailing list