#include "circuit.h" #include "assert.h" int Gate::cal_propagate_len(bool x) { int fpl[2]; fpl[0] = fpl[1] = 0; for(Gate* out : outputs) { if(!out->is_detected(this)) continue; fpl[!value] = std::max(fpl[!value], out->fault_propagate_len[!out->value] + 1); } return fpl[x]; } bool Gate::is_detected(Gate* one_of_input) { one_of_input->value = !one_of_input->value; bool detect = cal_value() != value; one_of_input->value = !one_of_input->value; return (cal_value() == value) && detect; } bool Gate::is_propagated() { return sa[0] || sa[1]; } bool Gate::cal_sa(bool x) { if(isPO) { if(x == 0) return value; else return !value; } bool sa0 = 0; bool sa1 = 0; for(Gate* out : outputs) { if(!out->is_propagated()) continue; if(out->cal_value() != out->value) continue; this->value = !this->value; bool detect = out->cal_value() != out->value; this->value = !this->value; if(!detect) continue; sa0 |= this->value; sa1 |= !this->value; } if(x == 0) return sa0; else return sa1; } int Gate::cal_value() { int res; switch(type) { case NOT: res = !inputs[0]->value; break; case BUF: res = inputs[0]->value; break; case AND: res = inputs[0]->value; for(int i=1; ivalue; } break; case NAND: res = inputs[0]->value; for(int i=1; ivalue; } res = !res; break; case OR: res = inputs[0]->value; for(int i=1; ivalue; } break; case NOR: res = inputs[0]->value; for(int i=1; ivalue; } res = !res; break; case XOR: res = inputs[0]->value; for(int i=1; ivalue; } break; case XNOR: res = inputs[0]->value; for(int i=1; ivalue; } res = !res; break; case INPUT: res = value; break; default: assert(false); break; } return res; }