Transition to 64b instructions + COMSAT Execution

This commit is contained in:
VinhTA-Computer-Master 2022-09-15 01:59:34 -07:00 committed by GitHub
parent af9b4335df
commit 122e2f99c8
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
9 changed files with 1176 additions and 399 deletions

View File

@ -50,13 +50,13 @@ void CGRA_FPRegisterFile::setFPRF(int regfilesize)
float CGRA_FPRegisterFile::Read(int address)
{
DPRINTF(FPRegfile_DEBUG, "Inside Register file Read()\n");
DPRINTF(FPRegfile_DEBUG, "Inside Register file reading address: %d\n", address);
if (address >= REGFILESIZE)
{
DPRINTF(CGRA_Detailed,"Requested Register is: %d\n",address);
throw new CGRAException("Register access out of range");
}
DPRINTF(CGRA_Detailed,"\nIN READ FPREGFILE FPR0 = %f\n",data_RF[0]);
//DPRINTF(CGRA_Detailed,"\nIN READ FPREGFILE FPR0 = %f\n",data_RF[0]);
DPRINTF(CGRA_Detailed,"FPR0: %f\tFPR1: %f\tFPR2: %f\tFPR3: %f\n",data_RF[0],data_RF[1],data_RF[2],data_RF[3]);
if(address < config_boundary)
{
@ -67,6 +67,8 @@ float CGRA_FPRegisterFile::Read(int address)
}
else
{
DPRINTF(CGRA_Detailed,"\nREAD: FPREG NUMBER: %d dist: %d\n",address,distance);
DPRINTF(CGRA_Detailed,"Rotating FPREGS data: %d\tREG: %d\n",data_RF[(address+distance)%config_boundary],(address+distance)%config_boundary);
DPRINTF(FPRegfile_DEBUG, "Exiting Register file Read()\n");
return data_RF[address];
}
@ -77,6 +79,7 @@ void CGRA_FPRegisterFile::Write(int address, float value)
DPRINTF(FPRegfile_DEBUG, "Inside Register file Write()\n");
if (address >= REGFILESIZE)
{
DPRINTF(CGRA_Detailed,"Requested Write Register is: %d\n",address);
throw new CGRAException("Register access out of range");
}

View File

@ -21,7 +21,7 @@ CGRA_Instruction::CGRA_Instruction(unsigned long Instructionword)
ENCODE_instruction();
}
CGRA_Instruction::CGRA_Instruction(Datatype dt,OPCode opc,bool predic,PEInputMux LMuxSel, PEInputMux RMuxSel, int RRegAdd1,int RRegAdd2, int WAdd, bool WE, int ImmVal, bool EDMAdd, bool DMData)
CGRA_Instruction::CGRA_Instruction(Datatype dt,OPCode opc,bool predic,PEInputMux LMuxSel, PEInputMux RMuxSel, int RRegAdd1,int RRegAdd2, int WAdd, bool WE, long ImmVal, bool EDMAdd, bool DMData)
{
DType=dt;
opCode=opc;
@ -35,6 +35,7 @@ CGRA_Instruction::CGRA_Instruction(Datatype dt,OPCode opc,bool predic,PEInputMux
ImmediateValue=ImmVal;
SelectDataMemoryAddressBus=EDMAdd;
SelectDataMemoryDataBus=DMData;
LE = 0;
}
CGRA_Instruction::~CGRA_Instruction()
@ -67,6 +68,10 @@ bool CGRA_Instruction::getPredicator()
return Predicator;
}
bool CGRA_Instruction::getLE(){
return LE;
}
PEInputMux CGRA_Instruction::getLeftMuxSelector()
{
return LeftMuxSelector;
@ -114,7 +119,7 @@ bool CGRA_Instruction::getSelectDataMemoryDataBus()
void CGRA_Instruction::ENCODE_instruction()
{
unsigned long ins_trunc= InsWord & 0xffffffff;
unsigned long ins_trunc= InsWord & 0x1fffffffffffffffUL;
/*DPRINTF(Instruction_Debug, "InsWord: %lx\n", (InsWord));
DPRINTF(Instruction_Debug, "InsWord: %lx\n", (InsWord & 0xffffffff));
DPRINTF(Instruction_Debug, "INSOPCODE: %lx\n", ((INS_OPCODE)));
@ -151,120 +156,121 @@ void CGRA_Instruction::ENCODE_instruction()
DType = empty2;
break;
}
switch((ins_trunc & INS_OPCODE) >> SHIFT_OPCODE){
case Add:
opCode = Add;
break;
case Sub:
opCode = Sub;
break;
case Mult:
opCode = Mult;
break;
case AND:
opCode = AND;
break;
case OR:
opCode = OR;
break;
case XOR:
opCode = XOR;
break;
case cgraASR:
opCode = cgraASR;
break;
case cgraASL:
opCode = cgraASL;
break;
case NOOP:
opCode= NOOP;
break;
case GT:
opCode= GT;
break;
case LT:
opCode= LT;
break;
case EQ:
opCode= EQ;
break;
case NEQ:
opCode= NEQ;
break;
case Div:
opCode= Div;
break;
case Rem:
opCode= Rem;
break;
//case Sqrt:
case LSHR:
opCode= LSHR;
break;
}
Predicator= (InsWord & INS_PREDICT )>>SHIFT_PREDICT;
DPRINTF(Instruction_Debug, "Predicator: %d\n", (int) Predicator);
DPRINTF(Instruction_Debug, "LMUX selector: %d\n", (int) LeftMuxSelector);
switch((InsWord & INS_LMUX ) >> SHIFT_LMUX){
case Register:
LeftMuxSelector = Register;
break;
case Left:
LeftMuxSelector = Left;
break;
case Right:
LeftMuxSelector = Right;
break;
case Up:
LeftMuxSelector = Up;
break;
case Down:
LeftMuxSelector = Down;
break;
case DataBus:
LeftMuxSelector = DataBus;
break;
case Immediate:
LeftMuxSelector = Immediate;
break;
case Self:
LeftMuxSelector= Self;
break;
}
switch((InsWord & INS_RMUX ) >> SHIFT_RMUX){
case Register:
RightMuxSelector = Register;
break;
case Left:
RightMuxSelector = Left;
break;
case Right:
RightMuxSelector = Right;
break;
case Up:
RightMuxSelector = Up;
break;
case Down:
RightMuxSelector = Down;
break;
case DataBus:
RightMuxSelector = DataBus;
break;
case Immediate:
RightMuxSelector = Immediate;
break;
case Self:
RightMuxSelector= Self;
break;
}
switch((ins_trunc & INS_OPCODE) >> SHIFT_OPCODE){
case Add:
opCode = Add;
break;
case Sub:
opCode = Sub;
break;
case Mult:
opCode = Mult;
break;
case AND:
opCode = AND;
break;
case OR:
opCode = OR;
break;
case XOR:
opCode = XOR;
break;
case cgraASR:
opCode = cgraASR;
break;
case cgraASL:
opCode = cgraASL;
break;
case NOOP:
opCode= NOOP;
break;
case GT:
opCode= GT;
break;
case LT:
opCode= LT;
break;
case EQ:
opCode= EQ;
break;
case NEQ:
opCode= NEQ;
break;
case Div:
opCode= Div;
break;
case Rem:
opCode= Rem;
break;
//case Sqrt:
case LSHR:
opCode= LSHR;
break;
}
Predicator= (InsWord & INS_PREDICT )>>SHIFT_PREDICT;
LE= (InsWord & INS_LE) >> SHIFT_LE;
switch((InsWord & INS_LMUX ) >> SHIFT_LMUX){
case Register:
LeftMuxSelector = Register;
break;
case Left:
LeftMuxSelector = Left;
break;
case Right:
LeftMuxSelector = Right;
break;
case Up:
LeftMuxSelector = Up;
break;
case Down:
LeftMuxSelector = Down;
break;
case DataBus:
LeftMuxSelector = DataBus;
break;
case Immediate:
LeftMuxSelector = Immediate;
break;
case Self:
LeftMuxSelector= Self;
break;
}
switch((InsWord & INS_RMUX ) >> SHIFT_RMUX){
case Register:
RightMuxSelector = Register;
break;
case Left:
RightMuxSelector = Left;
break;
case Right:
RightMuxSelector = Right;
break;
case Up:
RightMuxSelector = Up;
break;
case Down:
RightMuxSelector = Down;
break;
case DataBus:
RightMuxSelector = DataBus;
break;
case Immediate:
RightMuxSelector = Immediate;
break;
case Self:
RightMuxSelector= Self;
break;
}
ReadRegAddress1= (InsWord & INS_R1 )>>SHIFT_R1 ;
ReadRegAddress2= (InsWord & INS_R2 )>>SHIFT_R2 ;
WriteRegAddress= (InsWord & INS_RW )>>SHIFT_RW ;
WriteRegisterEnable= (InsWord & INS_WE )>>SHIFT_WE ;
ImmediateValue= (InsWord & INS_IMMEDIATE )>>SHIFT_IMMEDIATE ;
SelectDataMemoryAddressBus= (InsWord & INS_AB )>>SHIFT_ABUS ;
SelectDataMemoryDataBus= (InsWord & INS_DB )>>SHIFT_DBUS ;
ReadRegAddress1= (InsWord & INS_R1 )>>SHIFT_R1 ;
ReadRegAddress2= (InsWord & INS_R2 )>>SHIFT_R2 ;
WriteRegAddress= (InsWord & INS_RW )>>SHIFT_RW ;
WriteRegisterEnable= (InsWord & INS_WE )>>SHIFT_WE ;
ImmediateValue= ((LE)? (InsWord & INS_LE_IMMEDIATE):(InsWord & INS_IMMEDIATE)) >> SHIFT_IMMEDIATE;
SelectDataMemoryAddressBus= (InsWord & INS_AB )>>SHIFT_ABUS ;
SelectDataMemoryDataBus= (InsWord & INS_DB )>>SHIFT_DBUS ;
}
unsigned long CGRA_Instruction::getOpCode_DECODE()
@ -342,9 +348,9 @@ unsigned long CGRA_Instruction::getWriteRegisterEnable_DECODE()
unsigned long CGRA_Instruction::getImmediateValue_DECODE()
{
unsigned long InsWord = 0;
if(ImmediateValue > 0Xfff){
printf("ERROR: CAN'T HOLD IMMEDIATE VALUE, SETTING VALUE = 0xfff\n");
ImmediateValue = 0xfff;
if(ImmediateValue > 0x3ffffffffUL){
printf("ERROR: CAN'T HOLD IMMEDIATE VALUE, SETTING VALUE = 0x3ffffffffUL\n");
ImmediateValue = 0x3ffffffffUL;
}
InsWord |= ImmediateValue;
InsWord <<= SHIFT_IMMEDIATE;
@ -370,11 +376,20 @@ unsigned long CGRA_Instruction::getSelectDataMemoryDataBus_DECODE()
return InsWord;
}
unsigned long CGRA_Instruction::getLE_DECODE(){
unsigned long InsWord = 0;
InsWord |= LE;
InsWord <<=SHIFT_LE;
InsWord &= INS_LE;
return InsWord;
}
unsigned long CGRA_Instruction::DecodeInstruction(CGRA_Instruction* Ins)
{
unsigned long InsWord =0;
InsWord |= Ins->getOpCode_DECODE();
InsWord |= Ins->getPredicator_DECODE();
InsWord |= Ins->getLE_DECODE();
InsWord |= Ins->getLeftMuxSelector_DECODE();
InsWord |= Ins->getRightMuxSelector_DECODE();
InsWord |= Ins->getReadRegAddress1_DECODE();
@ -398,7 +413,7 @@ Pred_Instruction::Pred_Instruction(unsigned long Instructionword)
ENCODE_Pred_instruction();
}
Pred_Instruction::Pred_Instruction(Datatype dt,PredOPCode popc,PEInputMux LMuxSel, PEInputMux RMuxSel, PEInputMux PMuxSel, int RRegAdd1,int RRegAdd2, int RRegAddP, int ImmVal)
Pred_Instruction::Pred_Instruction(Datatype dt,PredOPCode popc,PEInputMux LMuxSel, PEInputMux RMuxSel, PEInputMux PMuxSel, int RRegAdd1,int RRegAdd2, int RRegAddP, long ImmVal)
{
DType=dt;
popCode=popc;
@ -462,7 +477,7 @@ int Pred_Instruction::getImmediateValue()
void Pred_Instruction::ENCODE_Pred_instruction()
{
unsigned long pred_trunc=PredInsWord & 0xffffffff;
unsigned long pred_trunc=PredInsWord & 0x1fffffffffffffffUL;
switch(((unsigned long)(PredInsWord & INS_PDATATYPE))>>SHIFT_PDATATYPE)
{
case character:
@ -604,6 +619,14 @@ unsigned long Pred_Instruction::getPredOpCode_DECODE()
return PredInsWord;
}
unsigned long Pred_Instruction::getLE_DECODE(){
unsigned long PredInsWord = 0;
PredInsWord |= 0;
PredInsWord <<=SHIFT_LE;
PredInsWord &= INS_LE;
return PredInsWord;
}
unsigned long Pred_Instruction::getPredicator_DECODE()
{
unsigned long PredInsWord = 0;
@ -670,8 +693,8 @@ unsigned long Pred_Instruction::getReadRegAddressP_DECODE()
unsigned long Pred_Instruction::getImmediateValue_DECODE()
{
unsigned long PredInsWord = 0;
if(ImmediateValue > 0Xfff){
ImmediateValue = 0xfff;
if(ImmediateValue > 0x3ffffffffUL){
ImmediateValue = 0x3ffffffffUL;
}
PredInsWord |= ImmediateValue;
PredInsWord <<= SHIFT_IMMEDIATE;
@ -684,6 +707,7 @@ unsigned long Pred_Instruction::DecodePredInstruction(Pred_Instruction* Ins)
unsigned long PredInsWord =0;
PredInsWord |= Ins->getPredOpCode_DECODE();
PredInsWord |= Ins->getPredicator_DECODE();
PredInsWord |= Ins->getLE_DECODE();
PredInsWord |= Ins->getLeftMuxSelector_DECODE();
PredInsWord |= Ins->getRightMuxSelector_DECODE();
PredInsWord |= Ins->getPredMuxSelector_DECODE();
@ -693,3 +717,336 @@ unsigned long Pred_Instruction::DecodePredInstruction(Pred_Instruction* Ins)
PredInsWord |= Ins->getImmediateValue_DECODE();
return PredInsWord;
}
// LE Instruction Definitions
LE_Instruction::LE_Instruction(){
}
LE_Instruction::LE_Instruction(unsigned long Instructionword)
{
LEInsWord = Instructionword;
ENCODE_LE_instruction();
}
LE_Instruction::LE_Instruction(Datatype dt,OPCode opc,PEInputMux LMuxSel,PEInputMux RMuxSel,int RRegAdd1,int RRegAdd2, int WAdd, bool WE, long ImmVal, int BranchOffset){
DType=dt;
opCode=opc;
LeftMuxSelector=LMuxSel;
RightMuxSelector=RMuxSel;
ReadRegAddress1=RRegAdd1;
ReadRegAddress2=RRegAdd2;
WriteRegAddress=WAdd;
WriteRegisterEnable=WE;
branchOffset = BranchOffset;
ImmediateValue=ImmVal;
}
LE_Instruction::~LE_Instruction(){
}
Datatype LE_Instruction::getDatatype(){
return DType;
}
OPCode LE_Instruction::getOpCode(){
return opCode;
}
PEInputMux LE_Instruction::getLeftMuxSelector(){
return LeftMuxSelector;
}
PEInputMux LE_Instruction::getRightMuxSelector(){
return RightMuxSelector;
}
int LE_Instruction::getReadRegAddress1(){
return ReadRegAddress1;
}
int LE_Instruction::getReadRegAddress2(){
return ReadRegAddress2;
}
int LE_Instruction::getWriteRegAddress(){
return WriteRegAddress;
}
bool LE_Instruction::getWriteRegisterEnable(){
return WriteRegisterEnable;
}
unsigned LE_Instruction::getBranchOffset(){
return branchOffset;
}
int LE_Instruction::getImmediateValue(){
return ImmediateValue;
}
void LE_Instruction::ENCODE_LE_instruction(){
unsigned long ins_trunc= LEInsWord & 0x1fffffffffffffffUL;
switch(((unsigned long)(LEInsWord & INS_DATATYPE))>>SHIFT_DATATYPE)
{
case character:
DType = character;
break;
case int32:
DType = int32;
break;
case int16:
DType = int16;
break;
case float32:
DType = float32;
break;
case float64:
DType = float64;
break;
case float16:
DType = float16;
break;
case empty1:
DType = empty1;
break;
case empty2:
DType = empty2;
break;
}
switch((ins_trunc & INS_OPCODE) >> SHIFT_OPCODE){
case Add:
opCode = Add;
break;
case Sub:
opCode = Sub;
break;
case Mult:
opCode = Mult;
break;
case AND:
opCode = AND;
break;
case OR:
opCode = OR;
break;
case XOR:
opCode = XOR;
break;
case cgraASR:
opCode = cgraASR;
break;
case cgraASL:
opCode = cgraASL;
break;
case NOOP:
opCode= NOOP;
break;
case GT:
opCode= GT;
break;
case LT:
opCode= LT;
break;
case EQ:
opCode= EQ;
break;
case NEQ:
opCode= NEQ;
break;
case Div:
opCode= Div;
break;
case Rem:
opCode= Rem;
break;
case LSHR:
opCode= LSHR;
break;
}
switch((LEInsWord & INS_LMUX ) >> SHIFT_LMUX){
case Register:
LeftMuxSelector = Register;
break;
case Left:
LeftMuxSelector = Left;
break;
case Right:
LeftMuxSelector = Right;
break;
case Up:
LeftMuxSelector = Up;
break;
case Down:
LeftMuxSelector = Down;
break;
case DataBus:
LeftMuxSelector = DataBus;
break;
case Immediate:
LeftMuxSelector = Immediate;
break;
case Self:
LeftMuxSelector= Self;
break;
}
switch((LEInsWord & INS_RMUX ) >> SHIFT_RMUX){
case Register:
RightMuxSelector = Register;
break;
case Left:
RightMuxSelector = Left;
break;
case Right:
RightMuxSelector = Right;
break;
case Up:
RightMuxSelector = Up;
break;
case Down:
RightMuxSelector = Down;
break;
case DataBus:
RightMuxSelector = DataBus;
break;
case Immediate:
RightMuxSelector = Immediate;
break;
case Self:
RightMuxSelector= Self;
break;
}
ReadRegAddress1 = (LEInsWord & INS_R1 )>>SHIFT_R1 ;
ReadRegAddress2 = (LEInsWord & INS_R2 )>>SHIFT_R2 ;
WriteRegAddress = (LEInsWord & INS_RW )>>SHIFT_RW ;
WriteRegisterEnable = (LEInsWord & INS_WE )>>SHIFT_WE ;
branchOffset = (LEInsWord & INS_BRANCH_OFFSET)>>SHIFT_BRANCH_OFFSET;
ImmediateValue = (LEInsWord & INS_LE_IMMEDIATE)>>SHIFT_IMMEDIATE ;
}
unsigned long LE_Instruction::getOpCode_DECODE()
{
unsigned long InsWord = 0;
InsWord |=opCode;
InsWord <<= SHIFT_OPCODE;
InsWord &= INS_OPCODE;
return InsWord;
}
unsigned long LE_Instruction::getPredicator_DECODE(){
unsigned long InsWord = 0;
InsWord |= 0;
InsWord <<= SHIFT_PREDICT;
InsWord &= INS_PREDICT;
return InsWord;
}
unsigned long LE_Instruction::getLE_DECODE(){
unsigned long InsWord = 0;
InsWord |= 1;
InsWord <<= SHIFT_LE;
InsWord &= INS_LE;
return InsWord;
}
unsigned long LE_Instruction::getLeftMuxSelector_DECODE()
{
unsigned long InsWord = 0;
InsWord |=LeftMuxSelector;
InsWord <<= SHIFT_LMUX;
InsWord &= INS_LMUX;
return InsWord;
}
unsigned long LE_Instruction::getRightMuxSelector_DECODE()
{
unsigned long InsWord = 0;
InsWord |=RightMuxSelector;
InsWord <<= SHIFT_RMUX;
InsWord &= INS_RMUX;
return InsWord;
}
unsigned long LE_Instruction::getReadRegAddress1_DECODE()
{
unsigned long InsWord = 0;
InsWord |= ReadRegAddress1;
InsWord <<= SHIFT_R1;
InsWord &= INS_R1;
return InsWord;
}
unsigned long LE_Instruction::getReadRegAddress2_DECODE()
{
unsigned long InsWord = 0;
InsWord |= ReadRegAddress2;
InsWord <<= SHIFT_R2;
InsWord &= INS_R2;
return InsWord;
}
unsigned long LE_Instruction::getWriteRegAddress_DECODE()
{
unsigned long InsWord = 0;
InsWord |= WriteRegAddress;
InsWord <<= SHIFT_RW;
InsWord &= INS_RW;
return InsWord;
}
unsigned long LE_Instruction::getWriteRegisterEnable_DECODE()
{
unsigned long InsWord = 0;
InsWord |= WriteRegisterEnable;
InsWord <<= SHIFT_WE;
InsWord &= INS_WE;
return InsWord;
}
unsigned long LE_Instruction::getBranchOffset_DECODE()
{
unsigned long InsWord = 0;
InsWord |= branchOffset;
InsWord <<= SHIFT_BRANCH_OFFSET;
InsWord &= INS_BRANCH_OFFSET;
return InsWord;
}
unsigned long LE_Instruction::getImmediateValue_DECODE()
{
unsigned long InsWord = 0;
if(ImmediateValue > WIDTH_LE_IMMEDIATE){
printf("ERROR: CAN'T HOLD IMMEDIATE VALUE, SETTING VALUE = 0x3ffffffUL\n");
ImmediateValue = WIDTH_LE_IMMEDIATE;
}
InsWord |= ImmediateValue;
InsWord <<= SHIFT_IMMEDIATE;
InsWord &= INS_LE_IMMEDIATE;
return InsWord;
}
unsigned long DecodeLEInstruction(LE_Instruction* Ins)
{
unsigned long InsWord =0;
InsWord |= Ins->getOpCode_DECODE();
InsWord |= Ins->getPredicator_DECODE();
InsWord |= Ins->getLE_DECODE();
InsWord |= Ins->getLeftMuxSelector_DECODE();
InsWord |= Ins->getRightMuxSelector_DECODE();
InsWord |= Ins->getReadRegAddress1_DECODE();
InsWord |= Ins->getReadRegAddress2_DECODE();
InsWord |= Ins->getWriteRegAddress_DECODE();
InsWord |= Ins->getWriteRegisterEnable_DECODE();
InsWord |= Ins->getBranchOffset_DECODE();
InsWord |= Ins->getImmediateValue_DECODE();
return InsWord;
}

View File

@ -6,6 +6,10 @@
*
* edited: 24 May 2017
* Auhtor: Shail Dave
*
* Last edited: 5 April 2022
* Author: Vinh Ta
* Update: Added new field (LoopExit) to instruction word
*/
#ifndef INSTRUCTION_H_
@ -19,7 +23,7 @@ public:
CGRA_Instruction();
CGRA_Instruction(unsigned long InstructionWord);
CGRA_Instruction(Datatype DType,OPCode opc,bool predic,PEInputMux LMuxSel,PEInputMux RMuxSel,\
int RRegAdd1,int RRegAdd2, int WAdd, bool WE, int ImmVal, bool EDMAdd, bool DMData);
int RRegAdd1,int RRegAdd2, int WAdd, bool WE, long ImmVal, bool EDMAdd, bool DMData);
virtual ~CGRA_Instruction();
@ -29,7 +33,8 @@ public:
Datatype getDatatype();
OPCode getOpCode();
bool getPredicator();
PEInputMux getLeftMuxSelector();
bool getLE();
PEInputMux getLeftMuxSelector();
PEInputMux getRightMuxSelector();
int getReadRegAddress1();
int getReadRegAddress2();
@ -52,6 +57,7 @@ public:
unsigned long getImmediateValue_DECODE();
unsigned long getSelectDataMemoryAddressBus_DECODE();
unsigned long getSelectDataMemoryDataBus_DECODE();
unsigned long getLE_DECODE();
unsigned long DecodeInstruction(CGRA_Instruction* Ins);
@ -59,16 +65,17 @@ private:
Datatype DType;
OPCode opCode;
bool Predicator;
bool LE;
PEInputMux LeftMuxSelector;
PEInputMux RightMuxSelector;
int ReadRegAddress1;
int ReadRegAddress2;
int WriteRegAddress;
bool WriteRegisterEnable;
int ImmediateValue;
long ImmediateValue;
bool SelectDataMemoryAddressBus;
bool SelectDataMemoryDataBus;
//unsigned branchOffset;
unsigned long InsWord;
};
@ -78,7 +85,7 @@ public:
Pred_Instruction();
Pred_Instruction(unsigned long InstructionWord);
Pred_Instruction(Datatype DType,PredOPCode popc,PEInputMux LMuxSel,PEInputMux RMuxSel,PEInputMux PMuxSel,\
int RRegAdd1,int RRegAdd2, int RRegAddP, int ImmVal);
int RRegAdd1,int RRegAdd2, int RRegAddP, long ImmVal);
virtual ~Pred_Instruction();
@ -96,6 +103,7 @@ public:
unsigned long getPredOpCode_DECODE();
unsigned long getPredicator_DECODE();
unsigned long getLE_DECODE();
unsigned long getLeftMuxSelector_DECODE();
unsigned long getRightMuxSelector_DECODE();
unsigned long getPredMuxSelector_DECODE();
@ -115,9 +123,61 @@ private:
int ReadRegAddress1;
int ReadRegAddress2;
int ReadRegAddressP;
int ImmediateValue;
long ImmediateValue;
unsigned long PredInsWord;
};
class LE_Instruction
{
public:
LE_Instruction();
LE_Instruction(unsigned long InstructionWord);
LE_Instruction(Datatype dt,OPCode opc,PEInputMux LMuxSel,PEInputMux RMuxSel, \
int RRegAdd1,int RRegAdd2, int WAdd, bool WE, long ImmVal, int BranchOffset);
virtual ~LE_Instruction();
Datatype getDatatype();
OPCode getOpCode();
PEInputMux getLeftMuxSelector();
PEInputMux getRightMuxSelector();
int getReadRegAddress1();
int getReadRegAddress2();
int getWriteRegAddress();
bool getWriteRegisterEnable();
unsigned getBranchOffset();
int getImmediateValue();
void ENCODE_LE_instruction();
unsigned long getOpCode_DECODE();
unsigned long getPredicator_DECODE();
unsigned long getLE_DECODE();
unsigned long getLeftMuxSelector_DECODE();
unsigned long getRightMuxSelector_DECODE();
unsigned long getReadRegAddress1_DECODE();
unsigned long getReadRegAddress2_DECODE();
unsigned long getWriteRegAddress_DECODE();
unsigned long getWriteRegisterEnable_DECODE();
unsigned long getBranchOffset_DECODE();
unsigned long getImmediateValue_DECODE();
unsigned long DecodeLEInstruction(LE_Instruction* Ins);
private:
Datatype DType;
OPCode opCode;
PEInputMux LeftMuxSelector;
PEInputMux RightMuxSelector;
int ReadRegAddress1;
int ReadRegAddress2;
int WriteRegAddress;
bool WriteRegisterEnable;
unsigned branchOffset;
long ImmediateValue;
unsigned long LEInsWord;
};
#endif /* INSTRUCTION_H_ */

View File

@ -65,6 +65,7 @@ bool CGRA_PE::getPredOutput()
void CGRA_PE::Fetch(CGRA_Instruction* ins)
{
DPRINTF(PE_DEBUG, "Inside Fetch()\n");
//delete ins;
this->ins = ins;
DPRINTF(PE_DEBUG, "Exiting Fetch()\n");
}
@ -86,7 +87,7 @@ void CGRA_PE::Decode()
//cout << "predictor bit: " << ins->getPredicator() << "\topcode: " << ins->getOpCode() << endl;
// we don't need to separately decode fields in HW implementation
//ins->decode_CGRA_Instruction();
dt = ins->getDatatype();
dt = ins->getDatatype();
if(dt == character || dt == int16 || dt == int32)
{
@ -166,17 +167,18 @@ void CGRA_PE::Decode()
case Register:
InputP = (bool)RegFile.Read(predIns->getReadRegAddressP());
break;
// 1.9.2022 fix: pred*In -> *In
case Left:
InputP = (*PredleftIn);
InputP = (*leftIn);
break;
case Right:
InputP = (*PredrightIn);
InputP = (*rightIn);
break;
case Up:
InputP = (*PredupIn);
InputP = (*upIn);
break;
case Down:
InputP = (*PreddownIn);
InputP = (*downIn);
break;
case Immediate:
InputP=(ins->getImmediateValue()==1)? true : false;
@ -193,68 +195,135 @@ void CGRA_PE::Decode()
{
if((ins->getOpCode()!=NOOP))
{
switch (ins->getLeftMuxSelector())
{
case Register:
DPRINTF(CGRA_Detailed,"\n******** DB FPINPUT1 ReadAddress%d************\n",ins->getReadRegAddress1());
FPInput1 = FPRegFile.Read(ins->getReadRegAddress1());
break;
case Left:
FPInput1 = (*FPleftIn);
break;
case Right:
FPInput1 = *(FPrightIn);
break;
case Up:
FPInput1 = *(FPupIn);
break;
case Down:
FPInput1 = *(FPdownIn);
break;
case DataBus:
FPInput1 = *(FdataBs);
DPRINTF(CGRA_Detailed,"\n******** DB FPINPUT1 %f************\n",Input1);
break;
case Immediate:
FPInput1=ins->getImmediateValue();
break;
case Self:
FPInput1=FPOutput;
break;
default:
throw new CGRAException("CGRA Left Mux selector out of range");
}
if(ins->getOpCode() != address_generator){
switch (ins->getLeftMuxSelector())
{
case Register:
DPRINTF(CGRA_Detailed,"\n******** DB FPINPUT1 ReadAddress%d************\n",ins->getReadRegAddress1());
FPInput1 = FPRegFile.Read(ins->getReadRegAddress1());
break;
case Left:
FPInput1 = (*FPleftIn);
break;
case Right:
FPInput1 = *(FPrightIn);
break;
case Up:
FPInput1 = *(FPupIn);
break;
case Down:
FPInput1 = *(FPdownIn);
break;
case DataBus:
FPInput1 = *(FdataBs);
DPRINTF(CGRA_Detailed,"\n******** DB FPINPUT1 %f************\n",Input1);
break;
case Immediate:
FPInput1=ins->getImmediateValue();
break;
case Self:
FPInput1=FPOutput;
break;
default:
throw new CGRAException("CGRA Left Mux selector out of range");
}
switch (ins->getRightMuxSelector())
{
case Register:
DPRINTF(CGRA_Detailed,"\n******** DB FPINPUT2 ReadAddress%d************\n",ins->getReadRegAddress2());
FPInput2 = FPRegFile.Read(ins->getReadRegAddress2());
break;
case Left:
FPInput2 = (*FPleftIn);
break;
case Right:
FPInput2 = *(FPrightIn);
break;
case Up:
FPInput2 = *(FPupIn);
break;
case Down:
FPInput2 = *(FPdownIn);
break;
case DataBus:
FPInput2 = *(FdataBs);
DPRINTF(CGRA_Detailed,"\n******** DB FPINPUT2 %f************\n",FPInput2);
break;
case Immediate:
FPInput2=(float)(ins->getImmediateValue());
break;
case Self:
FPInput2=FPOutput;
break;
default:
throw new CGRAException("CGRA Right Mux selector out of range");
switch (ins->getRightMuxSelector())
{
case Register:
DPRINTF(CGRA_Detailed,"\n******** DB FPINPUT2 ReadAddress%d************\n",ins->getReadRegAddress2());
FPInput2 = FPRegFile.Read(ins->getReadRegAddress2());
break;
case Left:
FPInput2 = (*FPleftIn);
break;
case Right:
FPInput2 = *(FPrightIn);
break;
case Up:
FPInput2 = *(FPupIn);
break;
case Down:
FPInput2 = *(FPdownIn);
break;
case DataBus:
FPInput2 = *(FdataBs);
DPRINTF(CGRA_Detailed,"\n******** DB FPINPUT2 %f************\n",FPInput2);
break;
case Immediate:
FPInput2=(float)(ins->getImmediateValue());
break;
case Self:
FPInput2=FPOutput;
break;
default:
throw new CGRAException("CGRA Right Mux selector out of range");
}
} else {
switch (ins->getLeftMuxSelector())
{
case Register:
DPRINTF(CGRA_Detailed,"\n******** DB FPINPUT1 ReadAddress%d************\n",ins->getReadRegAddress1());
Input1 = FPRegFile.Read(ins->getReadRegAddress1()); // Inspect me: should I be RegFile or FPRegFile?
break;
case Left:
Input1 = (*leftIn);
break;
case Right:
Input1 = *(rightIn);
break;
case Up:
Input1 = *(upIn);
break;
case Down:
Input1 = *(downIn);
break;
case DataBus:
Input1 = *(dataBs);
DPRINTF(CGRA_Detailed,"\n******** DB FPINPUT1 %f************\n",Input1); // Inspect me: should I be dataBs or FdataBs?
break;
case Immediate:
Input1=ins->getImmediateValue();
break;
case Self:
Input1=Output;
break;
default:
throw new CGRAException("CGRA Left Mux selector out of range");
}
switch (ins->getRightMuxSelector())
{
case Register:
DPRINTF(CGRA_Detailed,"\n******** DB FPINPUT2 ReadAddress%d************\n",ins->getReadRegAddress2());
FPInput2 = FPRegFile.Read(ins->getReadRegAddress2());
break;
case Left:
FPInput2 = (*FPleftIn);
break;
case Right:
FPInput2 = *(FPrightIn);
break;
case Up:
FPInput2 = *(FPupIn);
break;
case Down:
FPInput2 = *(FPdownIn);
break;
case DataBus:
FPInput2 = *(FdataBs);
DPRINTF(CGRA_Detailed,"\n******** DB FPINPUT2 %f************\n",FPInput2);
break;
case Immediate:
FPInput2=(float)(ins->getImmediateValue());
break;
case Self:
FPInput2=FPOutput;
break;
default:
throw new CGRAException("CGRA Right Mux selector out of range");
}
}
}
@ -295,18 +364,23 @@ void CGRA_PE::Decode()
throw new CGRAException("CGRA Pred Mux selector out of range");
}
}
}
DPRINTF(PE_DEBUG, "Exiting Decode()\n");
}
void CGRA_PE::IExecute()
unsigned CGRA_PE::IExecute()
{
DPRINTF(PE_DEBUG, "Inside Execute()\n");
int ins_opcode=ins->getOpCode();
bool predicate_bit = ins->getPredicator();
DPRINTF(CGRA_Detailed, "Predictor bit: %d\t Opcode: %d\n" , (int) predicate_bit, ins_opcode);
bool predicate_bit = ins->getPredicator();
bool LE_bit = ins->getLE();
unsigned branch_offset = 0;
/*DPRINTF(CGRA_Detailed, "Predictor bit: %d\t Opcode: %d\n" , (int) predicate_bit, ins_opcode);
if(ins->getLeftMuxSelector() == Register || ins->getRightMuxSelector() == Register){
DPRINTF(CGRA_Execute, "Register file content:\n"
}*/
if(!predicate_bit)
{
@ -419,12 +493,32 @@ void CGRA_PE::IExecute()
DPRINTF(CGRA_Detailed,"Writing output %d to register %d\n",Output,writeRegisterNumber);
}
if(ins_opcode==EQ || ins_opcode==NEQ || ins_opcode==GT || ins_opcode==LT)
if(LE_bit){
LE_Instruction temp(ins->getInsWord());
LE_Instruction *LE_Ins = &temp;
DPRINTF(CGRA_Execute, "LE Branch: %lx\n", LE_Ins->getBranchOffset());
if(LE_Ins->getBranchOffset() == 0x3ff){
if(ins_opcode == NEQ || ins_opcode == LT || ins_opcode == AND || ins_opcode == OR || ins_opcode == XOR)
(this->Controller_Reg) = Output; // Output = 0 to exit
else this->Controller_Reg = !Output; // Output = 1 to exit
}
else{
if(ins_opcode == NEQ || ins_opcode == LT || ins_opcode == AND || ins_opcode == OR || ins_opcode == XOR) // Fix me: should NEQ be false to branch?
branch_offset = (!Output)? LE_Ins->getBranchOffset():0;
else
branch_offset = (Output == 1)? LE_Ins->getBranchOffset():0;
DPRINTF(CGRA_Detailed, "\n***LE Instruction - branching %d cycles***\n", branch_offset);
}
}
/*else if(ins_opcode==EQ || ins_opcode==NEQ || ins_opcode==GT || ins_opcode==LT)
//else if(ins_opcode == EQ) // Modified only for simple_loop benchmark!
{
//write the result to the controller bus
//(this->Controller_Reg) = !((Input1 == 1) && (Input2 == 0));
(this->Controller_Reg) = !Output;
}
(this->Controller_Reg) = (ins_opcode == EQ)? !Output:Output;
}*/
}
else
{
@ -454,7 +548,7 @@ void CGRA_PE::IExecute()
DPRINTF(CGRA_Detailed,"\n******** LDUI IN THIS PE %d************\n",Output);
break;
case sel:
Output = (InputP == false) ? Input1 : Input2;
Output = (InputP == true) ? Input1 : Input2;
DPRINTF(CGRA_Detailed,"\nInput1 = %d\tInput2 = %d\tInputP = %d\n",Input1, Input2, (int)InputP);
DPRINTF(CGRA_Detailed,"\n******** Selection IN THIS PE %d************\n",Output);
break;
@ -525,7 +619,7 @@ void CGRA_PE::IExecute()
}
}
if (ins->getSelectDataMemoryDataBus() && (!predicate_bit))
if (ins->getSelectDataMemoryDataBus() && (!predicate_bit) && (!LE_bit))
{
DPRINTF(CGRA_Detailed,"\n******** DB Output %d************\n",Output);
(*dataBs) = Output;
@ -533,14 +627,18 @@ void CGRA_PE::IExecute()
}
DPRINTF(CGRA_Detailed,"Distance is: %d\n",RegFile.distance);
DPRINTF(PE_DEBUG, "Exiting Execute()\n");
return branch_offset;
}
void CGRA_PE::FExecute()
unsigned CGRA_PE::FExecute()
{
DPRINTF(PE_DEBUG, "Inside Execute()\n");
int ins_opcode=ins->getOpCode();
bool predicate_bit = ins->getPredicator();
bool predicate_bit = ins->getPredicator();
bool LE_bit = ins->getLE();
unsigned branch_offset = 0;
//DPRINTF(CGRA_Detailed, "Predictor bit: %d\n", (int) predicate_bit);
if(!predicate_bit)
@ -654,11 +752,36 @@ void CGRA_PE::FExecute()
DPRINTF(CGRA_Detailed,"Writing output %f to register %d\n",FPOutput,writeRegisterNumber);
}
if(ins_opcode==EQ || ins_opcode==NEQ || ins_opcode==GT || ins_opcode==LT)
if(LE_bit){
LE_Instruction temp(ins->DecodeInstruction(ins));
LE_Instruction *LE_Ins = &temp;
if(LE_Ins->getBranchOffset() == 0x3ff){
if(ins_opcode == NEQ || ins_opcode == LT || ins_opcode == GT || ins_opcode == AND || ins_opcode == OR || ins_opcode == XOR)
(this->Controller_Reg) = (Output != 0)? 1:0;
else this->Controller_Reg = (Output == 0)? 1:0;
}
else{
if(ins_opcode == NEQ || ins_opcode == LT || ins_opcode == GT || ins_opcode == AND || ins_opcode == OR || ins_opcode == XOR) // Fix me: should NEQ be false to branch?
branch_offset = (Output == 0)? LE_Ins->getBranchOffset():0;
else
branch_offset = (Output != 0)? LE_Ins->getBranchOffset():0;
DPRINTF(CGRA_Detailed, "\n***LE Instruction - branching %d cycles***\n", branch_offset);
}
}
/*if(LE_bit){
LE_Instruction temp(ins->DecodeInstruction(ins));
LE_Instruction *LE_Ins = &temp;
branch_offset = (FPOutput != 0)? LE_Ins->getBranchOffset():0;
DPRINTF(CGRA_Detailed, "\nLE Instruction - branching %d cycles\n", branch_offset);
}
else if(ins_opcode==EQ || ins_opcode==NEQ || ins_opcode==GT || ins_opcode==LT)
{
//write the result to the controller bus
DPRINTF(CGRA_Detailed,"\nCOMPARE INSTRUCTION OUTPUT = %f\n",FPOutput);
}
}*/
}
else
{
@ -698,9 +821,10 @@ void CGRA_PE::FExecute()
DPRINTF(CGRA_Detailed,"\n******** Loop Exit Control IN THIS PE %f************\n",FPOutput);
break;
case address_generator:
FPOutput=(int)FPInput1;
DPRINTF(CGRA_Detailed,"\nFPInput1 = %f\tFPInput2 = %f\n",FPInput1, FPInput2);
DPRINTF(CGRA_Detailed,"\n******** ADDRESS GENERATED IN THIS PE %f************\n",FPOutput);
Output=(int)Input1;
DPRINTF(CGRA_Detailed,"\nInput1 = %d\tInput2 = %d\n",Input1, Input2);
DPRINTF(CGRA_Detailed,"\nFPInput1 = %f\tFPInput2 = %f\n",FPInput1, FPInput2);
DPRINTF(CGRA_Detailed,"\n******** ADDRESS GENERATED IN THIS PE %d************\n",Output);
break;
case signExtend:
{
@ -761,11 +885,11 @@ void CGRA_PE::FExecute()
{
if (ins->getSelectDataMemoryAddressBus())
{
DPRINTF(CGRA_Detailed,"\n*********Setting Address %lx ******\n",(unsigned int)FPOutput);
(*addressBs) = (int)FPOutput;
DPRINTF(CGRA_Detailed,"\n*********Setting Address %lx ******\n",(unsigned int)Output);
(*addressBs) = (unsigned int)Output;
(*BsStatus) = CGRA_MEMORY_READ;
(*BsDatatype) = CGRA_MEMORY_FP;
(*alignmentBs) = FPInput2;
(*alignmentBs) = (int) FPInput2;
}
}
}
@ -778,6 +902,8 @@ void CGRA_PE::FExecute()
}
DPRINTF(CGRA_Detailed,"Distance is: %d\n",RegFile.distance);
DPRINTF(PE_DEBUG, "Exiting Execute()\n");
return branch_offset;
}
@ -1025,7 +1151,8 @@ void CGRA_PE::WriteBack()
{
DPRINTF(PE_DEBUG, "Inside WB()\n");
bool ins_predicate = ins->getPredicator();
if(!ins_predicate) {
bool LE_bit = ins->getLE();
if(!ins_predicate && !LE_bit) {
if (ins->getSelectDataMemoryDataBus())
{
@ -1039,6 +1166,7 @@ void CGRA_PE::WriteBack()
}
DPRINTF(PE_DEBUG, "Exiting WB()\n");
}
delete ins;
}
void CGRA_PE::SetNeighbours(int* Left,int* Right,int* Up,int* Down)

View File

@ -98,8 +98,8 @@ public:
void Fetch(CGRA_Instruction* ins);
void Decode();
void IExecute();
void FExecute();
unsigned IExecute();
unsigned FExecute();
void DExecute();
void WriteBack();

View File

@ -42,6 +42,7 @@ void CGRA_RegisterFile::setRF(int regfilesize)
DPRINTF(Regfile_DEBUG, "Inside Register file setRF() %d\n",regfilesize);
REGFILESIZE = regfilesize;
//data_RF.reserve(REGFILESIZE);
//delete[] data_RF;
data_RF = new int[REGFILESIZE];
for(int i=0; i < regfilesize; i++)
data_RF[i] = 0;
@ -56,8 +57,8 @@ int CGRA_RegisterFile::Read(int address)
DPRINTF(CGRA_Detailed,"Requested Register is: %d\n",address);
throw new CGRAException("Register access out of range");
}
//DPRINTF(CGRA_Detailed,"\nIN READ REGFILE R0 = %d\n",data_RF[0]);
//DPRINTF(CGRA_Detailed,"R0: %d\tR1: %d\tR2: %d\tR3: %d\n",data_RF[0],data_RF[1],data_RF[2],data_RF[3]);
DPRINTF(CGRA_Detailed,"R0: %d\tR1: %d\tR2: %d\tR3: %d\n",data_RF[0],data_RF[1],data_RF[2],data_RF[3]);
if(address < config_boundary)
{
DPRINTF(CGRA_Detailed,"\nREAD: REG NUMBER: %d dist: %d\n",address,distance);
@ -77,6 +78,7 @@ void CGRA_RegisterFile::Write(int address, int value)
DPRINTF(Regfile_DEBUG, "Inside Register file Write()\n");
if (address >= REGFILESIZE)
{
DPRINTF(CGRA_Detailed,"Requested Write Register is: %d\n",address);
throw new CGRAException("Register access out of range");
}

View File

@ -36,6 +36,7 @@
#define CGRA_MEMORY_INT 1
#define CGRA_MEMORY_FP 2
/*
OUTDATED: April 2022
Instruction Encoding / Decoding for regular instruction format (R-Type)
31 30 29 28| 27 | 26 25 24| 23 22 21| 20 19| 18 17| 16 15| 14| 13 | 12 | 11 10 9 8 7 6 5 4 3 2 1 0 |
OpCode |Predict| LMUX | RMUX | R1 | R2 | RW | WE| AB | DB | Immediate | /write comparison result to controller
@ -45,74 +46,98 @@ P-Type Instruction Encoding / Decoding
OpCode | 1 | LMUX | RMUX | R1 | R2 | RP | PMUX | Immediate |
*/
/*
64-bit instruction word
Normal Instruction Decode:
63 62 61 | 60 59 58 57 | 56 | 55 | 54 53 52 | 51 50 49 | 48 47 46 45 | 44 43 42 41 | 40 39 38 37 | 36 | 35 | 34 | 33 ... 0
DT | OpCode | P | LE | LMUX | RMUX | R1 | R2 | RW | WE | AB | DB | Immediate
P-Type Instruction Decode:
63 62 61 | 60 59 58 57 | 56 | 55 | 54 53 52 | 51 50 49 | 48 47 46 45 | 44 43 42 41 | 40 39 38 37 | 36 35 34 | 33 ... 0
DT | OpCode | 1 | 0 | LMUX | RMUX | R1 | R2 | RP | PMUX | Immediate
Loop Exit Instruction Decode:
63 62 61 | 60 59 58 57 | 56 | 55 | 54 53 52 | 51 50 49 | 48 47 46 45 | 44 43 42 41 | 40 39 38 37 | 36 | 35 ... 26 | 25...0
DT | OpCode | 0 | 1 | LMUX | RMUX | R1 | R2 | RW | WE | BrImm | Imme
*/
// the UL here is to supress the warning.
#define WIDTH_DATATYPE 0x3UL
#define WIDTH_OPCODE 0xf
#define WIDTH_PREDICT 0x1
#define WIDTH_MUX 0x7
#define WIDTH_REGISTER 0x3
#define WIDTH_ENABLE 0x1
#define WIDTH_IMMEDIATE 0xfff
#define WIDTH_DATATYPE 0x3UL
#define WIDTH_OPCODE 0xfUL
#define WIDTH_PREDICT 0x1UL
#define WIDTH_LE 0x1UL
#define WIDTH_MUX 0x7UL
#define WIDTH_REGISTER 0xfUL
#define WIDTH_ENABLE 0x1UL
#define WIDTH_IMMEDIATE 0x3ffffffffUL
#define WIDTH_BRANCH_OFFSET 0x3ffUL
#define WIDTH_LE_IMMEDIATE 0x3ffffffUL
#define SHIFT_DATATYPE 32
#define SHIFT_OPCODE 28
#define SHIFT_PREDICT 27
#define SHIFT_LMUX 24
#define SHIFT_RMUX 21
#define SHIFT_R1 19
#define SHIFT_R2 17
#define SHIFT_RW 15
#define SHIFT_WE 14
#define SHIFT_ABUS 13
#define SHIFT_DBUS 12
#define SHIFT_IMMEDIATE 00
#define SHIFT_DATATYPE 61
#define SHIFT_OPCODE 57
#define SHIFT_PREDICT 56
#define SHIFT_LE 55
#define SHIFT_LMUX 52
#define SHIFT_RMUX 49
#define SHIFT_R1 45
#define SHIFT_R2 41
#define SHIFT_RW 37
#define SHIFT_WE 36
#define SHIFT_ABUS 35
#define SHIFT_DBUS 34
#define SHIFT_IMMEDIATE 00
#define SHIFT_BRANCH_OFFSET 26
#define INS_DATATYPE (WIDTH_DATATYPE)<<SHIFT_DATATYPE
#define INS_OPCODE (WIDTH_OPCODE)<<SHIFT_OPCODE
#define INS_PREDICT (WIDTH_PREDICT)<<SHIFT_PREDICT
#define INS_LMUX (WIDTH_MUX)<<SHIFT_LMUX
#define INS_RMUX (WIDTH_MUX)<<SHIFT_RMUX
#define INS_R1 (WIDTH_REGISTER)<<SHIFT_R1
#define INS_R2 (WIDTH_REGISTER)<<SHIFT_R2
#define INS_RW (WIDTH_REGISTER)<<SHIFT_RW
#define INS_WE (WIDTH_ENABLE)<<SHIFT_WE
#define INS_AB (WIDTH_ENABLE)<<SHIFT_ABUS
#define INS_DB (WIDTH_ENABLE)<<SHIFT_DBUS
#define INS_IMMEDIATE (WIDTH_IMMEDIATE)<<SHIFT_IMMEDIATE
#define INS_DATATYPE (WIDTH_DATATYPE)<<SHIFT_DATATYPE
#define INS_OPCODE (WIDTH_OPCODE)<<SHIFT_OPCODE
#define INS_PREDICT (WIDTH_PREDICT)<<SHIFT_PREDICT
#define INS_LE (WIDTH_LE)<<SHIFT_LE
#define INS_LMUX (WIDTH_MUX)<<SHIFT_LMUX
#define INS_RMUX (WIDTH_MUX)<<SHIFT_RMUX
#define INS_R1 (WIDTH_REGISTER)<<SHIFT_R1
#define INS_R2 (WIDTH_REGISTER)<<SHIFT_R2
#define INS_RW (WIDTH_REGISTER)<<SHIFT_RW
#define INS_WE (WIDTH_ENABLE)<<SHIFT_WE
#define INS_AB (WIDTH_ENABLE)<<SHIFT_ABUS
#define INS_DB (WIDTH_ENABLE)<<SHIFT_DBUS
#define INS_BRANCH_OFFSET (WIDTH_BRANCH_OFFSET)<<SHIFT_BRANCH_OFFSET
#define INS_IMMEDIATE (WIDTH_IMMEDIATE)<<SHIFT_IMMEDIATE
#define INS_LE_IMMEDIATE (WIDTH_LE_IMMEDIATE)<<SHIFT_IMMEDIATE
// P-Type
#define WIDTH_PDATATYPE 0x3UL
#define WIDTH_POPCODE 0xf
#define WIDTH_PMUX 0x7
#define WIDTH_PREGISTER 0x3
#define WIDTH_PDATATYPE 0x3UL
#define WIDTH_POPCODE 0xfUL
#define WIDTH_PMUX 0x7UL
#define WIDTH_PREGISTER 0xfUL
#define SHIFT_PDATATYPE 32
#define SHIFT_POPCODE 28
#define SHIFT_PLMUX 24
#define SHIFT_PRMUX 21
#define SHIFT_PR1 19
#define SHIFT_PR2 17
#define SHIFT_PRP 15
#define SHIFT_PPMUX 12
#define INS_PDATATYPE (WIDTH_PDATATYPE)<<SHIFT_PDATATYPE
#define INS_POPCODE (WIDTH_POPCODE)<<SHIFT_POPCODE
#define INS_PLMUX (WIDTH_PMUX)<<SHIFT_PLMUX
#define INS_PRMUX (WIDTH_PMUX)<<SHIFT_PRMUX
#define INS_PPMUX (WIDTH_PMUX)<<SHIFT_PPMUX
#define INS_PR1 (WIDTH_REGISTER)<<SHIFT_PR1
#define INS_PR2 (WIDTH_REGISTER)<<SHIFT_PR2
#define INS_PRP (WIDTH_REGISTER)<<SHIFT_PRP
#define SHIFT_PDATATYPE 61
#define SHIFT_POPCODE 57
#define SHIFT_PLMUX 52
#define SHIFT_PRMUX 49
#define SHIFT_PR1 45
#define SHIFT_PR2 41
#define SHIFT_PRP 37
#define SHIFT_PPMUX 34
#define INS_PDATATYPE (WIDTH_PDATATYPE)<<SHIFT_PDATATYPE
#define INS_POPCODE (WIDTH_POPCODE)<<SHIFT_POPCODE
#define INS_PLMUX (WIDTH_PMUX)<<SHIFT_PLMUX
#define INS_PRMUX (WIDTH_PMUX)<<SHIFT_PRMUX
#define INS_PPMUX (WIDTH_PMUX)<<SHIFT_PPMUX
#define INS_PR1 (WIDTH_REGISTER)<<SHIFT_PR1
#define INS_PR2 (WIDTH_REGISTER)<<SHIFT_PR2
#define INS_PRP (WIDTH_REGISTER)<<SHIFT_PRP
// for FloatingPoint support
#define SHIFT_SIGN 31
#define SHIFT_EXPONENT 23
#define SHIFT_SIGN 63
#define SHIFT_EXPONENT 52
#define SHIFT_MANTISSA 00
#define WIDTH_SIGN 0x1
#define WIDTH_EXPONENT 0xff
#define WIDTH_MANTISSA 0xffffff
#define WIDTH_SIGN 0x1UL
#define WIDTH_EXPONENT 0x7ffUL
#define WIDTH_MANTISSA 0xfffffffffffffUL
#define INS_SIGN (WIDTH_SIGN)<<SHIFT_SIGN
#define INS_EXPONENT (WIDTH_EXPONENT)<<SHIFT_EXPONENT
@ -192,8 +217,8 @@ typedef union {
// use the same memory (32 bits).
// The ordering is taken
// from the LSB to the MSB.
unsigned int mantissa : 23;
unsigned int exponent : 8;
unsigned long mantissa : 52;
unsigned int exponent : 11;
unsigned int sign : 1;
} raw;

View File

@ -73,6 +73,9 @@ using namespace TheISA;
volatile unsigned long cgraCycles = 0;
unsigned long debugCycles = 0;
//uint64_t *fetched_instructions;
std::map<unsigned long, int> PC_index_map;
int mem_content;
void
AtomicCGRA::init()
@ -136,6 +139,7 @@ AtomicCGRA::AtomicCGRA(AtomicCGRAParams *p)
//CGRA RELATED START
DPRINTF(CGRA,"Setting Up CGRA\n");
CGRA_Mode = 0;
//cpu_switch = false;
Setup_CGRA();
DPRINTF(CGRA,"CGRA instantiated\n");
}
@ -144,6 +148,7 @@ AtomicCGRA::AtomicCGRA(AtomicCGRAParams *p)
AtomicCGRA::~AtomicCGRA()
{
delete[] CGRA_instructions;
//delete[] fetched_instructions;
delete[] MemData;
delete[] FMemData;
delete[] MemBusDatatype;
@ -567,7 +572,7 @@ AtomicCGRA::readMem(Addr addr, uint8_t * data, unsigned size,
SimpleExecContext& t_info = *threadInfo[curThread];
SimpleThread* thread = t_info.thread;
//printf("readMem() address: %lx\n", addr);
//printf("Break: readMem() address: %lx\n", addr);
// use the CPU's statically allocated read request and packet objects
const RequestPtr &req = data_read_req;
@ -592,7 +597,6 @@ AtomicCGRA::readMem(Addr addr, uint8_t * data, unsigned size,
frag_size = std::min(cacheLineSize() - addrBlockOffset(frag_addr, cacheLineSize()),(Addr) size_left);
while (1) {
//if(frag_addr != 632388)
//predicate = genMemFragmentRequest(req, frag_addr, size, flags,
// byte_enable, frag_size, size_left);
Addr inst_addr = threadInfo[curThread]->thread->pcState().instAddr();
@ -604,17 +608,21 @@ AtomicCGRA::readMem(Addr addr, uint8_t * data, unsigned size,
BaseTLB::Execute);
}
//printf("\tPredicate = %d - fault = %d - getFlags = %d - size_left = %d\n", predicate, fault == NoFault, !req->getFlags().isSet(Request::NO_ACCESS), size_left);
//printf("ReadMem(): Req = %d\n", req);
// Now do the access.
if (predicate && fault == NoFault &&
!req->getFlags().isSet(Request::NO_ACCESS)) {
//printf("ReadMem(): pkt -> ");
Packet pkt(req, Packet::makeReadCmd(req));
//printf("dataStatic -> ");
pkt.dataStatic(data);
if (req->isLocalAccess()) {
dcache_latency += req->localAccessor(thread->getTC(), &pkt);
} else {
//printf("sendPacket -> ");
dcache_latency += sendPacket(dcachePort, &pkt);
}
//printf("done read\n");
@ -625,6 +633,7 @@ AtomicCGRA::readMem(Addr addr, uint8_t * data, unsigned size,
if (req->isLLSC()) {
TheISA::handleLockedRead(thread, req);
}
//printf("\treadMem(): data = %d\n", *data);
}
//If there's a fault, return it
@ -637,7 +646,7 @@ AtomicCGRA::readMem(Addr addr, uint8_t * data, unsigned size,
}
// If we don't need to access further cache lines, stop now.
if (size_left == 0) {
if (size_left <= 0) {
if (req->isLockedRMW() && fault == NoFault) {
assert(!locked);
locked = true;
@ -774,6 +783,8 @@ AtomicCGRA::writeMem(uint8_t *data, unsigned size, Addr addr,
Request::Flags flags, uint64_t *res,
const std::vector<bool>& byte_enable, int xdim)
{
//printf("Break: writeMem() address: %lx\n", addr);
SimpleExecContext& t_info = *threadInfo[curThread];
SimpleThread* thread = t_info.thread;
static uint8_t zero_array[64] = {};
@ -807,7 +818,7 @@ AtomicCGRA::writeMem(uint8_t *data, unsigned size, Addr addr,
int frag_size = 0;
int size_left = size;
int curr_frag_id = 0;
bool predicate = true;
//bool predicate = true;
Fault fault = NoFault;
frag_size = std::min(cacheLineSize() - addrBlockOffset(frag_addr, cacheLineSize()),(Addr) size_left);
@ -822,13 +833,13 @@ AtomicCGRA::writeMem(uint8_t *data, unsigned size, Addr addr,
// if (predicate){
fault = thread->dtb->translateAtomic(req, thread->getTC(),
BaseTLB::Execute);
//printf("WriteMem(): fault = %d\n", fault == NoFault);
//printf("Break: WriteMem(): fault = %d\n", fault == NoFault);
//printf("WriteMem(): Req: %d\n", req);
fault = NoFault;
//fault = NoFault;
// }
// Now do the access.
if (predicate && fault == NoFault) {
if (fault == NoFault) {
bool do_access = true; // flag to suppress cache access
//std::cout << "curr_frag_id = " << curr_frag_id << std::endl;
if (req->isLLSC()) {
@ -836,7 +847,7 @@ AtomicCGRA::writeMem(uint8_t *data, unsigned size, Addr addr,
do_access =
TheISA::handleLockedWrite(thread, req,
dcachePort.cacheBlockMask);
//printf("handleLockWrite(): do_access = %d\n", do_access);
//printf("Break: handleLockWrite(): do_access = %d\n", do_access);
do_access = true;
} else if (req->isSwap()) {
assert(curr_frag_id == 0);
@ -845,7 +856,7 @@ AtomicCGRA::writeMem(uint8_t *data, unsigned size, Addr addr,
req->setExtraData(*res);
}
}
//printf("writeMem(): do_access = %d - getFlags = %d\n", do_access, !req->getFlags().isSet(Request::NO_ACCESS));
//printf("Break: writeMem(): do_access = %d - getFlags = %d\n", do_access, !req->getFlags().isSet(Request::NO_ACCESS));
if (do_access && !req->getFlags().isSet(Request::NO_ACCESS)) {
Packet pkt(req, Packet::makeWriteCmd(req));
pkt.dataStatic(data);
@ -874,11 +885,13 @@ AtomicCGRA::writeMem(uint8_t *data, unsigned size, Addr addr,
if (res && req->isSwap() && req->isCondSwap()) {
*res = req->getExtraData();
}
} else {
DPRINTF(CGRA||CGRA_Detailed, "\n***WARNING: CGRA WriteMem: Cannot translate to physical address!***\n");
}
size_left = 0;
//size_left = 0;
//If there's a fault or we don't need to access a second cache line,
//stop now.
if (fault != NoFault || size_left == 0)
if (fault != NoFault || size_left <= 0)
{
if (req->isLockedRMW() && fault == NoFault) {
assert(!req->isMasked());
@ -888,6 +901,7 @@ AtomicCGRA::writeMem(uint8_t *data, unsigned size, Addr addr,
if (fault != NoFault && req->isPrefetch()) {
return NoFault;
} else {
//DPRINTF(CGRA, "WARNING: Write no fault: %u\n", fault==NoFault);
return fault;
}
}
@ -971,6 +985,10 @@ AtomicCGRA::amoMem(Addr addr, uint8_t* data, unsigned size,
void AtomicCGRA::CGRA_Execution(SimpleExecContext& t_info)
{
Prolog_Branch_Cycle = 0;
//SimpleExecContext& t_info = *threadInfo[curThread];
SimpleThread* thread = t_info.thread;
DPRINTF(SimpleCPU, "CGRA Pipeline\n");
Fault fault = NoFault;
DPRINTF(CGRA_Execute, "\n\n ~~~~~~ CGRA_Execution @ numCycles = %d ~~~~~~~\n", cgraCycles);
@ -1015,7 +1033,7 @@ void AtomicCGRA::CGRA_Execution(SimpleExecContext& t_info)
for (unsigned i = 0; i < CGRA_XDim; i++)
for (unsigned j = 0; j < CGRA_YDim; j++)
cgra_PEs[i * CGRA_YDim + j].Decode();
if(!isTCdynamic)
{
if((Len == 0) & (state == KERN))
@ -1028,11 +1046,11 @@ void AtomicCGRA::CGRA_Execution(SimpleExecContext& t_info)
{
for (int j = 0; j < CGRA_YDim; j++)
{
DPRINTF(CGRA_Detailed, "Ins: %ld, %lx @ PE %d\n", CGRA_instructions[i*CGRA_YDim + j], CGRA_instructions[i*CGRA_YDim + j], (i*CGRA_YDim)+j);
if(cgra_PEs[i * CGRA_YDim + j].GetDatatype() == character || cgra_PEs[i * CGRA_YDim + j].GetDatatype() == int32) //; int16
cgra_PEs[i * CGRA_YDim + j].IExecute();
DPRINTF(CGRA_Detailed, "Ins: %lx @ %lx \t@ PE %d\n", CGRA_instructions[i*CGRA_YDim + j], thread->instAddr() + ((i*CGRA_XDim)+j)*(sizeof(unsigned long)), (i*CGRA_YDim)+j);
if(cgra_PEs[i * CGRA_YDim + j].GetDatatype() == character || cgra_PEs[i * CGRA_YDim + j].GetDatatype() == int32 || cgra_PEs[i * CGRA_YDim + j].GetDatatype() == int16)
Prolog_Branch_Cycle += cgra_PEs[i * CGRA_YDim + j].IExecute();
else if(cgra_PEs[i * CGRA_YDim + j].GetDatatype() == float32)
cgra_PEs[i * CGRA_YDim + j].FExecute();
Prolog_Branch_Cycle += cgra_PEs[i * CGRA_YDim + j].FExecute();
//else if(cgra_PEs[i * CGRA_YDim + j].GetDatatype() == float64)
// cgra_PEs[i * CGRA_YDim + j].DExecute();
@ -1069,14 +1087,20 @@ void AtomicCGRA::CGRA_Execution(SimpleExecContext& t_info)
if (MemBusStatus[i] == CGRA_MEMORY_READ)
{
//read int of fp memdata based on the datatype of the membus.
if(MemBusDatatype[i] == CGRA_MEMORY_INT)
readMem((Addr) MemAddress[i], (uint8_t *) &MemData[i], (unsigned)MemAccessAlignment[i], (unsigned) 163, be, i);
else
readMem((Addr) MemAddress[i], (uint8_t *) &FMemData[i], (unsigned)MemAccessAlignment[i], (unsigned) 163, be, i);
DPRINTF(CGRA_Execute, "\n************* MEM READ *************\n");
DPRINTF(CGRA_Execute, "Row: %d - Address: %lx\n", i, MemAddress[i]);
//int content;
if(MemBusDatatype[i] == CGRA_MEMORY_INT){
readMem((Addr) MemAddress[i], (uint8_t *) &mem_content, (unsigned)MemAccessAlignment[i], (unsigned) 163, be, i);
MemData[i] = mem_content;
mem_content = 0;
DPRINTF(CGRA_Execute, "Read data: %d\n", MemData[i]);
}
else {
readMem((Addr) MemAddress[i], (uint8_t *) &FMemData[i], (unsigned)MemAccessAlignment[i], (unsigned) 163, be, i);
DPRINTF(CGRA_Execute, "Read data: %d\n", FMemData[i]);
}
MemAccessCount++;
printf("\n************* MEM READ *************\n");
printf("Row: %d - address: %d - data: %d\n", i, MemAddress[i], MemData[i]);
//x_dim=0;
MemBusStatus[i] = CGRA_MEMORY_RESET;
}
else if (MemBusStatus[i] == CGRA_MEMORY_WRITE)
@ -1084,42 +1108,19 @@ void AtomicCGRA::CGRA_Execution(SimpleExecContext& t_info)
// write int of fp memdata based on the datatype of the membus.
DPRINTF(CGRA_Memory, "i in the MemBus loop %d\n", i);
DPRINTF(CGRA_Detailed, "In Memwrite with membus: %d\n", MemBusDatatype[i]);
//DPRINTF(CGRA_Detailed, "In Memwrite with membus: %d\n", i);
if(MemBusDatatype[i] == CGRA_MEMORY_INT)
{
DPRINTF(CGRA_Detailed, "In writing INT %d\t to address:%lx\t -- &Data: %lx\t and uint: %lx\n" , MemData[i], MemAddress[i], &MemData[i], (uint8_t *) &MemData[i]);
/****************************/
///////////////////////////////////
/*
printf("\n********** STARTING READ/WRITE TEST ************\n\n");
int k = 100;
const std::vector<bool> be2;
for(k=200; k<300; k++){
//const std::vector<bool> be2;
//const std::vector<bool> be3;
uint8_t writeData = k;
int wm = (writeMem((uint8_t *) &writeData, (unsigned) MemAccessAlignment[i], (Addr) MemAddress[i], (unsigned) 131, unknownRes, be2, i) == NoFault);
uint8_t readData;
int rm = (readMem((Addr) MemAddress[i], (uint8_t *) &readData, (unsigned)MemAccessAlignment[i], (unsigned) 163, be, i) == NoFault);
printf("writeData(%d) = %d\treadData(%d) = %d\n", wm, writeData, rm, readData);
}
printf("\n********** END READ/WRITE TEST ************\n\n");
*/
///////////////////////////////////
DPRINTF(CGRA||CGRA_Detailed, "In writing INT %d\t to address:%lx\t -- row: %d\n" , MemData[i], (Addr) (MemAddress[i] & 0xffffffff), i);
const std::vector<bool> be1;
writeMem((uint8_t *) &MemData[i], (unsigned) MemAccessAlignment[i], (Addr) MemAddress[i], (unsigned) 0b10110111, unknownRes, be1, i);
uint8_t memdata;
readMem((Addr) MemAddress[i], (uint8_t *) &memdata, (unsigned)MemAccessAlignment[i], (unsigned) 163, be1, i);
writeMem((uint8_t *) &MemData[i], (unsigned) MemAccessAlignment[i], (Addr) (MemAddress[i] & 0xffffffff), (unsigned) 0b10110111, unknownRes, be1, i);
/*****************************/
}
else
{
DPRINTF(CGRA_Detailed, "In writing %f\t to address:%lx\t -- &Data: %lx\t and uint: %lx\n" , FMemData[i], MemAddress[i], &FMemData[i], (uint8_t *) &FMemData[i]);
//writeMem((uint8_t *) &FMemData[i], (unsigned) MemAccessAlignment[i], (Addr) MemAddress[i], (unsigned) 0b10110111, unknownRes, be, i);
DPRINTF(CGRA||CGRA_Detailed, "In writing %f\t to address:%lx\t -- row: %d\n" , FMemData[i], MemAddress[i], i);
const std::vector<bool> be1;
writeMem((uint8_t *) &FMemData[i], (unsigned) MemAccessAlignment[i], (Addr) MemAddress[i], (unsigned) 0b10110111, unknownRes, be1, i);
}
MemAccessCount++;
//x_dim=0;
@ -1174,6 +1175,15 @@ void AtomicCGRA::CGRA_advanceTime()
}
} //CGRA_Execution
/*void AtomicCGRA::fetch_CGRA_inst(long cycle_pc, uint64_t* CGRA_inst){
DPRINTF(CGRA_Execute, "Fetching instructions @ %lx\n", cycle_pc);
for(int i=0; i<CGRA_XDim; i++)
for(int j=0; j<CGRA_YDim; j++){
DPRINTF(CGRA_Execute, "%d: Fetched %lx\t\t", i*CGRA_XDim+j, (uint64_t) *((long*)cycle_pc + (i*CGRA_XDim+j)));
CGRA_inst[i*CGRA_XDim + j] = (uint64_t) *((long*)cycle_pc + (i*CGRA_XDim+j));
}
}*/
void
AtomicCGRA::tick()
{
@ -1260,26 +1270,64 @@ AtomicCGRA::tick()
Packet ifetch_pkt = Packet(ifetch_req, MemCmd::ReadReq);
if(is_CPU()) {
ifetch_pkt.dataStatic(&inst);
//DPRINTF(CGRA_Execute, "CPU1 is_CPU(): %lx\n", inst);
}
ifetch_pkt.dataStatic(&inst);
//DPRINTF(CGRA_Execute, "CPU::Fetched inst %lx @ PC: %lx\n", inst, thread->instAddr());
}
else
ifetch_pkt.dataStatic(CGRA_instructions);
ifetch_pkt.dataStatic(CGRA_instructions);
icache_latency = sendPacket(icachePort, &ifetch_pkt);
assert(!ifetch_pkt.isError());
icache_latency = sendPacket(icachePort, &ifetch_pkt);
assert(!ifetch_pkt.isError());
// ifetch_req is initialized to read the instruction directly
// into the CPU object's inst field.
//}
/* Added by Vinh TA */
if(!is_CPU()){
DPRINTF(CGRA_Execute, "Fetching PC: %lx - Index: %d\n", thread->instAddr(), PC_index_map[thread->instAddr()]);
for(int i=0; i<CGRA_XDim*CGRA_YDim; i++){
int addr = PC_index_map[thread->instAddr()] + i;
if((CGRA_instructions[i] != fetched_instructions[addr])){ // & (INS_DATATYPE<<SHIFT_DATATYPE)) < int32){
DPRINTF(ExecFaulting||CGRA_Detailed, "Instruction Fetch Failed @ PE %d - Fetching back up instructions\n", i);
//int addr = PC_index_map[thread->instAddr()] + i;
CGRA_instructions[i] = fetched_instructions[addr];
DPRINTF(ExecFaulting, "Refetched Instructions: %lx\n", CGRA_instructions[i]);
}
}
}
}
}
if (is_CPU()) {
//DPRINTF(SimpleCPU, "CGRA is_CPU().\n");
//DPRINTF(CGRA, "inside isCPU reg: %d\n", (int) thread->readIntReg(11));
//DPRINTF(CGRA, "inside isCPU reg: %d\n", (int) thread->readIntReg(11));
/*char output[30];
char status[6];
FILE *fp = popen("test -f CGRAExec/CGRA_ACTIVE.* && echo true || echo false", "r");
if(fp == NULL)
fatal("Failed to check CGRA status!\n");
fgets(output, sizeof(output), fp);
//DPRINTF(CGRA, "\n*******************\nCOMMAND OUTPUT: %s \n****************\n", output);
pclose(fp);
if(output[0] == 't'){
//command = "ls CGRAExec/CGRA_ACTIVE.*";
fp = popen("ls CGRAExec/CGRA_ACTIVE.*", "r");
if(fp == NULL)
fatal("Failed to find CGRA loop!\n");
fgets(output, sizeof(output), fp);
memcpy(status, output+21, 6);
pclose(fp);
cpu_switch = true;
loopID = atoi(status);
DPRINTF(CGRA||CGRA_Detailed, "Switching to CGRA - loop %d\n", loopID);
//command = "rm CGRAExec/CGRA_ACTIVE*";
fp = popen("rm CGRAExec/CGRA_ACTIVE*", "r");
if(fp == NULL)
fatal("Cannot remove loopID file!\n");
pclose(fp);
}*/
#ifdef DEBUG_BINARY
DPRINTF(CGRA||CGRA_Detailed, "CPU::Executing inst %lx @ PC: %lx\n", inst, thread->instAddr());
#endif
preExecute();
Tick stall_ticks = 0;
@ -1305,6 +1353,30 @@ AtomicCGRA::tick()
postExecute();
}
#ifdef PC_DEBUG
if((unsigned long) thread->instAddr() >= PC_DEBUG_BASE && (unsigned long) thread->instAddr() <= PC_DEBUG_TOP){
DPRINTF(CGRA||CGRA_Detailed, "Inst %lx @ PC: %lx\n", inst, thread->instAddr());
DPRINTF(CGRA||CGRA_Detailed, "\tR0: %d - R1: %d - R2: %d - R3: %d - R4: %d - R5: %d - R6: %d - R7: %d\n", \
(int)thread->readIntReg(0), \
(int)thread->readIntReg(1), \
(int)thread->readIntReg(2), \
(int)thread->readIntReg(3), \
(int)thread->readIntReg(4), \
(int)thread->readIntReg(5), \
(int)thread->readIntReg(6), \
(int)thread->readIntReg(7));
DPRINTF(CGRA||CGRA_Detailed, "\tR8: %d - R9: %d - R10: %d - R11: %lx - R12: %lx - R13: %lx - R14: %lx - R15: %lx\n", \
(int)thread->readIntReg(8), \
(int)thread->readIntReg(9), \
(int)thread->readIntReg(10),\
(int)thread->readIntReg(11),\
(int)thread->readIntReg(12),\
(int)thread->readIntReg(13),\
(int)thread->readIntReg(14),\
(int)thread->readIntReg(15));
}
#endif
// @todo remove me after debugging with legion done
if (curStaticInst && (!curStaticInst->isMicroop() ||
curStaticInst->isFirstMicroop()))
@ -1323,31 +1395,43 @@ AtomicCGRA::tick()
latency += divCeil(stall_ticks, clockPeriod()) *
clockPeriod();
}
if ((int) thread->readIntReg(11) == 17)
/*if ((int) thread->readIntReg(CPU_STATE_REG) == CGRA_DEACTIVATE) // 17)
{
DPRINTF(CGRA,"********Deleting CGRA********\n");
thread->setStatus(ThreadContext::Halted);
suspendContext(0);
}
//thread->setStatus(ThreadContext::Halted);
//suspendContext(0);
}*/ // No more implemented
if ((int) thread->readIntReg(11) == 15)
if ((int) thread->readIntReg(CPU_STATE_REG) == CGRA_ACTIVATE) //15)
//if(cpu_switch)
{
DPRINTF(CGRA,"************************Setting UP the CGRA************\n");
loopID = thread->readIntReg(CGRA_LOOPID_REG);
//cpu_switch = false;
/*FILE* fp = fopen("CGRAExec/CGRA.ACTIVE", "r");
if(fp == NULL) fatal("Failed to read loopID\n");
fscanf(fp, "%d\n%d", &loopID, &callback_reg);
fclose(fp);
//fp = popen("rm CGRAExec/CGRA.ACTIVE", "r");
//if(fp == NULL) fatal("Failed to remove file!\n");
//pclose(fp);*/
DPRINTF(CGRA||CGRA_Detailed,"\n\n**************Setting UP the CGRA - loopID: %d******************\n", loopID);
Setup_CGRA_Execution(thread);
if(Prolog>0 || KernelCounter>0 || EPILog>0)
{
Switch_To_CGRA();
DPRINTF(CGRA,"\nExecuting 1 CGRA Cycle.\n");
schedule(tickEvent, nextCycle());
DPRINTF(CGRA,"\nExiting 1 CGRA Cycle.\n");
}
else
{
//CGRA execution over
DPRINTF(CGRA||CGRA_Detailed,"SHOULD NOT GET HERE!\n");
Prepare_to_Switch_Back_to_CPU(thread);
Restore_CPU_Execution(thread);
thread->setIntReg(11, 16);
DPRINTF(CGRA, "Setting CPU_STATE_REG to %d\n", CGRA_SWITCH);
thread->setIntReg(CPU_STATE_REG, CGRA_SWITCH); // 16);
Switch_To_CPU();
DPRINTF(CGRA,"\nCALL IN ADVANCE INST TO CPU.\n");
@ -1377,6 +1461,12 @@ AtomicCGRA::tick()
if (_status != Idle)
reschedule(tickEvent, curTick() + latency, true);
}
if ((int) thread->readIntReg(SIM_CLOCK_REG) == SYS_CLOCK)
{
DPRINTF(CGRA,"********Reading Clocks: %d********\n", debugCycles);
thread->setIntReg(SIM_CLOCK_REG, debugCycles);
}
}
else {
DPRINTF(CGRA_Execute, "Inside CGRA Execution else statement.\n");
@ -1389,24 +1479,25 @@ AtomicCGRA::tick()
if(state==FINISH)
{
DPRINTF(CGRA,"************************PREPARING TO MOVE TO CPU************\n");
DPRINTF(CGRA_Detailed,"\n************************PREPARING TO MOVE TO CPU************\n");
Prepare_to_Switch_Back_to_CPU(thread);
}
/*}
//CGRA EXECUTION OVER
if ((int) thread->readIntReg(8) == 66)
{
DPRINTF(CGRA,"newPC=%ld, II=%ld, EPILog=%ld, Prolog=%ld, Len=%ld\n", (long) newPC, (long) II, (long) EPILog, (long) Prolog, (long) Len);
DPRINTF(CGRA,"**********************CGRA Execution is over**********************\n");
if ((int) thread->readIntReg(CGRA_STATE_REG) == CGRA_EXEC_OVER) // 66)
{*/
//DPRINTF(CGRA,"newPC=%ld, II=%ld, EPILog=%ld, Prolog=%ld, Len=%ld\n", (long) newPC, (long) II, (long) EPILog, (long) Prolog, (long) Len);
DPRINTF(CGRA_Detailed,"newPC=%ld, II=%ld, EPILog=%ld, Prolog=%ld, Len=%ld\n", (long) newPC, (long) II, (long) EPILog, (long) Prolog, (long) Len);
DPRINTF(CGRA||CGRA_Detailed,"\n\n********************** CGRA Execution is over @ %d **********************\n", debugCycles);
Restore_CPU_Execution(thread);
Switch_To_CPU();
thread->setIntReg(11, 16);
thread->setIntReg(8, 60);
DPRINTF(CGRA,"******REG R11= %d*********\n",(int)thread->readIntReg(11));
DPRINTF(CGRA,"AFTER COMPLETETION PC: %x\n",(unsigned long) thread->instAddr());
//thread->setIntReg(CPU_STATE_REG, callback_reg);
//thread->setIntReg(CGRA_STATE_REG, 60);
//DPRINTF(CGRA,"******CPU_STATE_REG = %lx*********\n",(unsigned)thread->readIntReg(CPU_STATE_REG));
//DPRINTF(CGRA_Detailed,"AFTER COMPLETETION PC: %x\n\n\n",(unsigned long) thread->instAddr());
for (int i = 0; i < CGRA_XDim; i++)
for (int j = 0; j < CGRA_YDim; j++)
cgra_PEs[i * CGRA_YDim + j].ClearRegfile();
//If thread is not joined after CGRA Execution
//and we need to continue from old PC of CGRA controller
if(fault != NoFault || !t_info.stayAtPC)
@ -1460,7 +1551,7 @@ AtomicCGRA::tick()
DPRINTF(Setup_DEBUG, "Inside Setup_CGRA() with %d x %d and RF %d\n", CGRA_XDim, CGRA_YDim, RFSize);
//CGRA_instructions = new uint32_t[16]; //Shail: TODO Parameterize this
CGRA_instructions = new uint64_t[CGRA_XDim * CGRA_YDim];
CGRA_instructions = new uint64_t[CGRA_XDim * CGRA_YDim];
//unknownRes = new uint64_t[16]; // Shail: TODO Parameterize this
unknownRes = new uint64_t[CGRA_XDim * CGRA_YDim];
written = 0;
@ -1645,12 +1736,12 @@ void AtomicCGRA::Setup_CGRA_Parameters()
std::ostringstream osLoopID;
osLoopID << TotalLoops;
ifstream execLoop;
/*(ifstream execLoop;
execLoop.open("./CGRAExec/LoopID.txt");
std::string loopID;
execLoop >> loopID;
execLoop >> loopID;*/
std::string directoryPath = "./CGRAExec/" + loopID + "/initCGRA.txt";
std::string directoryPath = "./CGRAExec/L" + std::to_string(loopID) + "/initCGRA.txt";
unsigned long temp;
ifstream initCGRAFile;
@ -1668,20 +1759,23 @@ void AtomicCGRA::Setup_CGRA_Parameters()
initCGRAFile >> EPILogPC;
initCGRAFile >> PROLogPC;
initCGRAFile >> KernelPC;
initCGRAFile >> Prolog_extension_cycle;
initCGRAFile >> Prolog_version_cycle;
initCGRAFile.close();
DPRINTF(CGRA,"Loop count is %d\n",KernelCounter);
DPRINTF(CGRA,"Epilog Length is %d\n",EPILog);
DPRINTF(CGRA,"LiveVar_St_Epilog Length is %d\n",LiveVar_St_Epilog);
DPRINTF(CGRA,"II is %d\n",II);
DPRINTF(CGRA_Detailed,"Loop count is %d\n",KernelCounter);
DPRINTF(CGRA_Detailed,"Epilog Length is %d\n",EPILog);
DPRINTF(CGRA_Detailed,"LiveVar_St_Epilog Length is %d\n",LiveVar_St_Epilog);
DPRINTF(CGRA_Detailed,"II is %d\n",II);
int epilog_count = (int) ceil((float) ((EPILog-LiveVar_St_Epilog)/II));
int prolog_count = 1;
DPRINTF(CGRA,"Epilog count is %d\n",epilog_count);
DPRINTF(CGRA,"Prolog count is %d\n",prolog_count);
DPRINTF(CGRA,"Kernel Counter is %d\n",KernelCounter);
DPRINTF(CGRA, "Prolog PC is %lx\n,", PROLogPC);
DPRINTF(CGRA, "Kernel PC is %lx\n", KernelPC);
DPRINTF(CGRA, "Epilog PC is %lx\n", EPILogPC);
DPRINTF(CGRA_Detailed,"Epilog count is %d\n",epilog_count);
DPRINTF(CGRA_Detailed,"Prolog count is %d\n",prolog_count);
DPRINTF(CGRA_Detailed,"Kernel Counter is %d\n",KernelCounter);
DPRINTF(CGRA_Detailed, "Prolog PC is %lx\n", PROLogPC);
DPRINTF(CGRA_Detailed, "Kernel PC is %lx\n", KernelPC);
DPRINTF(CGRA_Detailed, "Epilog PC is %lx\n", EPILogPC);
newPC=PROLogPC;
Len=Prolog;
@ -1689,31 +1783,99 @@ void AtomicCGRA::Setup_CGRA_Parameters()
CycleCounter = 0;
Conditional_Reg = true;
if(KernelCounter <= 0) isTCdynamic = true;
isTCdynamic = (KernelCounter <= 0)? true:false;
DPRINTF(CGRA,"CGRA PARAMETERS: PROLOG= %d, EPILOG=%d, II=%d, KernelCounter=%d\n",Prolog,EPILog,II,KernelCounter);
DPRINTF(CGRA_Execute,"CGRA PARAMETERS: PROLOG= %d, EPILOG=%d, II=%d, KernelCounter=%d TCdynamic=%d\n",Prolog,EPILog,II,KernelCounter,isTCdynamic);
DPRINTF(CGRA,"CGRA PARAMETERS: PROLOGPC= %lx, EPILOGPC=%lx, KernelPC=%lx\n",(unsigned int)PROLogPC,(unsigned int)EPILogPC,(unsigned int)KernelPC);
DPRINTF(CGRA_Execute,"CGRA PARAMETERS: PROLOG=%d, EPILOG=%d, II=%d, KernelCounter=%d TCdynamic=%d, PROLOG_EXT=%d, PROLOG_VERSION_LEN=%d\n",Prolog,EPILog,II,KernelCounter,isTCdynamic, Prolog_extension_cycle, Prolog_version_cycle);
DPRINTF(CGRA_Detailed,"CGRA PARAMETERS: PROLOGPC= %lx, EPILOGPC=%lx, KernelPC=%lx\n",(unsigned int)PROLogPC,(unsigned int)EPILogPC,(unsigned int)KernelPC);
DPRINTF(CGRA_Execute,"CGRA PARAMETERS: PROLOGPC= %lx, EPILOGPC=%lx, KernelPC=%lx\n",(unsigned int)PROLogPC,(unsigned int)EPILogPC,(unsigned int)KernelPC);
// Added by Vinh TA
// Update: instruction fetch backup for fetch errors (read directly from bin file
//delete[] fetched_instructions;
DPRINTF(CGRA_Detailed, "Instruction size: %d - backup size: %d\n", (Prolog + Prolog_extension_cycle + II + EPILog)*CGRA_XDim*CGRA_YDim, sizeof(fetched_instructions)/sizeof(uint64_t));
if((Prolog + Prolog_extension_cycle + II + EPILog)*CGRA_XDim*CGRA_YDim > MAX_INSTRUCTION_SIZE)
fatal("FATAL: Instructions exceeded MAX_INSTRUCTION_SIZE!\n");
//fetched_instructions = new uint64_t[(Prolog + Prolog_extension_cycle + II + EPILog)*CGRA_XDim*CGRA_YDim];
std::string prolog_ins = "./CGRAExec/L" + std::to_string(loopID) + "/prolog_ins.bin";
std::string kernel_ins = "./CGRAExec/L" + std::to_string(loopID) + "/kernel_ins.bin";
std::string epilog_ins = "./CGRAExec/L" + std::to_string(loopID) + "/epilog_ins.bin";
FILE *instruction_stream;
int read_size, pro_ext_size, pro_ver_size;
instruction_stream = fopen(prolog_ins.c_str(), "rb");
fread(&read_size,sizeof(int),1,instruction_stream);
fread(&pro_ext_size,sizeof(int),1,instruction_stream);
fread(&pro_ver_size,sizeof(int),1,instruction_stream);
DPRINTF(ExecFaulting,"Read prolog size: %d - prolog ext size: %d - prolog ver size: %d\n", read_size, pro_ext_size, pro_ver_size);
fread(&fetched_instructions,sizeof(uint64_t),(read_size + pro_ext_size),instruction_stream);
fclose(instruction_stream);
instruction_stream = fopen(kernel_ins.c_str(), "rb");
fread(&read_size,sizeof(int),1,instruction_stream);
DPRINTF(ExecFaulting,"Read kernel size: %d\n", read_size);
fread(&fetched_instructions[(Prolog+Prolog_extension_cycle)*CGRA_XDim*CGRA_YDim],sizeof(uint64_t),read_size,instruction_stream);
fclose(instruction_stream);
instruction_stream = fopen(epilog_ins.c_str(), "rb");
fread(&read_size,sizeof(int),1,instruction_stream);
DPRINTF(ExecFaulting,"Read epilog size: %d\n", read_size);
fread(&fetched_instructions[(Prolog+Prolog_extension_cycle+II)*CGRA_XDim*CGRA_YDim],sizeof(uint64_t),read_size,instruction_stream);
fclose(instruction_stream);
/* Manually adjust insword for patricia bench!
for(int i=0; i<(Prolog + Prolog_extension_cycle + II + EPILog)*CGRA_XDim*CGRA_YDim; i++)
if(fetched_instructions[i] == 0x4d1c000800000002UL && (i % 64 == 36)) fetched_instructions[i] -= 1; */
DPRINTF(ExecFaulting, "Fetched prolog:\n");
for(int i=0; i<Prolog*CGRA_XDim*CGRA_YDim + pro_ext_size; i++)
DPRINTF(ExecFaulting, "%d: %lx\n", i, fetched_instructions[i]);
for(int i=0; i<Prolog+Prolog_extension_cycle; i++)
PC_index_map.insert(std::make_pair(PROLogPC + (i*CGRA_XDim*CGRA_YDim*sizeof(uint64_t)),(i*CGRA_XDim*CGRA_YDim)));
DPRINTF(ExecFaulting, "Fetched kernel:\n");
for(int i=0; i<II*CGRA_XDim*CGRA_YDim; i++)
DPRINTF(ExecFaulting, "%d: %lx\n", i, fetched_instructions[(Prolog*CGRA_XDim*CGRA_YDim)+i]);
for(int i=Prolog+Prolog_extension_cycle, j=0; i<Prolog+Prolog_extension_cycle+II; i++)
PC_index_map.insert(std::make_pair(KernelPC + ((j++)*CGRA_XDim*CGRA_YDim*sizeof(uint64_t)),(i*CGRA_XDim*CGRA_YDim)));
DPRINTF(ExecFaulting, "Fetched epilog:\n");
for(int i=0; i<EPILog*CGRA_XDim*CGRA_YDim; i++)
DPRINTF(ExecFaulting, "%d: %lx\n", i, fetched_instructions[((Prolog+II)*CGRA_XDim*CGRA_YDim)+i]);
for(int i=Prolog+Prolog_extension_cycle+II, j=0; i<Prolog+Prolog_extension_cycle+II+EPILog; i++)
PC_index_map.insert(std::make_pair(EPILogPC + ((j++)*CGRA_XDim*CGRA_YDim*sizeof(uint64_t)),(i*CGRA_XDim*CGRA_YDim)));
}
void AtomicCGRA::Setup_CGRA_Execution(SimpleThread* thread)
{
DPRINTF(CGRA,"Inside Setup_CGRA_Execution\n");
DPRINTF(CGRA,"CGRA: OLD PC: %x\n",(unsigned int) thread->instAddr());
DPRINTF(CGRA_Detailed,"Inside Setup_CGRA_Execution\n");
DPRINTF(CGRA_Detailed,"\nEntering CGRA: OLD PC: %x\n",(unsigned int) thread->instAddr());
//DPRINTF(Instruction_print, "CGRA: OLD PC: %x\n",(unsigned long) tc->instAddr());
Setup_CGRA_Parameters();
DPRINTF(CGRA,"CGRA PC : %x\n",(unsigned int)newPC);
DPRINTF(CGRA,"**********************CGRA Execution is started**************************** \n");
DPRINTF(CGRA,"\n********************** CGRA Execution is started @ %d ****************************\n", debugCycles);
backPC = thread->pcState();
thread->pcState((Addr) newPC);
for (int i = 0; i < CGRA_XDim; i++)
{
for (int j = 0; j < CGRA_YDim; j++)
{
cgra_PEs[i * CGRA_YDim + j].SetController_Reg();
}
}
}
void AtomicCGRA::Prepare_to_Switch_Back_to_CPU(SimpleThread* thread)
{
thread->setIntReg(11, 16);
//thread->setIntReg(CPU_STATE_REG, CGRA_SWITCH); // 16);
//make sure to go back to actual processor state
thread->setIntReg(8, 66);
//thread->setIntReg(CGRA_STATE_REG, CGRA_EXEC_OVER); // 66);
//make sure that you reset the state of the core to make sure it will fetch afterward
_status = BaseCGRA::Running;
}
@ -1763,12 +1925,20 @@ void AtomicCGRA::CGRA_advancePC(SimpleThread* thread)
{
if(state==PRO)
{
DPRINTF(CGRA_Detailed,"\nPROLOG->KERNEL\n");
DPRINTF(Instruction_print,"\nPROLOG->KERNEL\n");
state=KERN;
newPC=KernelPC;
Len=II;
Conditional_Reg=1;
if(Prolog_Branch_Cycle == 0){
DPRINTF(CGRA_Detailed,"\nPROLOG->KERNEL\n");
DPRINTF(Instruction_print,"\nPROLOG->KERNEL\n");
state=KERN;
newPC=KernelPC;
Len=II;
Conditional_Reg=1;
}
else {
newPC += ((sizeof(long))*(CGRA_XDim*CGRA_YDim)*Prolog_Branch_Cycle);
DPRINTF(CGRA_Execute, "\nJumped to: %lx\n", newPC);
Len = Prolog_version_cycle;
state = EPI;
}
}
else if(state==KERN)
{
@ -1788,13 +1958,16 @@ void AtomicCGRA::CGRA_advancePC(SimpleThread* thread)
}
}
else
{
//DPRINTF(Instruction_print, "newPC: %lx\n", newPC) ;
//DPRINTF(Instruction_print, "size of long: %ld\t size of unsigned long: %ld\n", sizeof(long), sizeof(unsigned long));
//exit(1);
newPC+=(sizeof(long))*(CGRA_XDim*CGRA_YDim); //Shail: Parameterize this
{
if(Prolog_Branch_Cycle == 0)
newPC += ((sizeof(long))*(CGRA_XDim*CGRA_YDim));
else{
newPC += ((sizeof(long))*(CGRA_XDim*CGRA_YDim)*Prolog_Branch_Cycle);
DPRINTF(CGRA_Execute, "\nJumped to: %lx\n", newPC);
Len = Prolog_version_cycle;
state = EPI;
}
}
thread->pcState((Addr) newPC);
}

View File

@ -54,6 +54,28 @@
#define KERN 2
#define EPI 3
#define FINISH 4
#define CGRA_STATE_REG 0
#define CPU_STATE_REG 12
#define SIM_CLOCK_REG 12
#define CGRA_LOOPID_REG 11
#define CGRA_ACTIVATE 0xefefefef // Previously 15
#define CGRA_DEACTIVATE 0xdfffffff // Previously 17
#define CGRA_SWITCH 0xcfcfcfcf // Previously 16
#define CGRA_EXEC_OVER 0xbfffffff // Previously 66
#define SYS_CLOCK 0xafffffff
//#define DEBUG_BINARY // Print binary inst and PC for CPU exec
//#define PC_DEBUG // Print set of 14 regiters at selected PC range
#ifdef PC_DEBUG
#define PC_DEBUG_BASE 0x36a48
#define PC_DEBUG_TOP 0x377b8
#endif
#define MAX_INSTRUCTION_SIZE 32000
/*CGRA RELATED INCLUDES AND DEFINES END*/
enum ConnectionType {Simple_Connection, Diagonal_Connection, Hop_Connection, Only_Hop_Connection};
@ -85,8 +107,9 @@ class AtomicCGRA: public BaseCGRA
//uint32_t *CGRA_instructions;
uint64_t *CGRA_instructions;
unsigned int FetchedInstuction;
int loopID;
void fetchInstructions(unsigned int *InstMem);
//void fetch_CGRA_inst(long, uint64_t*);
/*AtomicCGRA related CGRA functions. This is replaced by tick() in atomic mode
due to the functionality of atomic mode in gem5.*/
@ -143,6 +166,8 @@ class AtomicCGRA: public BaseCGRA
unsigned II;
unsigned EPILog;
unsigned Prolog;
unsigned Prolog_extension_cycle;
unsigned Prolog_version_cycle;
unsigned Len;
int originalLen;
int KernelCounter;
@ -150,6 +175,8 @@ class AtomicCGRA: public BaseCGRA
int LiveVar_St_Epilog;
unsigned long long TotalLoops = 0;
unsigned callback_reg;
unsigned short state;
bool written;
@ -157,11 +184,13 @@ class AtomicCGRA: public BaseCGRA
int operand1;
bool Conditional_Reg;
unsigned Prolog_Branch_Cycle;
//bool * PE_Conditional_Reg[CGRA_XDim*CGRA_YDim];
bool ** PE_Conditional_Reg;
bool isTCdynamic = false;
//std::vector<CGRA_PE> cgra_PEs;
CGRA_PE* cgra_PEs;
CGRA_PE* cgra_PEs;
uint64_t fetched_instructions[MAX_INSTRUCTION_SIZE];
TheISA::PCState backPC;
/*CGRA DEFINITIONS END*/