【发布时间】:2011-02-25 20:16:00
【问题描述】:
我有一个很大的 VS2010 解决方案,其中包含一堆 C# 项目。其中一个项目通过 P/Invoke 使用 C++(本机,也称为非托管)库。为了确保一切都正确构建,我在同一个解决方案中包含了上述 C++ 项目。现在,问题就从这里开始了。
简而言之:MSBuild 神秘地删除了一些输出文件,而 VS2010 可以正确构建。
.
长篇大论:
以前(VS2005/2008),我会使用称为“项目依赖项”的漂亮功能。这使您可以选择给定项目所依赖的特定项目,以便环境确保首先构建这些项目。
然而,VS2010 已经朝着 MSBuild 的方向发展,现在项目依赖项根本不起作用。他们只是没有。 (例如见this question) 现在,为了确保我的 C++ 项目在使用它之前构建,我必须“添加引用”。所以我做到了。一切似乎都很好。
然后,我转到命令行并启动 MSBuild 以构建相同的解决方案。一切都很好,再次。但是当我查看输出文件夹时,没有 C++ 项目的输出!
MSBuild 控制台输出清楚地表明 C++ 项目在某个时间点确实已构建。我什至在一些项目中插入了一些“dir bin\MYPROJNAME.dll”语句作为后期构建步骤,以查看文件是否存在 - 它们是! Here 是命令行窗口的截图。红色圈出的是文件存在的时刻(顶部),然后是文件丢失的时刻(底部)。
另一个奇怪的事情是,该项目显然被构建了两次。请参阅屏幕截图中的红色下划线 - 这是关于构建同一项目的第二条消息(第一条消息以及所有编译器输出都在屏幕上方)。
看起来确实是第二次构建事件导致文件被删除:当我完全禁用构建这个项目时(通过解决方案属性),它只构建了一次,并且文件最终存在。我本可以将其称为“解决方案”,但随后它在 Visual Studio 本身中中断:VS 只是不构建项目。
解决此问题的另一种方法是从正在使用的 C# 项目中删除“项目引用”。然后 MSBuild 将只构建 C++ 项目一次,并且文件将在那里。但随后它又出现在另一个地方:对 C++ 项目的更改不会触发正在使用的 C# 项目的重建。
所以问题是:如何让 MSBuild 不删除该死的文件?
【问题讨论】:
-
查看解决方案中使用的平台目标。这在 VS2010 中可能会变得很混乱,特别是如果您从早期版本导入它。将输出详细程度也设置为 11,以更详细地了解它正在考虑的内容。您可以将其带到 connect.microsoft.com,但您需要更好地记录它。至少包括项目和解决方案文件。
-
@Hans,谢谢。我已使用您的建议并使用
/v:diag运行 MSBuild。这让我有了更多的了解,但我仍然不知所措。下面是 MSBuild 输出的相关部分:apreleva.com/trs/missingdll.txt 注意“构建”目标是如何被跳过的(第 89 行),因为“之前构建成功”。然而,所有各种“清理”目标都未能被跳过。有什么想法吗? -
哦,我还必须补充一点,我正在使用
/t:Rebuild构建,因此“清理”目标实际上正在正确执行。这里的“构建”目标有问题:它不应该被跳过。 -
我是个白痴,但 32/64 位混合是您的目标平台、开发环境或引用库中的一个因素吗?对我来说,VS2010 对这类问题的直言不讳比以前的版本少。
-
@Kynth,这对我来说似乎不太可能。是的,我的工作机器是 64 位的,而 MSBuild 是 64 位进程,VS2010 是 32 位,这可能会造成不一致。但是我的构建服务器是 32 位机器,所以 MSBuild 在那里作为 32 位进程运行,但仍然产生相同的结果。
标签: visual-studio-2010 msbuild build