bool Atpg::Backtrace() { Gate *g = &cir_->gates_[current_obj_.first]; Value objv = current_obj_.second; while (!(g->type_==Gate::PI || g->type_==Gate::PPI)) { // while objective net not fed by P/PI if (g->getOutputCtrlValue()==X) { //NOT, BUF, TODO: XOR, XNOR if (g->type_==Gate::INV) objv = EvalNot(objv); g = &cir_->gates_[g->fis_[0]]; assert(impl_->GetVal(g->id_)==X); continue; } Gate *gnext = NULL; if (objv==EvalNot(g->getOutputCtrlValue())) { // if objv is easy to set // choose input of "g" which // 1) is at X // 2) is easiest to control gnext = FindEasiestToSetFanIn(g, objv); } else if (objv==g->getOutputCtrlValue()) { // is objv is hard to set // choose input of "g" which // 1) is at X // 2) is hardest to control gnext = FindHardestToSetFanIn(g, objv); } if (g->isInverse()) objv = EvalNot(objv); g = gnext; } return impl_->MakeDecision(g, objv); }