ecos_kernel_test: experiment calculates timeout in STEP 2
git-svn-id: https://www4.informatik.uni-erlangen.de/i4svn/danceos/trunk/devel/fail@1492 8c4709b5-6ec9-48aa-a5cd-a96041d1645a
This commit is contained in:
@ -46,19 +46,19 @@ bool EcosKernelTestCampaign::readMemoryMap(fail::MemoryMap &mm, char const * con
|
||||
return (count > 0);
|
||||
}
|
||||
|
||||
bool EcosKernelTestCampaign::writeTraceInfo(unsigned instr_counter, unsigned lowest_addr, unsigned highest_addr) {
|
||||
bool EcosKernelTestCampaign::writeTraceInfo(unsigned instr_counter, unsigned timeout, unsigned lowest_addr, unsigned highest_addr) {
|
||||
ofstream ti(traceinfo_name, ios::out | ios::app);
|
||||
if (!ti.is_open()) {
|
||||
cout << "failed to open " << traceinfo_name << endl;
|
||||
return false;
|
||||
}
|
||||
ti << instr_counter << endl << lowest_addr << endl << highest_addr << endl;
|
||||
ti << instr_counter << endl << timeout << endl << lowest_addr << endl << highest_addr << endl;
|
||||
ti.flush();
|
||||
ti.close();
|
||||
return true;
|
||||
}
|
||||
|
||||
bool EcosKernelTestCampaign::readTraceInfo(unsigned &instr_counter, unsigned &lowest_addr, unsigned &highest_addr) {
|
||||
bool EcosKernelTestCampaign::readTraceInfo(unsigned &instr_counter, unsigned &timeout, unsigned &lowest_addr, unsigned &highest_addr) {
|
||||
ifstream file(traceinfo_name);
|
||||
if (!file.is_open()) {
|
||||
cout << "failed to open " << traceinfo_name << endl;
|
||||
@ -75,9 +75,12 @@ bool EcosKernelTestCampaign::readTraceInfo(unsigned &instr_counter, unsigned &lo
|
||||
ss >> instr_counter;
|
||||
break;
|
||||
case 1:
|
||||
ss >> lowest_addr;
|
||||
ss >> timeout;
|
||||
break;
|
||||
case 2:
|
||||
ss >> lowest_addr;
|
||||
break;
|
||||
case 3:
|
||||
ss >> highest_addr;
|
||||
break;
|
||||
}
|
||||
@ -123,8 +126,8 @@ bool EcosKernelTestCampaign::run()
|
||||
ProtoIStream ps(&tracef);
|
||||
|
||||
// read trace info
|
||||
unsigned instr_counter, lowest_addr, highest_addr;
|
||||
EcosKernelTestCampaign::readTraceInfo(instr_counter, lowest_addr, highest_addr);
|
||||
unsigned instr_counter, estimated_timeout, lowest_addr, highest_addr;
|
||||
EcosKernelTestCampaign::readTraceInfo(instr_counter, estimated_timeout, lowest_addr, highest_addr);
|
||||
|
||||
// a map of addresses of ECC protected objects
|
||||
MemoryMap mm;
|
||||
|
||||
@ -15,7 +15,7 @@ class EcosKernelTestCampaign : public fail::Campaign {
|
||||
public:
|
||||
virtual bool run();
|
||||
static bool readMemoryMap(fail::MemoryMap &mm, char const * const filename);
|
||||
static bool writeTraceInfo(unsigned instr_counter, unsigned lowest_addr, unsigned highest_addr);
|
||||
static bool readTraceInfo(unsigned &instr_counter, unsigned &lowest_addr, unsigned &highest_addr);
|
||||
static bool writeTraceInfo(unsigned instr_counter, unsigned timeout, unsigned lowest_addr, unsigned highest_addr);
|
||||
static bool readTraceInfo(unsigned &instr_counter, unsigned &timeout, unsigned &lowest_addr, unsigned &highest_addr);
|
||||
};
|
||||
|
||||
|
||||
@ -98,6 +98,7 @@ bool EcosKernelTestExperiment::retrieveGuestAddresses() {
|
||||
}
|
||||
assert(number_of_guest_events > 0);
|
||||
//log << "Breakpoint at 'ECOS_FUNC_FINISH' reached: created memory map (" << number_of_guest_events << " entries)" << endl;
|
||||
//TODO: check if ECOS_FUNC_FINISH was reached!!!
|
||||
log << "Record timeout reached: created memory map (" << number_of_guest_events << " entries)" << endl;
|
||||
delete str;
|
||||
|
||||
@ -177,6 +178,14 @@ bool EcosKernelTestExperiment::performTrace() {
|
||||
simulator.addListener(&ev_count);
|
||||
unsigned instr_counter = 0;
|
||||
|
||||
// on the way, count elapsed time
|
||||
TimerListener time_step(10000); //TODO: granularity?
|
||||
//elapsed_time.setCounter(0xFFFFFFFFU); // not working for TimerListener
|
||||
simulator.addListener(&time_step);
|
||||
unsigned elapsed_time = 1; // always run 1 step
|
||||
// just increase elapsed_time counter by 1, which serves as time for ECC recovery algorithm
|
||||
++elapsed_time; // (this is a rough guess ... TODO)
|
||||
|
||||
// on the way, record lowest and highest memory address accessed
|
||||
MemAccessListener ev_mem(ANY_ADDR, MemAccessEvent::MEM_READWRITE);
|
||||
simulator.addListener(&ev_mem);
|
||||
@ -187,9 +196,19 @@ bool EcosKernelTestExperiment::performTrace() {
|
||||
BaseListener* ev = simulator.resume();
|
||||
while(ev != &bp) {
|
||||
if(ev == &ev_count) {
|
||||
++instr_counter;
|
||||
if(instr_counter++ == 0xFFFFFFFFU) {
|
||||
log << "ERROR: instr_counter overflowed" << endl;
|
||||
return false;
|
||||
}
|
||||
simulator.addListener(&ev_count);
|
||||
}
|
||||
else if(ev == &time_step) {
|
||||
if(elapsed_time++ == 0xFFFFFFFFU) {
|
||||
log << "ERROR: elapsed_time overflowed" << endl;
|
||||
return false;
|
||||
}
|
||||
simulator.addListener(&time_step);
|
||||
}
|
||||
else if(ev == &ev_mem) {
|
||||
unsigned trigger_addr = ev_mem.getTriggerAddress();
|
||||
if( (lowest_addr == 0) && (highest_addr == 0) ) {
|
||||
@ -206,11 +225,19 @@ bool EcosKernelTestExperiment::performTrace() {
|
||||
ev = simulator.resume();
|
||||
}
|
||||
|
||||
unsigned long long estimated_timeout_overflow_check = ((unsigned long long)elapsed_time) * time_step.getTimeout();
|
||||
if(estimated_timeout_overflow_check > 0xFFFFFFFFU) {
|
||||
log << "Timeout estimation overflowed" << endl;
|
||||
return false;
|
||||
}
|
||||
unsigned estimated_timeout = (unsigned)estimated_timeout_overflow_check;
|
||||
|
||||
log << dec << "tracing finished after " << instr_counter << " instructions" << endl;
|
||||
log << hex << "all memory accesses within [ 0x" << lowest_addr << " , 0x" << highest_addr << " ]" << endl;
|
||||
log << dec << "elapsed time: " << estimated_timeout << " [TimerListener units]" << endl;
|
||||
|
||||
// save these values for experiment STEP 3
|
||||
EcosKernelTestCampaign::writeTraceInfo(instr_counter, lowest_addr, highest_addr);
|
||||
EcosKernelTestCampaign::writeTraceInfo(instr_counter, estimated_timeout, lowest_addr, highest_addr);
|
||||
|
||||
simulator.removeFlow(&tp);
|
||||
|
||||
@ -233,8 +260,8 @@ bool EcosKernelTestExperiment::faultInjection() {
|
||||
log << "STEP 3: The actual experiment." << endl;
|
||||
|
||||
// read trace info
|
||||
unsigned instr_counter, lowest_addr, highest_addr;
|
||||
EcosKernelTestCampaign::readTraceInfo(instr_counter, lowest_addr, highest_addr);
|
||||
unsigned instr_counter, estimated_timeout, lowest_addr, highest_addr;
|
||||
EcosKernelTestCampaign::readTraceInfo(instr_counter, estimated_timeout, lowest_addr, highest_addr);
|
||||
|
||||
BPSingleListener bp;
|
||||
|
||||
@ -359,18 +386,14 @@ bool EcosKernelTestExperiment::faultInjection() {
|
||||
simulator.addListener(&ev_mem_high);
|
||||
|
||||
// timeout (e.g., stuck in a HLT instruction)
|
||||
// 10000us = 500000 instructions
|
||||
TimerListener ev_timeout(500000);
|
||||
TimerListener ev_timeout(estimated_timeout);
|
||||
simulator.addListener(&ev_timeout);
|
||||
//TODO: if ev_timeout would depend on instr_counter, ev_end would not be needed!
|
||||
// --> (instr_counter + ECOS_RECOVERYINSTR) * factor?
|
||||
|
||||
// remaining instructions until "normal" ending
|
||||
// number of instructions that are executed additionally for error corrections
|
||||
enum { ECOS_RECOVERYINSTR = 0x2000 }; // (this is a rough guess ... TODO)
|
||||
BPSingleListener ev_end(ANY_ADDR);
|
||||
ev_end.setCounter(instr_counter + ECOS_RECOVERYINSTR - instr_offset);
|
||||
simulator.addListener(&ev_end);
|
||||
//BPSingleListener ev_end(ANY_ADDR);
|
||||
//ev_end.setCounter(instr_counter - instr_offset + ECOS_RECOVERYINSTR);
|
||||
//simulator.addListener(&ev_end);
|
||||
|
||||
// eCos' test output function, which will show if the test PASSed or FAILed
|
||||
BPSingleListener func_test_output(ECOS_FUNC_TEST_OUTPUT);
|
||||
@ -429,7 +452,7 @@ bool EcosKernelTestExperiment::faultInjection() {
|
||||
result->set_error_corrected(error_corrected);
|
||||
|
||||
// record ecos_test_result
|
||||
if (ecos_test_passed && !ecos_test_failed) {
|
||||
if ( (ecos_test_passed == true) && (ecos_test_failed == false) ) {
|
||||
result->set_ecos_test_result(result->PASS);
|
||||
} else {
|
||||
result->set_ecos_test_result(result->FAIL);
|
||||
@ -439,7 +462,7 @@ bool EcosKernelTestExperiment::faultInjection() {
|
||||
// do we reach finish?
|
||||
log << "experiment finished ordinarily" << endl;
|
||||
result->set_resulttype(result->FINISHED);
|
||||
} else if (ev == &ev_timeout || ev == &ev_end) {
|
||||
} else if (ev == &ev_timeout /*|| ev == &ev_end*/) {
|
||||
log << "Result TIMEOUT" << endl;
|
||||
result->set_resulttype(result->TIMEOUT);
|
||||
} else if (ev == &ev_below_text || ev == &ev_beyond_text) {
|
||||
|
||||
Reference in New Issue
Block a user