[Atomics] Add dmb/dsb/isb instructions to ARM
This is not currently implemented in the simulator, just the assembler and disassembler. BUG=v8:4614 LOG=y Review URL: https://codereview.chromium.org/1699173003 Cr-Commit-Position: refs/heads/master@{#34093}
This commit is contained in:
parent
44823c3c69
commit
2869071588
@ -2145,6 +2145,21 @@ void Assembler::svc(uint32_t imm24, Condition cond) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void Assembler::dmb(BarrierOption option) {
|
||||||
|
emit(kSpecialCondition | 0x57ff*B12 | 5*B4 | option);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void Assembler::dsb(BarrierOption option) {
|
||||||
|
emit(kSpecialCondition | 0x57ff*B12 | 4*B4 | option);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void Assembler::isb(BarrierOption option) {
|
||||||
|
emit(kSpecialCondition | 0x57ff*B12 | 6*B4 | option);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
// Coprocessor instructions.
|
// Coprocessor instructions.
|
||||||
void Assembler::cdp(Coprocessor coproc,
|
void Assembler::cdp(Coprocessor coproc,
|
||||||
int opcode_1,
|
int opcode_1,
|
||||||
|
@ -990,6 +990,11 @@ class Assembler : public AssemblerBase {
|
|||||||
void bkpt(uint32_t imm16); // v5 and above
|
void bkpt(uint32_t imm16); // v5 and above
|
||||||
void svc(uint32_t imm24, Condition cond = al);
|
void svc(uint32_t imm24, Condition cond = al);
|
||||||
|
|
||||||
|
// Synchronization instructions
|
||||||
|
void dmb(BarrierOption option);
|
||||||
|
void dsb(BarrierOption option);
|
||||||
|
void isb(BarrierOption option);
|
||||||
|
|
||||||
// Coprocessor instructions
|
// Coprocessor instructions
|
||||||
|
|
||||||
void cdp(Coprocessor coproc, int opcode_1,
|
void cdp(Coprocessor coproc, int opcode_1,
|
||||||
|
@ -219,6 +219,22 @@ enum {
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
enum BarrierOption {
|
||||||
|
OSHLD = 0x1,
|
||||||
|
OSHST = 0x2,
|
||||||
|
OSH = 0x3,
|
||||||
|
NSHLD = 0x5,
|
||||||
|
NSHST = 0x6,
|
||||||
|
NSH = 0x7,
|
||||||
|
ISHLD = 0x9,
|
||||||
|
ISHST = 0xa,
|
||||||
|
ISH = 0xb,
|
||||||
|
LD = 0xd,
|
||||||
|
ST = 0xe,
|
||||||
|
SY = 0xf,
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
// Addressing modes and instruction variants.
|
// Addressing modes and instruction variants.
|
||||||
|
|
||||||
|
@ -1695,6 +1695,12 @@ void Decoder::DecodeType6CoprocessorIns(Instruction* instr) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static const char* const barrier_option_names[] = {
|
||||||
|
"invalid", "oshld", "oshst", "osh", "invalid", "nshld", "nshst", "nsh",
|
||||||
|
"invalid", "ishld", "ishst", "ish", "invalid", "ld", "st", "sy",
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
void Decoder::DecodeSpecialCondition(Instruction* instr) {
|
void Decoder::DecodeSpecialCondition(Instruction* instr) {
|
||||||
switch (instr->SpecialValue()) {
|
switch (instr->SpecialValue()) {
|
||||||
case 5:
|
case 5:
|
||||||
@ -1771,6 +1777,24 @@ void Decoder::DecodeSpecialCondition(Instruction* instr) {
|
|||||||
out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_,
|
out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_,
|
||||||
"pld [r%d, #+%d]", Rn, offset);
|
"pld [r%d, #+%d]", Rn, offset);
|
||||||
}
|
}
|
||||||
|
} else if (instr->SpecialValue() == 0xA && instr->Bits(22, 20) == 7) {
|
||||||
|
int option = instr->Bits(3, 0);
|
||||||
|
switch (instr->Bits(7, 4)) {
|
||||||
|
case 4:
|
||||||
|
out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_,
|
||||||
|
"dsb %s", barrier_option_names[option]);
|
||||||
|
break;
|
||||||
|
case 5:
|
||||||
|
out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_,
|
||||||
|
"dmb %s", barrier_option_names[option]);
|
||||||
|
break;
|
||||||
|
case 6:
|
||||||
|
out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_,
|
||||||
|
"isb %s", barrier_option_names[option]);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
Unknown(instr);
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
Unknown(instr);
|
Unknown(instr);
|
||||||
}
|
}
|
||||||
|
@ -3912,6 +3912,9 @@ void Simulator::DecodeSpecialCondition(Instruction* instr) {
|
|||||||
case 0xB:
|
case 0xB:
|
||||||
if ((instr->Bits(22, 20) == 5) && (instr->Bits(15, 12) == 0xf)) {
|
if ((instr->Bits(22, 20) == 5) && (instr->Bits(15, 12) == 0xf)) {
|
||||||
// pld: ignore instruction.
|
// pld: ignore instruction.
|
||||||
|
} else if (instr->SpecialValue() == 0xA && instr->Bits(22, 20) == 7) {
|
||||||
|
// dsb, dmb, isb: ignore instruction for now.
|
||||||
|
// TODO(binji): implement
|
||||||
} else {
|
} else {
|
||||||
UNIMPLEMENTED();
|
UNIMPLEMENTED();
|
||||||
}
|
}
|
||||||
|
@ -1031,3 +1031,45 @@ TEST(LoadStore) {
|
|||||||
|
|
||||||
VERIFY_RUN();
|
VERIFY_RUN();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
TEST(Barrier) {
|
||||||
|
SET_UP();
|
||||||
|
|
||||||
|
if (CpuFeatures::IsSupported(ARMv7)) {
|
||||||
|
CpuFeatureScope scope(&assm, ARMv7);
|
||||||
|
|
||||||
|
COMPARE(dmb(OSHLD),
|
||||||
|
"f57ff051 dmb oshld");
|
||||||
|
COMPARE(dmb(OSHST),
|
||||||
|
"f57ff052 dmb oshst");
|
||||||
|
COMPARE(dmb(OSH),
|
||||||
|
"f57ff053 dmb osh");
|
||||||
|
COMPARE(dmb(NSHLD),
|
||||||
|
"f57ff055 dmb nshld");
|
||||||
|
COMPARE(dmb(NSHST),
|
||||||
|
"f57ff056 dmb nshst");
|
||||||
|
COMPARE(dmb(NSH),
|
||||||
|
"f57ff057 dmb nsh");
|
||||||
|
COMPARE(dmb(ISHLD),
|
||||||
|
"f57ff059 dmb ishld");
|
||||||
|
COMPARE(dmb(ISHST),
|
||||||
|
"f57ff05a dmb ishst");
|
||||||
|
COMPARE(dmb(ISH),
|
||||||
|
"f57ff05b dmb ish");
|
||||||
|
COMPARE(dmb(LD),
|
||||||
|
"f57ff05d dmb ld");
|
||||||
|
COMPARE(dmb(ST),
|
||||||
|
"f57ff05e dmb st");
|
||||||
|
COMPARE(dmb(SY),
|
||||||
|
"f57ff05f dmb sy");
|
||||||
|
|
||||||
|
COMPARE(dsb(ISH),
|
||||||
|
"f57ff04b dsb ish");
|
||||||
|
|
||||||
|
COMPARE(isb(ISH),
|
||||||
|
"f57ff06b isb ish");
|
||||||
|
}
|
||||||
|
|
||||||
|
VERIFY_RUN();
|
||||||
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user