Files
BinaryHardening-cfgrip/main.cpp
T

104 lines
2.5 KiB
C++

#include "types.hpp"
#include "loader/binary.hpp"
#include "cfg/builder.hpp"
#include "disasm/engine.hpp"
int main(int argc, char* argv[])
{
if (argc < 2)
{
cerr << "usage: cfgrip [--subs-only] [--clean] <binary>" << endl;
return 1;
}
bool subsOnly = false;
bool clean = false;
string path;
for (int i = 1; i < argc; i++)
{
string arg = argv[i];
if (arg == "--subs-only")
subsOnly = true;
else if (arg == "--clean")
clean = true;
else
path = arg;
}
if (path.empty())
{
cerr << "usage: cfgrip [--subs-only] [--clean] <binary>" << endl;
return 1;
}
auto binary = Binary::create(path);
if (!binary)
{
cerr << "failed to load binary: " << path << endl;
return 1;
}
cout << "format: ";
switch (binary->getFormat())
{
case BinaryFormat::PE: cout << "PE"; break;
case BinaryFormat::ELF: cout << "ELF"; break;
default: cout << "unknown";
}
cout << endl;
cout << "arch: ";
switch (binary->getArch())
{
case Arch::X86: cout << "x86"; break;
case Arch::X64: cout << "x86-64"; break;
default: cout << "unknown";
}
cout << endl;
cout << "entry: 0x" << hex << binary->getEntryPoint() << dec << endl;
cout << "imports: " << binary->getImportedFunctions().size() << endl;
for (const auto& imp : binary->getImportedFunctions())
{
cout << " 0x" << hex << imp.address << " " << imp.name;
if (!imp.library.empty()) cout << " (" << imp.library << ")";
cout << dec << endl;
}
Disassembler dis;
if (!dis.init(binary->getArch()))
{
cerr << "failed to init capstone" << endl;
return 1;
}
CFGBuilder builder(binary.get(), &dis, subsOnly);
if (subsOnly) cout << "mode: subs-only" << endl;
CFG cfg = builder.build();
if (clean)
{
CFGBuilder::clean(cfg);
cout << "clean: xrefs=" << cfg.xrefs.size() << " functions=" << cfg.functions.size() << endl;
}
cout << "functions: " << cfg.functions.size() << endl;
cout << "indirect targets: " << cfg.indirect_targets.size() << endl;
string suffix;
if (subsOnly) suffix += ".subs";
if (clean) suffix += ".clean";
string out = path + suffix + ".cfg";
ofstream f(out);
if (f)
{
f << cfg.toJSON();
f.close();
cout << "cfg written to: " << out << endl;
}
return 0;
}