Skip to content

Commit

Permalink
chore: replace magic value with enum
Browse files Browse the repository at this point in the history
  • Loading branch information
Wenkang Huang committed Sep 8, 2023
1 parent 814f719 commit 1ddbc21
Show file tree
Hide file tree
Showing 2 changed files with 79 additions and 48 deletions.
110 changes: 62 additions & 48 deletions libs2eplugins/src/s2e/Plugins/Searchers/ValidPathSearcher.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,8 @@ void ValidPathSearcher::initialize() {
s2e()->getExecutor()->setSearcher(this);
m_onStateForkConn =
s2e()->getCorePlugin()->onStateFork.connect(sigc::mem_fun(*this, &ValidPathSearcher::onStateFork));
m_onTranslateBlockEndConn = s2e()->getCorePlugin()->onTranslateBlockEnd.connect(
sigc::mem_fun(*this, &ValidPathSearcher::onTranslateBlockEnd));

onARMFunctionConn = s2e()->getPlugin<ARMFunctionMonitor>();
onARMFunctionConn->onARMFunctionCallEvent.connect(sigc::mem_fun(*this, &ValidPathSearcher::onARMFunctionCall));
Expand All @@ -31,67 +33,37 @@ void ValidPathSearcher::initialize() {
m_searcherActive = false;
}

bool ValidPathSearcher::insertToForkStates(uint32_t callerPC, uint32_t forkPC, S2EExecutionState *state) {
const auto &foundSameCallerPC = m_forkStateItems.find(callerPC);
if (foundSameCallerPC != m_forkStateItems.end()) {
const auto &foundSameForkPC = foundSameCallerPC->second.find(forkPC);
if (foundSameForkPC != foundSameCallerPC->second.end()) {
if (foundSameForkPC->second.size() >= 2) {
return false;
}
}
}
m_forkStateItems[callerPC][forkPC].push_back(state);
m_idStateMap[state->getID()] = {state, forkPC, 0};
return true;
}

void ValidPathSearcher::onStateFork(S2EExecutionState *state, const std::vector<S2EExecutionState *> &newStates,
const std::vector<klee::ref<klee::Expr>> &newConditions) {
getDebugStream() << "onStateFork" << '\n';

uint32_t forkPC = state->regs()->getPc();
getDebugStream() << "[forkPC: " << hexval(forkPC) << "] "
<< "[stateID: " << hexval(state->getID()) << "] "
<< "[new stateID: " << hexval(newStates[0]->getID()) << "] "
<< "[new stateID: " << hexval(newStates[1]->getID()) << "] "
<< "\n";
insertToForkStates(m_callerPC, forkPC, newStates[0]);
insertToForkStates(m_callerPC, forkPC, newStates[1]);
m_searcherActive = true;
}

klee::ExecutionState &ValidPathSearcher::selectState() {
getDebugStream() << "selectState"
<< "\n";

if (m_selfSwitch) {
m_selfSwitch = false;
m_idStateMap[m_curState->getID()].flag = 2;
m_idStateMap[m_curState->getID()].flag = VALID;
getDebugStream() << "[self switch, stateID: " << m_curState->getID() << "] "
<< "\n";
return *m_curState;
}

// flag 0 firstly
for (auto it = m_idStateMap.rbegin(); it != m_idStateMap.rend(); ++it) {
if (it->second.flag == 0) {
it->second.flag = 2;
if (it->second.flag == UNVISITED) {
it->second.flag = VALID;
m_curState = it->second.state;
getDebugStream() << "[flag 0: selected stateID: " << m_curState->getID() << "] "
getDebugStream() << "[selected unvisited stateID: " << m_curState->getID() << "] "
<< "\n";
return *m_curState;
}
}
// flag 2 secondly
// for (auto it = m_idStateMap.rbegin(); it != m_idStateMap.rend(); ++it) {
// if (it->second.flag == 2) {
// m_curState = it->second.state;
// getDebugStream() << "[flag 2: selected stateID: " << m_curState->getID() << "] "
// << "\n";
// return *m_curState;
// }
// }
// flag 2 secondly
for (auto it = m_idStateMap.rbegin(); it != m_idStateMap.rend(); ++it) {
if (it->second.flag == VALID) {
m_curState = it->second.state;
getDebugStream() << "[selected valid stateID: " << m_curState->getID() << "] "
<< "\n";
return *m_curState;
}
}

getDebugStream() << "[no option, stateID: " << m_curState->getID() << "] "
<< "\n";
Expand All @@ -104,22 +76,62 @@ void ValidPathSearcher::update(klee::ExecutionState *current, const klee::StateS
S2EExecutionState *removedState = static_cast<S2EExecutionState *>(it);
auto found = m_idStateMap.find(removedState->getID());
if (found != m_idStateMap.end()) {
found->second.flag = 1;
found->second.flag = INVALID;
}
}
}

bool ValidPathSearcher::empty() {
getDebugStream() << "empty"
<< "\n";
for (const auto &it : m_idStateMap) {
if (it.second.flag == 0 || it.second.flag == 2) {
if (it.second.flag == UNVISITED || it.second.flag == VALID) {
getDebugStream() << "empty"
<< "\n";
return false;
}
}
return true;
}

bool ValidPathSearcher::insertToForkStates(uint32_t callerPC, uint32_t forkPC, S2EExecutionState *state) {
const auto &foundSameCallerPC = m_forkStateItems.find(callerPC);
if (foundSameCallerPC != m_forkStateItems.end()) {
const auto &foundSameForkPC = foundSameCallerPC->second.find(forkPC);
if (foundSameForkPC != foundSameCallerPC->second.end()) {
if (foundSameForkPC->second.size() >= 2) {
return false;
}
}
}
m_forkStateItems[callerPC][forkPC].push_back(state);
m_idStateMap[state->getID()] = {state, forkPC, UNVISITED};
return true;
}

void ValidPathSearcher::onStateFork(S2EExecutionState *state, const std::vector<S2EExecutionState *> &newStates,
const std::vector<klee::ref<klee::Expr>> &newConditions) {
getDebugStream() << "onStateFork" << '\n';

uint32_t forkPC = state->regs()->getPc();
getDebugStream() << "[forkPC: " << hexval(forkPC) << "] "
<< "[stateID: " << hexval(state->getID()) << "] "
<< "[new stateID: " << hexval(newStates[0]->getID()) << "] "
<< "[new stateID: " << hexval(newStates[1]->getID()) << "] "
<< "\n";
insertToForkStates(m_callerPC, forkPC, newStates[0]);
insertToForkStates(m_callerPC, forkPC, newStates[1]);
m_idStateMap[state->getID()].flag = VALID;
m_searcherActive = true;
}

void ValidPathSearcher::onTranslateBlockEnd(ExecutionSignal *signal, S2EExecutionState *state, TranslationBlock *tb,
uint64_t pc, bool isStatic, uint64_t staticTargetPc) {
getDebugStream() << "onTranslateBlockEnd" << '\n';

m_tbNum++;
getDebugStream() << "[the number of blocks: " << m_tbNum << "]"
<< "\n";
}

void ValidPathSearcher::onARMFunctionCall(S2EExecutionState *state, uint32_t pcCaller, uint64_t pcCtxHashVal,
uint32_t pcReturn) {
getDebugStream() << "onARMFunctionCall"
Expand Down Expand Up @@ -147,9 +159,11 @@ void ValidPathSearcher::onARMFunctionReturn(S2EExecutionState *state, uint32_t p
uint32_t forkPC = m_idStateMap[state->getID()].forkPC;

for (auto &it : m_forkStateItems[callerPC][forkPC]) {
if (m_idStateMap[it->getID()].flag == 0) {
if (m_idStateMap[it->getID()].flag == INVALID) {
m_selfSwitch = true;
m_curState = m_idStateMap[it->getID()].state;
getDebugStream() << "self switch"
<< "\n";
void *cp = g_s2e->getPlugin("CorePlugin");
s2e()->getExecutor()->validPathSearcherStateSwitchCallback(cp);
s2e()->getExecutor()->setCpuExitRequest();
Expand Down
17 changes: 17 additions & 0 deletions libs2eplugins/src/s2e/Plugins/Searchers/ValidPathSearcher.h
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,8 @@ struct StateItem {
uint32_t flag;
};

enum StatePhase { UNVISITED, INVALID, VALID };

class ValidPathSearcher : public Plugin, public klee::Searcher {
S2E_PLUGIN

Expand All @@ -48,8 +50,10 @@ class ValidPathSearcher : public Plugin, public klee::Searcher {

private:
sigc::connection m_onStateForkConn;
sigc::connection m_onTranslateBlockEndConn;
ARMFunctionMonitor *onARMFunctionConn;

uint32_t m_tbNum;
uint32_t m_callerPC;
uint32_t m_returnPC;
S2EExecutionState *m_curState;
Expand All @@ -69,6 +73,19 @@ class ValidPathSearcher : public Plugin, public klee::Searcher {
*/
void onStateFork(S2EExecutionState *state, const std::vector<S2EExecutionState *> &newStates,
const std::vector<klee::ref<klee::Expr>> &newConditions);

/**
*
* @param signal
* @param state
* @param tb
* @param pc
* @param isStatic
* @param staticTargetPc
*/
void onTranslateBlockEnd(ExecutionSignal *signal, S2EExecutionState *state, TranslationBlock *tb, uint64_t pc,
bool isStatic, uint64_t staticTargetPc);

/**
* callback when function call.
*
Expand Down

0 comments on commit 1ddbc21

Please sign in to comment.