home *** CD-ROM | disk | FTP | other *** search
/ Tricks of the Windows Gam…ming Gurus (2nd Edition) / Disc2.iso / msdn_vcb / samples / vc98 / sdk / dbmsg / oledb / tablecopy / error.cpp < prev    next >
Encoding:
C/C++ Source or Header  |  1998-03-12  |  12.9 KB  |  416 lines

  1. //-----------------------------------------------------------------------------
  2. // Microsoft OLE DB TABLECOPY Sample
  3. // Copyright (C) 1995-1998 Microsoft Corporation
  4. //
  5. // @doc
  6. //
  7. // @module ERROR.CPP
  8. //
  9. //-----------------------------------------------------------------------------
  10.  
  11. ////////////////////////////////////////////////////////////////////////
  12. // Includes
  13. //
  14. ////////////////////////////////////////////////////////////////////////
  15. #include "WinMain.h"
  16. #include "Error.h"
  17.  
  18. #include <olectl.h>      // IConnectionPoints interface
  19.  
  20.  
  21. ////////////////////////////////////////////////////////////////////////
  22. // Defines
  23. //
  24. ////////////////////////////////////////////////////////////////////////
  25.  
  26. //Displays values like VALUE as   VALUE , L"VALUE"
  27. #define VALUE_WCHAR(value) value, L#value
  28.  
  29.  
  30. typedef struct _INTERFACEMAP
  31. {
  32.     const IID*    pIID;                // The sql type value
  33.     WCHAR*        pwszInterface;        // Name for display
  34. } INTERFACEMAP;
  35.  
  36.  
  37. INTERFACEMAP rgInterfaceMap[] =
  38. {
  39.     //IUnknown
  40.         & VALUE_WCHAR(IID_IUnknown),
  41.  
  42.     //TEnumerator
  43.         & VALUE_WCHAR(IID_IParseDisplayName),
  44.         & VALUE_WCHAR(IID_ISourcesRowset),
  45.  
  46.     //TDataSource
  47.         & VALUE_WCHAR(IID_IDBInitialize),
  48.         & VALUE_WCHAR(IID_IDBProperties),
  49.         & VALUE_WCHAR(IID_IDBCreateSession),
  50.         & VALUE_WCHAR(IID_IDBInfo),
  51.         & VALUE_WCHAR(IID_IPersist),
  52.         & VALUE_WCHAR(IID_IDBDataSourceAdmin),
  53.         & VALUE_WCHAR(IID_IPersistFile),
  54.         & VALUE_WCHAR(IID_ISupportErrorInfo),
  55.  
  56.     //TSession
  57.         & VALUE_WCHAR(IID_IGetDataSource),
  58.         & VALUE_WCHAR(IID_IOpenRowset),
  59.         & VALUE_WCHAR(IID_ISessionProperties),
  60.         & VALUE_WCHAR(IID_IDBCreateCommand),
  61.         & VALUE_WCHAR(IID_IDBSchemaRowset),
  62.         & VALUE_WCHAR(IID_IIndexDefinition),
  63.         & VALUE_WCHAR(IID_ITableDefinition),
  64.         & VALUE_WCHAR(IID_ITransactionJoin),
  65.         & VALUE_WCHAR(IID_ITransactionLocal),
  66.         & VALUE_WCHAR(IID_ITransactionObject),
  67.  
  68.     //TCommand
  69.         & VALUE_WCHAR(IID_IAccessor),
  70.         & VALUE_WCHAR(IID_IColumnsInfo),
  71.         & VALUE_WCHAR(IID_ICommand),
  72.         & VALUE_WCHAR(IID_ICommandProperties),
  73.         & VALUE_WCHAR(IID_ICommandText),
  74.         & VALUE_WCHAR(IID_IConvertType),
  75.         & VALUE_WCHAR(IID_IColumnsRowset),
  76.         & VALUE_WCHAR(IID_ICommandPrepare),
  77.         & VALUE_WCHAR(IID_ICommandWithParameters),
  78.     
  79.     //TRowset
  80.         & VALUE_WCHAR(IID_IRowset),
  81.         & VALUE_WCHAR(IID_IRowsetInfo),
  82.         & VALUE_WCHAR(IID_IColumnsRowset),
  83.         & VALUE_WCHAR(IID_IConnectionPointContainer),
  84.         & VALUE_WCHAR(IID_IRowsetChange),
  85.         & VALUE_WCHAR(IID_IRowsetIdentity),
  86.         & VALUE_WCHAR(IID_IRowsetLocate),
  87.         & VALUE_WCHAR(IID_IRowsetResynch),
  88.         & VALUE_WCHAR(IID_IRowsetScroll),
  89.         & VALUE_WCHAR(IID_IRowsetUpdate),
  90.     
  91.     //TIndex
  92.         & VALUE_WCHAR(IID_IRowsetIndex),
  93.     
  94.     //TError
  95.         & VALUE_WCHAR(IID_IErrorInfo),
  96.         & VALUE_WCHAR(IID_IErrorRecords),
  97.         & VALUE_WCHAR(IID_ISQLErrorInfo),
  98. };
  99.  
  100.  
  101. ////////////////////////////////////////////////////////////////////////
  102. // ERRORMAP
  103. //
  104. ////////////////////////////////////////////////////////////////////////
  105. typedef struct _ERRORMAP
  106. {
  107.     HRESULT        hr;            // HRESULT
  108.     WCHAR*        pwszError;    // Name
  109. } ERRORMAP;
  110.  
  111. ERRORMAP rgErrorMap[] =
  112. {
  113.      VALUE_WCHAR(NULL),
  114.  
  115.      //System Errors
  116.      VALUE_WCHAR(E_FAIL),
  117.      VALUE_WCHAR(E_INVALIDARG),
  118.      VALUE_WCHAR(E_OUTOFMEMORY),
  119.      VALUE_WCHAR(E_NOINTERFACE),
  120.      VALUE_WCHAR(REGDB_E_CLASSNOTREG),
  121.      VALUE_WCHAR(CLASS_E_NOAGGREGATION),
  122.      VALUE_WCHAR(E_UNEXPECTED),
  123.      VALUE_WCHAR(E_NOTIMPL),
  124.      VALUE_WCHAR(E_POINTER),
  125.      VALUE_WCHAR(E_HANDLE),
  126.      VALUE_WCHAR(E_ABORT),
  127.      VALUE_WCHAR(E_ACCESSDENIED),
  128.      VALUE_WCHAR(E_PENDING),
  129.  
  130.      //OLE DB Errors
  131.      VALUE_WCHAR(DB_E_BADACCESSORHANDLE),
  132.      VALUE_WCHAR(DB_E_ROWLIMITEXCEEDED),
  133.      VALUE_WCHAR(DB_E_READONLYACCESSOR),
  134.      VALUE_WCHAR(DB_E_SCHEMAVIOLATION),
  135.      VALUE_WCHAR(DB_E_BADROWHANDLE),
  136.      VALUE_WCHAR(DB_E_OBJECTOPEN),
  137.      VALUE_WCHAR(DB_E_CANTCONVERTVALUE),
  138.      VALUE_WCHAR(DB_E_BADBINDINFO),
  139.      VALUE_WCHAR(DB_SEC_E_PERMISSIONDENIED),
  140.      VALUE_WCHAR(DB_E_NOTAREFERENCECOLUMN),
  141.      VALUE_WCHAR(DB_E_NOCOMMAND),
  142.      VALUE_WCHAR(DB_E_BADBOOKMARK),
  143.      VALUE_WCHAR(DB_E_BADLOCKMODE),
  144.      VALUE_WCHAR(DB_E_PARAMNOTOPTIONAL),
  145.      VALUE_WCHAR(DB_E_BADCOLUMNID),
  146.      VALUE_WCHAR(DB_E_BADRATIO),
  147.      VALUE_WCHAR(DB_E_ERRORSINCOMMAND),
  148.      VALUE_WCHAR(DB_E_CANTCANCEL),
  149.      VALUE_WCHAR(DB_E_DIALECTNOTSUPPORTED),
  150.      VALUE_WCHAR(DB_E_DUPLICATEDATASOURCE),
  151.      VALUE_WCHAR(DB_E_CANNOTRESTART),
  152.      VALUE_WCHAR(DB_E_NOTFOUND),
  153.      VALUE_WCHAR(DB_E_NEWLYINSERTED),
  154.      VALUE_WCHAR(DB_E_UNSUPPORTEDCONVERSION),
  155.      VALUE_WCHAR(DB_E_BADSTARTPOSITION),
  156.      VALUE_WCHAR(DB_E_NOTREENTRANT),
  157.      VALUE_WCHAR(DB_E_ERRORSOCCURRED),
  158.      VALUE_WCHAR(DB_E_NOAGGREGATION),
  159.      VALUE_WCHAR(DB_E_DELETEDROW),
  160.      VALUE_WCHAR(DB_E_CANTFETCHBACKWARDS),
  161.      VALUE_WCHAR(DB_E_ROWSNOTRELEASED),
  162.      VALUE_WCHAR(DB_E_BADSTORAGEFLAG),
  163.      VALUE_WCHAR(DB_E_BADSTATUSVALUE),
  164.      VALUE_WCHAR(DB_E_CANTSCROLLBACKWARDS),
  165.      VALUE_WCHAR(DB_E_MULTIPLESTATEMENTS),
  166.      VALUE_WCHAR(DB_E_INTEGRITYVIOLATION),
  167.      VALUE_WCHAR(DB_E_ABORTLIMITREACHED),
  168.      VALUE_WCHAR(DB_E_DUPLICATEINDEXID),
  169.      VALUE_WCHAR(DB_E_NOINDEX),
  170.      VALUE_WCHAR(DB_E_INDEXINUSE),
  171.      VALUE_WCHAR(DB_E_NOTABLE),
  172.      VALUE_WCHAR(DB_E_CONCURRENCYVIOLATION),
  173.      VALUE_WCHAR(DB_E_BADCOPY),
  174.      VALUE_WCHAR(DB_E_BADPRECISION),
  175.      VALUE_WCHAR(DB_E_BADSCALE),
  176.      VALUE_WCHAR(DB_E_BADID),
  177.      VALUE_WCHAR(DB_E_BADTYPE),
  178.      VALUE_WCHAR(DB_E_DUPLICATECOLUMNID),
  179.      VALUE_WCHAR(DB_E_DUPLICATETABLEID),
  180.      VALUE_WCHAR(DB_E_TABLEINUSE),
  181.      VALUE_WCHAR(DB_E_NOLOCALE),
  182.      VALUE_WCHAR(DB_E_BADRECORDNUM),
  183.      VALUE_WCHAR(DB_E_BOOKMARKSKIPPED),
  184.      VALUE_WCHAR(DB_E_BADPROPERTYVALUE),
  185.      VALUE_WCHAR(DB_E_INVALID),
  186.      VALUE_WCHAR(DB_E_BADACCESSORFLAGS),
  187.      VALUE_WCHAR(DB_E_BADSTORAGEFLAGS),
  188.      VALUE_WCHAR(DB_E_BYREFACCESSORNOTSUPPORTED),
  189.      VALUE_WCHAR(DB_E_NULLACCESSORNOTSUPPORTED),
  190.      VALUE_WCHAR(DB_E_NOTPREPARED),
  191.      VALUE_WCHAR(DB_E_BADACCESSORTYPE),
  192.      VALUE_WCHAR(DB_E_WRITEONLYACCESSOR),
  193.      VALUE_WCHAR(DB_SEC_E_AUTH_FAILED),
  194.      VALUE_WCHAR(DB_E_CANCELED),
  195.      VALUE_WCHAR(DB_E_BADSOURCEHANDLE),
  196.      VALUE_WCHAR(DB_E_PARAMUNAVAILABLE),
  197.      VALUE_WCHAR(DB_E_ALREADYINITIALIZED),
  198.      VALUE_WCHAR(DB_E_NOTSUPPORTED),
  199.      VALUE_WCHAR(DB_E_MAXPENDCHANGESEXCEEDED),
  200.      VALUE_WCHAR(DB_E_BADORDINAL),
  201.      VALUE_WCHAR(DB_E_PENDINGCHANGES),
  202.      VALUE_WCHAR(DB_E_DATAOVERFLOW),
  203.      VALUE_WCHAR(DB_E_BADHRESULT),
  204.      VALUE_WCHAR(DB_E_BADLOOKUPID),
  205.      VALUE_WCHAR(DB_E_BADDYNAMICERRORID),
  206.      VALUE_WCHAR(DB_E_PENDINGINSERT),
  207.      VALUE_WCHAR(DB_E_BADCONVERTFLAG),
  208.      VALUE_WCHAR(DB_S_ROWLIMITEXCEEDED),
  209.      VALUE_WCHAR(DB_S_COLUMNTYPEMISMATCH),
  210.      VALUE_WCHAR(DB_S_TYPEINFOOVERRIDDEN),
  211.      VALUE_WCHAR(DB_S_BOOKMARKSKIPPED),
  212.      VALUE_WCHAR(DB_S_ENDOFROWSET),
  213.      VALUE_WCHAR(DB_S_COMMANDREEXECUTED),
  214.      VALUE_WCHAR(DB_S_BUFFERFULL),
  215.      VALUE_WCHAR(DB_S_NORESULT),
  216.      VALUE_WCHAR(DB_S_CANTRELEASE),
  217.      VALUE_WCHAR(DB_S_DIALECTIGNORED),
  218.      VALUE_WCHAR(DB_S_UNWANTEDPHASE),
  219.      VALUE_WCHAR(DB_S_UNWANTEDREASON),
  220.      VALUE_WCHAR(DB_S_COLUMNSCHANGED),
  221.      VALUE_WCHAR(DB_S_ERRORSRETURNED),
  222.      VALUE_WCHAR(DB_S_BADROWHANDLE),
  223.      VALUE_WCHAR(DB_S_DELETEDROW),
  224.      VALUE_WCHAR(DB_S_STOPLIMITREACHED),
  225.      VALUE_WCHAR(DB_S_LOCKUPGRADED),
  226.      VALUE_WCHAR(DB_S_PROPERTIESCHANGED),
  227.      VALUE_WCHAR(DB_S_ERRORSOCCURRED),
  228.      VALUE_WCHAR(DB_S_PARAMUNAVAILABLE),
  229.      VALUE_WCHAR(DB_S_MULTIPLECHANGES),
  230. };
  231.  
  232.  
  233. ////////////////////////////////////////////////////////////////////////
  234. // WCHAR* GetErrorName
  235. //
  236. ////////////////////////////////////////////////////////////////////////
  237. WCHAR* GetErrorName(HRESULT hr)
  238. {
  239.     for(ULONG i=0; i<NUMELE(rgErrorMap); i++)    
  240.     {
  241.         if(hr == rgErrorMap[i].hr) 
  242.             return rgErrorMap[i].pwszError;
  243.     }
  244.  
  245.     //Otherwise just return Unknown
  246.     return rgErrorMap[0].pwszError;
  247. }
  248.  
  249.  
  250. ////////////////////////////////////////////////////////////////////////
  251. // WCHAR* GetInterfaceName
  252. //
  253. ////////////////////////////////////////////////////////////////////////
  254. WCHAR* GetInterfaceName(REFIID riid)
  255. {
  256.     for(ULONG i=0; i<NUMELE(rgInterfaceMap); i++)    
  257.     {
  258.         if(riid == *(rgInterfaceMap[i].pIID)) 
  259.             return rgInterfaceMap[i].pwszInterface;
  260.     }
  261.  
  262.     //Otherwise just return IUnknown
  263.     return rgInterfaceMap[0].pwszInterface;
  264. }
  265.  
  266.  
  267. ////////////////////////////////////////////////////////////////////////
  268. // HRESULT GetErrorRecords
  269. //
  270. // Get the error message generated by an OLE DB object
  271. /////////////////////////////////////////////////////////////////////////////
  272. HRESULT GetErrorRecords(ULONG* pcRecords, IErrorRecords** ppIErrorRecords)
  273. {
  274.     ASSERT(pcRecords && ppIErrorRecords);
  275.     HRESULT hr;
  276.  
  277.     //NULL output params
  278.     *pcRecords = 0;
  279.     *ppIErrorRecords = NULL;
  280.     
  281.     ISupportErrorInfo* pISupportErrorInfo = NULL;
  282.     IErrorInfo* pIErrorInfo = NULL;
  283.  
  284.     //See if this interface supports ErrorInfo
  285.     //If not there is no reason to display any error
  286.     if((hr = GetErrorInfo(0, &pIErrorInfo))==S_OK && pIErrorInfo)
  287.     {
  288.         //IErrorRecords may not be supported on the existing error object.
  289.         //Some other things could have posted an error object (VB) for example...
  290.         QTESTC(hr = pIErrorInfo->QueryInterface(IID_IErrorRecords, (void**)ppIErrorRecords));
  291.         XTESTC(hr = (*ppIErrorRecords)->GetRecordCount(pcRecords));
  292.     }
  293.         
  294. CLEANUP:
  295.     SAFE_RELEASE(pISupportErrorInfo);
  296.     SAFE_RELEASE(pIErrorInfo);
  297.     return hr;
  298. }
  299.  
  300.  
  301. ////////////////////////////////////////////////////////////////////////
  302. // HRESULT GetSqlErrorInfo
  303. //
  304. // Get the error message generated by an OLE DB object
  305. /////////////////////////////////////////////////////////////////////////////
  306. HRESULT GetSqlErrorInfo(ULONG iRecord, IErrorRecords* pIErrorRecords, BSTR* pBstr)
  307. {
  308.     ASSERT(pBstr);
  309.     HRESULT hr = S_OK;
  310.  
  311.     ISQLErrorInfo* pISQLErrorInfo = NULL;
  312.     LONG lNativeError = 0;
  313.  
  314.     //Get the Error Records
  315.     if(pIErrorRecords)
  316.     {
  317.         //If there is ErrorInfo, GetSQLInfo for the desired record
  318.         //ISQLErrorInfo is not mandatory
  319.         QTESTC(hr = pIErrorRecords->GetCustomErrorObject(iRecord, IID_ISQLErrorInfo, (IUnknown**)&pISQLErrorInfo));
  320.         
  321.         //If there was a CustomErrorObject
  322.         if(pISQLErrorInfo)
  323.             hr = pISQLErrorInfo->GetSQLInfo(pBstr, &lNativeError);
  324.     }
  325.  
  326. CLEANUP:
  327.     SAFE_RELEASE(pISQLErrorInfo);
  328.     return hr;
  329. }
  330.  
  331.  
  332. ////////////////////////////////////////////////////////////////////////
  333. // HRESULT DisplayAllErrors
  334. //
  335. /////////////////////////////////////////////////////////////////////////////
  336. HRESULT DisplayAllErrors(HWND hWnd, HRESULT Actualhr, WCHAR* pwszFile, ULONG ulLine)
  337. {
  338.     HRESULT hr = S_OK;
  339.  
  340.     ULONG cRecords = 0;
  341.     IErrorRecords* pIErrorRecords = NULL;
  342.  
  343.     //Try to display Extened ErrorInfo
  344.     if((hr = GetErrorRecords(&cRecords, &pIErrorRecords))==S_OK) 
  345.     {
  346.         hr = DisplayErrorRecords(hWnd, cRecords, pIErrorRecords, pwszFile, ulLine);
  347.     }
  348.     //If not available, display MSG Box with info
  349.     else
  350.     {
  351.         //display the Error
  352.         wMessageBox(hWnd, (hWnd ? MB_APPLMODAL : MB_TASKMODAL) | MB_ICONEXCLAMATION | MB_OK, wsz_ERRORINFO, 
  353.             L"Interface: %s\nResult: %x = %s\n\nIErrorInfo: %s\n\nFile: %s\nLine: %d", L"Unknown", Actualhr, GetErrorName(Actualhr), L"Error Object not available", pwszFile, ulLine);
  354.     }
  355.  
  356.     
  357.     SAFE_RELEASE(pIErrorRecords);
  358.     return hr;
  359. }
  360.  
  361.  
  362. ////////////////////////////////////////////////////////////////////////
  363. // HRESULT DisplayErrorRecords
  364. //
  365. /////////////////////////////////////////////////////////////////////////////
  366. HRESULT DisplayErrorRecords(HWND hWnd, ULONG cRecords, IErrorRecords* pIErrorRecords, WCHAR* pwszFile, ULONG ulLine)
  367. {
  368.     HRESULT hr = S_OK;
  369.  
  370.     IErrorInfo* pIErrorInfo = NULL;
  371.     BSTR bstrErrorInfo = NULL;
  372.     BSTR bstrSQLInfo = NULL;
  373.  
  374.     LCID lcid = GetSystemDefaultLCID(); 
  375.  
  376.     //Get the Error Records
  377.     if(cRecords && pIErrorRecords)
  378.     {
  379.         LONG lNativeError = 0;
  380.         ERRORINFO ErrorInfo;
  381.  
  382.         //Loop through the records
  383.         for(ULONG i=0; i<cRecords; i++)
  384.         {
  385.             //GetErrorInfo
  386.             XTESTC(hr = pIErrorRecords->GetErrorInfo(i,lcid,&pIErrorInfo));
  387.                 
  388.             //Get the Description
  389.             XTESTC(hr = pIErrorInfo->GetDescription(&bstrErrorInfo));
  390.                 
  391.             //Get the Basic ErrorInfo
  392.             XTESTC(hr = pIErrorRecords->GetBasicErrorInfo(i,&ErrorInfo));
  393.             
  394.             //Get the SQL Info
  395.             GetSqlErrorInfo(i, pIErrorRecords, &bstrSQLInfo);
  396.  
  397.             //Display the Error
  398.             if(bstrSQLInfo)
  399.                 wMessageBox(hWnd, (hWnd ? MB_APPLMODAL : MB_TASKMODAL) | MB_ICONEXCLAMATION | MB_OK, wsz_ERRORINFO, L"Interface: %s\nResult: %x = %s\n\nIErrorInfo: [%s] %s\n\nFile: %s\nLine: %d", GetInterfaceName(ErrorInfo.iid), ErrorInfo.hrError, GetErrorName(ErrorInfo.hrError), bstrSQLInfo, bstrErrorInfo, pwszFile, ulLine);
  400.             else
  401.                 wMessageBox(hWnd, (hWnd ? MB_APPLMODAL : MB_TASKMODAL) | MB_ICONEXCLAMATION | MB_OK, wsz_ERRORINFO, L"Interface: %s\nResult: %x = %s\n\nIErrorInfo: %s\n\nFile: %s\nLine: %d", GetInterfaceName(ErrorInfo.iid), ErrorInfo.hrError, GetErrorName(ErrorInfo.hrError), bstrErrorInfo, pwszFile, ulLine);
  402.  
  403.             SAFE_RELEASE(pIErrorInfo);
  404.             SAFE_SYSFREE(bstrErrorInfo);
  405.             SAFE_SYSFREE(bstrSQLInfo);
  406.         }
  407.     }
  408.     
  409.  
  410. CLEANUP:
  411.     SAFE_RELEASE(pIErrorInfo);
  412.     SAFE_SYSFREE(bstrErrorInfo);
  413.     SAFE_SYSFREE(bstrSQLInfo);
  414.     return hr;
  415. }
  416.