summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBrandon Miller <brandon@vector35.com>2024-04-11 10:40:09 -0400
committerBrandon Miller <bkmiller89@icloud.com>2024-04-25 10:56:18 -0400
commit465a8d5d7afd5a5648338009e0fb8dbe4f199347 (patch)
treef3ead9b2b65a291fd7a97b2ddbbda2f10a5462ac
parent4b2b3d561b92a01f4d29b86d5510d39e4d1accf3 (diff)
Querying candidate base address reasons
Querying vector of reason information for a candidate base address using the new core API
-rw-r--r--basedetection.cpp23
-rw-r--r--binaryninjaapi.h19
-rw-r--r--binaryninjacore.h39
-rw-r--r--examples/triage/baseaddress.cpp73
-rw-r--r--examples/triage/baseaddress.h4
5 files changed, 85 insertions, 73 deletions
diff --git a/basedetection.cpp b/basedetection.cpp
index 4389f1b7..e994ede5 100644
--- a/basedetection.cpp
+++ b/basedetection.cpp
@@ -21,7 +21,6 @@
#include "binaryninjaapi.h"
using namespace BinaryNinja;
-using namespace std;
BaseAddressDetection::BaseAddressDetection(Ref<BinaryView> bv)
@@ -65,13 +64,29 @@ bool BaseAddressDetection::IsAborted()
}
-std::set<std::pair<size_t, uint64_t>> BaseAddressDetection::GetScores(BaseAddressDetectionConfidence* confidence)
+std::set<std::pair<size_t, uint64_t>> BaseAddressDetection::GetScores(BNBaseAddressDetectionConfidence* confidence,
+ uint64_t *lastTestedBaseAddress)
{
std::set<std::pair<size_t, uint64_t>> result;
BNBaseAddressDetectionScore scores[10];
- size_t numCandidates = BNGetBaseAddressDetectionScores(m_object, scores, 10,
- (BNBaseAddressDetectionConfidence *)confidence);
+ size_t numCandidates = BNGetBaseAddressDetectionScores(m_object, scores, 10, confidence, lastTestedBaseAddress);
for (size_t i = 0; i < numCandidates; i++)
result.insert(std::make_pair(scores[i].Score, scores[i].BaseAddress));
return result;
}
+
+
+std::vector<BNBaseAddressDetectionReason> BaseAddressDetection::GetReasonsForBaseAddress(uint64_t baseAddress)
+{
+ std::vector<BNBaseAddressDetectionReason> result;
+ size_t count;
+ BNBaseAddressDetectionReason *reasons = BNGetBaseAddressDetectionReasons(m_object, baseAddress, &count);
+ if (!reasons)
+ return result;
+
+ for (size_t i = 0; i < count; i++)
+ result.push_back(reasons[i]);
+
+ free(reasons);
+ return result;
+}
diff --git a/binaryninjaapi.h b/binaryninjaapi.h
index 6bd33c80..803ebf76 100644
--- a/binaryninjaapi.h
+++ b/binaryninjaapi.h
@@ -17391,13 +17391,6 @@ namespace BinaryNinja {
uint32_t MaxPointersPerCluster;
};
- enum BaseAddressDetectionConfidence
- {
- NoConfidence = 0,
- LowConfidence = 1,
- HighConfidence = 2,
- };
-
/*!
\ingroup baseaddressdetection
*/
@@ -17418,10 +17411,18 @@ namespace BinaryNinja {
/*! Get the top 10 candidate base addresses and thier scores
- \param confidence Confidence level that the top base address candidate is correct
+ \param confidence Confidence level that indicates the likelihood the top base address candidate is correct
+ \param lastTestedBaseAddress Last base address tested before analysis was aborted or completed
\return Set of pairs containing candidate base addresses and their scores
*/
- std::set<std::pair<size_t, uint64_t>> GetScores(BaseAddressDetectionConfidence* confidence);
+ std::set<std::pair<size_t, uint64_t>> GetScores(BNBaseAddressDetectionConfidence* confidence, uint64_t *lastTestedBaseAddress);
+
+ /*! Get a vector of BNBaseAddressDetectionReasons containing information that indicates why a base address was reported as a candidate
+
+ \param baseAddress Base address to query reasons for
+ \return Vector of reason structures containing information about why a base address was reported as a candidate
+ */
+ std::vector<BNBaseAddressDetectionReason> GetReasonsForBaseAddress(uint64_t baseAddress);
/*! Abort base address detection
*/
diff --git a/binaryninjacore.h b/binaryninjacore.h
index 25d7618e..ffe17dba 100644
--- a/binaryninjacore.h
+++ b/binaryninjacore.h
@@ -3160,25 +3160,25 @@ extern "C"
typedef enum BNBaseAddressDetectionPOISetting
{
- POI_ANALYSIS_STRINGS_ONLY,
- POI_ANALYSIS_FUNCTIONS_ONLY,
- POI_ANALYSIS_ALL,
+ POIAnalysisStringsOnly,
+ POIAnalysisFunctionsOnly,
+ POIAnalysisAll,
} BNBaseAddressDetectionPOISetting;
typedef enum BNBaseAddressDetectionPOIType
{
- POI_STRING,
- POI_FUNCTION,
- POI_DATA_VARIABLE,
- POI_FILE_START,
- POI_FILE_END,
+ POIString,
+ POIFunction,
+ POIDataVariable,
+ POIFileStart,
+ POIFileEnd,
} BNBaseAddressDetectionPOIType;
typedef enum BNBaseAddressDetectionConfidence
{
- CONFIDENCE_UNASSIGNED,
- CONFIDENCE_LOW,
- CONFIDENCE_HIGH,
+ NoConfidence,
+ LowConfidence,
+ HighConfidence,
} BNBaseAddressDetectionConfidence;
typedef struct BNBaseAddressDetectionSettings
@@ -3197,7 +3197,7 @@ extern "C"
{
uint64_t Pointer;
uint64_t POIOffset;
- BNBaseAddressDetectionPOIType BaseAddressDetectionPOIType;
+ BNBaseAddressDetectionPOIType POIType;
} BNBaseAddressDetectionReason;
typedef struct BNBaseAddressDetectionScore
@@ -3206,15 +3206,6 @@ extern "C"
uint64_t BaseAddress;
} BNBaseAddressDetectionScore;
- typedef struct BNBaseAddressDetectionResults
- {
- BNBaseAddressDetectionConfidence Confidence;
- BNBaseAddressDetectionScore** Scores;
- BNBaseAddressDetectionReason** Reasons;
- char* ErrorStr;
- uint64_t LastTestedBaseAddress;
- } BNBaseAddressDetectionResults;
-
BINARYNINJACOREAPI char* BNAllocString(const char* contents);
BINARYNINJACOREAPI void BNFreeString(char* str);
BINARYNINJACOREAPI char** BNAllocStringList(const char** contents, size_t size);
@@ -7049,8 +7040,10 @@ extern "C"
// Base Address Detection
BINARYNINJACOREAPI BNBaseAddressDetection* BNCreateBaseAddressDetection(BNBinaryView *view);
BINARYNINJACOREAPI bool BNDetectBaseAddress(BNBaseAddressDetection* bad, BNBaseAddressDetectionSettings& settings);
- BINARYNINJACOREAPI size_t BNGetBaseAddressDetectionScores(BNBaseAddressDetection* bad,
- BNBaseAddressDetectionScore* scores, size_t count, BNBaseAddressDetectionConfidence* confidence);
+ BINARYNINJACOREAPI size_t BNGetBaseAddressDetectionScores(BNBaseAddressDetection* bad, BNBaseAddressDetectionScore* scores, size_t count,
+ BNBaseAddressDetectionConfidence* confidence, uint64_t* lastTestedBaseAddress);
+ BINARYNINJACOREAPI BNBaseAddressDetectionReason* BNGetBaseAddressDetectionReasons(BNBaseAddressDetection* bad,
+ uint64_t baseAddress, size_t* count);
BINARYNINJACOREAPI void BNAbortBaseAddressDetection(BNBaseAddressDetection* bad);
BINARYNINJACOREAPI bool BNIsBaseAddressDetectionAborted(BNBaseAddressDetection* bad);
BINARYNINJACOREAPI void BNFreeBaseAddressDetection(BNBaseAddressDetection* bad);
diff --git a/examples/triage/baseaddress.cpp b/examples/triage/baseaddress.cpp
index 41068cfb..542a1f94 100644
--- a/examples/triage/baseaddress.cpp
+++ b/examples/triage/baseaddress.cpp
@@ -6,10 +6,10 @@ using namespace std;
BNBaseAddressDetectionPOISetting BaseAddressDetectionPOISettingFromString(const std::string& setting)
{
if (setting == "Strings only")
- return POI_ANALYSIS_STRINGS_ONLY;
+ return POIAnalysisStringsOnly;
if (setting == "Functions only")
- return POI_ANALYSIS_FUNCTIONS_ONLY;
- return POI_ANALYSIS_ALL; // Default to All
+ return POIAnalysisFunctionsOnly;
+ return POIAnalysisAll; // Default to All
}
@@ -17,34 +17,34 @@ std::string BaseAddressDetectionPOITypeToString(BNBaseAddressDetectionPOIType ty
{
switch (type)
{
- case POI_STRING:
- return "String";
- case POI_FUNCTION:
- return "Function";
- case POI_DATA_VARIABLE:
- return "Data variable";
- case POI_FILE_END:
- return "File end";
- case POI_FILE_START:
- return "File start";
- default:
- return "Unknown";
+ case POIString:
+ return "String";
+ case POIFunction:
+ return "Function";
+ case POIDataVariable:
+ return "Data variable";
+ case POIFileEnd:
+ return "File end";
+ case POIFileStart:
+ return "File start";
+ default:
+ return "Unknown";
}
}
-std::string BaseAddressDetectionConfidenceToString(BinaryNinja::BaseAddressDetectionConfidence level)
+std::string BaseAddressDetectionConfidenceToString(BNBaseAddressDetectionConfidence level)
{
switch (level)
{
- case BinaryNinja::NoConfidence:
- return "Unassigned";
- case BinaryNinja::HighConfidence:
- return "High";
- case BinaryNinja::LowConfidence:
- return "Low";
- default:
- return "Unknown";
+ case NoConfidence:
+ return "Unassigned";
+ case HighConfidence:
+ return "High";
+ case LowConfidence:
+ return "Low";
+ default:
+ return "Unknown";
}
}
@@ -124,21 +124,24 @@ void BaseAddressDetectionThread::run()
if (!m_baseDetection->DetectBaseAddress(settings))
emit ResultReady(results);
- auto scores = m_baseDetection->GetScores(&results.Confidence);
+ auto scores = m_baseDetection->GetScores(&results.Confidence, &results.LastTestedBaseAddress);
results.Scores = scores;
+ for (const auto& score : scores)
+ {
+ auto reasons = m_baseDetection->GetReasonsForBaseAddress(score.second);
+ results.Reasons[score.second] = reasons;
+ }
+
emit ResultReady(results);
}
-
void BaseAddressDetectionWidget::HandleResults(const BaseAddressDetectionQtResults& results)
{
if (!results.Status.empty())
m_status->setText(QString::fromStdString(results.Status));
- /* TODO
if (results.Status.empty() && m_worker->IsAborted())
- m_status->setText("Aborted by user (Last Base: 0x" + QString::number(results.Results.LastTestedBaseAddress, 16) + ")");
- */
+ m_status->setText("Aborted by user (Last Base: 0x" + QString::number(results.LastTestedBaseAddress, 16) + ")");
if (results.Scores.empty())
{
@@ -159,27 +162,25 @@ void BaseAddressDetectionWidget::HandleResults(const BaseAddressDetectionQtResul
}
m_resultsTableWidget->clearContents();
- /* TODO
size_t numRows = 0;
- for (auto rit = results.Results.Scores.rbegin(); rit != results.Results.Scores.rend(); rit++)
- numRows += results.Results.Reasons.at(rit->second).size();
+ for (auto rit = results.Scores.rbegin(); rit != results.Scores.rend(); rit++)
+ numRows += results.Reasons.at(rit->second).size();
m_resultsTableWidget->setRowCount(numRows);
size_t row = 0;
- for (auto rit = results.Results.Scores.rbegin(); rit != results.Results.Scores.rend(); rit++)
+ for (auto rit = results.Scores.rbegin(); rit != results.Scores.rend(); rit++)
{
auto [score, baseaddr] = *rit;
- for (const auto& reason : results.Results.Reasons.at(baseaddr))
+ for (const auto& reason : results.Reasons.at(baseaddr))
{
m_resultsTableWidget->setItem(row, 0, new QTableWidgetItem("0x" + QString::number(baseaddr, 16)));
m_resultsTableWidget->setItem(row, 1, new QTableWidgetItem("0x" + QString::number(reason.Pointer, 16)));
m_resultsTableWidget->setItem(row, 2, new QTableWidgetItem("0x" + QString::number(reason.POIOffset, 16)));
m_resultsTableWidget->setItem(row, 3, new QTableWidgetItem(
- QString::fromStdString(BaseAddressDetectionPOITypeToString(reason.BaseAddressDetectionPOIType))));
+ QString::fromStdString(BaseAddressDetectionPOITypeToString(reason.POIType))));
row++;
}
}
- */
m_detectBaseAddressButton->setEnabled(true);
m_abortButton->setHidden(true);
diff --git a/examples/triage/baseaddress.h b/examples/triage/baseaddress.h
index aa5e70ab..f6dc79f1 100644
--- a/examples/triage/baseaddress.h
+++ b/examples/triage/baseaddress.h
@@ -28,7 +28,9 @@ struct BaseAddressDetectionQtResults
{
std::string Status;
std::set<std::pair<size_t, uint64_t>> Scores;
- BinaryNinja::BaseAddressDetectionConfidence Confidence;
+ BNBaseAddressDetectionConfidence Confidence;
+ std::map<uint64_t, std::vector<BNBaseAddressDetectionReason>> Reasons;
+ uint64_t LastTestedBaseAddress;
};
class BaseAddressDetectionThread : public QThread