| 1 | #pragma once |
| 2 | // Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. |
| 3 | |
| 4 | #include "dutilsources.h" |
| 5 | |
| 6 | #define DAPI __stdcall |
| 7 | #define DAPIV __cdecl // used only for functions taking variable length arguments |
| 8 | |
| 9 | #define DAPI_(type) EXTERN_C type DAPI |
| 10 | #define DAPIV_(type) EXTERN_C type DAPIV |
| 11 | |
| 12 | |
| 13 | // asserts and traces |
| 14 | typedef BOOL (DAPI *DUTIL_ASSERTDISPLAYFUNCTION)(__in_z LPCSTR sz); |
| 15 | |
| 16 | typedef void (CALLBACK *DUTIL_CALLBACK_TRACEERROR)( |
| 17 | __in_z LPCSTR szFile, |
| 18 | __in int iLine, |
| 19 | __in REPORT_LEVEL rl, |
| 20 | __in UINT source, |
| 21 | __in HRESULT hrError, |
| 22 | __in_z __format_string LPCSTR szFormat, |
| 23 | __in va_list args |
| 24 | ); |
| 25 | |
| 26 | #ifdef __cplusplus |
| 27 | extern "C" { |
| 28 | #endif |
| 29 | |
| 30 | /******************************************************************** |
| 31 | DutilInitialize - initialize dutil. |
| 32 | |
| 33 | *******************************************************************/ |
| 34 | HRESULT DAPI DutilInitialize( |
| 35 | __in_opt DUTIL_CALLBACK_TRACEERROR pfnTraceErrorCallback |
| 36 | ); |
| 37 | |
| 38 | /******************************************************************** |
| 39 | DutilUninitialize - uninitialize dutil. |
| 40 | |
| 41 | *******************************************************************/ |
| 42 | void DAPI DutilUninitialize(); |
| 43 | |
| 44 | /******************************************************************* |
| 45 | DutilSizetToDword - safely convert SIZE_T to DWORD. |
| 46 | |
| 47 | Returns |
| 48 | E_INVALIDARG - If SIZE_T value is greater than DWORD_MAX. |
| 49 | ********************************************************************/ |
| 50 | HRESULT DAPI DutilSizetToDword(SIZE_T sizet, DWORD* pdw); |
| 51 | |
| 52 | /******************************************************************** |
| 53 | DutilSuppressTraceErrorSource - tells dutil to skip calling |
| 54 | pfnTraceErrorCallback for the current thread. This is reference |
| 55 | counted, so dutil won't start calling it again until there is an |
| 56 | equal number of calls to DutilUnsuppressTraceErrorSource. |
| 57 | Returns whether the count was incremented. |
| 58 | |
| 59 | *******************************************************************/ |
| 60 | BOOL DAPI DutilSuppressTraceErrorSource(); |
| 61 | |
| 62 | /******************************************************************** |
| 63 | DutilUnsuppressTraceErrorSource - opposite of DutilSuppressTraceErrorSource. |
| 64 | |
| 65 | *******************************************************************/ |
| 66 | BOOL DAPI DutilUnsuppressTraceErrorSource(); |
| 67 | |
| 68 | void DAPI Dutil_SetAssertModule(__in HMODULE hAssertModule); |
| 69 | void DAPI Dutil_SetAssertDisplayFunction(__in DUTIL_ASSERTDISPLAYFUNCTION pfn); |
| 70 | void DAPI Dutil_Assert(__in_z LPCSTR szFile, __in int iLine); |
| 71 | void DAPI Dutil_AssertSz(__in_z LPCSTR szFile, __in int iLine, __in_z __format_string LPCSTR szMessage); |
| 72 | |
| 73 | void DAPI Dutil_TraceSetLevel(__in REPORT_LEVEL ll, __in BOOL fTraceFilenames); |
| 74 | REPORT_LEVEL DAPI Dutil_TraceGetLevel(); |
| 75 | void DAPIV Dutil_Trace(__in_z LPCSTR szFile, __in int iLine, __in REPORT_LEVEL rl, __in_z __format_string LPCSTR szMessage, ...); |
| 76 | void DAPIV Dutil_TraceError(__in_z LPCSTR szFile, __in int iLine, __in REPORT_LEVEL rl, __in HRESULT hr, __in_z __format_string LPCSTR szMessage, ...); |
| 77 | void DAPIV Dutil_TraceErrorSource(__in_z LPCSTR szFile, __in int iLine, __in REPORT_LEVEL rl, __in UINT source, __in HRESULT hr, __in_z __format_string LPCSTR szMessage, ...); |
| 78 | void DAPI Dutil_RootFailure(__in_z LPCSTR szFile, __in int iLine, __in HRESULT hrError); |
| 79 | |
| 80 | #ifdef __cplusplus |
| 81 | } |
| 82 | #endif |
| 83 | |
| 84 | |
| 85 | #ifdef DEBUG |
| 86 | |
| 87 | #define AssertSetModule(m) (void)Dutil_SetAssertModule(m) |
| 88 | #define AssertSetDisplayFunction(pfn) (void)Dutil_SetAssertDisplayFunction(pfn) |
| 89 | #define Assert(f) ((f) ? (void)0 : (void)Dutil_Assert(__FILE__, __LINE__)) |
| 90 | #define AssertSz(f, sz) ((f) ? (void)0 : (void)Dutil_AssertSz(__FILE__, __LINE__, sz)) |
| 91 | |
| 92 | #define TraceSetLevel(l, f) (void)Dutil_TraceSetLevel(l, f) |
| 93 | #define TraceGetLevel() (REPORT_LEVEL)Dutil_TraceGetLevel() |
| 94 | #define Trace(l, f, ...) (void)Dutil_Trace(__FILE__, __LINE__, l, f, __VA_ARGS__) |
| 95 | #define TraceError(x, f, ...) (void)Dutil_TraceError(__FILE__, __LINE__, REPORT_ERROR, x, f, __VA_ARGS__) |
| 96 | #define TraceErrorDebug(x, f, ...) (void)Dutil_TraceError(__FILE__, __LINE__, REPORT_DEBUG, x, f, __VA_ARGS__) |
| 97 | |
| 98 | #else // !DEBUG |
| 99 | |
| 100 | #define AssertSetModule(m) |
| 101 | #define AssertSetDisplayFunction(pfn) |
| 102 | #define Assert(f) |
| 103 | #define AssertSz(f, sz) |
| 104 | |
| 105 | #define TraceSetLevel(l, f) |
| 106 | #define Trace(l, f, ...) |
| 107 | #define TraceError(x, f, ...) |
| 108 | #define TraceErrorDebug(x, f, ...) |
| 109 | |
| 110 | #endif // DEBUG |
| 111 | |
| 112 | // DUTIL_SOURCE_DEFAULT can be overriden |
| 113 | #ifndef DUTIL_SOURCE_DEFAULT |
| 114 | #define DUTIL_SOURCE_DEFAULT DUTIL_SOURCE_UNKNOWN |
| 115 | #endif |
| 116 | |
| 117 | // Exit macros |
| 118 | #define ExitFunction() { goto LExit; } |
| 119 | #define ExitFunction1(x) { x; goto LExit; } |
| 120 | |
| 121 | #define ExitFunctionWithLastError(x) { x = HRESULT_FROM_WIN32(::GetLastError()); goto LExit; } |
| 122 | |
| 123 | #define ExitTraceSource(d, x, s, ...) { TraceError(x, s, __VA_ARGS__); (void)Dutil_TraceErrorSource(__FILE__, __LINE__, REPORT_ERROR, d, x, s, __VA_ARGS__); } |
| 124 | #define ExitTraceDebugSource(d, x, s, ...) { TraceErrorDebug(x, s, __VA_ARGS__); (void)Dutil_TraceErrorSource(__FILE__, __LINE__, REPORT_DEBUG, d, x, s, __VA_ARGS__); } |
| 125 | |
| 126 | #define ExitOnLastErrorSource(d, x, s, ...) { DWORD Dutil_er = ::GetLastError(); x = HRESULT_FROM_WIN32(Dutil_er); if (FAILED(x)) { Dutil_RootFailure(__FILE__, __LINE__, x); ExitTraceSource(d, x, s, __VA_ARGS__); goto LExit; } } |
| 127 | #define ExitOnLastErrorDebugTraceSource(d, x, s, ...) { DWORD Dutil_er = ::GetLastError(); x = HRESULT_FROM_WIN32(Dutil_er); if (FAILED(x)) { Dutil_RootFailure(__FILE__, __LINE__, x); ExitTraceDebugSource(d, x, s, __VA_ARGS__); goto LExit; } } |
| 128 | #define ExitWithLastErrorSource(d, x, s, ...) { DWORD Dutil_er = ::GetLastError(); x = HRESULT_FROM_WIN32(Dutil_er); if (!FAILED(x)) { x = E_FAIL; } Dutil_RootFailure(__FILE__, __LINE__, x); ExitTraceSource(d, x, s, __VA_ARGS__); goto LExit; } |
| 129 | #define ExitOnFailureSource(d, x, s, ...) if (FAILED(x)) { ExitTraceSource(d, x, s, __VA_ARGS__); goto LExit; } |
| 130 | #define ExitOnRootFailureSource(d, x, s, ...) if (FAILED(x)) { Dutil_RootFailure(__FILE__, __LINE__, x); ExitTraceSource(d, x, s, __VA_ARGS__); goto LExit; } |
| 131 | #define ExitWithRootFailureSource(d, x, e, s, ...) { x = FAILED(e) ? e : E_FAIL; Dutil_RootFailure(__FILE__, __LINE__, x); ExitTraceSource(d, x, s, __VA_ARGS__); goto LExit; } |
| 132 | #define ExitOnFailureDebugTraceSource(d, x, s, ...) if (FAILED(x)) { ExitTraceDebugSource(d, x, s, __VA_ARGS__); goto LExit; } |
| 133 | #define ExitOnNullSource(d, p, x, e, s, ...) if (NULL == p) { x = e; Dutil_RootFailure(__FILE__, __LINE__, x); ExitTraceSource(d, x, s, __VA_ARGS__); goto LExit; } |
| 134 | #define ExitOnNullWithLastErrorSource(d, p, x, s, ...) if (NULL == p) { DWORD Dutil_er = ::GetLastError(); x = HRESULT_FROM_WIN32(Dutil_er); if (!FAILED(x)) { x = E_FAIL; } Dutil_RootFailure(__FILE__, __LINE__, x); ExitTraceSource(d, x, s, __VA_ARGS__); goto LExit; } |
| 135 | #define ExitOnNullDebugTraceSource(d, p, x, e, s, ...) if (NULL == p) { x = e; Dutil_RootFailure(__FILE__, __LINE__, x); ExitTraceDebugSource(d, x, s, __VA_ARGS__); goto LExit; } |
| 136 | #define ExitOnInvalidHandleWithLastErrorSource(d, p, x, s, ...) if (INVALID_HANDLE_VALUE == p) { DWORD Dutil_er = ::GetLastError(); x = HRESULT_FROM_WIN32(Dutil_er); if (!FAILED(x)) { x = E_FAIL; } Dutil_RootFailure(__FILE__, __LINE__, x); ExitTraceSource(d, x, s, __VA_ARGS__); goto LExit; } |
| 137 | #define ExitOnWin32ErrorSource(d, e, x, s, ...) if (ERROR_SUCCESS != e) { x = HRESULT_FROM_WIN32(e); if (!FAILED(x)) { x = E_FAIL; } Dutil_RootFailure(__FILE__, __LINE__, x); ExitTraceSource(d, x, s, __VA_ARGS__); goto LExit; } |
| 138 | #define ExitOnOptionalXmlQueryFailureSource(d, x, b, s, ...) { { if (S_FALSE == x || E_NOTFOUND == x) { b = FALSE; x = S_OK; } else { b = SUCCEEDED(x); } }; ExitOnRootFailureSource(d, x, s, __VA_ARGS__); } |
| 139 | #define ExitOnRequiredXmlQueryFailureSource(d, x, s, ...) { if (S_FALSE == x) { x = E_NOTFOUND; } ExitOnRootFailureSource(d, x, s, __VA_ARGS__); } |
| 140 | #define ExitOnWaitObjectFailureSource(d, x, b, s, ...) { { if (HRESULT_FROM_WIN32(WAIT_TIMEOUT) == x) { b = TRUE; x = S_OK; } else { b = FALSE; } }; ExitOnFailureSource(d, x, s, __VA_ARGS__); } |
| 141 | #define ExitOnPathFailureSource(d, x, b, s, ...) { { if (E_PATHNOTFOUND == x || E_FILENOTFOUND == x) { b = FALSE; x = S_OK; } else { b = SUCCEEDED(x); } }; ExitOnFailureSource(d, x, s, __VA_ARGS__); } |
| 142 | #define ExitWithPathLastErrorSource(d, x, s, ...) { DWORD Dutil_er = ::GetLastError(); x = HRESULT_FROM_WIN32(Dutil_er); if (!FAILED(x)) { x = E_FAIL; } else if (E_PATHNOTFOUND == x || E_FILENOTFOUND == x) { x = S_OK; } ExitOnRootFailureSource(d, x, s, __VA_ARGS__); } |
| 143 | |
| 144 | #define ExitOnLastError(x, s, ...) ExitOnLastErrorSource(DUTIL_SOURCE_DEFAULT, x, s, __VA_ARGS__) |
| 145 | #define ExitOnLastErrorDebugTrace(x, s, ...) ExitOnLastErrorDebugTraceSource(DUTIL_SOURCE_DEFAULT, x, s, __VA_ARGS__) |
| 146 | #define ExitWithLastError(x, s, ...) ExitWithLastErrorSource(DUTIL_SOURCE_DEFAULT, x, s, __VA_ARGS__) |
| 147 | #define ExitOnFailure(x, s, ...) ExitOnFailureSource(DUTIL_SOURCE_DEFAULT, x, s, __VA_ARGS__) |
| 148 | #define ExitOnRootFailure(x, s, ...) ExitOnRootFailureSource(DUTIL_SOURCE_DEFAULT, x, s, __VA_ARGS__) |
| 149 | #define ExitWithRootFailure(x, e, s, ...) ExitWithRootFailureSource(DUTIL_SOURCE_DEFAULT, x, e, s, __VA_ARGS__) |
| 150 | #define ExitOnFailureDebugTrace(x, s, ...) ExitOnFailureDebugTraceSource(DUTIL_SOURCE_DEFAULT, x, s, __VA_ARGS__) |
| 151 | #define ExitOnNull(p, x, e, s, ...) ExitOnNullSource(DUTIL_SOURCE_DEFAULT, p, x, e, s, __VA_ARGS__) |
| 152 | #define ExitOnNullWithLastError(p, x, s, ...) ExitOnNullWithLastErrorSource(DUTIL_SOURCE_DEFAULT, p, x, s, __VA_ARGS__) |
| 153 | #define ExitOnNullDebugTrace(p, x, e, s, ...) ExitOnNullDebugTraceSource(DUTIL_SOURCE_DEFAULT, p, x, e, s, __VA_ARGS__) |
| 154 | #define ExitOnInvalidHandleWithLastError(p, x, s, ...) ExitOnInvalidHandleWithLastErrorSource(DUTIL_SOURCE_DEFAULT, p, x, s, __VA_ARGS__) |
| 155 | #define ExitOnWin32Error(e, x, s, ...) ExitOnWin32ErrorSource(DUTIL_SOURCE_DEFAULT, e, x, s, __VA_ARGS__) |
| 156 | #define ExitOnOptionalXmlQueryFailure(x, b, s, ...) ExitOnOptionalXmlQueryFailureSource(DUTIL_SOURCE_DEFAULT, x, b, s, __VA_ARGS__) |
| 157 | #define ExitOnRequiredXmlQueryFailure(x, s, ...) ExitOnRequiredXmlQueryFailureSource(DUTIL_SOURCE_DEFAULT, x, s, __VA_ARGS__) |
| 158 | #define ExitOnWaitObjectFailure(x, b, s, ...) ExitOnWaitObjectFailureSource(DUTIL_SOURCE_DEFAULT, x, b, s, __VA_ARGS__) |
| 159 | #define ExitOnPathFailure(x, b, s, ...) ExitOnPathFailureSource(DUTIL_SOURCE_DEFAULT, x, b, s, __VA_ARGS__) |
| 160 | #define ExitWithPathLastError(x, s, ...) ExitWithPathLastErrorSource(DUTIL_SOURCE_DEFAULT, x, s, __VA_ARGS__) |
| 161 | |
| 162 | // release macros |
| 163 | #define ReleaseObject(x) if (x) { x->Release(); } |
| 164 | #define ReleaseObjectArray(prg, cel) if (prg) { for (DWORD Dutil_ReleaseObjectArrayIndex = 0; Dutil_ReleaseObjectArrayIndex < cel; ++Dutil_ReleaseObjectArrayIndex) { ReleaseObject(prg[Dutil_ReleaseObjectArrayIndex]); } ReleaseMem(prg); } |
| 165 | #define ReleaseVariant(x) { ::VariantClear(&x); } |
| 166 | #define ReleaseNullObject(x) if (x) { (x)->Release(); x = NULL; } |
| 167 | #define ReleaseCertificate(x) if (x) { ::CertFreeCertificateContext(x); x=NULL; } |
| 168 | #define ReleaseHandle(x) if (x) { ::CloseHandle(x); x = NULL; } |
| 169 | |
| 170 | |
| 171 | // useful defines and macros |
| 172 | #define Unused(x) ((void)x) |
| 173 | |
| 174 | #ifndef countof |
| 175 | #if 1 |
| 176 | #define countof(ary) (sizeof(ary) / sizeof(ary[0])) |
| 177 | #else |
| 178 | #ifndef __cplusplus |
| 179 | #define countof(ary) (sizeof(ary) / sizeof(ary[0])) |
| 180 | #else |
| 181 | template<typename T> static char countofVerify(void const *, T) throw() { return 0; } |
| 182 | template<typename T> static void countofVerify(T *const, T *const *) throw() {}; |
| 183 | #define countof(arr) (sizeof(countofVerify(arr,&(arr))) * sizeof(arr)/sizeof(*(arr))) |
| 184 | #endif |
| 185 | #endif |
| 186 | #endif |
| 187 | |
| 188 | #define roundup(x, n) roundup_typed(x, n, DWORD) |
| 189 | #define roundup_typed(x, n, t) (((t)(x) + ((t)(n) - 1)) & ~((t)(n) - 1)) |
| 190 | |
| 191 | #define HRESULT_FROM_RPC(x) ((HRESULT) ((x) | FACILITY_RPC)) |
| 192 | |
| 193 | #ifndef MAXSIZE_T |
| 194 | #define MAXSIZE_T ((SIZE_T)~((SIZE_T)0)) |
| 195 | #endif |
| 196 | |
| 197 | typedef const BYTE* LPCBYTE; |
| 198 | |
| 199 | #define E_FILENOTFOUND HRESULT_FROM_WIN32(ERROR_FILE_NOT_FOUND) |
| 200 | #define E_PATHNOTFOUND HRESULT_FROM_WIN32(ERROR_PATH_NOT_FOUND) |
| 201 | #define E_INVALIDDATA HRESULT_FROM_WIN32(ERROR_INVALID_DATA) |
| 202 | #define E_INVALIDSTATE HRESULT_FROM_WIN32(ERROR_INVALID_STATE) |
| 203 | #define E_INSUFFICIENT_BUFFER HRESULT_FROM_WIN32(ERROR_INSUFFICIENT_BUFFER) |
| 204 | #define E_MOREDATA HRESULT_FROM_WIN32(ERROR_MORE_DATA) |
| 205 | #define E_NOMOREITEMS HRESULT_FROM_WIN32(ERROR_NO_MORE_ITEMS) |
| 206 | #define E_NOTFOUND HRESULT_FROM_WIN32(ERROR_NOT_FOUND) |
| 207 | #define E_MODNOTFOUND HRESULT_FROM_WIN32(ERROR_MOD_NOT_FOUND) |
| 208 | #define E_BADCONFIGURATION HRESULT_FROM_WIN32(ERROR_BAD_CONFIGURATION) |
| 209 | |
| 210 | #define AddRefAndRelease(x) { x->AddRef(); x->Release(); } |
| 211 | |
| 212 | #define MAKEDWORD(lo, hi) ((DWORD)MAKELONG(lo, hi)) |
| 213 | #define MAKEQWORDVERSION(mj, mi, b, r) (((DWORD64)MAKELONG(r, b)) | (((DWORD64)MAKELONG(mi, mj)) << 32)) |
| 214 | |
| 215 | |
| 216 | #ifdef __cplusplus |
| 217 | extern "C" { |
| 218 | #endif |
| 219 | |
| 220 | // other functions |
| 221 | |
| 222 | /******************************************************************* |
| 223 | LoadSystemLibrary - Securely loads the module from the |
| 224 | Windows system directory. |
| 225 | |
| 226 | Returns |
| 227 | E_MODNOTFOUND - The module could not be found. |
| 228 | * - Another error occured. |
| 229 | ********************************************************************/ |
| 230 | HRESULT DAPI LoadSystemLibrary( |
| 231 | __in_z LPCWSTR wzModuleName, |
| 232 | __out HMODULE* phModule |
| 233 | ); |
| 234 | |
| 235 | /******************************************************************* |
| 236 | LoadSystemLibraryWithPath - Fully qualifies the path to a module in |
| 237 | the Windows system directory and loads it |
| 238 | and returns the path |
| 239 | |
| 240 | Returns |
| 241 | E_MODNOTFOUND - The module could not be found. |
| 242 | * - Another error occured. |
| 243 | ********************************************************************/ |
| 244 | HRESULT DAPI LoadSystemLibraryWithPath( |
| 245 | __in_z LPCWSTR wzModuleName, |
| 246 | __out HMODULE* phModule, |
| 247 | __deref_out_z_opt LPWSTR* psczPath |
| 248 | ); |
| 249 | |
| 250 | /******************************************************************* |
| 251 | LoadSystemApiSet - Securely loads the API set provided by the system. |
| 252 | |
| 253 | Returns |
| 254 | E_MODNOTFOUND - The module could not be found. |
| 255 | * - Another error occured. |
| 256 | ********************************************************************/ |
| 257 | DAPI_(HRESULT) LoadSystemApiSet( |
| 258 | __in_z LPCWSTR wzApiSet, |
| 259 | __out HMODULE* phModule |
| 260 | ); |
| 261 | |
| 262 | #ifdef __cplusplus |
| 263 | } |
| 264 | #endif |