兄弟帮忙看一段获取IHTMLDocument2接口的代码,MSDN上面找的,该怎么处理

兄弟帮忙看一段获取IHTMLDocument2接口的代码,MSDN上面找的
原本是想获取INTERNET EXPLORER_SERVER里面的文本,用了下面这个函数,获取接口正常,但一使用接口就出错。后来我直接尝试获取接口的原函数,还是不行,执行到spDoc->put_bgColor( CComVariant("red") );这一行就死掉了,麻烦高手帮我看一下,下面是我在MSDN上面找到的代码,一起贴上来,

还有说一下我用的是WIN7+VS2008,IE的窗口句柄是直接用Spy++得到的,

BOOL CALLBACK MyEnumChildProc(HWND hwnd,LPARAM lParam)
{
  TCHAR buf[100];

  ::GetClassName( hwnd, (LPTSTR)&buf, 100 );
  if ( _tcscmp( buf, _T("Internet Explorer_Server") ) == 0 )
  {
  *(HWND*)lParam = hwnd;
  return FALSE;
  }
  else
  return TRUE;
}

void OnGetDocInterface(HWND hWnd) 
{
  CoInitialize( NULL );
  // Explicitly load MSAA so we know if it's installed
  HINSTANCE hInst = ::LoadLibrary( _T("OLEACC.DLL") );
  if ( hInst != NULL )
  {
  if ( hWnd != NULL )
  {
  HWND hWndChild=NULL;
  // Get 1st document window
  ::EnumChildWindows( hWnd, MyEnumChildProc, (LPARAM)&hWndChild );
  if ( hWndChild )
  {
  CComPtr<IHTMLDocument2> spDoc;
  LRESULT lRes;
   
  UINT nMsg = ::RegisterWindowMessage( _T("WM_HTML_GETOBJECT") );
  ::SendMessageTimeout( hWndChild, nMsg, 0L, 0L, SMTO_ABORTIFHUNG, 1000, (DWORD*)&lRes );

  LPFNOBJECTFROMLRESULT pfObjectFromLresult = (LPFNOBJECTFROMLRESULT)::GetProcAddress( hInst, "ObjectFromLresult");
  if ( pfObjectFromLresult != NULL )
  {
  HRESULT hr;
  hr = (*pfObjectFromLresult)( lRes, IID_IHTMLDocument, 0, (void**)&spDoc );
  if ( SUCCEEDED(hr))
  {
  // Change background color to red
  spDoc->put_bgColor( CComVariant("red") );
  }
  }
  } // else document not ready
  } // else Internet Explorer is not running
  ::FreeLibrary( hInst );
  } // else Active Accessibility is not installed
  CoUninitialize();
}

------解决方案--------------------
ObjectFromLresult 仅限项目内部使用,MSDN的解释:Neither clients nor servers should call this function.

实际上这个API本来不应该公开,它只能用于当前线程中创建的组件,跨线程不能用,跨进程更不用说。
------解决方案--------------------
事实上,这种方法是可以用的,获取【其他进程】的doc进行操作没有任何问题!

我曾经用这种方法写过一个自动玩qq网页游戏怪物对对碰的辅助工具(使用IE打开qq怪物对对碰游戏,然后用工具选中该IE窗口,就可以自动玩)

C/C++ code

HRESULT CMyQQGameToolDlg::GetIHTMLDocument2FromHWND(IHTMLDocument2 ** pDoc2)
{
    LRESULT lRes;
    UINT nMsg = ::RegisterWindowMessage( _T("WM_HTML_GETOBJECT") );
    ::SendMessageTimeout(m_hIE, nMsg, 0L, 0L, SMTO_ABORTIFHUNG, 1000, (DWORD*)&lRes );

    LPFNOBJECTFROMLRESULT pfObjectFromLresult = (LPFNOBJECTFROMLRESULT)::GetProcAddress( m_hInstMSAA, "ObjectFromLresult");
    if (NULL == pfObjectFromLresult)
    {
        ...
    }

    HRESULT hr;
    hr = (*pfObjectFromLresult)( lRes, IID_IHTMLDocument, 0, (void**)pDoc2 );
    if (FAILED(hr))
    {
        ...
    }

    return S_OK;
}

调用处的代码
     // GET IE hwnd
     ...

     CComPtr<IHTMLDocument2> spDoc2;
     HRESULT hr = E_FAIL;
     hr = GetIHTMLDocument2FromHWND(&spDoc2);

     /////////////////////////////////////////////////////
     // 直接操作spDoc2会有异常!
      // 再QI一次获取另外的接口就可以操作了
      // 
     CComQIPtr<IHTMLDocument3> spDoc3 = spDoc2;
    hr = spDoc3->getElementById(...