[Vm-dev] VM Maker: Cog-tpr.322.mcz
commits at source.squeak.org
commits at source.squeak.org
Sat May 21 17:54:58 UTC 2016
tim Rowledge uploaded a new version of Cog to project VM Maker:
http://source.squeak.org/VMMaker/Cog-tpr.322.mcz
==================== Summary ====================
Name: Cog-tpr.322
Author: tpr
Time: 21 May 2016, 10:54:50.890085 am
UUID: de0414b6-8d89-4319-9243-f7e4c0db3206
Ancestors: Cog-eem.321
Update ARM simulation of FP code; not complete as yet but mostly there.
=============== Diff against Cog-eem.321 ===============
Item was added:
+ ----- Method: GdbARMAlien>>fpCPSR (in category 'accessing') -----
+ fpCPSR
+ "The VFP cpsr flags are kept as a single word in the Alien structure. Return just the top 4 bits, the actual flags"
+ ^(self unsignedLongAt: 1785) >>28!
Item was added:
+ ----- Method: GdbARMAlien>>handleBasicDoubleArithmetic:at: (in category 'floating-point emulation') -----
+ handleBasicDoubleArithmetic: instr at: pc
+ "Emulate a basic math - add/sub/mul/div - VFP instruction."
+ | rn rd rm vn vm |
+ rn := instr >> 16 bitAnd: 15.
+ rd := instr >> 12 bitAnd: 15.
+ rm := instr bitAnd: 15.
+ vn := Float fromIEEE64BitWord: (self perform: (self registerStateGetters at: rn + 18)). "Assume accesses fp regs"
+ vm := Float fromIEEE64BitWord: (self perform: (self registerStateGetters at: rm + 18)). "Assume accesses fp regs"
+
+ "simplest to match the entire instruction pattern rather than mess around shifting and masking and merging"
+ (instr bitAnd: 16rFF00FF0)
+ caseOf: {
+ [16rE200B00 "FMULD"] ->
+ [| r |
+ r := vn * vm.
+ self perform: (self registerStateSetters at: rd + 18) with: r asIEEE64BitWord].
+ [16rE300B00 "FADDD"] ->
+ [| r |
+ r := vn + vm.
+ self perform: (self registerStateSetters at: rd + 18) with: r asIEEE64BitWord].
+ [16rE300B40 "FSUBD"] ->
+ [| r |
+ r := vn - vm.
+ self perform: (self registerStateSetters at: rd + 18) with: r asIEEE64BitWord].
+ [16rE800B00"FDIVD"] ->
+ [| r |
+ r := vn / vm.
+ self perform: (self registerStateSetters at: rd + 18) with: r asIEEE64BitWord].}
+ otherwise: [self reportPrimitiveFailure].
+ self pc: pc + 4!
Item was added:
+ ----- Method: GdbARMAlien>>handleExtendedDoubleArithmetic:at: (in category 'floating-point emulation') -----
+ handleExtendedDoubleArithmetic: instr at: pc
+ "Emulate an extended math - cmp/sqrt/sitod - VFP instruction."
+ | rn rd rm vn vm vd |
+ rn := instr >> 16 bitAnd: 15.
+ rd := instr >> 12 bitAnd: 15.
+ rm := instr bitAnd: 15.
+ vn := Float fromIEEE64BitWord: (self perform: (self registerStateGetters at: rn + 18)). "Assume accesses fp regs"
+ vm := Float fromIEEE64BitWord: (self perform: (self registerStateGetters at: rm + 18)). "Assume accesses fp regs"
+
+ "simplest to match the entire instruction pattern rather than mess around shifting and masking and merging"
+ (instr bitAnd: 16rFF00FF0)
+ caseOf: {
+ [16rEB80B80 "FCMPD"] ->
+ ["read rd, compare with rm (ignore rn) and set FPSCR NZCV flags. Sigh"
+ vd := Float fromIEEE64BitWord: (self perform: (self registerStateGetters at: rd + 18)).
+ self break].
+ [16rEB80BC0 "FSITOD"] ->
+ [| r |
+ r := vm asFloat.
+ self perform: (self registerStateSetters at: rd + 18) with: r asIEEE64BitWord].
+ [16rEB10BC0 "FSQRTD"] ->
+ [| r |
+ r := vm sqrt.
+ self perform: (self registerStateSetters at: rd + 18) with: r asIEEE64BitWord].
+ }
+ otherwise: [self reportPrimitiveFailure].
+ self pc: pc + 4!
Item was added:
+ ----- Method: GdbARMAlien>>handleFPLoadStore:at: (in category 'floating-point emulation') -----
+ handleFPLoadStore: instr at: pc
+ "Emulate a VFP load/store instruction."
+ | rn rd offset |
+ rn := instr >> 16 bitAnd: 15.
+ rd := instr >> 12 bitAnd: 15.
+ offset := instr bitAnd: 16rFF.
+
+ "examine the U and Lbits"
+ (instr >>20 bitAnd: 16rF)
+ caseOf: {
+ [0"Store neg"] ->
+ [| r addr|
+ addr := (self register: rn) - (offset<<2).
+ r := self perform: (self registerStateGetters at: rd + 18).
+ self unsignedLongLongAt: addr put: r].
+ [1"Load neg"] ->
+ [| r addr|
+ addr := (self register: rn) - (offset<<2).
+ r := self unsignedLongLongAt: addr.
+ self perform: (self registerStateSetters at: rd + 18) with: r ].
+ [8"Store pos"] ->
+ [| r addr|
+ addr := (self register: rn) + (offset<<2).
+ r := self perform: (self registerStateGetters at: rd + 18).
+ self unsignedLongLongAt: addr put: r].
+ [9"Load pos"] ->
+ [| r addr|
+ addr := (self register: rn) + (offset<<2).
+ r := self unsignedLongLongAt: addr.
+ self perform: (self registerStateSetters at: rd + 18) with: r ].}
+ otherwise: [self reportPrimitiveFailure].
+ self pc: pc + 4!
Item was added:
+ ----- Method: GdbARMAlien>>handleFPStatus:at: (in category 'floating-point emulation') -----
+ handleFPStatus: instr at: pc
+ "Emulate transferring the FP status to the ARM CPSR."
+ | fpcpsr |
+ fpcpsr := self fpCPSR.
+ self vflag: (fpcpsr bitAnd: 1).
+ self cflag: ((fpcpsr >>1) bitAnd: 1).
+ self zflag: ((fpcpsr >>2) bitAnd: 1).
+ self nflag: ((fpcpsr >>3) bitAnd: 1).
+ self pc: pc + 4!
Item was changed:
----- Method: GdbARMAlien>>handleFailingFPArithmetic:at: (in category 'error handling') -----
handleFailingFPArithmetic: instr at: pc
+
+ "basic arithmetic"
+ (instr bitAnd: 16rF400FB0) = 16rE000B00 ifTrue:
+ [^self handleBasicDoubleArithmetic: instr at: pc].
+
+ "extension instructions sqrt/cmp/sitod"
+ (instr bitAnd: 16rFF00F70) = 16rEB00B40 ifTrue:
+ [^self handleExtendedDoubleArithmetic: instr at: pc].
+
+ "move ARM reg to coproc reg. "
+ (instr bitAnd: 16rFF00FFF) = 16rE000A10 ifTrue:
+ [^self handleRegToDoubleTransfer: instr at: pc].
+
+ "move FPSCR reg to ARM CPSR"
+ (instr bitAnd: 16rFFFFFFF) = 16rEF1FA10 ifTrue:
+ [^self handleFPStatus: instr at: pc].
+
+ "load and store ops. All doubles; we only use FLDD & FSTD"
+ (instr bitAnd: 16rF600F00) = 16rD000B00 ifTrue:
+ [^self handleFPLoadStore: instr at: pc].
+
+
- | oneRegTransferMask twoRegTransferMask |
- oneRegTransferMask := 16rF000F00.
- (instr bitAnd: oneRegTransferMask) = 16rE000B00 ifTrue:
- [^self handleOneRegTransferDoubleArithmetic: instr at: pc].
- (instr bitAnd: oneRegTransferMask) = 16rE000A00 ifTrue:
- [^self handleOneRegTransferSingleArithmetic: instr at: pc].
- twoRegTransferMask := 16rFE00FC0.
- (instr bitAnd: twoRegTransferMask) = 16rC400B00 ifTrue:
- [^self handleTwoRegTransferDoubleArithmetic: instr at: pc].
- (instr bitAnd: twoRegTransferMask) = 16rC400A00 ifTrue:
- [^self handleTwoRegTransferSingleArithmetic: instr at: pc].
^self reportPrimitiveFailure!
Item was added:
+ ----- Method: GdbARMAlien>>handleRegToDoubleTransfer:at: (in category 'floating-point emulation') -----
+ handleRegToDoubleTransfer: instr at: pc
+ "Emulate an ARM to VFP instruction."
+ | rn rd vn |
+ rn := (instr >> 16 bitAnd: 15) << 1 bitOr: (instr >>6 bitAnd: 1).
+ rd := instr >> 12 bitAnd: 15.
+ vn := self register: rn.
+
+ self perform: (self registerStateSetters at: rd + 18) with: vn.
+ self pc: pc + 4!
Item was changed:
----- Method: GdbARMAlien>>instructionIsAnyFPArithmetic: (in category 'testing') -----
instructionIsAnyFPArithmetic: instr
+ "Identify VFP instructions.
+ See C3.1 - C3.4 in the ARM ARM v5 DDI01001."
+ | cp isFP |
+
+ "All FP instructions are coprocessor instructions on coproc 10 or 11"
+ cp := instr>>8 bitAnd: 16rF.
+ isFP := cp = 10 or:[cp = 11].
+ (isFP and: [(instr>>25 bitAnd: 7) = 6]) ifTrue: [^true].
+ (isFP and: [(instr>>24 bitAnd: 16rF) = 16rE]) ifTrue: [^true].
+
+ "nope"
- "Identify single register transfer and double register transfer VFP instructions.
- See C3.3 & C3.4 in the ARM ARM."
- | oneRegTransferMask twoRegTransferMask |
- oneRegTransferMask := 16rF000F00.
- (instr bitAnd: oneRegTransferMask) = 16rE000A00 ifTrue:
- [^true].
- (instr bitAnd: oneRegTransferMask) = 16rE000B00 ifTrue:
- [^true].
- twoRegTransferMask := 16rFE00FC0.
- (instr bitAnd: twoRegTransferMask) = 16rC400A00 ifTrue:
- [^true].
- (instr bitAnd: twoRegTransferMask) = 16rC400B00 ifTrue:
- [^true].
^false!
More information about the Vm-dev
mailing list