-
Notifications
You must be signed in to change notification settings - Fork 8
/
Utility.cpp
198 lines (168 loc) · 4.49 KB
/
Utility.cpp
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
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
// IDA plugin utility support
#include "StdAfx.h"
#include <tchar.h>
#include <winnt.h>
static ALIGN(16) TIMESTAMP performanceFrequency = 0;
struct OnUtilityInit
{
OnUtilityInit()
{
LARGE_INTEGER large;
QueryPerformanceFrequency(&large);
performanceFrequency = (TIMESTAMP) large.QuadPart;
}
} static _utilityInit;
qstring &GetVersionString(UINT32 version, qstring &version_string)
{
version_string.sprnt("%u.%u.%u", GET_VERSION_MAJOR(MY_VERSION), GET_VERSION_MINOR(MY_VERSION), GET_VERSION_PATCH(MY_VERSION));
VERSION_STAGE stage = GET_VERSION_STAGE(version);
switch (GET_VERSION_STAGE(version))
{
case VERSION_ALPHA: version_string += "-alpha"; break;
case VERSION_BETA: version_string += "-beta"; break;
};
return version_string;
}
// Return high resolution floating elapsed seconds
TIMESTAMP GetTimestamp()
{
LARGE_INTEGER large;
QueryPerformanceCounter(&large);
return ((TIMESTAMP) large.QuadPart / performanceFrequency);
}
void trace(__in LPCSTR format, ...)
{
if (format)
{
va_list vl;
char buffer[4096]; // 4096 is the OS buffer limit
va_start(vl, format);
vsprintf_s(buffer, sizeof(buffer), format, vl);
va_end(vl);
OutputDebugStringA(buffer);
}
}
LPCSTR TimestampString(TIMESTAMP time, __out_bcount_z(64) LPSTR buffer)
{
if(time >= HOUR)
sprintf_s(buffer, 64, "%.2f hours", (time / (TIMESTAMP) HOUR));
else
if(time >= MINUTE)
sprintf_s(buffer, 64, "%.2f minutes", (time / (TIMESTAMP) MINUTE));
else
if(time < (TIMESTAMP) 0.01)
sprintf_s(buffer, 64, "%.2f ms", (time * (TIMESTAMP) 1000.0));
else
sprintf_s(buffer, 64, "%.2f seconds", time);
return buffer;
}
LPSTR NumberCommaString(UINT64 n, __out_bcount_z(32) LPSTR buffer)
{
int i = 0, c = 0;
do
{
buffer[i] = ('0' + (n % 10)); i++;
n /= 10;
if ((c += (3 && n)) >= 3)
{
buffer[i] = ','; i++;
c = 0;
}
} while (n);
buffer[i] = 0;
return _strrev(buffer);
}
// Get an error string for a GetLastError() code
LPSTR GetErrorString(DWORD lastError, __out_bcount_z(1024) LPSTR buffer)
{
if (!FormatMessageA((FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS), NULL, lastError, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), buffer, 1024, NULL))
strcpy_s(buffer, 1024, "Unknown");
else
{
if (LPSTR lineFeed = strstr(buffer, "\r"))
*lineFeed = 0;
}
return buffer;
}
// Dump byte range to debug output
void DumpData(LPCVOID ptr, int size, BOOL showAscii)
{
#define RUN 16
if(ptr && (size > 0))
{
__try
{
PBYTE pSrc = (PBYTE) ptr;
char lineStr[256] = {0};
int uOffset = 0;
// Create offset string based on input size
char offsetStr[16];
int iDigits = (int) strlen(_itoa(size, offsetStr, 16));
sprintf(offsetStr, "[%%0%dX]: ", max(iDigits, 2));
// Do runs
char valueStr[(RUN + 1) * 3];
while(size >= RUN)
{
sprintf(lineStr, offsetStr, uOffset);
// Hex
BYTE *pLine = pSrc;
for(int i = 0; i < RUN; i++)
{
sprintf(valueStr, "%02X ", *pLine);
strcat(lineStr, valueStr);
++pLine;
}
// ASCII
if (showAscii)
{
strcat(lineStr, " ");
pLine = pSrc;
for (int i = 0; i < RUN; i++)
{
sprintf(valueStr, "%c", (*pLine >= ' ') ? *pLine : '.');
strcat(lineStr, valueStr);
++pLine;
}
}
msg("%s\n", lineStr);
uOffset += RUN, pSrc += RUN, size -= RUN;
};
// Final if not an even run line
if(size > 0)
{
sprintf(lineStr, offsetStr, uOffset);
// Hex
BYTE *pLine = pSrc;
for(int i = 0; i < size; i++)
{
sprintf(valueStr, "%02X ", *pLine);
strcat(lineStr, valueStr);
++pLine;
}
if (showAscii)
{
// Pad out line
for (int i = 0; i < (RUN - size); i++) strcat(lineStr, " ");
strcat(lineStr, " ");
// ASCII
pLine = pSrc;
for (int i = 0; i < size; i++)
{
sprintf(valueStr, "%c", (*pLine >= ' ') ? *pLine : '.');
strcat(lineStr, valueStr);
++pLine;
}
}
msg("%s\n", lineStr);
}
}__except(TRUE){}
}
#undef RUN
}
// ------------------------------------------------------------------------------------------------
// Print C SEH information
int ReportException(LPCSTR name, LPEXCEPTION_POINTERS nfo)
{
msg(MSG_TAG "** Exception: 0x%08X @ 0x%llX, in %s()! **\n", nfo->ExceptionRecord->ExceptionCode, nfo->ExceptionRecord->ExceptionAddress, name);
return EXCEPTION_EXECUTE_HANDLER;
}