[英]Visual Studio trying to use 64bit C runtime lib when compiling for 32bit
[英]VS COM Project Compiles in 32bit but throws error C2259 when trying to compile 64bit
您好,我當前正在運行Visual Studio 2010,並且具有上下文菜單外殼擴展,可以在32位計算機上以32位完全運行,因此存在所有方法。 這是一個ATL項目。 32位上沒有錯誤甚至警告。
這是問題。 當我進入Visual Studio下的配置管理器並將活動解決方案平台從Win32切換到x64並嘗試進行編譯時,出現錯誤“錯誤C2259:'ATL :: CCOMObject:無法實例化抽象類”。
由於這個完全相同的項目確實可以在32bit中編譯和運行,所以為什么將x64的錯誤拋出給我?
任何想法或正確方向的觀點將不勝感激。
所需並實現的主要方法如下:
STDMETHODIMP Initialize(LPCITEMIDLIST, LPDATAOBJECT, HKEY);
STDMETHODIMP GetCommandString(UINT, UINT, UINT*, LPSTR, UINT);
STDMETHODIMP InvokeCommand(LPCMINVOKECOMMANDINFO);
STDMETHODIMP QueryContextMenu(HMENU, UINT, UINT, UINT, UINT);
要節省代碼空間,請創建一個Atl項目。 創建初始項后,添加一個新類“ TestingContextMenu”,其余的代碼將引用此類。
stdafk.h
#include "resource.h"
#include <atlbase.h>
#include <atlcom.h>
#include <atlctl.h>
#include <shlobj.h>
#include <comdef.h>
#include <string>
#include <list>
typedef std::list< std::basic_string<TCHAR> > string_list;
TestingContextMenu.h僅包含已添加/更改的部分
#include "stdafx.h"
using namespace std;
class ATL_NO_VTABLE CTestingContextMenu:
public CComObjectRootEx<CComSingleThreadModel>,
public CComCoClass<CTestingContextMenu, &CLSID_TestingContextMenu>,
public IShellExtInit,
public IContextMenu
{
// Comment out or remove IDispatch
BEGIN_COM_MAP(CMainMagnimbusContextMenu)
//COM_INTERFACE_ENTRY(ITestingContextMenu)
//COM_INTERFACE_ENTRY(IDispatch)
COM_INTERFACE_ENTRY(IShellExtInit)
COM_INTERFACE_ENTRY(IContextMenu)
END_COM_MAP()
protected:
TCHAR m_szFile[MAX_PATH];
list<string> Filenames;
list<string> FilenamesCopier;
public:
STDMETHODIMP Initialize(LPCITEMIDLIST, LPDATAOBJECT, HKEY);
STDMETHODIMP GetCommandString(UINT, UINT, UINT*, LPSTR, UINT);
STDMETHODIMP InvokeCommand(LPCMINVOKECOMMANDINFO);
STDMETHODIMP QueryContextMenu(HMENU, UINT, UINT, UINT, UINT);
}; //There is other code within this but it is autogenerated
TestingContextMenu.cpp
#include "stdafx.h"
#include "TestingContextMenu"
#include <sstream>
using namespace std;
#pragma comment(lib, "comsuppw")
STDMETHODIMP CMainMagnimbusContextMenu::Initialize (
LPCITEMIDLIST pidlFolder,
LPDATAOBJECT pDataObj,
HKEY hProgID )
{
FORMATETC fmt = { CF_HDROP, NULL, DVASPECT_CONTENT, -1, TYMED_HGLOBAL };
STGMEDIUM stg = { TYMED_HGLOBAL };
HDROP hDrop;
if ( FAILED( pDataObj->GetData ( &fmt, &stg ) ))
return E_INVALIDARG;
hDrop = (HDROP) GlobalLock ( stg.hGlobal );
UINT uNumFiles = DragQueryFile ( hDrop, 0xFFFFFFFF, NULL, 0 );
HRESULT hr = S_OK;
if ( 0 == uNumFiles )
{
GlobalUnlock ( stg.hGlobal );
ReleaseStgMedium ( &stg );
return E_INVALIDARG;
}
UINT counter = 0;
// Get the name of the every file and store it in our member variable m_szFile.
for(counter = 0; counter < uNumFiles; counter++)
{
if ( 0 == DragQueryFile ( hDrop, counter, m_szFile, MAX_PATH ) )
{
hr = E_INVALIDARG;
}
wchar_t* t = _wcsdup(m_szFile);
char ch[260];
char DefChar = ' ';
WideCharToMultiByte(CP_ACP,0,t,-1, ch,260,&DefChar, NULL);
string ss(ch);
Filenames.push_back(ss);
FilenamesCopier.push_back(ss);
}
GlobalUnlock ( stg.hGlobal );
ReleaseStgMedium ( &stg );
return hr;
}
其余功能可應要求提供。 但是我注意到了一些新東西。 如果您僅實現了上述功能和代碼,並且配置管理器設置為構建x64,則會出現我遇到的初始錯誤。 這甚至意味着不實現QueryContextMenu,GetCommandString或invoke命令。 您在此設置中遇到的唯一錯誤是我的原始錯誤,這是我們期望的,因為未實現它們。 但是,將該配置管理器切換回Win32,您會得到預期的錯誤,例如3個未解決的外部問題,以及在命名GetCommandString,InvokeCommand和QueryContextMenu后出現的3個錯誤。 再次期望是否未實現,但是為什么x64上的編譯器只能識別我原來的錯誤,這是很多人認為的錯誤,而不是未實現的方法,但是在win32設置中,未實現時會顯示全部錯誤。
上一段只是我注意到的東西。 我確實正確實現了所有3種方法,並且可以在Win32中正確編譯,但不能在x64中正確編譯。
您的GetCommandString
參數與接口方法定義的參數不匹配。
你的
STDMETHODIMP GetCommandString(UINT, UINT, UINT*, LPSTR, UINT)
需要是
STDMETHODIMP GetCommandString(UINT_PTR, UINT, UINT*, LPSTR, UINT)
在Win32
,不匹配並不是那么重要(參數類型解析為相同類型),而在x64
則變得重要。 編譯器生成輸出應該給您提示,包括缺少的方法名稱。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.