我有一个用C ++开发的Windows库,它使用ATL集合,ATL CString和与CComPtr的COM接口。我从库中删除了所有非winrt允许的API调用,并且构建正常,所以我将库包装在C ++ / CX ref-class中,我试图从Windows应用商店应用程序中使用它。应用程序运行正常,但Win-Store App认证失败,出现以下错误:
发现错误:支持的API测试检测到以下错误: 此版本不支持kernel32.dll中的API GetModuleHandleW 申请类型。 MyLibrary.dll调用此API。 API 不支持kernel32.dll中的InitializeCriticalSectionAndSpinCount 对于此应用程序类型。 MyLibrary.dll调用此API。
我的库的VS项目是为Windows应用商店配置的,具有以下设置:
这些设置按预期激活/停用SDK中所需的宏(例如,WINAPI_FAMILY为WINAPI_FAMILY_APP)。
我100%确定我没有在我的库中直接调用GetModuleHandleW或InitializeCriticalSectionAndSpinCount ,所以我认为这个问题必须来自一些未在Windows中正确过滤的ATL类的方法8 SDK。
潜入ATL头文件并不是很有用,因为看起来在那里正确过滤了所有内容,例如从ATL看到这个片段:: CComCriticalSection :: Init
#if !defined(_ATL_USE_WINAPI_FAMILY_DESKTOP_APP) || defined(_ATL_STATIC_LIB_IMPL)
if (!_AtlInitializeCriticalSectionEx(&m_sec, 0, 0))
#else
if (!InitializeCriticalSectionAndSpinCount(&m_sec, 0))
#endif
为了证明我的理论,我采用了一个十六进制编辑器并从我的Kernel32.lib文件中编辑了GetModuleHandleW,它给出了以下链接错误:
atls.lib(atlwinverapi.obj):错误LNK2001:未解析的外部符号 __imp__GetModuleHandleW @ 4
所以看来我的理论没有错。请注意,我正在使用发布版本执行所有这些操作,因为调试版本未通过认证。
现在的问题是:
除了查看头文件外,有什么办法可以让我确切知道ATL中哪个类正在破坏我的库?
中的同样问题我添加了一个bug report on microsoft connect,其中包含一个可以重现此问题的小示例代码。
答案 0 :(得分:1)
这是我猜的。查看文件atlwinverapi.h。在那里,宏_ATL_NTDDI_MIN有条件地为x86 / x64定义了一种方式,而另一种方式定义为ARM。
我认为在最近添加XP支持的VSUpdate期间可能会发生这种情况。现在在文件atlwinverapi.cpp(我想进入atls.lib),在方法_AtlInitializeCriticalSectionEx中,你会注意到它正在调用InitializeCriticalSectionAndSpinCount,如果_ATL_NTDDI_MIN< NTDDI_VISTA。
我假设您正在构建x86或x64,这就是您遇到此问题的原因。如果您为ARM构建,则不会看到此问题。
当然,您将无法在ARM上运行WACK,但您可以在二进制文件上运行dumpbin / imports,看看它是否仍然使用这些不兼容的API。
答案 1 :(得分:0)
希望这个链接可以帮到你。它来自MSDN。 http://ecn.channel9.msdn.com/events/Win8CppEvent/PortingToMetro.pptx