|
|
//+---------------------------------------------------------------------
//
// File: misc.cxx
//
// Contents: Useful OLE helper and debugging functions
//
//----------------------------------------------------------------------
extern "C" { #include <nt.h>
#include <ntrtl.h>
#include <nturtl.h>
#include <windows.h>
#include <stdio.h>
#include <stdlib.h>
#include <basetyps.h>
#include "dswarn.h"
#include "oledsdbg.h"
}
#if (defined(BUILD_FOR_NT40))
typedef unsigned long HRESULT; #endif
static HRESULT ADsDebugOutHRESULT(DWORD dwFlags, HRESULT r);
#if DBG == 1
//+---------------------------------------------------------------
//
// Function: PrintHRESULT
//
// Synopsis: Outputs the name of the SCODE and a carriage return
// to the debugging device.
//
// Arguments: [dwFlags] -- Flags to ADsDebugOut.
// [scode] -- The status code to report.
//
// Notes: This function disappears in retail builds.
//
//----------------------------------------------------------------
STDAPI PrintHRESULT(DWORD dwFlags, HRESULT hr) { ADsDebugOut((dwFlags | DEB_NOCOMPNAME, " ")); ADsDebugOutHRESULT(dwFlags | DEB_NOCOMPNAME, hr); ADsDebugOut((dwFlags | DEB_NOCOMPNAME, "\n"));
return hr; }
//+---------------------------------------------------------------
//
// Function: ADsDebugOutHRESULT
//
// Synopsis: Outputs the name of the SCODE to the debugging device.
//
// Arguments: [dwFlags] -- Flags to ADsDebugOut.
// [scode] -- The status code to report.
//
// Notes: This function disappears in retail builds.
//
//----------------------------------------------------------------
static HRESULT ADsDebugOutHRESULT(DWORD dwFlags, HRESULT r) { LPWSTR lpstr;
#define CASE_SCODE(sc) \
case sc: lpstr = (LPWSTR)L#sc; break;
switch (r) { /* SCODE's defined in SCODE.H */ CASE_SCODE(S_OK) CASE_SCODE(S_FALSE) CASE_SCODE(OLE_S_USEREG) CASE_SCODE(OLE_S_STATIC) CASE_SCODE(OLE_S_MAC_CLIPFORMAT) CASE_SCODE(DRAGDROP_S_DROP) CASE_SCODE(DRAGDROP_S_USEDEFAULTCURSORS) CASE_SCODE(DRAGDROP_S_CANCEL) CASE_SCODE(DATA_S_SAMEFORMATETC) CASE_SCODE(VIEW_S_ALREADY_FROZEN) CASE_SCODE(CACHE_S_FORMATETC_NOTSUPPORTED) CASE_SCODE(CACHE_S_SAMECACHE) CASE_SCODE(CACHE_S_SOMECACHES_NOTUPDATED) CASE_SCODE(OLEOBJ_S_INVALIDVERB) CASE_SCODE(OLEOBJ_S_CANNOT_DOVERB_NOW) CASE_SCODE(OLEOBJ_S_INVALIDHWND) CASE_SCODE(INPLACE_S_TRUNCATED) CASE_SCODE(CONVERT10_S_NO_PRESENTATION) CASE_SCODE(MK_S_REDUCED_TO_SELF) CASE_SCODE(MK_S_ME) CASE_SCODE(MK_S_HIM) CASE_SCODE(MK_S_US) CASE_SCODE(MK_S_MONIKERALREADYREGISTERED) CASE_SCODE(STG_S_CONVERTED)
CASE_SCODE(E_UNEXPECTED) CASE_SCODE(E_NOTIMPL) CASE_SCODE(E_OUTOFMEMORY) CASE_SCODE(E_INVALIDARG) CASE_SCODE(E_NOINTERFACE) CASE_SCODE(E_POINTER) CASE_SCODE(E_HANDLE) CASE_SCODE(E_ABORT) CASE_SCODE(E_FAIL) CASE_SCODE(E_ACCESSDENIED)
/* SCODE's defined in DVOBJ.H */ // CASE_SCODE(DATA_E_FORMATETC)
// same as DATA_E_FORMATETC CASE_SCODE(DV_E_FORMATETC)
CASE_SCODE(VIEW_E_DRAW) // same as VIEW_E_DRAW CASE_SCODE(E_DRAW)
CASE_SCODE(CACHE_E_NOCACHE_UPDATED)
/* SCODE's defined in OLE2.H */ CASE_SCODE(OLE_E_OLEVERB) CASE_SCODE(OLE_E_ADVF) CASE_SCODE(OLE_E_ENUM_NOMORE) CASE_SCODE(OLE_E_ADVISENOTSUPPORTED) CASE_SCODE(OLE_E_NOCONNECTION) CASE_SCODE(OLE_E_NOTRUNNING) CASE_SCODE(OLE_E_NOCACHE) CASE_SCODE(OLE_E_BLANK) CASE_SCODE(OLE_E_CLASSDIFF) CASE_SCODE(OLE_E_CANT_GETMONIKER) CASE_SCODE(OLE_E_CANT_BINDTOSOURCE) CASE_SCODE(OLE_E_STATIC) CASE_SCODE(OLE_E_PROMPTSAVECANCELLED) CASE_SCODE(OLE_E_INVALIDRECT) CASE_SCODE(OLE_E_WRONGCOMPOBJ) CASE_SCODE(OLE_E_INVALIDHWND) CASE_SCODE(DV_E_DVTARGETDEVICE) CASE_SCODE(DV_E_STGMEDIUM) CASE_SCODE(DV_E_STATDATA) CASE_SCODE(DV_E_LINDEX) CASE_SCODE(DV_E_TYMED) CASE_SCODE(DV_E_CLIPFORMAT) CASE_SCODE(DV_E_DVASPECT) CASE_SCODE(DV_E_DVTARGETDEVICE_SIZE) CASE_SCODE(DV_E_NOIVIEWOBJECT) CASE_SCODE(CONVERT10_E_OLESTREAM_GET) CASE_SCODE(CONVERT10_E_OLESTREAM_PUT) CASE_SCODE(CONVERT10_E_OLESTREAM_FMT) CASE_SCODE(CONVERT10_E_OLESTREAM_BITMAP_TO_DIB) CASE_SCODE(CONVERT10_E_STG_FMT) CASE_SCODE(CONVERT10_E_STG_NO_STD_STREAM) CASE_SCODE(CONVERT10_E_STG_DIB_TO_BITMAP) CASE_SCODE(CLIPBRD_E_CANT_OPEN) CASE_SCODE(CLIPBRD_E_CANT_EMPTY) CASE_SCODE(CLIPBRD_E_CANT_SET) CASE_SCODE(CLIPBRD_E_BAD_DATA) CASE_SCODE(CLIPBRD_E_CANT_CLOSE) CASE_SCODE(DRAGDROP_E_NOTREGISTERED) CASE_SCODE(DRAGDROP_E_ALREADYREGISTERED) CASE_SCODE(DRAGDROP_E_INVALIDHWND) CASE_SCODE(OLEOBJ_E_NOVERBS) CASE_SCODE(INPLACE_E_NOTUNDOABLE) CASE_SCODE(INPLACE_E_NOTOOLSPACE)
/* SCODE's defined in STORAGE.H */ CASE_SCODE(STG_E_INVALIDFUNCTION) CASE_SCODE(STG_E_FILENOTFOUND) CASE_SCODE(STG_E_PATHNOTFOUND) CASE_SCODE(STG_E_TOOMANYOPENFILES) CASE_SCODE(STG_E_ACCESSDENIED) CASE_SCODE(STG_E_INVALIDHANDLE) CASE_SCODE(STG_E_INSUFFICIENTMEMORY) CASE_SCODE(STG_E_INVALIDPOINTER) CASE_SCODE(STG_E_NOMOREFILES) CASE_SCODE(STG_E_DISKISWRITEPROTECTED) CASE_SCODE(STG_E_SEEKERROR) CASE_SCODE(STG_E_WRITEFAULT) CASE_SCODE(STG_E_READFAULT) CASE_SCODE(STG_E_LOCKVIOLATION) CASE_SCODE(STG_E_FILEALREADYEXISTS) CASE_SCODE(STG_E_INVALIDPARAMETER) CASE_SCODE(STG_E_MEDIUMFULL) CASE_SCODE(STG_E_ABNORMALAPIEXIT) CASE_SCODE(STG_E_INVALIDHEADER) CASE_SCODE(STG_E_INVALIDNAME) CASE_SCODE(STG_E_UNKNOWN) CASE_SCODE(STG_E_UNIMPLEMENTEDFUNCTION) CASE_SCODE(STG_E_INVALIDFLAG) CASE_SCODE(STG_E_INUSE) CASE_SCODE(STG_E_NOTCURRENT) CASE_SCODE(STG_E_REVERTED) CASE_SCODE(STG_E_CANTSAVE) CASE_SCODE(STG_E_OLDFORMAT) CASE_SCODE(STG_E_OLDDLL) CASE_SCODE(STG_E_SHAREREQUIRED)
/* SCODE's defined in COMPOBJ.H */ CASE_SCODE(CO_E_NOTINITIALIZED) CASE_SCODE(CO_E_ALREADYINITIALIZED) CASE_SCODE(CO_E_CANTDETERMINECLASS) CASE_SCODE(CO_E_CLASSSTRING) CASE_SCODE(CO_E_IIDSTRING) CASE_SCODE(CO_E_APPNOTFOUND) CASE_SCODE(CO_E_APPSINGLEUSE) CASE_SCODE(CO_E_ERRORINAPP) CASE_SCODE(CO_E_DLLNOTFOUND) CASE_SCODE(CO_E_ERRORINDLL) CASE_SCODE(CO_E_WRONGOSFORAPP) CASE_SCODE(CO_E_OBJNOTREG) CASE_SCODE(CO_E_OBJISREG) CASE_SCODE(CO_E_OBJNOTCONNECTED) CASE_SCODE(CO_E_APPDIDNTREG) CASE_SCODE(CLASS_E_NOAGGREGATION) CASE_SCODE(REGDB_E_READREGDB) CASE_SCODE(REGDB_E_WRITEREGDB) CASE_SCODE(REGDB_E_KEYMISSING) CASE_SCODE(REGDB_E_INVALIDVALUE) CASE_SCODE(REGDB_E_CLASSNOTREG) CASE_SCODE(REGDB_E_IIDNOTREG) CASE_SCODE(RPC_E_CALL_REJECTED) CASE_SCODE(RPC_E_CALL_CANCELED) CASE_SCODE(RPC_E_CANTPOST_INSENDCALL) CASE_SCODE(RPC_E_CANTCALLOUT_INASYNCCALL) CASE_SCODE(RPC_E_CANTCALLOUT_INEXTERNALCALL) CASE_SCODE(RPC_E_CONNECTION_TERMINATED) #if defined(NO_NTOLEBUGS)
CASE_SCODE(RPC_E_SERVER_DIED) #endif // NO_NTOLEBUGS
CASE_SCODE(RPC_E_CLIENT_DIED) CASE_SCODE(RPC_E_INVALID_DATAPACKET) CASE_SCODE(RPC_E_CANTTRANSMIT_CALL) CASE_SCODE(RPC_E_CLIENT_CANTMARSHAL_DATA) CASE_SCODE(RPC_E_CLIENT_CANTUNMARSHAL_DATA) CASE_SCODE(RPC_E_SERVER_CANTMARSHAL_DATA) CASE_SCODE(RPC_E_SERVER_CANTUNMARSHAL_DATA) CASE_SCODE(RPC_E_INVALID_DATA) CASE_SCODE(RPC_E_INVALID_PARAMETER) CASE_SCODE(RPC_E_UNEXPECTED)
/* SCODE's defined in MONIKER.H */ CASE_SCODE(MK_E_CONNECTMANUALLY) CASE_SCODE(MK_E_EXCEEDEDDEADLINE) CASE_SCODE(MK_E_NEEDGENERIC) CASE_SCODE(MK_E_UNAVAILABLE) CASE_SCODE(MK_E_SYNTAX) CASE_SCODE(MK_E_NOOBJECT) CASE_SCODE(MK_E_INVALIDEXTENSION) CASE_SCODE(MK_E_INTERMEDIATEINTERFACENOTSUPPORTED) CASE_SCODE(MK_E_NOTBINDABLE) CASE_SCODE(MK_E_NOTBOUND) CASE_SCODE(MK_E_CANTOPENFILE) CASE_SCODE(MK_E_MUSTBOTHERUSER) CASE_SCODE(MK_E_NOINVERSE) CASE_SCODE(MK_E_NOSTORAGE) #if defined(NO_NTOLEBUGS)
CASE_SCODE(MK_S_MONIKERALREADYREGISTERED) #endif //NO_NTOLEBUGS
// Dispatch error codes
CASE_SCODE(DISP_E_MEMBERNOTFOUND)
default: ADsDebugOut((dwFlags, "<UNKNOWN SCODE 0x%lx>", r)); return r; }
#undef CASE_SCODE
ADsDebugOut((dwFlags, "<%ws (0x%lx)>", lpstr, r)); return r; }
//+---------------------------------------------------------------------------
//
// Function: BreakOnFailed
//
// Synopsis: Function called when CheckAndReturnResult or CheckResult
// examines a failure code. Set a breakpoint on this function
// to break on failures.
//
// History: 5-18-94 adams Created
//
//----------------------------------------------------------------------------
static void BreakOnFailed(void) { int x; x = 1; }
//+---------------------------------------------------------------
//
// Function: CheckAndReturnResult
//
// Synopsis: Issues a warning if the HRESULT indicates failure,
// and asserts if the HRESULT is not a permitted success code.
//
// Arguments: [hr] -- the HRESULT to be checked.
// [lpstrFile] -- the file where the HRESULT is being checked.
// [line] -- the line in the file where the HRESULT is
// being checked.
// [cSuccess] -- the number of permitted non-zero success codes.
// [...] -- list of success codes.
//
// Returns: The return value is exactly the HRESULT passed in.
//
// History: 1-06-94 adams Created.
// 5-24-94 adams Added call to BreakOnFailed.
//
// Notes: This function should not be used directly. Use
// the SRETURN and RRETURN macros instead.
//
//----------------------------------------------------------------
STDAPI CheckAndReturnResult( HRESULT hr, LPSTR lpstrFile, UINT line, int cSuccess, ...) { BOOL fOKReturnCode; va_list va; int i; HRESULT hrSuccess;
//
// Check if code is an error or permitted success.
//
fOKReturnCode = (FAILED(hr) || hr == S_OK || hr == S_FALSE || cSuccess == -1); if (!fOKReturnCode && cSuccess > 0) { va_start(va, cSuccess); for (i = 0; i < cSuccess; i++) { hrSuccess = va_arg(va, HRESULT); ADsAssert(SUCCEEDED(hrSuccess)); if (hr == hrSuccess) { fOKReturnCode = TRUE; break; } }
va_end(va); }
//
// Assert on non-permitted success code.
//
if (!fOKReturnCode) { /* ADsDebugOut((
DEB_ERROR, "ERROR: %s:%d returned bad success code", lpstrFile, line)); */
// (void) PrintHRESULT(DEB_ERROR | DEB_NOCOMPNAME, hr);
//
// I've removed the Assert but we should enable this
// to monitor all functions that are returning S_FALSE
// As far as possible, functions should not return
// S_FALSE except for the Next function of an Enumerator
// object.
// ADsAssert(0 && "An unpermitted success code was returned.");
}
//
// Warn on error result.
//
if (FAILED(hr)) { ADsDebugOut(( DEB_IWARN, "WARNING: %s:%d returning", lpstrFile, line));
PrintHRESULT(DEB_IWARN | DEB_NOCOMPNAME, hr);
BreakOnFailed(); }
return hr; }
//+---------------------------------------------------------------
//
// Function: CheckResult
//
// Synopsis: Issues a warning if the HRESULT indicates failure
//
// Arguments: [hr] -- the HRESULT to be checked
// [lpstrFile] -- the file where the HRESULT is being checked
// [line] -- the line in the file where the HRESULT is being checked
//
//
// History: 1-06-94 adams Error printed only on FAILURE, not also
// on non-zero success.
// 5-24-94 adams Added call to BreakOnFailed.
//
// Notes: This function should not be used directly. The RRETURN
// macro is provided for convenience.
//
//----------------------------------------------------------------
STDAPI_(void) CheckResult(HRESULT hr, LPSTR lpstrFile, UINT line) { if (FAILED(hr)) { ADsDebugOut((DEB_IWARN, "WARNING: ")); ADsDebugOutHRESULT(DEB_IWARN | DEB_NOCOMPNAME, hr); ADsDebugOut(( DEB_IWARN | DEB_NOCOMPNAME, " occurred at %s:%d.\n", lpstrFile, line));
BreakOnFailed(); } }
#endif // DBG == 1
|