在我的構建定義中,我需要一個所有編譯程序集的列表。這很簡單:如何排除本機DLL?
<CompiledAssemblies Include="$(OutDir)\MyCompany.*.dll" />
現在,如果我需要排除某些dll文件,我只想補充一個Exclude
屬性。但我想更進一步:
如何從上面的CompiledAssemblies
上排除所有原生 dll?
在我的構建定義中,我需要一個所有編譯程序集的列表。這很簡單:如何排除本機DLL?
<CompiledAssemblies Include="$(OutDir)\MyCompany.*.dll" />
現在,如果我需要排除某些dll文件,我只想補充一個Exclude
屬性。但我想更進一步:
如何從上面的CompiledAssemblies
上排除所有原生 dll?
原理並不困難:列表上的批處理,找出哪些dll是本地的,並創建一個只有那些列表的新列表。
一個簡單的方法來檢查一個DLL是否是一個正確的程序集正在運行corflags
:如果它返回0,它是一個程序集。或MSBuild的代碼(輸出redierected到NUL其他的MSBuild會以紅色顯示錯誤):
<ItemGroup>
<AllDlls Include="$(OutDir)\MyCompany.*.dll"/>
</ItemGroup>
<Target Name="RunCorFlags">
<Exec Command="corflags.exe %(AllDlls.Identity) > NUL" IgnoreExitCode="true">
<Output TaskParameter="ExitCode" ItemName="CorFlagsErrorCode"/>
</Exec>
</Target>
所以,現在我們只需要排除這些dll針對CorFlagsErrorCode爲1。這應該是很容易的,但我的ATM由於CorFlagsErrorCode將包含1和0的列表,所以不管有多少條目在批處理時,它都只會運行兩次,因爲批處理會跳過重複的項目。不管怎麼樣,CodeTaskFactory也提供了一個解決方案:
<Target Name="GetAssemblies" DependsOnTargets="RunCorFlags">
<GetAssembliesOnly Dlls="@(AllDlls)" CorFlagsErr="@(CorFlagsErrorCode)">
<Output TaskParameter="Assemblies" ItemName="CompiledAssemblies"/>
</GetAssembliesOnly>
<Message Text="CompiledAssemblies = %(CompiledAssemblies.Identity)"/>
</Target>
<UsingTask TaskName="GetAssembliesOnly" TaskFactory="CodeTaskFactory" AssemblyFile="$(MSBuildToolsPath)\Microsoft.Build.Tasks.v4.0.dll" >
<ParameterGroup>
<Dlls Required="true" ParameterType="Microsoft.Build.Framework.ITaskItem[]"/>
<CorFlagsErr Required="true" ParameterType="Microsoft.Build.Framework.ITaskItem[]"/>
<Assemblies Output="true" ParameterType="Microsoft.Build.Framework.ITaskItem[]"/>
</ParameterGroup>
<Task>
<Code Type="Fragment" Language="cs">
<![CDATA[
var temp = new List<ITaskItem>();
for(int i = 0 ; i < Dlls.Length ; ++i)
if(CorFlagsErr[ i ].ItemSpec == "0")
temp.Add(Dlls[ i ]);
Assemblies = temp.ToArray();
]]>
</Code>
</Task>
</UsingTask>
優秀!謝謝! – l33t
您可能正在構建程序集,因此您將成爲知道的人。但是,[.NET程序集](http://msdn.microsoft.com/zh-cn/library/zst29sk2(v = vs.110).aspx)是一組帶有清單的文件,通常至少有一個。 NET模塊。通常,這就是全部文件。但是,將依賴的本地dll捆綁到依賴於它們的程序集中有時很方便。對於一般的解決方案,您必須列出所有文件作爲排除對象,枚舉所有清單並從排除列表中刪除引用的文件。 –
我有一個只適用於.NET程序集的混淆步驟。捆綁原生DLL聽起來很有趣。 – l33t