summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/SConscript1
-rw-r--r--src/arch/sparc/isa/base.isa32
-rw-r--r--src/arch/sparc/isa/decoder.isa198
-rw-r--r--src/arch/sparc/isa/formats/basic.isa6
-rw-r--r--src/arch/sparc/isa/formats/branch.isa109
-rw-r--r--src/arch/sparc/isa/formats/integerop.isa145
-rw-r--r--src/arch/sparc/isa/formats/priv.isa20
-rw-r--r--src/arch/sparc/isa/includes.isa6
-rw-r--r--src/arch/sparc/isa/operands.isa44
-rw-r--r--src/arch/sparc/regfile.hh29
-rw-r--r--src/cpu/SConscript3
-rw-r--r--src/cpu/simple/timing.cc43
-rw-r--r--src/cpu/simple/timing.hh48
-rw-r--r--src/dev/io_device.cc54
-rw-r--r--src/dev/io_device.hh59
-rw-r--r--src/mem/physical.cc63
-rw-r--r--src/mem/physical.hh21
-rw-r--r--src/mem/tport.cc82
-rw-r--r--src/mem/tport.hh134
-rw-r--r--src/python/m5/objects/Device.py2
-rw-r--r--src/python/m5/objects/O3CPU.py144
-rw-r--r--src/python/m5/objects/Pci.py2
22 files changed, 734 insertions, 511 deletions
diff --git a/src/SConscript b/src/SConscript
index 10faf5aaf..812089a00 100644
--- a/src/SConscript
+++ b/src/SConscript
@@ -98,6 +98,7 @@ base_sources = Split('''
mem/packet.cc
mem/physical.cc
mem/port.cc
+ mem/tport.cc
mem/cache/base_cache.cc
mem/cache/cache.cc
diff --git a/src/arch/sparc/isa/base.isa b/src/arch/sparc/isa/base.isa
index 02f7cf61a..b518265aa 100644
--- a/src/arch/sparc/isa/base.isa
+++ b/src/arch/sparc/isa/base.isa
@@ -86,6 +86,11 @@ output header {{
const SymbolTable *symtab) const;
void printReg(std::ostream &os, int reg) const;
+ void printSrcReg(std::ostream &os, int reg) const;
+ void printDestReg(std::ostream &os, int reg) const;
+
+ void printRegArray(std::ostream &os,
+ const RegIndex indexArray[], int num) const;
};
bool passesCondition(uint32_t codes, uint32_t condition);
@@ -150,6 +155,33 @@ output decoder {{
ccprintf(os, "\t%s ", mnemonic);
}
+ void SparcStaticInst::printRegArray(std::ostream &os,
+ const RegIndex indexArray[], int num) const
+ {
+ if(num <= 0)
+ return;
+ printReg(os, indexArray[0]);
+ for(int x = 1; x < num; x++)
+ {
+ os << ", ";
+ printReg(os, indexArray[x]);
+ }
+ }
+
+ void
+ SparcStaticInst::printSrcReg(std::ostream &os, int reg) const
+ {
+ if(_numSrcRegs > reg)
+ printReg(os, _srcRegIdx[reg]);
+ }
+
+ void
+ SparcStaticInst::printDestReg(std::ostream &os, int reg) const
+ {
+ if(_numDestRegs > reg)
+ printReg(os, _destRegIdx[reg]);
+ }
+
void
SparcStaticInst::printReg(std::ostream &os, int reg) const
{
diff --git a/src/arch/sparc/isa/decoder.isa b/src/arch/sparc/isa/decoder.isa
index fa8832920..274d51fc5 100644
--- a/src/arch/sparc/isa/decoder.isa
+++ b/src/arch/sparc/isa/decoder.isa
@@ -39,30 +39,30 @@ decode OP default Unknown::unknown()
{
//Throw an illegal instruction acception
0x0: Trap::illtrap({{fault = new IllegalInstruction;}});
- 0x1: decode BPCC
+ format BranchN
{
- format Branch19
+ 0x1: decode BPCC
{
- 0x0: bpcci({{
+ 0x0: bpcci(19, {{
if(passesCondition(Ccr<3:0>, COND2))
NNPC = xc->readPC() + disp;
else
handle_annul
}});
- 0x2: bpccx({{
+ 0x2: bpccx(19, {{
if(passesCondition(Ccr<7:4>, COND2))
NNPC = xc->readPC() + disp;
else
handle_annul
}});
}
+ 0x2: bicc(22, {{
+ if(passesCondition(Ccr<3:0>, COND2))
+ NNPC = xc->readPC() + disp;
+ else
+ handle_annul
+ }});
}
- 0x2: Branch22::bicc({{
- if(passesCondition(Ccr<3:0>, COND2))
- NNPC = xc->readPC() + disp;
- else
- handle_annul
- }});
0x3: decode RCOND2
{
format BranchSplit
@@ -110,7 +110,7 @@ decode OP default Unknown::unknown()
0x5: Trap::fbpfcc({{fault = new FpDisabled;}});
0x6: Trap::fbfcc({{fault = new FpDisabled;}});
}
- 0x1: Branch30::call({{
+ 0x1: BranchN::call(30, {{
R15 = xc->readPC();
NNPC = R15 + disp;
}});
@@ -134,7 +134,7 @@ decode OP default Unknown::unknown()
Rd.sdw = Rs1.sdw<31:0> * Rs2_or_imm13<31:0>;
Y = Rd.sdw;
}});
- 0x0C: subc({{Rd.sdw = Rs1.sdw + (~Rs2_or_imm13) + 1 + Ccr<0:0>}});
+ 0x0C: subc({{Rd.sdw = Rs1.sdw + (~Rs2_or_imm13) + 1 - Ccr<0:0>}});
0x0D: udivx({{
if(Rs2_or_imm13 == 0) fault = new DivisionByZero;
else Rd.udw = Rs1.udw / Rs2_or_imm13;
@@ -208,7 +208,7 @@ decode OP default Unknown::unknown()
0x1C: subccc({{
int64_t resTemp, val2 = Rs2_or_imm13;
int64_t carryin = Ccr<0:0>;
- Rd = resTemp = Rs1 + ~(val2 + carryin) + 1;}},
+ Rd = resTemp = Rs1 + ~val2 + 1 - carryin;}},
{{(~((Rs1<31:0> + (~(val2 + carryin))<31:0> + 1))<32:>)}},
{{Rs1<31:> != val2<31:> && Rs1<31:> != resTemp<31:>}},
{{(~((Rs1<63:1> + (~(val2 + carryin))<63:1>) + (Rs1<0:> + (~(val2+carryin))<0:> + 1)<63:1>))<63:>}},
@@ -272,8 +272,9 @@ decode OP default Unknown::unknown()
);
0x22: taddcctv({{
int64_t resTemp, val2 = Rs2_or_imm13;
- Rd = resTemp = Rs1 + val2;
- int32_t overflow = Rs1<1:0> || val2<1:0> || (Rs1<31:> == val2<31:> && val2<31:> != resTemp<31:>);
+ Rd = Rs1 + val2;
+ int32_t overflow = Rs1<1:0> || val2<1:0> ||
+ (Rs1<31:> == val2<31:> && val2<31:> != Rd<31:>);
if(overflow) fault = new TagOverflow;}},
{{((Rs1 & 0xFFFFFFFF + val2 & 0xFFFFFFFF) >> 31)}},
{{overflow}},
@@ -322,15 +323,21 @@ decode OP default Unknown::unknown()
0x1: srax({{Rd = Rs1.sdw >> (I ? SHCNT64 : Rs2<5:0>);}});
}
// XXX might want a format rdipr thing here
- 0x28: rdasr({{
+ 0x28: decode RS1 {
+ 0xF: decode I {
+ 0x0: Nop::stbar({{/*stuff*/}});
+ 0x1: Nop::membar({{/*stuff*/}});
+ }
+ default: rdasr({{
Rd = xc->readMiscRegWithEffect(RS1 + AsrStart, fault);
- }});
- 0x29: rdhpr({{
+ }});
+ }
+ 0x29: HPriv::rdhpr({{
// XXX Need to protect with format that traps non-priv/priv
// access
Rd = xc->readMiscRegWithEffect(RS1 + HprStart, fault);
}});
- 0x2A: rdpr({{
+ 0x2A: Priv::rdpr({{
// XXX Need to protect with format that traps non-priv
// access
Rd = xc->readMiscRegWithEffect(RS1 + PrStart, fault);
@@ -397,18 +404,152 @@ decode OP default Unknown::unknown()
0x0: BasicOperate::saved({{/*Boogy Boogy*/}});
0x1: BasicOperate::restored({{/*Boogy Boogy*/}});
}
- 0x32: wrpr({{
+ 0x32: Priv::wrpr({{
// XXX Need to protect with format that traps non-priv
// access
- xc->setMiscRegWithEffect(RD + PrStart, Rs1 ^ Rs2_or_imm13);
+ fault = xc->setMiscRegWithEffect(RD + PrStart, Rs1 ^ Rs2_or_imm13);
}});
- 0x33: wrhpr({{
+ 0x33: HPriv::wrhpr({{
// XXX Need to protect with format that traps non-priv/priv
// access
- xc->setMiscRegWithEffect(RD + HprStart, Rs1 ^ Rs2_or_imm13);
+ fault = xc->setMiscRegWithEffect(RD + HprStart, Rs1 ^ Rs2_or_imm13);
}});
- 0x34: Trap::fpop1({{fault = new FpDisabled;}});
+ 0x34: decode OPF{
+ 0x01: Trap::fmovs({{fault = new FpDisabled;}});
+ 0x02: Trap::fmovd({{fault = new FpDisabled;}});
+ 0x03: Trap::fmovq({{fault = new FpDisabled;}});
+ 0x05: Trap::fnegs({{fault = new FpDisabled;}});
+ 0x06: Trap::fnegd({{fault = new FpDisabled;}});
+ 0x07: Trap::fnegq({{fault = new FpDisabled;}});
+ 0x09: Trap::fabss({{fault = new FpDisabled;}});
+ 0x0A: Trap::fabsd({{fault = new FpDisabled;}});
+ 0x0B: Trap::fabsq({{fault = new FpDisabled;}});
+ 0x29: Trap::fsqrts({{fault = new FpDisabled;}});
+ 0x2A: Trap::fsqrtd({{fault = new FpDisabled;}});
+ 0x2B: Trap::fsqrtq({{fault = new FpDisabled;}});
+ 0x41: Trap::fadds({{fault = new FpDisabled;}});
+ 0x42: BasicOperate::faddd({{Frd = Frs1 + Frs2;}});
+ 0x43: Trap::faddq({{fault = new FpDisabled;}});
+ 0x45: Trap::fsubs({{fault = new FpDisabled;}});
+ 0x46: Trap::fsubd({{fault = new FpDisabled;}});
+ 0x47: Trap::fsubq({{fault = new FpDisabled;}});
+ 0x49: Trap::fmuls({{fault = new FpDisabled;}});
+ 0x4A: BasicOperate::fmuld({{Frd = Frs1.sf * Frs2.sf;}});
+ 0x4B: Trap::fmulq({{fault = new FpDisabled;}});
+ 0x4D: Trap::fdivs({{fault = new FpDisabled;}});
+ 0x4E: Trap::fdivd({{fault = new FpDisabled;}});
+ 0x4F: Trap::fdivq({{fault = new FpDisabled;}});
+ 0x69: Trap::fsmuld({{fault = new FpDisabled;}});
+ 0x6E: Trap::fdmulq({{fault = new FpDisabled;}});
+ 0x81: Trap::fstox({{fault = new FpDisabled;}});
+ 0x82: Trap::fdtox({{fault = new FpDisabled;}});
+ 0x83: Trap::fqtox({{fault = new FpDisabled;}});
+ 0x84: Trap::fxtos({{fault = new FpDisabled;}});
+ 0x88: Trap::fxtod({{fault = new FpDisabled;}});
+ 0x8C: Trap::fxtoq({{fault = new FpDisabled;}});
+ 0xC4: Trap::fitos({{fault = new FpDisabled;}});
+ 0xC6: Trap::fdtos({{fault = new FpDisabled;}});
+ 0xC7: Trap::fqtos({{fault = new FpDisabled;}});
+ 0xC8: Trap::fitod({{fault = new FpDisabled;}});
+ 0xC9: Trap::fstod({{fault = new FpDisabled;}});
+ 0xCB: Trap::fqtod({{fault = new FpDisabled;}});
+ 0xCC: Trap::fitoq({{fault = new FpDisabled;}});
+ 0xCD: Trap::fstoq({{fault = new FpDisabled;}});
+ 0xCE: Trap::fdtoq({{fault = new FpDisabled;}});
+ 0xD1: Trap::fstoi({{fault = new FpDisabled;}});
+ 0xD2: Trap::fdtoi({{fault = new FpDisabled;}});
+ 0xD3: Trap::fqtoi({{fault = new FpDisabled;}});
+ default: Trap::fpop1({{fault = new FpDisabled;}});
+ }
0x35: Trap::fpop2({{fault = new FpDisabled;}});
+ //This used to be just impdep1, but now it's a whole bunch
+ //of instructions
+ 0x36: decode OPF{
+ 0x00: Trap::edge8({{fault = new IllegalInstruction;}});
+ 0x01: Trap::edge8n({{fault = new IllegalInstruction;}});
+ 0x02: Trap::edge8l({{fault = new IllegalInstruction;}});
+ 0x03: Trap::edge8ln({{fault = new IllegalInstruction;}});
+ 0x04: Trap::edge16({{fault = new IllegalInstruction;}});
+ 0x05: Trap::edge16n({{fault = new IllegalInstruction;}});
+ 0x06: Trap::edge16l({{fault = new IllegalInstruction;}});
+ 0x07: Trap::edge16ln({{fault = new IllegalInstruction;}});
+ 0x08: Trap::edge32({{fault = new IllegalInstruction;}});
+ 0x09: Trap::edge32n({{fault = new IllegalInstruction;}});
+ 0x0A: Trap::edge32l({{fault = new IllegalInstruction;}});
+ 0x0B: Trap::edge32ln({{fault = new IllegalInstruction;}});
+ 0x10: Trap::array8({{fault = new IllegalInstruction;}});
+ 0x12: Trap::array16({{fault = new IllegalInstruction;}});
+ 0x14: Trap::array32({{fault = new IllegalInstruction;}});
+ 0x18: Trap::alignaddress({{fault = new IllegalInstruction;}});
+ 0x19: Trap::bmask({{fault = new IllegalInstruction;}});
+ 0x1A: Trap::alignaddresslittle({{fault = new IllegalInstruction;}});
+ 0x20: Trap::fcmple16({{fault = new IllegalInstruction;}});
+ 0x22: Trap::fcmpne16({{fault = new IllegalInstruction;}});
+ 0x24: Trap::fcmple32({{fault = new IllegalInstruction;}});
+ 0x26: Trap::fcmpne32({{fault = new IllegalInstruction;}});
+ 0x28: Trap::fcmpgt16({{fault = new IllegalInstruction;}});
+ 0x2A: Trap::fcmpeq16({{fault = new IllegalInstruction;}});
+ 0x2C: Trap::fcmpgt32({{fault = new IllegalInstruction;}});
+ 0x2E: Trap::fcmpeq32({{fault = new IllegalInstruction;}});
+ 0x31: Trap::fmul8x16({{fault = new IllegalInstruction;}});
+ 0x33: Trap::fmul8x16au({{fault = new IllegalInstruction;}});
+ 0x35: Trap::fmul8x16al({{fault = new IllegalInstruction;}});
+ 0x36: Trap::fmul8sux16({{fault = new IllegalInstruction;}});
+ 0x37: Trap::fmul8ulx16({{fault = new IllegalInstruction;}});
+ 0x38: Trap::fmuld8sux16({{fault = new IllegalInstruction;}});
+ 0x39: Trap::fmuld8ulx16({{fault = new IllegalInstruction;}});
+ 0x3A: Trap::fpack32({{fault = new IllegalInstruction;}});
+ 0x3B: Trap::fpack16({{fault = new IllegalInstruction;}});
+ 0x3D: Trap::fpackfix({{fault = new IllegalInstruction;}});
+ 0x3E: Trap::pdist({{fault = new IllegalInstruction;}});
+ 0x48: Trap::faligndata({{fault = new IllegalInstruction;}});
+ 0x4B: Trap::fpmerge({{fault = new IllegalInstruction;}});
+ 0x4C: Trap::bshuffle({{fault = new IllegalInstruction;}});
+ 0x4D: Trap::fexpand({{fault = new IllegalInstruction;}});
+ 0x50: Trap::fpadd16({{fault = new IllegalInstruction;}});
+ 0x51: Trap::fpadd16s({{fault = new IllegalInstruction;}});
+ 0x52: Trap::fpadd32({{fault = new IllegalInstruction;}});
+ 0x53: Trap::fpadd32s({{fault = new IllegalInstruction;}});
+ 0x54: Trap::fpsub16({{fault = new IllegalInstruction;}});
+ 0x55: Trap::fpsub16s({{fault = new IllegalInstruction;}});
+ 0x56: Trap::fpsub32({{fault = new IllegalInstruction;}});
+ 0x57: Trap::fpsub32s({{fault = new IllegalInstruction;}});
+ 0x60: BasicOperate::fzero({{Frd = 0;}});
+ 0x61: Trap::fzeros({{fault = new IllegalInstruction;}});
+ 0x62: Trap::fnor({{fault = new IllegalInstruction;}});
+ 0x63: Trap::fnors({{fault = new IllegalInstruction;}});
+ 0x64: Trap::fandnot2({{fault = new IllegalInstruction;}});
+ 0x65: Trap::fandnot2s({{fault = new IllegalInstruction;}});
+ 0x66: Trap::fnot2({{fault = new IllegalInstruction;}});
+ 0x67: Trap::fnot2s({{fault = new IllegalInstruction;}});
+ 0x68: Trap::fandnot1({{fault = new IllegalInstruction;}});
+ 0x69: Trap::fandnot1s({{fault = new IllegalInstruction;}});
+ 0x6A: Trap::fnot1({{fault = new IllegalInstruction;}});
+ 0x6B: Trap::fnot1s({{fault = new IllegalInstruction;}});
+ 0x6C: Trap::fxor({{fault = new IllegalInstruction;}});
+ 0x6D: Trap::fxors({{fault = new IllegalInstruction;}});
+ 0x6E: Trap::fnand({{fault = new IllegalInstruction;}});
+ 0x6F: Trap::fnands({{fault = new IllegalInstruction;}});
+ 0x70: Trap::fand({{fault = new IllegalInstruction;}});
+ 0x71: Trap::fands({{fault = new IllegalInstruction;}});
+ 0x72: Trap::fxnor({{fault = new IllegalInstruction;}});
+ 0x73: Trap::fxnors({{fault = new IllegalInstruction;}});
+ 0x74: Trap::fsrc1({{fault = new IllegalInstruction;}});
+ 0x75: Trap::fsrc1s({{fault = new IllegalInstruction;}});
+ 0x76: Trap::fornot2({{fault = new IllegalInstruction;}});
+ 0x77: Trap::fornot2s({{fault = new IllegalInstruction;}});
+ 0x78: Trap::fsrc2({{fault = new IllegalInstruction;}});
+ 0x79: Trap::fsrc2s({{fault = new IllegalInstruction;}});
+ 0x7A: Trap::fornot1({{fault = new IllegalInstruction;}});
+ 0x7B: Trap::fornot1s({{fault = new IllegalInstruction;}});
+ 0x7C: Trap::for({{fault = new IllegalInstruction;}});
+ 0x7D: Trap::fors({{fault = new IllegalInstruction;}});
+ 0x7E: Trap::fone({{fault = new IllegalInstruction;}});
+ 0x7F: Trap::fones({{fault = new IllegalInstruction;}});
+ 0x80: Trap::shutdown({{fault = new IllegalInstruction;}});
+ 0x81: Trap::siam({{fault = new IllegalInstruction;}});
+ }
+ 0x37: Trap::impdep2({{fault = new IllegalInstruction;}});
0x38: Branch::jmpl({{
Addr target = Rs1 + Rs2_or_imm13;
if(target & 0x3)
@@ -549,7 +690,7 @@ decode OP default Unknown::unknown()
NNPC = Tnpc + 4;
Tl = Tl - 1;
}});
- 0x1: BasicOperate::retry({{
+ 0x1: Priv::retry({{
if(Tl == 0)
return new IllegalInstruction;
Cwp = Tstate<4:0>;
@@ -645,12 +786,13 @@ decode OP default Unknown::unknown()
0x26: stqf({{fault = new FpDisabled;}});
0x27: stdf({{fault = new FpDisabled;}});
0x2D: Nop::prefetch({{ }});
- 0x30: ldfa({{return new FpDisabled;}});
+ 0x30: ldfa({{fault = new FpDisabled;}});
0x32: ldqfa({{fault = new FpDisabled;}});
0x33: lddfa({{fault = new FpDisabled;}});
0x34: stfa({{fault = new FpDisabled;}});
- 0x35: stqfa({{fault = new FpDisabled;}});
- 0x36: stdfa({{fault = new FpDisabled;}});
+ 0x36: stqfa({{fault = new FpDisabled;}});
+ //XXX need to work in the ASI thing
+ 0x37: Store::stdfa({{Mem = ((uint64_t)Frd);}}, {{64}});
0x3C: Cas::casa({{
uint64_t val = Mem.uw;
if(Rs2.uw == val)
diff --git a/src/arch/sparc/isa/formats/basic.isa b/src/arch/sparc/isa/formats/basic.isa
index 60432cb6b..0a47a7ffe 100644
--- a/src/arch/sparc/isa/formats/basic.isa
+++ b/src/arch/sparc/isa/formats/basic.isa
@@ -63,7 +63,6 @@ def template BasicExecute {{
{
Fault fault = NoFault;
- %(fp_enable_check)s;
%(op_decl)s;
%(op_rd)s;
%(code)s;
@@ -81,11 +80,6 @@ def template BasicDecode {{
return new %(class_name)s(machInst);
}};
-// Basic decode template, passing mnemonic in as string arg to constructor.
-def template BasicDecodeWithMnemonic {{
- return new %(class_name)s("%(mnemonic)s", machInst);
-}};
-
// The most basic instruction format... used only for a few misc. insts
def format BasicOperate(code, *flags) {{
iop = InstObjParams(name, Name, 'SparcStaticInst',
diff --git a/src/arch/sparc/isa/formats/branch.isa b/src/arch/sparc/isa/formats/branch.isa
index 7d46ce739..8a3f05173 100644
--- a/src/arch/sparc/isa/formats/branch.isa
+++ b/src/arch/sparc/isa/formats/branch.isa
@@ -69,47 +69,18 @@ output header {{
};
/**
- * Base class for branches with 19 bit displacements.
+ * Base class for branches with n bit displacements.
*/
- class Branch19 : public BranchDisp
+ template<int bits>
+ class BranchNBits : public BranchDisp
{
protected:
// Constructor
- Branch19(const char *mnem, MachInst _machInst,
+ BranchNBits(const char *mnem, MachInst _machInst,
OpClass __opClass) :
BranchDisp(mnem, _machInst, __opClass)
{
- disp = sign_ext(DISP19 << 2, 21);
- }
- };
-
- /**
- * Base class for branches with 22 bit displacements.
- */
- class Branch22 : public BranchDisp
- {
- protected:
- // Constructor
- Branch22(const char *mnem, MachInst _machInst,
- OpClass __opClass) :
- BranchDisp(mnem, _machInst, __opClass)
- {
- disp = sign_ext(DISP22 << 2, 24);
- }
- };
-
- /**
- * Base class for branches with 30 bit displacements.
- */
- class Branch30 : public BranchDisp
- {
- protected:
- // Constructor
- Branch30(const char *mnem, MachInst _machInst,
- OpClass __opClass) :
- BranchDisp(mnem, _machInst, __opClass)
- {
- disp = sign_ext(DISP30 << 2, 32);
+ disp = sign_ext(_machInst << 2, bits + 2);
}
};
@@ -149,29 +120,23 @@ output header {{
}};
output decoder {{
+
+ template class BranchNBits<19>;
+
+ template class BranchNBits<22>;
+
+ template class BranchNBits<30>;
+
std::string Branch::generateDisassembly(Addr pc,
const SymbolTable *symtab) const
{
std::stringstream response;
printMnemonic(response, mnemonic);
-
- if (_numSrcRegs > 0)
- {
- printReg(response, _srcRegIdx[0]);
- for(int x = 1; x < _numSrcRegs; x++)
- {
+ printRegArray(response, _srcRegIdx, _numSrcRegs);
+ if(_numDestRegs && _numSrcRegs)
response << ", ";
- printReg(response, _srcRegIdx[x]);
- }
- }
-
- if (_numDestRegs > 0)
- {
- if(_numSrcRegs > 0)
- response << ", ";
- printReg(response, _destRegIdx[0]);
- }
+ printDestReg(response, 0);
return response.str();
}
@@ -182,27 +147,13 @@ output decoder {{
std::stringstream response;
printMnemonic(response, mnemonic);
-
- if (_numSrcRegs > 0)
- {
- printReg(response, _srcRegIdx[0]);
- for(int x = 1; x < _numSrcRegs; x++)
- {
- response << ", ";
- printReg(response, _srcRegIdx[x]);
- }
- }
-
+ printRegArray(response, _srcRegIdx, _numSrcRegs);
if(_numSrcRegs > 0)
response << ", ";
-
ccprintf(response, "0x%x", imm);
-
if (_numDestRegs > 0)
- {
response << ", ";
- printReg(response, _destRegIdx[0]);
- }
+ printDestReg(response, 0);
return response.str();
}
@@ -292,32 +243,10 @@ def format Branch(code, *opt_flags) {{
}};
// Primary format for branch instructions:
-def format Branch19(code, *opt_flags) {{
- code = re.sub(r'handle_annul', handle_annul, code)
- codeBlk = CodeBlock(code)
- iop = InstObjParams(name, Name, 'Branch19', codeBlk, opt_flags)
- header_output = BasicDeclare.subst(iop)
- decoder_output = BasicConstructor.subst(iop)
- exec_output = BranchExecute.subst(iop)
- decode_block = BasicDecode.subst(iop)
-}};
-
-// Primary format for branch instructions:
-def format Branch22(code, *opt_flags) {{
- code = re.sub(r'handle_annul', handle_annul, code)
- codeBlk = CodeBlock(code)
- iop = InstObjParams(name, Name, 'Branch22', codeBlk, opt_flags)
- header_output = BasicDeclare.subst(iop)
- decoder_output = BasicConstructor.subst(iop)
- exec_output = BranchExecute.subst(iop)
- decode_block = BasicDecode.subst(iop)
-}};
-
-// Primary format for branch instructions:
-def format Branch30(code, *opt_flags) {{
+def format BranchN(bits, code, *opt_flags) {{
code = re.sub(r'handle_annul', handle_annul, code)
codeBlk = CodeBlock(code)
- iop = InstObjParams(name, Name, 'Branch30', codeBlk, opt_flags)
+ iop = InstObjParams(name, Name, "BranchNBits<%d>" % bits, codeBlk, opt_flags)
header_output = BasicDeclare.subst(iop)
decoder_output = BasicConstructor.subst(iop)
exec_output = BranchExecute.subst(iop)
diff --git a/src/arch/sparc/isa/formats/integerop.isa b/src/arch/sparc/isa/formats/integerop.isa
index 1894ce541..27616216e 100644
--- a/src/arch/sparc/isa/formats/integerop.isa
+++ b/src/arch/sparc/isa/formats/integerop.isa
@@ -132,7 +132,7 @@ output header {{
OpClass __opClass) :
IntOpImm(mnem, _machInst, __opClass)
{
- imm = (IMM22 << 10) & 0xFFFFFC00;
+ imm = (IMM22 & 0x3FFFFF) << 10;
}
std::string generateDisassembly(Addr pc,
@@ -157,12 +157,9 @@ output decoder {{
if(!strcmp(mnemonic, "or") && _srcRegIdx[0] == 0)
{
printMnemonic(os, "mov");
- if(_numSrcRegs > 0)
- printReg(os, _srcRegIdx[1]);
+ printSrcReg(os, 1);
ccprintf(os, ", ");
- if(_numDestRegs > 0)
- printReg(os, _destRegIdx[0]);
-
+ printDestReg(os, 0);
return true;
}
return false;
@@ -173,32 +170,24 @@ output decoder {{
{
if(!strcmp(mnemonic, "or"))
{
- if(_srcRegIdx[0] == 0)
+ if(_numSrcRegs > 0 && _srcRegIdx[0] == 0)
{
if(imm == 0)
- {
printMnemonic(os, "clr");
- if(_numDestRegs > 0)
- printReg(os, _destRegIdx[0]);
- return true;
- }
else
{
printMnemonic(os, "mov");
- ccprintf(os, ", 0x%x, ", imm);
- if(_numDestRegs > 0)
- printReg(os, _destRegIdx[0]);
- return true;
+ ccprintf(os, " 0x%x, ", imm);
}
+ printDestReg(os, 0);
+ return true;
}
else if(imm == 0)
{
printMnemonic(os, "mov");
- if(_numSrcRegs > 0)
- printReg(os, _srcRegIdx[0]);
+ printSrcReg(os, 0);
ccprintf(os, ", ");
- if(_numDestRegs > 0)
- printReg(os, _destRegIdx[0]);
+ printDestReg(os, 0);
return true;
}
}
@@ -210,25 +199,13 @@ output decoder {{
{
std::stringstream response;
- if(!printPseudoOps(response, pc, symtab))
- {
- printMnemonic(response, mnemonic);
- if (_numSrcRegs > 0)
- {
- printReg(response, _srcRegIdx[0]);
- for(int x = 1; x < _numSrcRegs; x++)
- {
- response << ", ";
- printReg(response, _srcRegIdx[x]);
- }
- }
- if (_numDestRegs > 0)
- {
- if(_numSrcRegs > 0)
- response << ", ";
- printReg(response, _destRegIdx[0]);
- }
- }
+ if(printPseudoOps(response, pc, symtab))
+ return response.str();
+ printMnemonic(response, mnemonic);
+ printRegArray(response, _srcRegIdx, _numSrcRegs);
+ if(_numDestRegs && _numSrcRegs)
+ response << ", ";
+ printDestReg(response, 0);
return response.str();
}
@@ -237,27 +214,16 @@ output decoder {{
{
std::stringstream response;
- if(!printPseudoOps(response, pc, symtab))
- {
- printMnemonic(response, mnemonic);
- if (_numSrcRegs > 0)
- {
- printReg(response, _srcRegIdx[0]);
- for(int x = 1; x < _numSrcRegs - 1; x++)
- {
- response << ", ";
- printReg(response, _srcRegIdx[x]);
- }
- }
- if(_numSrcRegs > 0)
- response << ", ";
- ccprintf(response, "0x%x", imm);
- if (_numDestRegs > 0)
- {
- response << ", ";
- printReg(response, _destRegIdx[0]);
- }
- }
+ if(printPseudoOps(response, pc, symtab))
+ return response.str();
+ printMnemonic(response, mnemonic);
+ printRegArray(response, _srcRegIdx, _numSrcRegs);
+ if(_numSrcRegs > 0)
+ response << ", ";
+ ccprintf(response, "0x%x", imm);
+ if(_numDestRegs > 0)
+ response << ", ";
+ printDestReg(response, 0);
return response.str();
}
@@ -267,10 +233,8 @@ output decoder {{
std::stringstream response;
printMnemonic(response, mnemonic);
- if(_numSrcRegs > 0)
- response << ", ";
ccprintf(response, "%%hi(0x%x), ", imm);
- printReg(response, _destRegIdx[0]);
+ printDestReg(response, 0);
return response.str();
}
}};
@@ -316,38 +280,29 @@ let {{
return (header_output, decoder_output, exec_output, decode_block)
calcCcCode = '''
- uint8_t tmp_ccriccc;
- uint8_t tmp_ccriccv;
- uint8_t tmp_ccriccz;
- uint8_t tmp_ccriccn;
- uint8_t tmp_ccrxccc;
- uint8_t tmp_ccrxccv;
- uint8_t tmp_ccrxccz;
- uint8_t tmp_ccrxccn;
-
- tmp_ccriccn = (Rd >> 31) & 1;
- tmp_ccriccz = ((Rd & 0xFFFFFFFF) == 0);
- tmp_ccrxccn = (Rd >> 63) & 1;
- tmp_ccrxccz = (Rd == 0);
- tmp_ccriccv = %(ivValue)s & 1;
- tmp_ccriccc = %(icValue)s & 1;
- tmp_ccrxccv = %(xvValue)s & 1;
- tmp_ccrxccc = %(xcValue)s & 1;
-
- Ccr = tmp_ccriccc | tmp_ccriccv << 1 |
- tmp_ccriccz << 2 | tmp_ccriccn << 3|
- tmp_ccrxccc << 4 | tmp_ccrxccv << 5|
- tmp_ccrxccz << 6| tmp_ccrxccn << 7;
-
-
- DPRINTF(Sparc, "in = %%d\\n", (uint16_t)tmp_ccriccn);
- DPRINTF(Sparc, "iz = %%d\\n", (uint16_t)tmp_ccriccz);
- DPRINTF(Sparc, "xn = %%d\\n", (uint16_t)tmp_ccrxccn);
- DPRINTF(Sparc, "xz = %%d\\n", (uint16_t)tmp_ccrxccz);
- DPRINTF(Sparc, "iv = %%d\\n", (uint16_t)tmp_ccriccv);
- DPRINTF(Sparc, "ic = %%d\\n", (uint16_t)tmp_ccriccc);
- DPRINTF(Sparc, "xv = %%d\\n", (uint16_t)tmp_ccrxccv);
- DPRINTF(Sparc, "xc = %%d\\n", (uint16_t)tmp_ccrxccc);
+ uint16_t _ic, _iv, _iz, _in, _xc, _xv, _xz, _xn;
+
+ _in = (Rd >> 31) & 1;
+ _iz = ((Rd & 0xFFFFFFFF) == 0);
+ _xn = (Rd >> 63) & 1;
+ _xz = (Rd == 0);
+ _iv = %(ivValue)s & 1;
+ _ic = %(icValue)s & 1;
+ _xv = %(xvValue)s & 1;
+ _xc = %(xcValue)s & 1;
+
+ Ccr = _ic << 0 | _iv << 1 | _iz << 2 | _in << 3 |
+ _xc << 4 | _xv << 5 | _xz << 6 | _xn << 7;
+
+
+ DPRINTF(Sparc, "in = %%d\\n", _in);
+ DPRINTF(Sparc, "iz = %%d\\n", _iz);
+ DPRINTF(Sparc, "xn = %%d\\n", _xn);
+ DPRINTF(Sparc, "xz = %%d\\n", _xz);
+ DPRINTF(Sparc, "iv = %%d\\n", _iv);
+ DPRINTF(Sparc, "ic = %%d\\n", _ic);
+ DPRINTF(Sparc, "xv = %%d\\n", _xv);
+ DPRINTF(Sparc, "xc = %%d\\n", _xc);
'''
}};
diff --git a/src/arch/sparc/isa/formats/priv.isa b/src/arch/sparc/isa/formats/priv.isa
index 7df59d736..d7ee01519 100644
--- a/src/arch/sparc/isa/formats/priv.isa
+++ b/src/arch/sparc/isa/formats/priv.isa
@@ -72,7 +72,11 @@ output decoder {{
std::string Priv::generateDisassembly(Addr pc,
const SymbolTable *symtab) const
{
- return "Privileged Instruction";
+ std::stringstream response;
+
+ printMnemonic(response, mnemonic);
+
+ return response.str();
}
}};
@@ -87,9 +91,10 @@ def template PrivExecute {{
if(%(check)s)
return new PrivilegedAction;
+ Fault fault = NoFault;
%(code)s;
%(op_wb)s;
- return NoFault;
+ return fault;
}
}};
@@ -116,10 +121,17 @@ let {{
// Primary format for integer operate instructions:
def format Priv(code, *opt_flags) {{
- checkCode = "((xc->readMiscReg(PrStart + MISCREG_PSTATE))<2:2>)"
+ checkCode = '''((xc->readMiscReg(PrStart + MISCREG_PSTATE))<2:2>) ||
+ ((xc->readMiscReg(HprStart + MISCREG_HPSTATE))<2:2>)'''
(header_output, decoder_output,
exec_output, decode_block) = doPrivFormat(code,
- checkCode, name, Name, opt_flags)
+ checkCode, name, Name, opt_flags + ('IprAccessOp',))
}};
+def format HPriv(code, *opt_flags) {{
+ checkCode = "((xc->readMiscReg(HprStart + MISCREG_HPSTATE))<2:2>)"
+ (header_output, decoder_output,
+ exec_output, decode_block) = doPrivFormat(code,
+ checkCode, name, Name, opt_flags + ('IprAccessOp',))
+}};
diff --git a/src/arch/sparc/isa/includes.isa b/src/arch/sparc/isa/includes.isa
index 40afb3722..3783051c4 100644
--- a/src/arch/sparc/isa/includes.isa
+++ b/src/arch/sparc/isa/includes.isa
@@ -36,7 +36,6 @@
output header {{
#include <sstream>
#include <iostream>
-#include <iomanip>
#include "cpu/static_inst.hh"
#include "arch/sparc/faults.hh"
@@ -50,7 +49,6 @@ output decoder {{
#include "base/loader/symtab.hh"
#include "cpu/thread_context.hh" // for Jump::branchTarget()
-#include <math.h>
#if defined(linux)
#include <fenv.h>
#endif
@@ -59,14 +57,10 @@ using namespace SparcISA;
}};
output exec {{
-#include <math.h>
#if defined(linux)
#include <fenv.h>
#endif
-#ifdef FULL_SYSTEM
-//#include "sim/pseudo_inst.hh"
-#endif
#include "cpu/base.hh"
#include "cpu/exetrace.hh"
#include "sim/sim_exit.hh"
diff --git a/src/arch/sparc/isa/operands.isa b/src/arch/sparc/isa/operands.isa
index 9e5c783e8..d250d3672 100644
--- a/src/arch/sparc/isa/operands.isa
+++ b/src/arch/sparc/isa/operands.isa
@@ -51,12 +51,12 @@ def operands {{
'RdHigh': ('IntReg', 'udw', 'RD | 1', 'IsInteger', 3),
'Rs1': ('IntReg', 'udw', 'RS1', 'IsInteger', 4),
'Rs2': ('IntReg', 'udw', 'RS2', 'IsInteger', 5),
- #'Fa': ('FloatReg', 'df', 'FA', 'IsFloating', 1),
- #'Fb': ('FloatReg', 'df', 'FB', 'IsFloating', 2),
- #'Fc': ('FloatReg', 'df', 'FC', 'IsFloating', 3),
- 'Mem': ('Mem', 'udw', None, ('IsMemRef', 'IsLoad', 'IsStore'), 4),
- 'NPC': ('NPC', 'udw', None, ( None, None, 'IsControl' ), 4),
- 'NNPC': ('NNPC', 'udw', None, (None, None, 'IsControl' ), 4),
+ 'Frd': ('FloatReg', 'df', 'RD', 'IsFloating', 10),
+ 'Frs1': ('FloatReg', 'df', 'RS1', 'IsFloating', 11),
+ 'Frs2': ('FloatReg', 'df', 'RS2', 'IsFloating', 12),
+ 'Mem': ('Mem', 'udw', None, ('IsMemRef', 'IsLoad', 'IsStore'), 20),
+ 'NPC': ('NPC', 'udw', None, ( None, None, 'IsControl' ), 31),
+ 'NNPC': ('NNPC', 'udw', None, (None, None, 'IsControl' ), 32),
#'Runiq': ('ControlReg', 'uq', 'Uniq', None, 1),
#'FPCR': ('ControlReg', 'uq', 'Fpcr', None, 1),
'R0': ('IntReg', 'udw', '0', None, 6),
@@ -65,24 +65,24 @@ def operands {{
'R16': ('IntReg', 'udw', '16', None, 9),
# Control registers
- 'Y': ('ControlReg', 'udw', 'MISCREG_Y', None, 12),
- 'Ccr': ('ControlReg', 'udw', 'MISCREG_CCR', None, 17),
- 'Asi': ('ControlReg', 'udw', 'MISCREG_ASI', None, 26),
+ 'Y': ('ControlReg', 'udw', 'MISCREG_Y', None, 40),
+ 'Ccr': ('ControlReg', 'udw', 'MISCREG_CCR', None, 41),
+ 'Asi': ('ControlReg', 'udw', 'MISCREG_ASI', None, 42),
- 'Tpc': ('ControlReg', 'udw', 'MISCREG_TPC', None, 28),
- 'Tnpc': ('ControlReg', 'udw', 'MISCREG_TNPC', None, 28),
- 'Tstate': ('ControlReg', 'udw', 'MISCREG_TSTATE', None, 28),
- 'Pstate': ('ControlReg', 'udw', 'MISCREG_PSTATE', None, 1),
- 'Tl': ('ControlReg', 'udw', 'MISCREG_TL', None, 27),
+ 'Tpc': ('ControlReg', 'udw', 'MISCREG_TPC', None, 43),
+ 'Tnpc': ('ControlReg', 'udw', 'MISCREG_TNPC', None, 44),
+ 'Tstate': ('ControlReg', 'udw', 'MISCREG_TSTATE', None, 45),
+ 'Pstate': ('ControlReg', 'udw', 'MISCREG_PSTATE', None, 46),
+ 'Tl': ('ControlReg', 'udw', 'MISCREG_TL', None, 47),
- 'Cwp': ('ControlReg', 'udw', 'MISCREG_CWP', None, 15),
- 'Cansave': ('ControlReg', 'udw', 'MISCREG_CANSAVE', None, 34),
- 'Canrestore': ('ControlReg', 'udw', 'MISCREG_CANRESTORE', None, 35),
- 'Cleanwin': ('ControlReg', 'udw', 'MISCREG_CLEANWIN', None, 37),
- 'Otherwin': ('ControlReg', 'udw', 'MISCREG_OTHERWIN', None, 36),
- 'Wstate': ('ControlReg', 'udw', 'MISCREG_WSTATE', None, 38),
- 'Gl': ('ControlReg', 'udw', 'MISCREG_GL', None, 12),
+ 'Cwp': ('ControlReg', 'udw', 'MISCREG_CWP', None, 48),
+ 'Cansave': ('ControlReg', 'udw', 'MISCREG_CANSAVE', None, 49),
+ 'Canrestore': ('ControlReg', 'udw', 'MISCREG_CANRESTORE', None, 50),
+ 'Cleanwin': ('ControlReg', 'udw', 'MISCREG_CLEANWIN', None, 51),
+ 'Otherwin': ('ControlReg', 'udw', 'MISCREG_OTHERWIN', None, 52),
+ 'Wstate': ('ControlReg', 'udw', 'MISCREG_WSTATE', None, 53),
+ 'Gl': ('ControlReg', 'udw', 'MISCREG_GL', None, 54),
- 'Fsr': ('ControlReg', 'udw', 'MISCREG_FSR', None, 47)
+ 'Fsr': ('ControlReg', 'udw', 'MISCREG_FSR', None, 55)
}};
diff --git a/src/arch/sparc/regfile.hh b/src/arch/sparc/regfile.hh
index cbeb3c7b9..db48b2d78 100644
--- a/src/arch/sparc/regfile.hh
+++ b/src/arch/sparc/regfile.hh
@@ -55,14 +55,12 @@ namespace SparcISA
// NWINDOWS - number of register windows, can be 3 to 32
const int NWindows = 32;
-
const int AsrStart = 0;
const int PrStart = 32;
const int HprStart = 64;
const int MiscStart = 96;
const uint64_t Bit64 = (1ULL << 63);
-
class IntRegFile
{
protected:
@@ -182,7 +180,7 @@ namespace SparcISA
//Since the floating point registers overlap each other,
//A generic storage space is used. The float to be returned is
//pulled from the appropriate section of this region.
- char regSpace[SingleWidth / 8 * NumFloatRegs];
+ char regSpace[(SingleWidth / 8) * NumFloatRegs];
public:
@@ -200,15 +198,15 @@ namespace SparcISA
{
case SingleWidth:
float32_t result32;
- memcpy(&result32, regSpace + 4 * floatReg, width);
+ memcpy(&result32, regSpace + 4 * floatReg, sizeof(result32));
return htog(result32);
case DoubleWidth:
float64_t result64;
- memcpy(&result64, regSpace + 4 * floatReg, width);
+ memcpy(&result64, regSpace + 4 * floatReg, sizeof(result64));
return htog(result64);
case QuadWidth:
float128_t result128;
- memcpy(&result128, regSpace + 4 * floatReg, width);
+ memcpy(&result128, regSpace + 4 * floatReg, sizeof(result128));
return htog(result128);
default:
panic("Attempted to read a %d bit floating point register!", width);
@@ -224,15 +222,15 @@ namespace SparcISA
{
case SingleWidth:
uint32_t result32;
- memcpy(&result32, regSpace + 4 * floatReg, width);
+ memcpy(&result32, regSpace + 4 * floatReg, sizeof(result32));
return htog(result32);
case DoubleWidth:
uint64_t result64;
- memcpy(&result64, regSpace + 4 * floatReg, width);
+ memcpy(&result64, regSpace + 4 * floatReg, sizeof(result64));
return htog(result64);
case QuadWidth:
uint64_t result128;
- memcpy(&result128, regSpace + 4 * floatReg, width);
+ memcpy(&result128, regSpace + 4 * floatReg, sizeof(result128));
return htog(result128);
default:
panic("Attempted to read a %d bit floating point register!", width);
@@ -247,15 +245,16 @@ namespace SparcISA
uint32_t result32;
uint64_t result64;
+ DPRINTF(Sparc, "Setting floating point register %d\n", floatReg);
switch(width)
{
case SingleWidth:
result32 = gtoh((uint32_t)val);
- memcpy(regSpace + 4 * floatReg, &result32, width);
+ memcpy(regSpace + 4 * floatReg, &result32, sizeof(result32));
break;
case DoubleWidth:
result64 = gtoh((uint64_t)val);
- memcpy(regSpace + 4 * floatReg, &result64, width);
+ memcpy(regSpace + 4 * floatReg, &result64, sizeof(result64));
break;
case QuadWidth:
panic("Quad width FP not implemented.");
@@ -277,11 +276,11 @@ namespace SparcISA
{
case SingleWidth:
result32 = gtoh((uint32_t)val);
- memcpy(regSpace + 4 * floatReg, &result32, width);
+ memcpy(regSpace + 4 * floatReg, &result32, sizeof(result32));
break;
case DoubleWidth:
result64 = gtoh((uint64_t)val);
- memcpy(regSpace + 4 * floatReg, &result64, width);
+ memcpy(regSpace + 4 * floatReg, &result64, sizeof(result64));
break;
case QuadWidth:
panic("Quad width FP not implemented.");
@@ -625,11 +624,9 @@ namespace SparcISA
hpstateFields.red = 1;
hpstateFields.hpriv = 1;
hpstateFields.tlz = 0; // this is a guess
-
hintp = 0; // no interrupts pending
hstick_cmprFields.int_dis = 1; // disable timer compare interrupts
hstick_cmprFields.tick_cmpr = 0; // Reset to 0 for pretty printing
-
#else
/* //This sets up the initial state of the processor for usermode processes
pstateFields.priv = 0; //Process runs in user mode
@@ -687,6 +684,8 @@ namespace SparcISA
void copyMiscRegs(ThreadContext * tc);
+ protected:
+
bool isHyperPriv() { return hpstateFields.hpriv; }
bool isPriv() { return hpstateFields.hpriv || pstateFields.priv; }
bool isNonPriv() { return !isPriv(); }
diff --git a/src/cpu/SConscript b/src/cpu/SConscript
index 7d45c7870..2bb9a2399 100644
--- a/src/cpu/SConscript
+++ b/src/cpu/SConscript
@@ -160,7 +160,8 @@ if 'O3CPU' in env['CPU_MODELS']:
''')
if env['USE_CHECKER']:
sources += Split('o3/checker_builder.cc')
- env['SMT_CPU_MODELS'].append('O3CPU')
+ else:
+ env['SMT_CPU_MODELS'].append('O3CPU') # Checker doesn't support SMT right now
if 'OzoneCPU' in env['CPU_MODELS']:
need_bp_unit = True
diff --git a/src/cpu/simple/timing.cc b/src/cpu/simple/timing.cc
index 246bcec05..5c1654f7e 100644
--- a/src/cpu/simple/timing.cc
+++ b/src/cpu/simple/timing.cc
@@ -85,8 +85,16 @@ TimingSimpleCPU::CpuPort::recvStatusChange(Status status)
panic("TimingSimpleCPU doesn't expect recvStatusChange callback!");
}
+
+void
+TimingSimpleCPU::CpuPort::TickEvent::schedule(Packet *_pkt, Tick t)
+{
+ pkt = _pkt;
+ Event::schedule(t);
+}
+
TimingSimpleCPU::TimingSimpleCPU(Params *p)
- : BaseSimpleCPU(p), icachePort(this), dcachePort(this)
+ : BaseSimpleCPU(p), icachePort(this, p->clock), dcachePort(this, p->clock)
{
_status = Idle;
ifetch_pkt = dcache_pkt = NULL;
@@ -462,11 +470,26 @@ TimingSimpleCPU::completeIfetch(Packet *pkt)
}
}
+void
+TimingSimpleCPU::IcachePort::ITickEvent::process()
+{
+ cpu->completeIfetch(pkt);
+}
bool
TimingSimpleCPU::IcachePort::recvTiming(Packet *pkt)
{
- cpu->completeIfetch(pkt);
+ // These next few lines could be replaced with something faster
+ // who knows what though
+ Tick time = pkt->req->getTime();
+ while (time < curTick)
+ time += lat;
+
+ if (time == curTick)
+ cpu->completeIfetch(pkt);
+ else
+ tickEvent.schedule(pkt, time);
+
return true;
}
@@ -523,11 +546,25 @@ TimingSimpleCPU::completeDrain()
bool
TimingSimpleCPU::DcachePort::recvTiming(Packet *pkt)
{
- cpu->completeDataAccess(pkt);
+ Tick time = pkt->req->getTime();
+ while (time < curTick)
+ time += lat;
+
+ if (time == curTick)
+ cpu->completeDataAccess(pkt);
+ else
+ tickEvent.schedule(pkt, time);
+
return true;
}
void
+TimingSimpleCPU::DcachePort::DTickEvent::process()
+{
+ cpu->completeDataAccess(pkt);
+}
+
+void
TimingSimpleCPU::DcachePort::recvRetry()
{
// we shouldn't get a retry unless we have a packet that we're
diff --git a/src/cpu/simple/timing.hh b/src/cpu/simple/timing.hh
index ac36e5c99..d03fa4bc0 100644
--- a/src/cpu/simple/timing.hh
+++ b/src/cpu/simple/timing.hh
@@ -74,11 +74,12 @@ class TimingSimpleCPU : public BaseSimpleCPU
{
protected:
TimingSimpleCPU *cpu;
+ Tick lat;
public:
- CpuPort(const std::string &_name, TimingSimpleCPU *_cpu)
- : Port(_name), cpu(_cpu)
+ CpuPort(const std::string &_name, TimingSimpleCPU *_cpu, Tick _lat)
+ : Port(_name), cpu(_cpu), lat(_lat)
{ }
protected:
@@ -92,14 +93,26 @@ class TimingSimpleCPU : public BaseSimpleCPU
virtual void getDeviceAddressRanges(AddrRangeList &resp,
AddrRangeList &snoop)
{ resp.clear(); snoop.clear(); }
+
+ struct TickEvent : public Event
+ {
+ Packet *pkt;
+ TimingSimpleCPU *cpu;
+
+ TickEvent(TimingSimpleCPU *_cpu)
+ :Event(&mainEventQueue), cpu(_cpu) {}
+ const char *description() { return "Timing CPU clock event"; }
+ void schedule(Packet *_pkt, Tick t);
+ };
+
};
class IcachePort : public CpuPort
{
public:
- IcachePort(TimingSimpleCPU *_cpu)
- : CpuPort(_cpu->name() + "-iport", _cpu)
+ IcachePort(TimingSimpleCPU *_cpu, Tick _lat)
+ : CpuPort(_cpu->name() + "-iport", _cpu, _lat), tickEvent(_cpu)
{ }
protected:
@@ -107,14 +120,26 @@ class TimingSimpleCPU : public BaseSimpleCPU
virtual bool recvTiming(Packet *pkt);
virtual void recvRetry();
+
+ struct ITickEvent : public TickEvent
+ {
+
+ ITickEvent(TimingSimpleCPU *_cpu)
+ : TickEvent(_cpu) {}
+ void process();
+ const char *description() { return "Timing CPU clock event"; }
+ };
+
+ ITickEvent tickEvent;
+
};
class DcachePort : public CpuPort
{
public:
- DcachePort(TimingSimpleCPU *_cpu)
- : CpuPort(_cpu->name() + "-dport", _cpu)
+ DcachePort(TimingSimpleCPU *_cpu, Tick _lat)
+ : CpuPort(_cpu->name() + "-dport", _cpu, _lat), tickEvent(_cpu)
{ }
protected:
@@ -122,6 +147,17 @@ class TimingSimpleCPU : public BaseSimpleCPU
virtual bool recvTiming(Packet *pkt);
virtual void recvRetry();
+
+ struct DTickEvent : public TickEvent
+ {
+ DTickEvent(TimingSimpleCPU *_cpu)
+ : TickEvent(_cpu) {}
+ void process();
+ const char *description() { return "Timing CPU clock event"; }
+ };
+
+ DTickEvent tickEvent;
+
};
IcachePort icachePort;
diff --git a/src/dev/io_device.cc b/src/dev/io_device.cc
index 660efabfd..b51a93190 100644
--- a/src/dev/io_device.cc
+++ b/src/dev/io_device.cc
@@ -36,8 +36,7 @@
PioPort::PioPort(PioDevice *dev, System *s, std::string pname)
- : Port(dev->name() + pname), device(dev), sys(s),
- outTiming(0), drainEvent(NULL)
+ : SimpleTimingPort(dev->name() + pname), device(dev), sys(s)
{ }
@@ -61,48 +60,6 @@ PioPort::getDeviceAddressRanges(AddrRangeList &resp, AddrRangeList &snoop)
}
-void
-PioPort::recvRetry()
-{
- bool result = true;
- while (result && transmitList.size()) {
- result = Port::sendTiming(transmitList.front());
- if (result)
- transmitList.pop_front();
- }
- if (transmitList.size() == 0 && drainEvent) {
- drainEvent->process();
- drainEvent = NULL;
- }
-}
-
-void
-PioPort::SendEvent::process()
-{
- port->outTiming--;
- assert(port->outTiming >= 0);
- if (port->Port::sendTiming(packet))
- if (port->transmitList.size() == 0 && port->drainEvent) {
- port->drainEvent->process();
- port->drainEvent = NULL;
- }
- return;
-
- port->transmitList.push_back(packet);
-}
-
-void
-PioPort::resendNacked(Packet *pkt) {
- pkt->reinitNacked();
- if (transmitList.size()) {
- transmitList.push_front(pkt);
- } else {
- if (!Port::sendTiming(pkt))
- transmitList.push_front(pkt);
- }
-};
-
-
bool
PioPort::recvTiming(Packet *pkt)
{
@@ -117,15 +74,6 @@ PioPort::recvTiming(Packet *pkt)
return true;
}
-unsigned int
-PioPort::drain(Event *de)
-{
- if (outTiming == 0 && transmitList.size() == 0)
- return 0;
- drainEvent = de;
- return 1;
-}
-
PioDevice::~PioDevice()
{
if (pioPort)
diff --git a/src/dev/io_device.hh b/src/dev/io_device.hh
index fa3f98247..22a32e73a 100644
--- a/src/dev/io_device.hh
+++ b/src/dev/io_device.hh
@@ -37,6 +37,7 @@
#include "mem/packet_impl.hh"
#include "sim/eventq.hh"
#include "sim/sim_object.hh"
+#include "mem/tport.hh"
class Platform;
class PioDevice;
@@ -48,13 +49,9 @@ class System;
* sensitive to an address range use. The port takes all the memory
* access types and roles them into one read() and write() call that the device
* must respond to. The device must also provide the addressRanges() function
- * with which it returns the address ranges it is interested in. An extra
- * sendTiming() function is implemented which takes an delay. In this way the
- * device can immediatly call sendTiming(pkt, time) after processing a request
- * and the request will be handled by the port even if the port bus the device
- * connects to is blocked.
- */
-class PioPort : public Port
+ * with which it returns the address ranges it is interested in. */
+
+class PioPort : public SimpleTimingPort
{
protected:
/** The device that this port serves. */
@@ -64,10 +61,6 @@ class PioPort : public Port
* we are currently operating in. */
System *sys;
- /** A list of outgoing timing response packets that haven't been serviced
- * yet. */
- std::list<Packet*> transmitList;
-
/** The current status of the peer(bus) that we are connected to. */
Status peerStatus;
@@ -82,53 +75,9 @@ class PioPort : public Port
virtual void getDeviceAddressRanges(AddrRangeList &resp, AddrRangeList &snoop);
- void resendNacked(Packet *pkt);
-
- /**
- * This class is used to implemented sendTiming() with a delay. When a delay
- * is requested a new event is created. When the event time expires it
- * attempts to send the packet. If it cannot, the packet is pushed onto the
- * transmit list to be sent when recvRetry() is called. */
- class SendEvent : public Event
- {
- PioPort *port;
- Packet *packet;
-
- SendEvent(PioPort *p, Packet *pkt, Tick t)
- : Event(&mainEventQueue), port(p), packet(pkt)
- { schedule(curTick + t); }
-
- virtual void process();
-
- virtual const char *description()
- { return "Future scheduled sendTiming event"; }
-
- friend class PioPort;
- };
-
- /** Number of timing requests that are emulating the device timing before
- * attempting to end up on the bus.
- */
- int outTiming;
-
- /** If we need to drain, keep the drain event around until we're done
- * here.*/
- Event *drainEvent;
-
- /** Schedule a sendTiming() event to be called in the future. */
- void sendTiming(Packet *pkt, Tick time)
- { outTiming++; new PioPort::SendEvent(this, pkt, time); }
-
- /** This function is notification that the device should attempt to send a
- * packet again. */
- virtual void recvRetry();
-
public:
PioPort(PioDevice *dev, System *s, std::string pname = "-pioport");
- unsigned int drain(Event *de);
-
- friend class PioPort::SendEvent;
};
diff --git a/src/mem/physical.cc b/src/mem/physical.cc
index 2d66602ab..291c70d8c 100644
--- a/src/mem/physical.cc
+++ b/src/mem/physical.cc
@@ -26,6 +26,7 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* Authors: Ron Dreslinski
+ * Ali Saidi
*/
#include <sys/types.h>
@@ -52,24 +53,6 @@
using namespace std;
using namespace TheISA;
-PhysicalMemory::MemResponseEvent::MemResponseEvent(Packet *pkt, MemoryPort* _m)
- : Event(&mainEventQueue, CPU_Tick_Pri), pkt(pkt), memoryPort(_m)
-{
-
- this->setFlags(AutoDelete);
-}
-
-void
-PhysicalMemory::MemResponseEvent::process()
-{
- memoryPort->sendTiming(pkt);
-}
-
-const char *
-PhysicalMemory::MemResponseEvent::description()
-{
- return "Physical Memory Timing Access respnse event";
-}
PhysicalMemory::PhysicalMemory(const string &n, Tick latency)
: MemObject(n),base_addr(0), pmem_addr(NULL), port(NULL), lat(latency)
@@ -124,27 +107,8 @@ PhysicalMemory::deviceBlockSize()
return 0;
}
-bool
-PhysicalMemory::doTimingAccess (Packet *pkt, MemoryPort* memoryPort)
-{
- doFunctionalAccess(pkt);
-
- // turn packet around to go back to requester
- pkt->makeTimingResponse();
- MemResponseEvent* response = new MemResponseEvent(pkt, memoryPort);
- response->schedule(curTick + lat);
-
- return true;
-}
Tick
-PhysicalMemory::doAtomicAccess(Packet *pkt)
-{
- doFunctionalAccess(pkt);
- return lat;
-}
-
-void
PhysicalMemory::doFunctionalAccess(Packet *pkt)
{
assert(pkt->getAddr() + pkt->getSize() < pmem_size);
@@ -170,6 +134,7 @@ PhysicalMemory::doFunctionalAccess(Packet *pkt)
}
pkt->result = Packet::Success;
+ return lat;
}
Port *
@@ -195,7 +160,7 @@ PhysicalMemory::recvStatusChange(Port::Status status)
PhysicalMemory::MemoryPort::MemoryPort(const std::string &_name,
PhysicalMemory *_memory)
- : Port(_name), memory(_memory)
+ : SimpleTimingPort(_name), memory(_memory)
{ }
void
@@ -228,13 +193,20 @@ PhysicalMemory::MemoryPort::deviceBlockSize()
bool
PhysicalMemory::MemoryPort::recvTiming(Packet *pkt)
{
- return memory->doTimingAccess(pkt, this);
+ assert(pkt->result != Packet::Nacked);
+
+ Tick latency = memory->doFunctionalAccess(pkt);
+
+ pkt->makeTimingResponse();
+ sendTiming(pkt, latency);
+
+ return true;
}
Tick
PhysicalMemory::MemoryPort::recvAtomic(Packet *pkt)
{
- return memory->doAtomicAccess(pkt);
+ return memory->doFunctionalAccess(pkt);
}
void
@@ -243,7 +215,16 @@ PhysicalMemory::MemoryPort::recvFunctional(Packet *pkt)
memory->doFunctionalAccess(pkt);
}
-
+unsigned int
+PhysicalMemory::drain(Event *de)
+{
+ int count = port->drain(de);
+ if (count)
+ changeState(Draining);
+ else
+ changeState(Drained);
+ return count;
+}
void
PhysicalMemory::serialize(ostream &os)
diff --git a/src/mem/physical.hh b/src/mem/physical.hh
index 50fa75ed3..b549c1f8b 100644
--- a/src/mem/physical.hh
+++ b/src/mem/physical.hh
@@ -37,7 +37,7 @@
#include "base/range.hh"
#include "mem/mem_object.hh"
#include "mem/packet.hh"
-#include "mem/port.hh"
+#include "mem/tport.hh"
#include "sim/eventq.hh"
#include <map>
#include <string>
@@ -47,7 +47,7 @@
//
class PhysicalMemory : public MemObject
{
- class MemoryPort : public Port
+ class MemoryPort : public SimpleTimingPort
{
PhysicalMemory *memory;
@@ -74,16 +74,6 @@ class PhysicalMemory : public MemObject
int numPorts;
- struct MemResponseEvent : public Event
- {
- Packet *pkt;
- MemoryPort *memoryPort;
-
- MemResponseEvent(Packet *pkt, MemoryPort *memoryPort);
- void process();
- const char *description();
- };
-
private:
// prevent copying of a MainMemory object
PhysicalMemory(const PhysicalMemory &specmem);
@@ -110,13 +100,10 @@ class PhysicalMemory : public MemObject
void getAddressRanges(AddrRangeList &resp, AddrRangeList &snoop);
virtual Port *getPort(const std::string &if_name, int idx = -1);
void virtual init();
+ unsigned int drain(Event *de);
- // fast back-door memory access for vtophys(), remote gdb, etc.
- // uint64_t phys_read_qword(Addr addr) const;
private:
- bool doTimingAccess(Packet *pkt, MemoryPort *memoryPort);
- Tick doAtomicAccess(Packet *pkt);
- void doFunctionalAccess(Packet *pkt);
+ Tick doFunctionalAccess(Packet *pkt);
void recvStatusChange(Port::Status status);
diff --git a/src/mem/tport.cc b/src/mem/tport.cc
new file mode 100644
index 000000000..90cf68f02
--- /dev/null
+++ b/src/mem/tport.cc
@@ -0,0 +1,82 @@
+/*
+ * Copyright (c) 2006 The Regents of The University of Michigan
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met: redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer;
+ * redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution;
+ * neither the name of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * Authors: Ali Saidi
+ */
+
+#include "mem/tport.hh"
+
+void
+SimpleTimingPort::recvRetry()
+{
+ bool result = true;
+ while (result && transmitList.size()) {
+ result = Port::sendTiming(transmitList.front());
+ if (result)
+ transmitList.pop_front();
+ }
+ if (transmitList.size() == 0 && drainEvent) {
+ drainEvent->process();
+ drainEvent = NULL;
+ }
+}
+
+void
+SimpleTimingPort::SendEvent::process()
+{
+ port->outTiming--;
+ assert(port->outTiming >= 0);
+ if (port->Port::sendTiming(packet))
+ if (port->transmitList.size() == 0 && port->drainEvent) {
+ port->drainEvent->process();
+ port->drainEvent = NULL;
+ }
+ return;
+
+ port->transmitList.push_back(packet);
+}
+
+void
+SimpleTimingPort::resendNacked(Packet *pkt) {
+ pkt->reinitNacked();
+ if (transmitList.size()) {
+ transmitList.push_front(pkt);
+ } else {
+ if (!Port::sendTiming(pkt))
+ transmitList.push_front(pkt);
+ }
+};
+
+
+unsigned int
+SimpleTimingPort::drain(Event *de)
+{
+ if (outTiming == 0 && transmitList.size() == 0)
+ return 0;
+ drainEvent = de;
+ return 1;
+}
diff --git a/src/mem/tport.hh b/src/mem/tport.hh
new file mode 100644
index 000000000..5473e945e
--- /dev/null
+++ b/src/mem/tport.hh
@@ -0,0 +1,134 @@
+/*
+ * Copyright (c) 2006 The Regents of The University of Michigan
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met: redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer;
+ * redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution;
+ * neither the name of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * Authors: Ali Saidi
+ */
+
+/**
+ * @file
+ * Implement a port which adds simple support of a sendTiming() function that
+ * takes a delay. In this way the * device can immediatly call
+ * sendTiming(pkt, time) after processing a request and the request will be
+ * handled by the port even if the port bus the device connects to is blocked.
+ */
+
+/** recvTiming and drain should be implemented something like this when this
+ * class is used.
+
+bool
+PioPort::recvTiming(Packet *pkt)
+{
+ if (pkt->result == Packet::Nacked) {
+ resendNacked(pkt);
+ } else {
+ Tick latency = device->recvAtomic(pkt);
+ // turn packet around to go back to requester
+ pkt->makeTimingResponse();
+ sendTiming(pkt, latency);
+ }
+ return true;
+}
+
+PioDevice::drain(Event *de)
+{
+ unsigned int count;
+ count = SimpleTimingPort->drain(de);
+ if (count)
+ changeState(Draining);
+ else
+ changeState(Drained);
+ return count;
+}
+*/
+
+#ifndef __MEM_TPORT_HH__
+#define __MEM_TPORT_HH__
+
+#include "mem/port.hh"
+#include "sim/eventq.hh"
+#include <list>
+#include <string>
+
+class SimpleTimingPort : public Port
+{
+ protected:
+ /** A list of outgoing timing response packets that haven't been serviced
+ * yet. */
+ std::list<Packet*> transmitList;
+ /**
+ * This class is used to implemented sendTiming() with a delay. When a delay
+ * is requested a new event is created. When the event time expires it
+ * attempts to send the packet. If it cannot, the packet is pushed onto the
+ * transmit list to be sent when recvRetry() is called. */
+ class SendEvent : public Event
+ {
+ SimpleTimingPort *port;
+ Packet *packet;
+
+ SendEvent(SimpleTimingPort *p, Packet *pkt, Tick t)
+ : Event(&mainEventQueue), port(p), packet(pkt)
+ { setFlags(AutoDelete); schedule(curTick + t); }
+
+ virtual void process();
+
+ virtual const char *description()
+ { return "Future scheduled sendTiming event"; }
+
+ friend class SimpleTimingPort;
+ };
+
+
+ /** Number of timing requests that are emulating the device timing before
+ * attempting to end up on the bus.
+ */
+ int outTiming;
+
+ /** If we need to drain, keep the drain event around until we're done
+ * here.*/
+ Event *drainEvent;
+
+ /** Schedule a sendTiming() event to be called in the future. */
+ void sendTiming(Packet *pkt, Tick time)
+ { outTiming++; new SimpleTimingPort::SendEvent(this, pkt, time); }
+
+ /** This function is notification that the device should attempt to send a
+ * packet again. */
+ virtual void recvRetry();
+
+ void resendNacked(Packet *pkt);
+ public:
+
+ SimpleTimingPort(std::string pname)
+ : Port(pname), outTiming(0), drainEvent(NULL)
+ {}
+
+ unsigned int drain(Event *de);
+
+ friend class SimpleTimingPort::SendEvent;
+};
+
+#endif // __MEM_TPORT_HH__
diff --git a/src/python/m5/objects/Device.py b/src/python/m5/objects/Device.py
index 222f750da..f72c8e73f 100644
--- a/src/python/m5/objects/Device.py
+++ b/src/python/m5/objects/Device.py
@@ -12,7 +12,7 @@ class BasicPioDevice(PioDevice):
type = 'BasicPioDevice'
abstract = True
pio_addr = Param.Addr("Device Address")
- pio_latency = Param.Tick(1, "Programmed IO latency in simticks")
+ pio_latency = Param.Latency('1ns', "Programmed IO latency in simticks")
class DmaDevice(PioDevice):
type = 'DmaDevice'
diff --git a/src/python/m5/objects/O3CPU.py b/src/python/m5/objects/O3CPU.py
index d6bc454ad..41208929a 100644
--- a/src/python/m5/objects/O3CPU.py
+++ b/src/python/m5/objects/O3CPU.py
@@ -1,91 +1,101 @@
from m5 import build_env
from m5.config import *
from BaseCPU import BaseCPU
+from Checker import O3Checker
class DerivO3CPU(BaseCPU):
type = 'DerivO3CPU'
- activity = Param.Unsigned("Initial count")
- numThreads = Param.Unsigned("number of HW thread contexts")
-
- checker = Param.BaseCPU(NULL, "checker")
+ activity = Param.Unsigned(0, "Initial count")
+ numThreads = Param.Unsigned(1, "number of HW thread contexts")
+
+ if build_env['USE_CHECKER']:
+ if not build_env['FULL_SYSTEM']:
+ checker = Param.BaseCPU(O3Checker(workload=Parent.workload,
+ exitOnError=True,
+ warnOnlyOnLoadError=False),
+ "checker")
+ else:
+ checker = Param.BaseCPU(O3Checker(exitOnError=True, warnOnlyOnLoadError=False), "checker")
+ checker.itb = Parent.itb
+ checker.dtb = Parent.dtb
cachePorts = Param.Unsigned("Cache Ports")
icache_port = Port("Instruction Port")
dcache_port = Port("Data Port")
- decodeToFetchDelay = Param.Unsigned("Decode to fetch delay")
- renameToFetchDelay = Param.Unsigned("Rename to fetch delay")
- iewToFetchDelay = Param.Unsigned("Issue/Execute/Writeback to fetch "
- "delay")
- commitToFetchDelay = Param.Unsigned("Commit to fetch delay")
- fetchWidth = Param.Unsigned("Fetch width")
+ decodeToFetchDelay = Param.Unsigned(1, "Decode to fetch delay")
+ renameToFetchDelay = Param.Unsigned(1 ,"Rename to fetch delay")
+ iewToFetchDelay = Param.Unsigned(1, "Issue/Execute/Writeback to fetch "
+ "delay")
+ commitToFetchDelay = Param.Unsigned(1, "Commit to fetch delay")
+ fetchWidth = Param.Unsigned(8, "Fetch width")
- renameToDecodeDelay = Param.Unsigned("Rename to decode delay")
- iewToDecodeDelay = Param.Unsigned("Issue/Execute/Writeback to decode "
+ renameToDecodeDelay = Param.Unsigned(1, "Rename to decode delay")
+ iewToDecodeDelay = Param.Unsigned(1, "Issue/Execute/Writeback to decode "
"delay")
- commitToDecodeDelay = Param.Unsigned("Commit to decode delay")
- fetchToDecodeDelay = Param.Unsigned("Fetch to decode delay")
- decodeWidth = Param.Unsigned("Decode width")
+ commitToDecodeDelay = Param.Unsigned(1, "Commit to decode delay")
+ fetchToDecodeDelay = Param.Unsigned(1, "Fetch to decode delay")
+ decodeWidth = Param.Unsigned(8, "Decode width")
- iewToRenameDelay = Param.Unsigned("Issue/Execute/Writeback to rename "
+ iewToRenameDelay = Param.Unsigned(1, "Issue/Execute/Writeback to rename "
"delay")
- commitToRenameDelay = Param.Unsigned("Commit to rename delay")
- decodeToRenameDelay = Param.Unsigned("Decode to rename delay")
- renameWidth = Param.Unsigned("Rename width")
+ commitToRenameDelay = Param.Unsigned(1, "Commit to rename delay")
+ decodeToRenameDelay = Param.Unsigned(1, "Decode to rename delay")
+ renameWidth = Param.Unsigned(8, "Rename width")
- commitToIEWDelay = Param.Unsigned("Commit to "
+ commitToIEWDelay = Param.Unsigned(1, "Commit to "
"Issue/Execute/Writeback delay")
- renameToIEWDelay = Param.Unsigned("Rename to "
+ renameToIEWDelay = Param.Unsigned(2, "Rename to "
"Issue/Execute/Writeback delay")
- issueToExecuteDelay = Param.Unsigned("Issue to execute delay (internal "
+ issueToExecuteDelay = Param.Unsigned(1, "Issue to execute delay (internal "
"to the IEW stage)")
- dispatchWidth = Param.Unsigned("Dispatch width")
- issueWidth = Param.Unsigned("Issue width")
- wbWidth = Param.Unsigned("Writeback width")
- wbDepth = Param.Unsigned("Writeback depth")
- fuPool = Param.FUPool(NULL, "Functional Unit pool")
+ dispatchWidth = Param.Unsigned(8, "Dispatch width")
+ issueWidth = Param.Unsigned(8, "Issue width")
+ wbWidth = Param.Unsigned(8, "Writeback width")
+ wbDepth = Param.Unsigned(1, "Writeback depth")
+ fuPool = Param.FUPool("Functional Unit pool")
- iewToCommitDelay = Param.Unsigned("Issue/Execute/Writeback to commit "
+ iewToCommitDelay = Param.Unsigned(1, "Issue/Execute/Writeback to commit "
"delay")
- renameToROBDelay = Param.Unsigned("Rename to reorder buffer delay")
- commitWidth = Param.Unsigned("Commit width")
- squashWidth = Param.Unsigned("Squash width")
- trapLatency = Param.Tick("Trap latency")
- fetchTrapLatency = Param.Tick("Fetch trap latency")
-
- backComSize = Param.Unsigned("Time buffer size for backwards communication")
- forwardComSize = Param.Unsigned("Time buffer size for forward communication")
-
- predType = Param.String("Branch predictor type ('local', 'tournament')")
- localPredictorSize = Param.Unsigned("Size of local predictor")
- localCtrBits = Param.Unsigned("Bits per counter")
- localHistoryTableSize = Param.Unsigned("Size of local history table")
- localHistoryBits = Param.Unsigned("Bits for the local history")
- globalPredictorSize = Param.Unsigned("Size of global predictor")
- globalCtrBits = Param.Unsigned("Bits per counter")
- globalHistoryBits = Param.Unsigned("Bits of history")
- choicePredictorSize = Param.Unsigned("Size of choice predictor")
- choiceCtrBits = Param.Unsigned("Bits of choice counters")
-
- BTBEntries = Param.Unsigned("Number of BTB entries")
- BTBTagSize = Param.Unsigned("Size of the BTB tags, in bits")
-
- RASSize = Param.Unsigned("RAS size")
-
- LQEntries = Param.Unsigned("Number of load queue entries")
- SQEntries = Param.Unsigned("Number of store queue entries")
- LFSTSize = Param.Unsigned("Last fetched store table size")
- SSITSize = Param.Unsigned("Store set ID table size")
-
- numRobs = Param.Unsigned("Number of Reorder Buffers");
-
- numPhysIntRegs = Param.Unsigned("Number of physical integer registers")
- numPhysFloatRegs = Param.Unsigned("Number of physical floating point "
- "registers")
- numIQEntries = Param.Unsigned("Number of instruction queue entries")
- numROBEntries = Param.Unsigned("Number of reorder buffer entries")
-
- instShiftAmt = Param.Unsigned("Number of bits to shift instructions by")
+ renameToROBDelay = Param.Unsigned(1, "Rename to reorder buffer delay")
+ commitWidth = Param.Unsigned(8, "Commit width")
+ squashWidth = Param.Unsigned(8, "Squash width")
+ trapLatency = Param.Tick(13, "Trap latency")
+ fetchTrapLatency = Param.Tick(1, "Fetch trap latency")
+
+ backComSize = Param.Unsigned(5, "Time buffer size for backwards communication")
+ forwardComSize = Param.Unsigned(5, "Time buffer size for forward communication")
+
+ predType = Param.String("tournament", "Branch predictor type ('local', 'tournament')")
+ localPredictorSize = Param.Unsigned(2048, "Size of local predictor")
+ localCtrBits = Param.Unsigned(2, "Bits per counter")
+ localHistoryTableSize = Param.Unsigned(2048, "Size of local history table")
+ localHistoryBits = Param.Unsigned(11, "Bits for the local history")
+ globalPredictorSize = Param.Unsigned(8192, "Size of global predictor")
+ globalCtrBits = Param.Unsigned(2, "Bits per counter")
+ globalHistoryBits = Param.Unsigned(4096, "Bits of history")
+ choicePredictorSize = Param.Unsigned(8192, "Size of choice predictor")
+ choiceCtrBits = Param.Unsigned(2, "Bits of choice counters")
+
+ BTBEntries = Param.Unsigned(4096, "Number of BTB entries")
+ BTBTagSize = Param.Unsigned(16, "Size of the BTB tags, in bits")
+
+ RASSize = Param.Unsigned(16, "RAS size")
+
+ LQEntries = Param.Unsigned(32, "Number of load queue entries")
+ SQEntries = Param.Unsigned(32, "Number of store queue entries")
+ LFSTSize = Param.Unsigned(1024, "Last fetched store table size")
+ SSITSize = Param.Unsigned(1024, "Store set ID table size")
+
+ numRobs = Param.Unsigned(1, "Number of Reorder Buffers");
+
+ numPhysIntRegs = Param.Unsigned(256, "Number of physical integer registers")
+ numPhysFloatRegs = Param.Unsigned(256, "Number of physical floating point "
+ "registers")
+ numIQEntries = Param.Unsigned(64, "Number of instruction queue entries")
+ numROBEntries = Param.Unsigned(192, "Number of reorder buffer entries")
+
+ instShiftAmt = Param.Unsigned(2, "Number of bits to shift instructions by")
function_trace = Param.Bool(False, "Enable function trace")
function_trace_start = Param.Tick(0, "Cycle to start function trace")
diff --git a/src/python/m5/objects/Pci.py b/src/python/m5/objects/Pci.py
index 29014bb37..cc0d1cf4a 100644
--- a/src/python/m5/objects/Pci.py
+++ b/src/python/m5/objects/Pci.py
@@ -52,7 +52,7 @@ class PciDevice(DmaDevice):
pci_bus = Param.Int("PCI bus")
pci_dev = Param.Int("PCI device number")
pci_func = Param.Int("PCI function code")
- pio_latency = Param.Tick(1, "Programmed IO latency in simticks")
+ pio_latency = Param.Latency('1ns', "Programmed IO latency in simticks")
configdata = Param.PciConfigData(Parent.any, "PCI Config data")
class PciFake(PciDevice):