forked from strivexjun/DriverInjectDll
- Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathpe.cpp
More file actions
Latest commit
135 lines (124 loc) · 5.09 KB
/
Copy pathpe.cpp
File metadata and controls
135 lines (124 loc) · 5.09 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
#include"pe.h"
staticULONGRvaToSection(IMAGE_NT_HEADERS* pNtHdr, ULONG dwRVA)
{
USHORT wSections;
PIMAGE_SECTION_HEADER pSectionHdr;
pSectionHdr = IMAGE_FIRST_SECTION(pNtHdr);
wSections = pNtHdr->FileHeader.NumberOfSections;
for(int i = 0; i < wSections; i++)
{
if(pSectionHdr[i].VirtualAddress <= dwRVA)
if((pSectionHdr[i].VirtualAddress + pSectionHdr[i].Misc.VirtualSize) > dwRVA)
{
return i;
}
}
return (ULONG) - 1;
}
staticULONGRvaToOffset(PIMAGE_NT_HEADERS pnth, ULONG Rva, ULONG FileSize)
{
PIMAGE_SECTION_HEADER psh = IMAGE_FIRST_SECTION(pnth);
USHORT NumberOfSections = pnth->FileHeader.NumberOfSections;
for(int i = 0; i < NumberOfSections; i++)
{
if(psh->VirtualAddress <= Rva)
{
if((psh->VirtualAddress + psh->Misc.VirtualSize) > Rva)
{
Rva -= psh->VirtualAddress;
Rva += psh->PointerToRawData;
return Rva < FileSize ? Rva : PE_ERROR_VALUE;
}
}
psh++;
}
returnPE_ERROR_VALUE;
}
ULONGPE::GetExportOffset(constunsignedchar* FileData, ULONG FileSize, constchar* ExportName)
{
//Verify DOS Header
PIMAGE_DOS_HEADER pdh = (PIMAGE_DOS_HEADER)FileData;
if(pdh->e_magic != IMAGE_DOS_SIGNATURE)
{
DPRINT("[DeugMessage] Invalid IMAGE_DOS_SIGNATURE!\r\n");
returnPE_ERROR_VALUE;
}
//Verify PE Header
PIMAGE_NT_HEADERS pnth = (PIMAGE_NT_HEADERS)(FileData + pdh->e_lfanew);
if(pnth->Signature != IMAGE_NT_SIGNATURE)
{
DPRINT("[DeugMessage] Invalid IMAGE_NT_SIGNATURE!\r\n");
returnPE_ERROR_VALUE;
}
//Verify Export Directory
PIMAGE_DATA_DIRECTORY pdd = NULL;
if(pnth->OptionalHeader.Magic == IMAGE_NT_OPTIONAL_HDR64_MAGIC)
pdd = ((PIMAGE_NT_HEADERS64)pnth)->OptionalHeader.DataDirectory;
else
pdd = ((PIMAGE_NT_HEADERS32)pnth)->OptionalHeader.DataDirectory;
ULONG ExportDirRva = pdd[IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress;
ULONG ExportDirSize = pdd[IMAGE_DIRECTORY_ENTRY_EXPORT].Size;
ULONG ExportDirOffset = RvaToOffset(pnth, ExportDirRva, FileSize);
if(ExportDirOffset == PE_ERROR_VALUE)
{
DPRINT("[DeugMessage] Invalid Export Directory!\r\n");
returnPE_ERROR_VALUE;
}
//Read Export Directory
PIMAGE_EXPORT_DIRECTORY ExportDir = (PIMAGE_EXPORT_DIRECTORY)(FileData + ExportDirOffset);
ULONG NumberOfNames = ExportDir->NumberOfNames;
ULONG AddressOfFunctionsOffset = RvaToOffset(pnth, ExportDir->AddressOfFunctions, FileSize);
ULONG AddressOfNameOrdinalsOffset = RvaToOffset(pnth, ExportDir->AddressOfNameOrdinals, FileSize);
ULONG AddressOfNamesOffset = RvaToOffset(pnth, ExportDir->AddressOfNames, FileSize);
if(AddressOfFunctionsOffset == PE_ERROR_VALUE ||
AddressOfNameOrdinalsOffset == PE_ERROR_VALUE ||
AddressOfNamesOffset == PE_ERROR_VALUE)
{
DPRINT("[DeugMessage] Invalid Export Directory Contents!\r\n");
returnPE_ERROR_VALUE;
}
ULONG* AddressOfFunctions = (ULONG*)(FileData + AddressOfFunctionsOffset);
USHORT* AddressOfNameOrdinals = (USHORT*)(FileData + AddressOfNameOrdinalsOffset);
ULONG* AddressOfNames = (ULONG*)(FileData + AddressOfNamesOffset);
//Find Export
ULONG ExportOffset = PE_ERROR_VALUE;
for(ULONG i = 0; i < NumberOfNames; i++)
{
ULONG CurrentNameOffset = RvaToOffset(pnth, AddressOfNames[i], FileSize);
if(CurrentNameOffset == PE_ERROR_VALUE)
continue;
constchar* CurrentName = (constchar*)(FileData + CurrentNameOffset);
ULONG CurrentFunctionRva = AddressOfFunctions[AddressOfNameOrdinals[i]];
if(CurrentFunctionRva >= ExportDirRva && CurrentFunctionRva < ExportDirRva + ExportDirSize)
continue; //we ignore forwarded exports
if(!strcmp(CurrentName, ExportName)) //compare the export name to the requested export
{
ExportOffset = RvaToOffset(pnth, CurrentFunctionRva, FileSize);
break;
}
}
if(ExportOffset == PE_ERROR_VALUE)
{
DPRINT("[DeugMessage] Export %s not found in export table!\r\n", ExportName);
}
return ExportOffset;
}
PVOIDPE::GetPageBase(PVOID lpHeader, ULONG* Size, PVOID ptr)
{
if((unsignedchar*)ptr < (unsignedchar*)lpHeader)
return0;
ULONG dwRva = (ULONG)((unsignedchar*)ptr - (unsignedchar*)lpHeader);
IMAGE_DOS_HEADER* pdh = (IMAGE_DOS_HEADER*)lpHeader;
if(pdh->e_magic != IMAGE_DOS_SIGNATURE)
return0;
IMAGE_NT_HEADERS* pnth = (IMAGE_NT_HEADERS*)((unsignedchar*)lpHeader + pdh->e_lfanew);
if(pnth->Signature != IMAGE_NT_SIGNATURE)
return0;
IMAGE_SECTION_HEADER* psh = IMAGE_FIRST_SECTION(pnth);
int section = RvaToSection(pnth, dwRva);
if(section == -1)
return0;
if(Size)
*Size = psh[section].SizeOfRawData;
return (PVOID)((unsignedchar*)lpHeader + psh[section].VirtualAddress);
}