summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGabe Black <gblack@eecs.umich.edu>2010-06-02 12:58:11 -0500
committerGabe Black <gblack@eecs.umich.edu>2010-06-02 12:58:11 -0500
commitbb6fea91da7c5436d26d6b93f22b2dd5cd6287ba (patch)
tree60685658c676826c90f3938c589880ef892a6b97
parentdbee6e0c5406200066b8185fd38fa47dae7cdd2f (diff)
downloadgem5-bb6fea91da7c5436d26d6b93f22b2dd5cd6287ba.tar.xz
ARM: Implement the SRS instruction.
-rw-r--r--src/arch/arm/insts/mem.cc2
-rw-r--r--src/arch/arm/isa/insts/mem.isa32
-rw-r--r--src/arch/arm/isa/insts/str.isa46
3 files changed, 69 insertions, 11 deletions
diff --git a/src/arch/arm/insts/mem.cc b/src/arch/arm/insts/mem.cc
index eb16e42d0..ccac3a25d 100644
--- a/src/arch/arm/insts/mem.cc
+++ b/src/arch/arm/insts/mem.cc
@@ -110,7 +110,7 @@ SrsOp::generateDisassembly(Addr pc, const SymbolTable *symtab) const
ss << "!";
}
ss << ", #";
- switch (mode) {
+ switch (regMode) {
case MODE_USER:
ss << "user";
break;
diff --git a/src/arch/arm/isa/insts/mem.isa b/src/arch/arm/isa/insts/mem.isa
index e17235c81..51805c28e 100644
--- a/src/arch/arm/isa/insts/mem.isa
+++ b/src/arch/arm/isa/insts/mem.isa
@@ -38,9 +38,9 @@
// Authors: Gabe Black
let {{
- def loadStoreBaseWork(name, Name, imm, swp, rfe, codeBlobs, memFlags,
- instFlags, double, strex, base = 'Memory',
- execTemplateBase = ''):
+ def loadStoreBaseWork(name, Name, imm, swp, rfe, srs, codeBlobs,
+ memFlags, instFlags, double, strex,
+ base = 'Memory', execTemplateBase = ''):
# Make sure flags are in lists (convert to lists if not).
memFlags = makeList(memFlags)
instFlags = makeList(instFlags)
@@ -66,6 +66,9 @@ let {{
elif rfe:
declareTemplate = RfeDeclare
constructTemplate = RfeConstructor
+ elif srs:
+ declareTemplate = SrsDeclare
+ constructTemplate = SrsConstructor
elif imm:
if double:
declareTemplate = LoadStoreDImmDeclare
@@ -101,26 +104,35 @@ let {{
"memacc_code": accCode,
"postacc_code": postAccCode,
"predicate_test": predicateTest }
- return loadStoreBaseWork(name, Name, imm, False, False, codeBlobs,
- memFlags, instFlags, double, strex, base,
- execTemplateBase)
+ return loadStoreBaseWork(name, Name, imm, False, False, False,
+ codeBlobs, memFlags, instFlags, double,
+ strex, base, execTemplateBase)
def RfeBase(name, Name, eaCode, accCode, memFlags, instFlags):
codeBlobs = { "ea_code": eaCode,
"memacc_code": accCode,
"predicate_test": predicateTest }
- return loadStoreBaseWork(name, Name, False, False, True, codeBlobs,
- memFlags, instFlags, False, False,
+ return loadStoreBaseWork(name, Name, False, False, True, False,
+ codeBlobs, memFlags, instFlags, False, False,
'RfeOp', 'Load')
+ def SrsBase(name, Name, eaCode, accCode, memFlags, instFlags):
+ codeBlobs = { "ea_code": eaCode,
+ "memacc_code": accCode,
+ "postacc_code": "",
+ "predicate_test": predicateTest }
+ return loadStoreBaseWork(name, Name, False, False, False, True,
+ codeBlobs, memFlags, instFlags, False, False,
+ 'SrsOp', 'Store')
+
def SwapBase(name, Name, eaCode, preAccCode, postAccCode, memFlags,
instFlags):
codeBlobs = { "ea_code": eaCode,
"preacc_code": preAccCode,
"postacc_code": postAccCode,
"predicate_test": predicateTest }
- return loadStoreBaseWork(name, Name, False, True, False, codeBlobs,
- memFlags, instFlags, False, False,
+ return loadStoreBaseWork(name, Name, False, True, False, False,
+ codeBlobs, memFlags, instFlags, False, False,
'Swap', 'Swap')
def memClassName(base, post, add, writeback, \
diff --git a/src/arch/arm/isa/insts/str.isa b/src/arch/arm/isa/insts/str.isa
index f9002a6f7..023ce81ca 100644
--- a/src/arch/arm/isa/insts/str.isa
+++ b/src/arch/arm/isa/insts/str.isa
@@ -116,6 +116,40 @@ let {{
memFlags, [], base, strex=strex,
execTemplateBase = execTemplateBase)
+ def buildSrsStore(mnem, post, add, writeback):
+ name = mnem
+ Name = "SRS_" + storeImmClassName(post, add, writeback, 8)
+
+ offset = 0
+ if post != add:
+ offset += 4
+ if not add:
+ offset -= 8
+
+ eaCode = "EA = SpMode + %d;" % offset
+
+ wbDiff = -8
+ if add:
+ wbDiff = 8
+ accCode = '''
+ CPSR cpsr = Cpsr;
+ Mem.ud = (uint64_t)cSwap(LR.uw, cpsr.e) |
+ ((uint64_t)cSwap(Spsr.uw, cpsr.e) << 32);
+ '''
+ if writeback:
+ accCode += "SpMode = SpMode + %s;\n" % wbDiff
+
+ global header_output, decoder_output, exec_output
+
+ (newHeader,
+ newDecoder,
+ newExec) = SrsBase(name, Name, eaCode, accCode,
+ ["ArmISA::TLB::AlignWord", "ArmISA::TLB::MustBeOne"], [])
+
+ header_output += newHeader
+ decoder_output += newDecoder
+ exec_output += newExec
+
def buildRegStore(mnem, post, add, writeback, \
size=4, sign=False, user=False, strex=False):
name = mnem
@@ -241,6 +275,16 @@ let {{
buildDoubleImmStore(mnem, False, False, False)
buildDoubleRegStore(mnem, False, False, False)
+ def buildSrsStores(mnem):
+ buildSrsStore(mnem, True, True, True)
+ buildSrsStore(mnem, True, True, False)
+ buildSrsStore(mnem, True, False, True)
+ buildSrsStore(mnem, True, False, False)
+ buildSrsStore(mnem, False, True, True)
+ buildSrsStore(mnem, False, True, False)
+ buildSrsStore(mnem, False, False, True)
+ buildSrsStore(mnem, False, False, False)
+
buildStores("str")
buildStores("strt", user=True)
buildStores("strb", size=1)
@@ -248,6 +292,8 @@ let {{
buildStores("strh", size=2)
buildStores("strht", size=2, user=True)
+ buildSrsStores("srs")
+
buildDoubleStores("strd")
buildImmStore("strex", False, True, False, size=4, strex=True)