mirror of
https://github.com/corda/corda.git
synced 2025-01-09 06:23:04 +00:00
use register for indexing if constant offset is too large (or too small)
Immediate indexes on ARM must be no more than 12 bits, so we must use a temporary register for values which don't fit.
This commit is contained in:
parent
70fcbc2788
commit
7978102cb6
26
src/arm.cpp
26
src/arm.cpp
@ -866,7 +866,7 @@ store(Context* c, unsigned size, Assembler::Register* src,
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (release) c->client->releaseTemporary(normalized);
|
if (release) c->client->releaseTemporary(normalized);
|
||||||
} else {
|
} else if (size == 8 or abs(offset) == (abs(offset) & 0xFFF)) {
|
||||||
switch (size) {
|
switch (size) {
|
||||||
case 1:
|
case 1:
|
||||||
emit(c, strbi(src->low, base, offset));
|
emit(c, strbi(src->low, base, offset));
|
||||||
@ -888,6 +888,15 @@ store(Context* c, unsigned size, Assembler::Register* src,
|
|||||||
|
|
||||||
default: abort(c);
|
default: abort(c);
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
Assembler::Register tmp(c->client->acquireTemporary());
|
||||||
|
ResolvedPromise offsetPromise(offset);
|
||||||
|
Assembler::Constant offsetConstant(&offsetPromise);
|
||||||
|
moveCR(c, BytesPerWord, &offsetConstant, BytesPerWord, &tmp);
|
||||||
|
|
||||||
|
store(c, size, src, base, 0, tmp.low, 1, false);
|
||||||
|
|
||||||
|
c->client->releaseTemporary(tmp.low);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -962,7 +971,9 @@ load(Context* c, unsigned srcSize, int base, int offset, int index,
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (release) c->client->releaseTemporary(normalized);
|
if (release) c->client->releaseTemporary(normalized);
|
||||||
} else {
|
} else if ((srcSize == 8 and dstSize == 8)
|
||||||
|
or abs(offset) == (abs(offset) & 0xFFF))
|
||||||
|
{
|
||||||
switch (srcSize) {
|
switch (srcSize) {
|
||||||
case 1:
|
case 1:
|
||||||
if (signExtend) {
|
if (signExtend) {
|
||||||
@ -996,6 +1007,15 @@ load(Context* c, unsigned srcSize, int base, int offset, int index,
|
|||||||
|
|
||||||
default: abort(c);
|
default: abort(c);
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
Assembler::Register tmp(c->client->acquireTemporary());
|
||||||
|
ResolvedPromise offsetPromise(offset);
|
||||||
|
Assembler::Constant offsetConstant(&offsetPromise);
|
||||||
|
moveCR(c, BytesPerWord, &offsetConstant, BytesPerWord, &tmp);
|
||||||
|
|
||||||
|
load(c, srcSize, base, 0, tmp.low, 1, dstSize, dst, false, signExtend);
|
||||||
|
|
||||||
|
c->client->releaseTemporary(tmp.low);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1115,6 +1135,8 @@ compareRR(Context* c, unsigned aSize UNUSED, Assembler::Register* a,
|
|||||||
unsigned bSize UNUSED, Assembler::Register* b)
|
unsigned bSize UNUSED, Assembler::Register* b)
|
||||||
{
|
{
|
||||||
assert(c, aSize == 4 and bSize == 4);
|
assert(c, aSize == 4 and bSize == 4);
|
||||||
|
assert(c, b->low != a->low);
|
||||||
|
|
||||||
emit(c, cmp(b->low, a->low));
|
emit(c, cmp(b->low, a->low));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -54,5 +54,11 @@ public class Arrays {
|
|||||||
p = false;
|
p = false;
|
||||||
expect(array[1] == array[p ? 0 : 1]);
|
expect(array[1] == array[p ? 0 : 1]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
{ int[] array = new int[1024];
|
||||||
|
array[1023] = -1;
|
||||||
|
expect(array[1023] == -1);
|
||||||
|
expect(array[1022] == 0);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user