Skip to content

Commit 6549d43

Browse files
authored
[clr-interp] Fix additional iteration in Copy_Ref implementation on arm64 (#120879)
After a loop iteration is done, the code is subtracting 16, obtaining the current remaining counter. If the remaining counter is bigger than 0 then we do another iteration. This is wrong, because we can only do another 16 byte copy iteration if the remaining counter is bigger or equal to 16. In order to be correct, the code would have to branch to the very beginning of the macro. In case of negative result, we would fallback to 8 byte copy, but, if the result is negative, it means we already overcopied, so this implementation is wrong. The fix makes it such that when we subtract 16 after an iteration, we don't obtain the current remaining counter, rather the potential remaining counter, in case we did another copy iteration. If this counter is positive, then it is safe to do another iteration, if it is negative then we can't copy 16 bytes at a time, fallback to the next case. The PR also removes redundant looping for 8 bytes copy scenario, which can be hit at most once.
1 parent 9bb1d21 commit 6549d43

File tree

2 files changed

+6
-14
lines changed

2 files changed

+6
-14
lines changed

src/coreclr/vm/arm64/asmhelpers.S

Lines changed: 3 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -949,25 +949,21 @@ LEAF_END Load_Stack_Ref, _TEXT
949949

950950

951951
.macro Copy_Ref argReg
952-
cmp x11, #16
952+
subs x11, x11, #16
953953
blt LOCAL_LABEL(CopyBy8\argReg)
954954
LOCAL_LABEL(RefCopyLoop16\argReg):
955955
ldp x13, x14, [\argReg], #16
956956
stp x13, x14, [x9], #16
957957
subs x11, x11, #16
958-
bgt LOCAL_LABEL(RefCopyLoop16\argReg)
959-
beq LOCAL_LABEL(RefCopyDone\argReg)
960-
add x11, x11, #16
958+
bge LOCAL_LABEL(RefCopyLoop16\argReg)
961959
LOCAL_LABEL(CopyBy8\argReg):
960+
add x11, x11, #16
962961
cmp x11, #8
963962
blt LOCAL_LABEL(RefCopyLoop1\argReg)
964-
LOCAL_LABEL(RefCopyLoop8\argReg):
965963
ldr x13, [\argReg], #8
966964
str x13, [x9], #8
967965
subs x11, x11, #8
968-
bgt LOCAL_LABEL(RefCopyLoop8\argReg)
969966
beq LOCAL_LABEL(RefCopyDone\argReg)
970-
add x11, x11, #8
971967
LOCAL_LABEL(RefCopyLoop1\argReg):
972968
ldrb w13, [\argReg], #1
973969
strb w13, [x9], #1

src/coreclr/vm/arm64/asmhelpers.asm

Lines changed: 3 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1300,25 +1300,21 @@ StoreCopyLoop
13001300

13011301
MACRO
13021302
Copy_Ref $argReg
1303-
cmp x11, #16
1303+
subs x11, x11, #16
13041304
blt CopyBy8$argReg
13051305
RefCopyLoop16$argReg
13061306
ldp x13, x14, [$argReg], #16
13071307
stp x13, x14, [x9], #16
13081308
subs x11, x11, #16
1309-
bgt RefCopyLoop16$argReg
1310-
beq RefCopyDone$argReg
1311-
add x11, x11, #16
1309+
bge RefCopyLoop16$argReg
13121310
CopyBy8$argReg
1311+
add x11, x11, #16
13131312
cmp x11, #8
13141313
blt RefCopyLoop1$argReg
1315-
RefCopyLoop8$argReg
13161314
ldr x13, [$argReg], #8
13171315
str x13, [x9], #8
13181316
subs x11, x11, #8
1319-
bgt RefCopyLoop8$argReg
13201317
beq RefCopyDone$argReg
1321-
add x11, x11, #8
13221318
RefCopyLoop1$argReg
13231319
ldrb w13, [$argReg], #1
13241320
strb w13, [x9], #1

0 commit comments

Comments
 (0)