A64: Implement STLRB, STLRH, STLR, LDARB, LDARH, LDAR
This commit is contained in:
parent
5a65313236
commit
b02b861242
4 changed files with 91 additions and 58 deletions
|
@ -82,6 +82,7 @@ add_library(dynarmic
|
||||||
frontend/A64/translate/impl/floating_point_data_processing_two_register.cpp
|
frontend/A64/translate/impl/floating_point_data_processing_two_register.cpp
|
||||||
frontend/A64/translate/impl/impl.cpp
|
frontend/A64/translate/impl/impl.cpp
|
||||||
frontend/A64/translate/impl/impl.h
|
frontend/A64/translate/impl/impl.h
|
||||||
|
frontend/A64/translate/impl/load_store_exclusive.cpp
|
||||||
frontend/A64/translate/impl/load_store_load_literal.cpp
|
frontend/A64/translate/impl/load_store_load_literal.cpp
|
||||||
frontend/A64/translate/impl/load_store_multiple_structures.cpp
|
frontend/A64/translate/impl/load_store_multiple_structures.cpp
|
||||||
frontend/A64/translate/impl/load_store_register_immediate.cpp
|
frontend/A64/translate/impl/load_store_register_immediate.cpp
|
||||||
|
|
|
@ -124,38 +124,22 @@ INST(LDx_mult_2, "LDx (multiple structures)", "0Q001
|
||||||
//INST(LD4R_2, "LD4R", "0Q001101111mmmmm1110zznnnnnttttt")
|
//INST(LD4R_2, "LD4R", "0Q001101111mmmmm1110zznnnnnttttt")
|
||||||
|
|
||||||
// Loads and stores - Load/Store Exclusive
|
// Loads and stores - Load/Store Exclusive
|
||||||
//INST(STXRB, "STXRB", "00001000000sssss011111nnnnnttttt")
|
//INST(STXR, "STXRB, STXRH, STXR", "zz001000000sssss011111nnnnnttttt")
|
||||||
//INST(STLXRB, "STLXRB", "00001000000sssss111111nnnnnttttt")
|
//INST(STLXR, "STLXRB, STLXRH, STLXR", "zz001000000sssss111111nnnnnttttt")
|
||||||
//INST(CASP, "CASP, CASPA, CASPAL, CASPL", "0z0010000L1sssssp11111nnnnnttttt")
|
|
||||||
//INST(LDXRB, "LDXRB", "0000100001011111011111nnnnnttttt")
|
|
||||||
//INST(LDAXRB, "LDAXRB", "0000100001011111111111nnnnnttttt")
|
|
||||||
//INST(STLLRB, "STLLRB", "0000100010011111011111nnnnnttttt")
|
|
||||||
//INST(STLRB, "STLRB", "0000100010011111111111nnnnnttttt")
|
|
||||||
//INST(CASB, "CASB, CASAB, CASALB, CASLB", "000010001L1sssssp11111nnnnnttttt")
|
|
||||||
//INST(LDLARB, "LDLARB", "0000100011011111011111nnnnnttttt")
|
|
||||||
//INST(LDARB, "LDARB", "0000100011011111111111nnnnnttttt")
|
|
||||||
//INST(STXRH, "STXRH", "01001000000sssss011111nnnnnttttt")
|
|
||||||
//INST(STLXRH, "STLXRH", "01001000000sssss111111nnnnnttttt")
|
|
||||||
//INST(LDXRH, "LDXRH", "0100100001011111011111nnnnnttttt")
|
|
||||||
//INST(LDAXRH, "LDAXRH", "0100100001011111111111nnnnnttttt")
|
|
||||||
//INST(STLLRH, "STLLRH", "0100100010011111011111nnnnnttttt")
|
|
||||||
//INST(STLRH, "STLRH", "0100100010011111111111nnnnnttttt")
|
|
||||||
//INST(CASH, "CASH, CASAH, CASALH, CASLH", "010010001L1sssssp11111nnnnnttttt")
|
|
||||||
//INST(LDLARH, "LDLARH", "0100100011011111011111nnnnnttttt")
|
|
||||||
//INST(LDARH, "LDARH", "0100100011011111111111nnnnnttttt")
|
|
||||||
//INST(STXR, "STXR", "1-001000000sssss011111nnnnnttttt")
|
|
||||||
//INST(STLXR, "STLXR", "1-001000000sssss111111nnnnnttttt")
|
|
||||||
//INST(STXP, "STXP", "1z001000001sssss0uuuuunnnnnttttt")
|
//INST(STXP, "STXP", "1z001000001sssss0uuuuunnnnnttttt")
|
||||||
//INST(STLXP, "STLXP", "1z001000001sssss1uuuuunnnnnttttt")
|
//INST(STLXP, "STLXP", "1z001000001sssss1uuuuunnnnnttttt")
|
||||||
//INST(LDXR, "LDXR", "1-00100001011111011111nnnnnttttt")
|
//INST(LDXR, "LDXRB, LDXRH, LDXR", "zz00100001011111011111nnnnnttttt")
|
||||||
//INST(LDAXR, "LDAXR", "1-00100001011111111111nnnnnttttt")
|
//INST(LDAXRB, "LDAXRB", "zz00100001011111111111nnnnnttttt")
|
||||||
//INST(LDXP, "LDXP", "1z001000011111110uuuuunnnnnttttt")
|
//INST(LDXP, "LDXP", "1z001000011111110uuuuunnnnnttttt")
|
||||||
//INST(LDAXP, "LDAXP", "1z001000011111111uuuuunnnnnttttt")
|
//INST(LDAXP, "LDAXP", "1z001000011111111uuuuunnnnnttttt")
|
||||||
//INST(STLLR, "STLLR", "1-00100010011111011111nnnnnttttt")
|
//INST(STLLR, "STLLRB, STLLRH, STLLR", "zz00100010011111011111nnnnnttttt")
|
||||||
//INST(STLR, "STLR", "1-00100010011111111111nnnnnttttt")
|
INST(STLR, "STLRB, STLRH, STLR", "zz00100010011111111111nnnnnttttt")
|
||||||
//INST(CAS, "CAS, CASA, CASAL, CASL", "1-0010001L1sssssp11111nnnnnttttt")
|
//INST(LDLAR, "LDLARB, LDLARH, LDLAR", "zz00100011011111011111nnnnnttttt")
|
||||||
//INST(LDLAR, "LDLAR", "1-00100011011111011111nnnnnttttt")
|
INST(LDAR, "LDARB, LDARH, LDAR", "zz00100011011111111111nnnnnttttt")
|
||||||
//INST(LDAR, "LDAR", "1-00100011011111111111nnnnnttttt")
|
//INST(CASP, "CASP, CASPA, CASPAL, CASPL", "0z0010000L1sssssp11111nnnnnttttt") // ARMv8.1
|
||||||
|
//INST(CASB, "CASB, CASAB, CASALB, CASLB", "000010001L1sssssp11111nnnnnttttt") // ARMv8.1
|
||||||
|
//INST(CASH, "CASH, CASAH, CASALH, CASLH", "010010001L1sssssp11111nnnnnttttt") // ARMv8.1
|
||||||
|
//INST(CAS, "CAS, CASA, CASAL, CASL", "1z0010001L1sssssp11111nnnnnttttt") // ARMv8.1
|
||||||
|
|
||||||
// Loads and stores - Load register (literal)
|
// Loads and stores - Load register (literal)
|
||||||
INST(LDR_lit_gen, "LDR (literal)", "0z011000iiiiiiiiiiiiiiiiiiittttt")
|
INST(LDR_lit_gen, "LDR (literal)", "0z011000iiiiiiiiiiiiiiiiiiittttt")
|
||||||
|
|
|
@ -16,7 +16,7 @@
|
||||||
namespace Dynarmic::A64 {
|
namespace Dynarmic::A64 {
|
||||||
|
|
||||||
enum class AccType {
|
enum class AccType {
|
||||||
NORMAL, VEC, STREAM, VECSTREAM, ATOMIC, ORDERED, UNPRIV, IFETCH, PTW, DC, IC, AT,
|
NORMAL, VEC, STREAM, VECSTREAM, ATOMIC, ORDERED, ORDEREDRW, LIMITEDORDERED, UNPRIV, IFETCH, PTW, DC, IC, DCZVA, AT,
|
||||||
};
|
};
|
||||||
|
|
||||||
enum class MemOp {
|
enum class MemOp {
|
||||||
|
@ -187,38 +187,22 @@ struct TranslatorVisitor final {
|
||||||
bool LD4R_2(bool Q, Reg Rm, Imm<2> size, Reg Rn, Vec Vt);
|
bool LD4R_2(bool Q, Reg Rm, Imm<2> size, Reg Rn, Vec Vt);
|
||||||
|
|
||||||
// Loads and stores - Load/Store Exclusive
|
// Loads and stores - Load/Store Exclusive
|
||||||
bool STXRB(Reg Rs, Reg Rn, Reg Rt);
|
bool STXR(Imm<2> size, Reg Rs, Reg Rn, Reg Rt);
|
||||||
bool STLXRB(Reg Rs, Reg Rn, Reg Rt);
|
bool STLXR(Imm<2> size, Reg Rs, Reg Rn, Reg Rt);
|
||||||
|
bool STXP(Imm<1> size, Reg Rs, Reg Rt2, Reg Rn, Reg Rt);
|
||||||
|
bool STLXP(Imm<1> size, Reg Rs, Reg Rt2, Reg Rn, Reg Rt);
|
||||||
|
bool LDXR(Imm<2> size, Reg Rn, Reg Rt);
|
||||||
|
bool LDAXRB(Imm<2> size, Reg Rn, Reg Rt);
|
||||||
|
bool LDXP(Imm<1> size, Reg Rt2, Reg Rn, Reg Rt);
|
||||||
|
bool LDAXP(Imm<1> size, Reg Rt2, Reg Rn, Reg Rt);
|
||||||
|
bool STLLR(Imm<2> size, Reg Rn, Reg Rt);
|
||||||
|
bool STLR(Imm<2> size, Reg Rn, Reg Rt);
|
||||||
|
bool LDLAR(Imm<2> size, Reg Rn, Reg Rt);
|
||||||
|
bool LDAR(Imm<2> size, Reg Rn, Reg Rt);
|
||||||
bool CASP(bool sz, bool L, Reg Rs, bool o0, Reg Rn, Reg Rt);
|
bool CASP(bool sz, bool L, Reg Rs, bool o0, Reg Rn, Reg Rt);
|
||||||
bool LDXRB(Reg Rn, Reg Rt);
|
|
||||||
bool LDAXRB(Reg Rn, Reg Rt);
|
|
||||||
bool STLLRB(Reg Rn, Reg Rt);
|
|
||||||
bool STLRB(Reg Rn, Reg Rt);
|
|
||||||
bool CASB(bool L, Reg Rs, bool o0, Reg Rn, Reg Rt);
|
bool CASB(bool L, Reg Rs, bool o0, Reg Rn, Reg Rt);
|
||||||
bool LDLARB(Reg Rn, Reg Rt);
|
|
||||||
bool LDARB(Reg Rn, Reg Rt);
|
|
||||||
bool STXRH(Reg Rs, Reg Rn, Reg Rt);
|
|
||||||
bool STLXRH(Reg Rs, Reg Rn, Reg Rt);
|
|
||||||
bool LDXRH(Reg Rn, Reg Rt);
|
|
||||||
bool LDAXRH(Reg Rn, Reg Rt);
|
|
||||||
bool STLLRH(Reg Rn, Reg Rt);
|
|
||||||
bool STLRH(Reg Rn, Reg Rt);
|
|
||||||
bool CASH(bool L, Reg Rs, bool o0, Reg Rn, Reg Rt);
|
bool CASH(bool L, Reg Rs, bool o0, Reg Rn, Reg Rt);
|
||||||
bool LDLARH(Reg Rn, Reg Rt);
|
bool CAS(bool sz, bool L, Reg Rs, bool o0, Reg Rn, Reg Rt);
|
||||||
bool LDARH(Reg Rn, Reg Rt);
|
|
||||||
bool STXR(Reg Rs, Reg Rn, Reg Rt);
|
|
||||||
bool STLXR(Reg Rs, Reg Rn, Reg Rt);
|
|
||||||
bool STXP(bool sz, Reg Rs, Reg Rt2, Reg Rn, Reg Rt);
|
|
||||||
bool STLXP(bool sz, Reg Rs, Reg Rt2, Reg Rn, Reg Rt);
|
|
||||||
bool LDXR(Reg Rn, Reg Rt);
|
|
||||||
bool LDAXR(Reg Rn, Reg Rt);
|
|
||||||
bool LDXP(bool sz, Reg Rt2, Reg Rn, Reg Rt);
|
|
||||||
bool LDAXP(bool sz, Reg Rt2, Reg Rn, Reg Rt);
|
|
||||||
bool STLLR(Reg Rn, Reg Rt);
|
|
||||||
bool STLR(Reg Rn, Reg Rt);
|
|
||||||
bool CAS(bool L, Reg Rs, bool o0, Reg Rn, Reg Rt);
|
|
||||||
bool LDLAR(Reg Rn, Reg Rt);
|
|
||||||
bool LDAR(Reg Rn, Reg Rt);
|
|
||||||
|
|
||||||
// Loads and stores - Load register (literal)
|
// Loads and stores - Load register (literal)
|
||||||
bool LDR_lit_gen(bool opc_0, Imm<19> imm19, Reg Rt);
|
bool LDR_lit_gen(bool opc_0, Imm<19> imm19, Reg Rt);
|
||||||
|
|
64
src/frontend/A64/translate/impl/load_store_exclusive.cpp
Normal file
64
src/frontend/A64/translate/impl/load_store_exclusive.cpp
Normal file
|
@ -0,0 +1,64 @@
|
||||||
|
/* This file is part of the dynarmic project.
|
||||||
|
* Copyright (c) 2018 MerryMage
|
||||||
|
* This software may be used and distributed according to the terms of the GNU
|
||||||
|
* General Public License version 2 or any later version.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "frontend/A64/translate/impl/impl.h"
|
||||||
|
|
||||||
|
namespace Dynarmic::A64 {
|
||||||
|
|
||||||
|
static bool OrderedSharedDecodeAndOperation(TranslatorVisitor& tv, size_t size, bool L, bool o0, Reg Rn, Reg Rt) {
|
||||||
|
// Shared Decode
|
||||||
|
|
||||||
|
const AccType acctype = !o0 ? AccType::LIMITEDORDERED : AccType::ORDERED;
|
||||||
|
const MemOp memop = L ? MemOp::LOAD : MemOp::STORE;
|
||||||
|
const size_t elsize = 8 << size;
|
||||||
|
const size_t regsize = elsize == 64 ? 64 : 32;
|
||||||
|
const size_t datasize = elsize;
|
||||||
|
|
||||||
|
// Operation
|
||||||
|
|
||||||
|
const size_t dbytes = datasize / 8;
|
||||||
|
|
||||||
|
IR::U64 address;
|
||||||
|
if (Rn == Reg::SP) {
|
||||||
|
// TODO: Check SP Alignment
|
||||||
|
address = tv.SP(64);
|
||||||
|
} else {
|
||||||
|
address = tv.X(64, Rn);
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (memop) {
|
||||||
|
case MemOp::STORE: {
|
||||||
|
IR::UAny data = tv.X(datasize, Rt);
|
||||||
|
tv.Mem(address, dbytes, acctype, data);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case MemOp::LOAD: {
|
||||||
|
IR::UAny data = tv.Mem(address, dbytes, acctype);
|
||||||
|
tv.X(regsize, Rt, tv.ZeroExtend(data, regsize));
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
UNREACHABLE();
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool TranslatorVisitor::STLR(Imm<2> sz, Reg Rn, Reg Rt) {
|
||||||
|
const size_t size = sz.ZeroExtend<size_t>();
|
||||||
|
const bool L = 0;
|
||||||
|
const bool o0 = 1;
|
||||||
|
return OrderedSharedDecodeAndOperation(*this, size, L, o0, Rn, Rt);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool TranslatorVisitor::LDAR(Imm<2> sz, Reg Rn, Reg Rt) {
|
||||||
|
const size_t size = sz.ZeroExtend<size_t>();
|
||||||
|
const bool L = 1;
|
||||||
|
const bool o0 = 1;
|
||||||
|
return OrderedSharedDecodeAndOperation(*this, size, L, o0, Rn, Rt);
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace Dynarmic::A64
|
Loading…
Reference in a new issue