自己写了个DLL连接数据库,EXE程序调用出现Crash有关问题.请问

自己写了个DLL连接数据库,EXE程序调用出现Crash问题.请教?
自己写了个DLL连接数据库.当调用这个DLL的EXE退出的时候,就出现Crash.Crash的地方是:
//c:\program   files\microsoft   visual   studio   8\vc\include\comip.h
void   _Release()   throw()
        {
                if   (m_pInterface   !=   NULL)   {
                        m_pInterface-> Release();   //Crash
                }
        }

如果我把DLL中的代码放在Application中,即不用DLL,就没有问题.

我现在分离出了最小的代码集.可能还是有点长.
DLL的入口是一个CDataCenter类,它的静态方法调用一个实现了单态模式的类CADOManager,CADOManager类中包含一个成员变量_ConnectionPtr               m_pCon;连接和关闭数据库就是调用m_pCon的方法.

///////////////DataAccess.DLL

//class   CADOManager
//ADOManager.h
class   CADOManager
{
friend   CADOManager*   TheADOManager();
public:
CADOManager(void);
public:
~CADOManager(void);
BOOL   Inital();
BOOL   ExInital();
private:
_ConnectionPtr               m_pCon;
static   auto_ptr <CADOManager>   m_instance;
};
CADOManager*   TheADOManager();
//ADOManager.cpp
auto_ptr <CADOManager>   CADOManager::m_instance;
CADOManager::CADOManager(void)
{
}

CADOManager::~CADOManager(void)
{
}

BOOL   CADOManager::Inital()
{
m_pCon.CreateInstance(__uuidof(Connection));
m_pCon-> Open(_bstr_t(_T( "Provider=Microsoft.Jet.OLEDB.4.0;Data   Source=D:\\sss.xls;Extended   Properties=\ "Excel   8.0;HDR=Yes\ "; ")),_bstr_t(_T( " ")),_bstr_t(_T( " ")),adModeUnknown);
                  return   TRUE;
}
BOOL   CADOManager::ExInital()
{
m_pCon-> Close();
                  return   TRUE;
}
CADOManager*   TheADOManager()
{
if(0   ==   CADOManager::m_instance.get())
{
CADOManager::m_instance.reset(new   CADOManager);
}
return   CADOManager::m_instance.get();
}

//class   CDataCenter
//DataCenter.h
class   __declspec(dllexport)     CDataCenter
{
public:
static   BOOL   Inital();
static   BOOL   ExInital();
};

//DataCenter.cpp
BOOL   CDataCenter::Inital()
{
TheADOManager()-> Inital();
return   TRUE;
}
BOOL   CDataCenter::ExInital()
{
TheADOManager()-> ExInital();
return   TRUE;
}

////////////////////////Appliaction
//Code:
CDataCenter::Inital();
CDataCenter::ExInital();


------解决方案--------------------
检查一下你的CoUninitialize, 是不是在Release之前就被Call了。

用Smart Pointer的时候一定要小心全局变量,你这里 auto_ptr <CADOManager> CADOManager::m_instance; 要在CoUninitialize之前 (或者OleUninitialize)把所有的Release都弄干净,否则你的COM Apartment一丢,再Release就Crash了。
------解决方案--------------------
千万不要用catch(...)!

这是很多公司最后花无数多钱请专家的一个重要原因。C++的catch(...)会抓住Structure Exception, 这样就把一些比如Access Denied等致命的错误都抓住了,还有比如Heap Corruption,最后出错的时候已经无法跟踪解决了。这个catch(...)是 C++ 里设计很糟糕的一个东西。

楼主程序之所以Crash就是因为用了智能指针,因为是全局变量,所以在Main 函数结束以后Release才被自动叫到。这个时候通常COM 已经都结构了(CoUninitialze被叫过了),所以会立即Crash。这个根本不是 COM 的 exception, _com_error根本抓不到。