异步事件:已定义的链接器错误 [Windows Update API]
好吧,我一直在摆弄一些 Microsoft Windows Update API,并尝试进行一些异步下载。使用 IDownloadProgressChangedCallback 接口的类的回调引用的 API 类 有关 API 的更多信息可以在此处找到。到目前为止我所做的只是瞎猜(我从来没有搞乱过回调或异步代码,或者微软的API)。我不断遇到“已定义”相同方法的问题。这是我到目前为止所拥有的:
main 方法中的相关代码:
IDownloadJob *_DownloadJob = NULL;
tagVARIANT NodeValue ; \\>>PS<< HOW DO I SET THIS TO A DEFUALT VALUE?
hr = _UpdateDownloader->BeginDownload(new DownloadProgressChangedCallback ,new DownloadCompletedCallback, NodeValue,&_DownloadJob);
DownloadProgressChange.h:
#include <Wuapi.h>
#pragma once
class DownloadProgressChangedCallback : public IDownloadProgressChangedCallback
{
public:
HRESULT STDMETHODCALLTYPE Invoke( IDownloadJob *downloadJob, IDownloadProgressChangedCallbackArgs *callbackArgs);
HRESULT STDMETHODCALLTYPE QueryInterface( REFIID riid, __RPC__deref_out void __RPC_FAR *__RPC_FAR *ppvObject);
ULONG STDMETHODCALLTYPE AddRef( void) ;
ULONG STDMETHODCALLTYPE Release( void);
};
DownloadProgressChange.cpp:
#include "StdAfx.h"
#include "DownloadProgressChange.h"
HRESULT STDMETHODCALLTYPE Invoke( IDownloadJob *downloadJob, IDownloadProgressChangedCallbackArgs *callbackArgs)
{
return NULL;
}
HRESULT STDMETHODCALLTYPE QueryInterface( REFIID riid, __RPC__deref_out void __RPC_FAR *__RPC_FAR *ppvObject)
{
return NULL;
}
ULONG STDMETHODCALLTYPE AddRef( void)
{
return NULL;
}
ULONG STDMETHODCALLTYPE Release( void)
{
return NULL;
}
DownloadCompletedCallback.h
#include <Wuapi.h>
#pragma once
class DownloadCompletedCallback : public IDownloadCompletedCallback
{
public:
HRESULT STDMETHODCALLTYPE Invoke( IDownloadJob *searchJob, IDownloadCompletedCallbackArgs *callbackArgs);
HRESULT STDMETHODCALLTYPE QueryInterface( REFIID riid, __RPC__deref_out void __RPC_FAR *__RPC_FAR *ppvObject);
ULONG STDMETHODCALLTYPE AddRef( void) ;
ULONG STDMETHODCALLTYPE Release( void);
};
DownloadCompletedCallback.cpp
#include "StdAfx.h"
#include "DownloadCompletedCallback.h"
HRESULT STDMETHODCALLTYPE Invoke( IDownloadJob *searchJob, IDownloadCompletedCallbackArgs *callbackArgs)
{
return NULL;
}
HRESULT STDMETHODCALLTYPE QueryInterface( REFIID riid, __RPC__deref_out void __RPC_FAR *__RPC_FAR *ppvObject)
{
return NULL;
}
ULONG STDMETHODCALLTYPE AddRef( void)
{
return NULL;
}
ULONG STDMETHODCALLTYPE Release( void)
{
return NULL;
}
这是构建输出的响应:
1>------ Build started: Project: WinGet, Configuration: Debug Win32 ------
1>Build started 5/29/2011 10:29:15 PM.
1>InitializeBuildStatus:
1> Touching "Debug\WinGet.unsuccessfulbuild".
1>ClCompile:
1> All outputs are up-to-date.
1> All outputs are up-to-date.
1>ManifestResourceCompile:
1> All outputs are up-to-date.
1>DownloadProgressChange.obj : error LNK2005: "long __stdcall QueryInterface(struct _GUID const &,void * *)" (?QueryInterface@@YGJABU_GUID@@PAPAX@Z) already defined in DownloadCompletedCallback.obj
1>DownloadProgressChange.obj : error LNK2005: "unsigned long __stdcall AddRef(void)" (?AddRef@@YGKXZ) already defined in DownloadCompletedCallback.obj
1>DownloadProgressChange.obj : error LNK2005: "unsigned long __stdcall Release(void)" (?Release@@YGKXZ) already defined in DownloadCompletedCallback.obj
1>WinGet.obj : error LNK2001: unresolved external symbol "private: virtual long __stdcall DownloadCompletedCallback::QueryInterface(struct _GUID const &,void * *)" (?QueryInterface@DownloadCompletedCallback@@EAGJABU_GUID@@PAPAX@Z)
1>WinGet.obj : error LNK2001: unresolved external symbol "private: virtual unsigned long __stdcall DownloadCompletedCallback::AddRef(void)" (?AddRef@DownloadCompletedCallback@@EAGKXZ)
1>WinGet.obj : error LNK2001: unresolved external symbol "private: virtual unsigned long __stdcall DownloadCompletedCallback::Release(void)" (?Release@DownloadCompletedCallback@@EAGKXZ)
1>WinGet.obj : error LNK2001: unresolved external symbol "public: virtual long __stdcall DownloadCompletedCallback::Invoke(struct IDownloadJob *,struct IDownloadCompletedCallbackArgs *)" (?Invoke@DownloadCompletedCallback@@UAGJPAUIDownloadJob@@PAUIDownloadCompletedCallbackArgs@@@Z)
1>WinGet.obj : error LNK2001: unresolved external symbol "public: virtual long __stdcall DownloadProgressChangedCallback::QueryInterface(struct _GUID const &,void * *)" (?QueryInterface@DownloadProgressChangedCallback@@UAGJABU_GUID@@PAPAX@Z)
1>WinGet.obj : error LNK2001: unresolved external symbol "public: virtual unsigned long __stdcall DownloadProgressChangedCallback::AddRef(void)" (?AddRef@DownloadProgressChangedCallback@@UAGKXZ)
1>WinGet.obj : error LNK2001: unresolved external symbol "public: virtual unsigned long __stdcall DownloadProgressChangedCallback::Release(void)" (?Release@DownloadProgressChangedCallback@@UAGKXZ)
1>WinGet.obj : error LNK2001: unresolved external symbol "public: virtual long __stdcall DownloadProgressChangedCallback::Invoke(struct IDownloadJob *,struct IDownloadProgressChangedCallbackArgs *)" (?Invoke@DownloadProgressChangedCallback@@UAGJPAUIDownloadJob@@PAUIDownloadProgressChangedCallbackArgs@@@Z)
1>C:\Users\Nathan\Documents\Visual Studio 2010\Projects\WinGet\Debug\WinGet.exe : fatal error LNK1120: 8 unresolved externals
1>
1>Build FAILED.
1>
1>Time Elapsed 00:00:01.04
========== Build: 0 succeeded, 1 failed, 0 up-to-date, 0 skipped ==========
提前致谢!
Alright, so I've been messing around with some Microsoft Windows Update APIs and am attempting to have some asynchronous downloading. The API class class for a callback reference for a class that uses the IDownloadProgressChangedCallback interface More Info About The API Can Be Found Here. What I have done so far is just a shot in the dark (I've never messed with callbacks or asynchronous code, or Microsoft API's for that matter). I keep getting issues with having the same methods being "already defined". Here is what I have so far:
Relevent code in main method:
IDownloadJob *_DownloadJob = NULL;
tagVARIANT NodeValue ; \\>>PS<< HOW DO I SET THIS TO A DEFUALT VALUE?
hr = _UpdateDownloader->BeginDownload(new DownloadProgressChangedCallback ,new DownloadCompletedCallback, NodeValue,&_DownloadJob);
DownloadProgressChange.h:
#include <Wuapi.h>
#pragma once
class DownloadProgressChangedCallback : public IDownloadProgressChangedCallback
{
public:
HRESULT STDMETHODCALLTYPE Invoke( IDownloadJob *downloadJob, IDownloadProgressChangedCallbackArgs *callbackArgs);
HRESULT STDMETHODCALLTYPE QueryInterface( REFIID riid, __RPC__deref_out void __RPC_FAR *__RPC_FAR *ppvObject);
ULONG STDMETHODCALLTYPE AddRef( void) ;
ULONG STDMETHODCALLTYPE Release( void);
};
DownloadProgressChange.cpp:
#include "StdAfx.h"
#include "DownloadProgressChange.h"
HRESULT STDMETHODCALLTYPE Invoke( IDownloadJob *downloadJob, IDownloadProgressChangedCallbackArgs *callbackArgs)
{
return NULL;
}
HRESULT STDMETHODCALLTYPE QueryInterface( REFIID riid, __RPC__deref_out void __RPC_FAR *__RPC_FAR *ppvObject)
{
return NULL;
}
ULONG STDMETHODCALLTYPE AddRef( void)
{
return NULL;
}
ULONG STDMETHODCALLTYPE Release( void)
{
return NULL;
}
DownloadCompletedCallback.h
#include <Wuapi.h>
#pragma once
class DownloadCompletedCallback : public IDownloadCompletedCallback
{
public:
HRESULT STDMETHODCALLTYPE Invoke( IDownloadJob *searchJob, IDownloadCompletedCallbackArgs *callbackArgs);
HRESULT STDMETHODCALLTYPE QueryInterface( REFIID riid, __RPC__deref_out void __RPC_FAR *__RPC_FAR *ppvObject);
ULONG STDMETHODCALLTYPE AddRef( void) ;
ULONG STDMETHODCALLTYPE Release( void);
};
DownloadCompletedCallback.cpp
#include "StdAfx.h"
#include "DownloadCompletedCallback.h"
HRESULT STDMETHODCALLTYPE Invoke( IDownloadJob *searchJob, IDownloadCompletedCallbackArgs *callbackArgs)
{
return NULL;
}
HRESULT STDMETHODCALLTYPE QueryInterface( REFIID riid, __RPC__deref_out void __RPC_FAR *__RPC_FAR *ppvObject)
{
return NULL;
}
ULONG STDMETHODCALLTYPE AddRef( void)
{
return NULL;
}
ULONG STDMETHODCALLTYPE Release( void)
{
return NULL;
}
And Here Is The Response From The Build Output:
1>------ Build started: Project: WinGet, Configuration: Debug Win32 ------
1>Build started 5/29/2011 10:29:15 PM.
1>InitializeBuildStatus:
1> Touching "Debug\WinGet.unsuccessfulbuild".
1>ClCompile:
1> All outputs are up-to-date.
1> All outputs are up-to-date.
1>ManifestResourceCompile:
1> All outputs are up-to-date.
1>DownloadProgressChange.obj : error LNK2005: "long __stdcall QueryInterface(struct _GUID const &,void * *)" (?QueryInterface@@YGJABU_GUID@@PAPAX@Z) already defined in DownloadCompletedCallback.obj
1>DownloadProgressChange.obj : error LNK2005: "unsigned long __stdcall AddRef(void)" (?AddRef@@YGKXZ) already defined in DownloadCompletedCallback.obj
1>DownloadProgressChange.obj : error LNK2005: "unsigned long __stdcall Release(void)" (?Release@@YGKXZ) already defined in DownloadCompletedCallback.obj
1>WinGet.obj : error LNK2001: unresolved external symbol "private: virtual long __stdcall DownloadCompletedCallback::QueryInterface(struct _GUID const &,void * *)" (?QueryInterface@DownloadCompletedCallback@@EAGJABU_GUID@@PAPAX@Z)
1>WinGet.obj : error LNK2001: unresolved external symbol "private: virtual unsigned long __stdcall DownloadCompletedCallback::AddRef(void)" (?AddRef@DownloadCompletedCallback@@EAGKXZ)
1>WinGet.obj : error LNK2001: unresolved external symbol "private: virtual unsigned long __stdcall DownloadCompletedCallback::Release(void)" (?Release@DownloadCompletedCallback@@EAGKXZ)
1>WinGet.obj : error LNK2001: unresolved external symbol "public: virtual long __stdcall DownloadCompletedCallback::Invoke(struct IDownloadJob *,struct IDownloadCompletedCallbackArgs *)" (?Invoke@DownloadCompletedCallback@@UAGJPAUIDownloadJob@@PAUIDownloadCompletedCallbackArgs@@@Z)
1>WinGet.obj : error LNK2001: unresolved external symbol "public: virtual long __stdcall DownloadProgressChangedCallback::QueryInterface(struct _GUID const &,void * *)" (?QueryInterface@DownloadProgressChangedCallback@@UAGJABU_GUID@@PAPAX@Z)
1>WinGet.obj : error LNK2001: unresolved external symbol "public: virtual unsigned long __stdcall DownloadProgressChangedCallback::AddRef(void)" (?AddRef@DownloadProgressChangedCallback@@UAGKXZ)
1>WinGet.obj : error LNK2001: unresolved external symbol "public: virtual unsigned long __stdcall DownloadProgressChangedCallback::Release(void)" (?Release@DownloadProgressChangedCallback@@UAGKXZ)
1>WinGet.obj : error LNK2001: unresolved external symbol "public: virtual long __stdcall DownloadProgressChangedCallback::Invoke(struct IDownloadJob *,struct IDownloadProgressChangedCallbackArgs *)" (?Invoke@DownloadProgressChangedCallback@@UAGJPAUIDownloadJob@@PAUIDownloadProgressChangedCallbackArgs@@@Z)
1>C:\Users\Nathan\Documents\Visual Studio 2010\Projects\WinGet\Debug\WinGet.exe : fatal error LNK1120: 8 unresolved externals
1>
1>Build FAILED.
1>
1>Time Elapsed 00:00:01.04
========== Build: 0 succeeded, 1 failed, 0 up-to-date, 0 skipped ==========
Thanks in advance!
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
在 .cpp 文件中,您忘记将类范围放在函数定义上。它们应该是:
等(两个类中的所有函数。)
编辑:在此处添加我在下面添加到 Nemo 的答案中的注释,关于初始化您的 VARIANT:
为了节省您的精力和复杂性,我可以建议您使用 _variant_t班级。这是一个 VARIANT 包装器,可以为您处理很多原本难以处理的内容。以下是一些文档。
要更直接地回答您的问题,您需要查看 VariantInit() 函数 在这里。
In your .cpp files, you forgot to put the class scope on the function definitions. They should be:
etc. (All of the functions in both classes.)
Edit: adding here the comments I added below to Nemo's answer, about initializing your VARIANT:
To save you some effort and complexity, may I recommend that you use the _variant_t class. This is a VARIANT wrapper, and handles a lot of stuff for you that's otherwise unpleasant to deal with. Here's some documentation.
To answer your question more directly, you need to take a look at the VariantInit() function here.
在 .cpp 文件中,您需要指定正在定义的成员函数的完全限定名称:
[等]
如果没有
DownloadProgressChangedCallback::
前缀,您只需定义一个名为“的全局函数”调用”。链接器抱怨是因为 (a) 您已经执行了两次并且 (b) 您尚未定义您声明的实际成员函数。In your .cpp files, you need to specify the fully-qualified name of the member function you are defining:
[etc.]
Without the
DownloadProgressChangedCallback::
prefix, you are just defining a global function named "Invoke". The linker is complaining because (a) you have done that twice and (b) you have not defined the actual member functions you declared.