summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRekai Gonzalez Alberquilla <Rekai.GonzalezAlberquilla@arm.com>2015-10-09 14:50:54 -0500
committerRekai Gonzalez Alberquilla <Rekai.GonzalezAlberquilla@arm.com>2015-10-09 14:50:54 -0500
commitd3d159749a0a6c3b69a9181fab8db34b6ba0f7a1 (patch)
tree477a11d57b4428685247f1ad4bb5863b948f9c99
parent7624fc1fb461f1dd127763521d85f63e81617d71 (diff)
downloadgem5-d3d159749a0a6c3b69a9181fab8db34b6ba0f7a1.tar.xz
isa: Add parameter to pick different decoder inside ISA
The decoder is responsible for splitting instructions in micro operations (uops). Given that different micro architectures may split operations differently, this patch allows to specify which micro architecture each isa implements, so different cores in the system can split instructions differently, also decoupling uop splitting (microArch) from ISA (Arch). This is done making the decodification calls templates that receive a type 'DecoderFlavour' that maps the name of the operation to the class that implements it. This way there is only one selection point (converting the command line enum to the appropriate DecodeFeatures object). In addition, there is no explicit code replication: template instantiation hides that, and the compiler should be able to resolve a number of things at compile-time.
-rw-r--r--src/arch/alpha/decoder.hh3
-rw-r--r--src/arch/arm/ArmISA.py6
-rw-r--r--src/arch/arm/decoder.cc8
-rw-r--r--src/arch/arm/decoder.hh6
-rw-r--r--src/arch/arm/isa.cc1
-rw-r--r--src/arch/arm/isa.hh6
-rw-r--r--src/arch/arm/isa/formats/aarch64.isa29
-rw-r--r--src/arch/arm/isa/formats/neon64.isa38
-rw-r--r--src/arch/arm/isa/includes.isa1
-rw-r--r--src/arch/arm/isa/insts/neon64.isa19
-rw-r--r--src/arch/mips/decoder.hh3
-rw-r--r--src/arch/power/decoder.hh3
-rw-r--r--src/arch/sparc/decoder.hh3
-rw-r--r--src/arch/x86/decoder.hh3
-rw-r--r--src/cpu/o3/fetch_impl.hh3
15 files changed, 97 insertions, 35 deletions
diff --git a/src/arch/alpha/decoder.hh b/src/arch/alpha/decoder.hh
index d33722867..522359c28 100644
--- a/src/arch/alpha/decoder.hh
+++ b/src/arch/alpha/decoder.hh
@@ -39,6 +39,7 @@
namespace AlphaISA
{
+class ISA;
class Decoder
{
protected:
@@ -47,7 +48,7 @@ class Decoder
bool instDone;
public:
- Decoder() : instDone(false)
+ Decoder(ISA* isa = nullptr) : instDone(false)
{}
void
diff --git a/src/arch/arm/ArmISA.py b/src/arch/arm/ArmISA.py
index f5c56cfd5..7ef8afd88 100644
--- a/src/arch/arm/ArmISA.py
+++ b/src/arch/arm/ArmISA.py
@@ -1,4 +1,4 @@
-# Copyright (c) 2012-2013 ARM Limited
+# Copyright (c) 2012-2013, 2015 ARM Limited
# All rights reserved.
#
# The license below extends only to copyright in the software and shall
@@ -42,6 +42,9 @@ from m5.SimObject import SimObject
from ArmPMU import ArmPMU
+# Enum for DecoderFlavour
+class DecoderFlavour(Enum): vals = ['Generic']
+
class ArmISA(SimObject):
type = 'ArmISA'
cxx_class = 'ArmISA::ISA'
@@ -50,6 +53,7 @@ class ArmISA(SimObject):
system = Param.System(Parent.any, "System this ISA object belongs to")
pmu = Param.ArmPMU(NULL, "Performance Monitoring Unit")
+ decoderFlavour = Param.DecoderFlavour('Generic', "Decoder flavour specification")
midr = Param.UInt32(0x410fc0f0, "MIDR value")
diff --git a/src/arch/arm/decoder.cc b/src/arch/arm/decoder.cc
index 23fa89a3f..1502b061f 100644
--- a/src/arch/arm/decoder.cc
+++ b/src/arch/arm/decoder.cc
@@ -41,6 +41,8 @@
*/
#include "arch/arm/decoder.hh"
+
+#include "arch/arm/isa.hh"
#include "arch/arm/isa_traits.hh"
#include "arch/arm/utility.hh"
#include "base/trace.hh"
@@ -51,8 +53,10 @@ namespace ArmISA
GenericISA::BasicDecodeCache Decoder::defaultCache;
-Decoder::Decoder()
- : data(0), fpscrLen(0), fpscrStride(0)
+Decoder::Decoder(ISA* isa)
+ : data(0), fpscrLen(0), fpscrStride(0), decoderFlavour(isa
+ ? isa->decoderFlavour()
+ : Enums::Generic)
{
reset();
}
diff --git a/src/arch/arm/decoder.hh b/src/arch/arm/decoder.hh
index 757b6d683..f8748ab5e 100644
--- a/src/arch/arm/decoder.hh
+++ b/src/arch/arm/decoder.hh
@@ -50,10 +50,12 @@
#include "arch/generic/decode_cache.hh"
#include "base/types.hh"
#include "cpu/static_inst.hh"
+#include "enums/DecoderFlavour.hh"
namespace ArmISA
{
+class ISA;
class Decoder
{
protected:
@@ -70,6 +72,8 @@ class Decoder
int fpscrLen;
int fpscrStride;
+ Enums::DecoderFlavour decoderFlavour;
+
/// A cache of decoded instruction objects.
static GenericISA::BasicDecodeCache defaultCache;
@@ -86,7 +90,7 @@ class Decoder
void consumeBytes(int numBytes);
public: // Decoder API
- Decoder();
+ Decoder(ISA* isa = nullptr);
/** Reset the decoders internal state. */
void reset();
diff --git a/src/arch/arm/isa.cc b/src/arch/arm/isa.cc
index f90b8a2df..6f66e5ae1 100644
--- a/src/arch/arm/isa.cc
+++ b/src/arch/arm/isa.cc
@@ -127,6 +127,7 @@ const struct ISA::MiscRegInitializerEntry
ISA::ISA(Params *p)
: SimObject(p),
system(NULL),
+ _decoderFlavour(p->decoderFlavour),
pmu(p->pmu),
lookUpMiscReg(NUM_MISCREGS, {0,0})
{
diff --git a/src/arch/arm/isa.hh b/src/arch/arm/isa.hh
index a07017c17..ab5c72e6a 100644
--- a/src/arch/arm/isa.hh
+++ b/src/arch/arm/isa.hh
@@ -50,6 +50,7 @@
#include "arch/arm/types.hh"
#include "debug/Checkpoint.hh"
#include "sim/sim_object.hh"
+#include "enums/DecoderFlavour.hh"
struct ArmISAParams;
struct DummyArmISADeviceParams;
@@ -132,6 +133,9 @@ namespace ArmISA
// Parent system
ArmSystem *system;
+ // Micro Architecture
+ const Enums::DecoderFlavour _decoderFlavour;
+
/** Dummy device for to handle non-existing ISA devices */
DummyISADevice dummyDevice;
@@ -429,6 +433,8 @@ namespace ArmISA
void startup(ThreadContext *tc) {}
+ Enums::DecoderFlavour decoderFlavour() const { return _decoderFlavour; }
+
/// Explicitly import the otherwise hidden startup
using SimObject::startup;
diff --git a/src/arch/arm/isa/formats/aarch64.isa b/src/arch/arm/isa/formats/aarch64.isa
index b5a4dfa21..2d94aff51 100644
--- a/src/arch/arm/isa/formats/aarch64.isa
+++ b/src/arch/arm/isa/formats/aarch64.isa
@@ -1,4 +1,4 @@
-// Copyright (c) 2011-2014 ARM Limited
+// Copyright (c) 2011-2015 ARM Limited
// All rights reserved
//
// The license below extends only to copyright in the software and shall
@@ -46,8 +46,10 @@ namespace Aarch64
StaticInstPtr decodeLoadsStores(ExtMachInst machInst);
StaticInstPtr decodeDataProcReg(ExtMachInst machInst);
+ template <typename DecoderFeatures>
StaticInstPtr decodeFpAdvSIMD(ExtMachInst machInst);
StaticInstPtr decodeFp(ExtMachInst machInst);
+ template <typename DecoderFeatures>
StaticInstPtr decodeAdvSIMD(ExtMachInst machInst);
StaticInstPtr decodeAdvSIMDScalar(ExtMachInst machInst);
@@ -1278,12 +1280,13 @@ namespace Aarch64
output decoder {{
namespace Aarch64
{
+ template <typename DecoderFeatures>
StaticInstPtr
decodeAdvSIMD(ExtMachInst machInst)
{
if (bits(machInst, 24) == 1) {
if (bits(machInst, 10) == 0) {
- return decodeNeonIndexedElem(machInst);
+ return decodeNeonIndexedElem<DecoderFeatures>(machInst);
} else if (bits(machInst, 23) == 1) {
return new Unknown64(machInst);
} else {
@@ -1295,7 +1298,7 @@ namespace Aarch64
}
} else if (bits(machInst, 21) == 1) {
if (bits(machInst, 10) == 1) {
- return decodeNeon3Same(machInst);
+ return decodeNeon3Same<DecoderFeatures>(machInst);
} else if (bits(machInst, 11) == 0) {
return decodeNeon3Diff(machInst);
} else if (bits(machInst, 20, 17) == 0x0) {
@@ -1957,13 +1960,14 @@ namespace Aarch64
output decoder {{
namespace Aarch64
{
+ template <typename DecoderFeatures>
StaticInstPtr
decodeFpAdvSIMD(ExtMachInst machInst)
{
if (bits(machInst, 28) == 0) {
if (bits(machInst, 31) == 0) {
- return decodeAdvSIMD(machInst);
+ return decodeAdvSIMD<DecoderFeatures>(machInst);
} else {
return new Unknown64(machInst);
}
@@ -1978,6 +1982,18 @@ namespace Aarch64
}
}};
+let {{
+ decoder_output ='''
+namespace Aarch64
+{'''
+ for decoderFlavour, type_dict in decoders.iteritems():
+ decoder_output +='''
+template StaticInstPtr decodeFpAdvSIMD<%(df)sDecoder>(ExtMachInst machInst);
+''' % { "df" : decoderFlavour }
+ decoder_output +='''
+}'''
+}};
+
output decoder {{
namespace Aarch64
{
@@ -2041,7 +2057,10 @@ def format Aarch64() {{
return decodeGem5Ops(machInst);
} else {
// bit 27:25=111
- return decodeFpAdvSIMD(machInst);
+ switch(decoderFlavour){
+ default:
+ return decodeFpAdvSIMD<GenericDecoder>(machInst);
+ }
}
}
'''
diff --git a/src/arch/arm/isa/formats/neon64.isa b/src/arch/arm/isa/formats/neon64.isa
index 72bbd0c60..e0a913a6b 100644
--- a/src/arch/arm/isa/formats/neon64.isa
+++ b/src/arch/arm/isa/formats/neon64.isa
@@ -40,51 +40,54 @@ output header {{
namespace Aarch64
{
// AdvSIMD three same
+ template <typename DecoderFeatures>
StaticInstPtr decodeNeon3Same(ExtMachInst machInst);
// AdvSIMD three different
- StaticInstPtr decodeNeon3Diff(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeon3Diff(ExtMachInst machInst);
// AdvSIMD two-reg misc
- StaticInstPtr decodeNeon2RegMisc(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeon2RegMisc(ExtMachInst machInst);
// AdvSIMD across lanes
- StaticInstPtr decodeNeonAcrossLanes(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeonAcrossLanes(ExtMachInst machInst);
// AdvSIMD copy
- StaticInstPtr decodeNeonCopy(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeonCopy(ExtMachInst machInst);
// AdvSIMD vector x indexed element
+ template <typename DecoderFeatures>
StaticInstPtr decodeNeonIndexedElem(ExtMachInst machInst);
// AdvSIMD modified immediate
- StaticInstPtr decodeNeonModImm(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeonModImm(ExtMachInst machInst);
// AdvSIMD shift by immediate
- StaticInstPtr decodeNeonShiftByImm(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeonShiftByImm(ExtMachInst machInst);
// AdvSIMD TBL/TBX
- StaticInstPtr decodeNeonTblTbx(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeonTblTbx(ExtMachInst machInst);
// AdvSIMD ZIP/UZP/TRN
- StaticInstPtr decodeNeonZipUzpTrn(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeonZipUzpTrn(ExtMachInst machInst);
// AdvSIMD EXT
- StaticInstPtr decodeNeonExt(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeonExt(ExtMachInst machInst);
// AdvSIMD scalar three same
- StaticInstPtr decodeNeonSc3Same(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeonSc3Same(ExtMachInst machInst);
// AdvSIMD scalar three different
- StaticInstPtr decodeNeonSc3Diff(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeonSc3Diff(ExtMachInst machInst);
// AdvSIMD scalar two-reg misc
- StaticInstPtr decodeNeonSc2RegMisc(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeonSc2RegMisc(ExtMachInst machInst);
// AdvSIMD scalar pairwise
- StaticInstPtr decodeNeonScPwise(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeonScPwise(ExtMachInst machInst);
// AdvSIMD scalar copy
- StaticInstPtr decodeNeonScCopy(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeonScCopy(ExtMachInst machInst);
// AdvSIMD scalar x indexed element
- StaticInstPtr decodeNeonScIndexedElem(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeonScIndexedElem(ExtMachInst machInst);
// AdvSIMD scalar shift by immediate
- StaticInstPtr decodeNeonScShiftByImm(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeonScShiftByImm(ExtMachInst machInst);
// AdvSIMD load/store
- StaticInstPtr decodeNeonMem(ExtMachInst machInst);
+ inline StaticInstPtr decodeNeonMem(ExtMachInst machInst);
}
}};
output decoder {{
namespace Aarch64
{
+ template <typename DecoderFeatures>
StaticInstPtr
decodeNeon3Same(ExtMachInst machInst)
{
@@ -1267,6 +1270,7 @@ namespace Aarch64
}
}
+ template <typename DecoderFeatures>
StaticInstPtr
decodeNeonIndexedElem(ExtMachInst machInst)
{
diff --git a/src/arch/arm/isa/includes.isa b/src/arch/arm/isa/includes.isa
index 8f44e7e86..4fa032f55 100644
--- a/src/arch/arm/isa/includes.isa
+++ b/src/arch/arm/isa/includes.isa
@@ -67,6 +67,7 @@ output header {{
#include "arch/arm/isa_traits.hh"
#include "mem/packet.hh"
#include "sim/faults.hh"
+#include "enums/DecoderFlavour.hh"
}};
output decoder {{
diff --git a/src/arch/arm/isa/insts/neon64.isa b/src/arch/arm/isa/insts/neon64.isa
index f6565efe5..697ea80e2 100644
--- a/src/arch/arm/isa/insts/neon64.isa
+++ b/src/arch/arm/isa/insts/neon64.isa
@@ -1,6 +1,6 @@
// -*- mode: c++ -*-
-// Copyright (c) 2012-2013 ARM Limited
+// Copyright (c) 2012-2013, 2015 ARM Limited
// All rights reserved
//
// The license below extends only to copyright in the software and shall
@@ -42,6 +42,7 @@ let {{
header_output = ""
exec_output = ""
+ decoders = { 'Generic' : {} }
# FP types (FP operations always work with unsigned representations)
floatTypes = ("uint32_t", "uint64_t")
@@ -49,9 +50,9 @@ let {{
def threeEqualRegInstX(name, Name, opClass, types, rCount, op,
readDest=False, pairwise=False, scalar=False,
- byElem=False):
+ byElem=False, decoder='Generic'):
assert (not pairwise) or ((not byElem) and (not scalar))
- global header_output, exec_output
+ global header_output, exec_output, decoders
eWalkCode = simd64EnabledCheckCode + '''
RegVect srcReg1, destReg;
'''
@@ -3356,4 +3357,16 @@ let {{
threeRegScrambleInstX("zip2", "Zip2QX", "SimdAluOp", unsignedTypes, 4,
zipCode % "eCount / 2")
+ for decoderFlavour, type_dict in decoders.iteritems():
+ header_output += '''
+ class %(decoder_flavour)sDecoder {
+ public:
+ ''' % { "decoder_flavour" : decoderFlavour }
+ for type,name in type_dict.iteritems():
+ header_output += '''
+ template<typename Elem> using %(type)s = %(new_name)s<Elem>;''' % {
+ "type" : type, "new_name" : name
+ }
+ header_output += '''
+ };'''
}};
diff --git a/src/arch/mips/decoder.hh b/src/arch/mips/decoder.hh
index a3a68ad07..59e040658 100644
--- a/src/arch/mips/decoder.hh
+++ b/src/arch/mips/decoder.hh
@@ -40,6 +40,7 @@
namespace MipsISA
{
+class ISA;
class Decoder
{
protected:
@@ -48,7 +49,7 @@ class Decoder
bool instDone;
public:
- Decoder() : instDone(false)
+ Decoder(ISA* isa = nullptr) : instDone(false)
{}
void
diff --git a/src/arch/power/decoder.hh b/src/arch/power/decoder.hh
index a70802ced..cc086adc5 100644
--- a/src/arch/power/decoder.hh
+++ b/src/arch/power/decoder.hh
@@ -38,6 +38,7 @@
namespace PowerISA
{
+class ISA;
class Decoder
{
protected:
@@ -46,7 +47,7 @@ class Decoder
bool instDone;
public:
- Decoder() : instDone(false)
+ Decoder(ISA* isa = nullptr) : instDone(false)
{
}
diff --git a/src/arch/sparc/decoder.hh b/src/arch/sparc/decoder.hh
index b87ee682e..897d112dc 100644
--- a/src/arch/sparc/decoder.hh
+++ b/src/arch/sparc/decoder.hh
@@ -39,6 +39,7 @@
namespace SparcISA
{
+class ISA;
class Decoder
{
protected:
@@ -48,7 +49,7 @@ class Decoder
MiscReg asi;
public:
- Decoder() : instDone(false), asi(0)
+ Decoder(ISA* isa = nullptr) : instDone(false), asi(0)
{}
void process() {}
diff --git a/src/arch/x86/decoder.hh b/src/arch/x86/decoder.hh
index 6cd0c6199..d42751d21 100644
--- a/src/arch/x86/decoder.hh
+++ b/src/arch/x86/decoder.hh
@@ -47,6 +47,7 @@
namespace X86ISA
{
+class ISA;
class Decoder
{
private:
@@ -230,7 +231,7 @@ class Decoder
static InstCacheMap instCacheMap;
public:
- Decoder() : basePC(0), origPC(0), offset(0),
+ Decoder(ISA* isa = nullptr) : basePC(0), origPC(0), offset(0),
outOfBytes(true), instDone(false),
state(ResetState)
{
diff --git a/src/cpu/o3/fetch_impl.hh b/src/cpu/o3/fetch_impl.hh
index 1d0cfd137..cb123afd2 100644
--- a/src/cpu/o3/fetch_impl.hh
+++ b/src/cpu/o3/fetch_impl.hh
@@ -73,6 +73,7 @@
#include "sim/eventq.hh"
#include "sim/full_system.hh"
#include "sim/system.hh"
+#include "cpu/o3/isa_specific.hh"
using namespace std;
@@ -151,7 +152,7 @@ DefaultFetch<Impl>::DefaultFetch(O3CPU *_cpu, DerivO3CPUParams *params)
branchPred = params->branchPred;
for (ThreadID tid = 0; tid < numThreads; tid++) {
- decoder[tid] = new TheISA::Decoder;
+ decoder[tid] = new TheISA::Decoder(params->isa[tid]);
// Create space to buffer the cache line data,
// which may not hold the entire cache line.
fetchBuffer[tid] = new uint8_t[fetchBufferSize];