Repository navigation
Reference a solution project from multiple other projects with a different Platform #14657
Replies: 1 comment
|
The VS part is by design. Inside VS, project references are only queried for their output path, not built, and each project builds once per solution config. So you can't get Core built as both x64 and AnyCPU in one VS build. You probably don't need to though. MSB3270 looks at the assembly's processor architecture (PlatformTarget), not the Platform name, and the SDK only derives PlatformTarget from Platform when it's empty. A netstandard2.0 lib has no reason to be x64-only, so in Core.csproj: <PropertyGroup>
<PlatformTarget>AnyCPU</PlatformTarget>
</PropertyGroup>It still builds under the x64 solution platform, same output path, but the dll is MSIL. Then the generator can use a plain ProjectReference with no SetPlatform. If Core really has to be arch-specific, a second project compiling the same sources with Platforms=AnyCPU is the usual way. |
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
I am writing a Source Generator project in my company's solution, and it needs to reference another low-level shared library from the same solution. I will call that the
Coreproject. Most of the solution projects explicitly compile using thex64Platform (we define<Platforms>x64</Platforms>inDirectory.Build.props). TheCoreproject overrides this and defines<Platforms>x64;AnyCPU</Platforms>.The Source Generator project itself needs to be able to run on ARM64 processors (e.g. if building something on ARM64 Mac devices that will utilize the generator), so it explicitly sets
<Platforms>AnyCPU</Platforms>and only ever targets AnyCPU. It should, therefore, reference theAnyCPUversion ofCore. I have tried to accomplish this as follows:However, when building the solution (from Visual Studio or command line), I see the following warning:
I used the MSBuild Structured Log Viewer to see what was happening, and it looks like the
AssignProjectConfigurationtask is overridingSetConfiguration,SetPlatform,Configuration,Platform, andFullConfigurationto use whatever Configuration/Platform mapping is defined for theCoreproject in the solution file.Obviously I don't want to use that mapping, as I'm explicitly setting
SetPlatformandSetConfigurationto something else - I'm not sure why MSBuild just ignores that entirely.I tried the following hack just to see if it would fix the problem:
This actually works on command line! Even if I fully clean the solution (remove all the
binandobjfolders), it will build theCoreproject using the normal Solution configuration (Debug|x64or whatever), and then right before it builds the Source Generator project, it will buildCoreagain using theDebug|AnyCPUconfiguration. The Source Generator project consumes the correct version of the DLL (frombin\Debuginstead ofbin\x64\Debug).Unfortunately, however, this solution does not work inside Visual Studio. If I remove the
binandobjfolders and then try to build the solution inside Visual Studio, I get a build error from the Source Generator project:I used the instructions here to produce a binary log of Visual Studio's specific invocation of MSBuild to see what was different. I narrowed it down to the following:
msbuild/src/Tasks/Microsoft.Common.CurrentVersion.targets
Lines 2120 to 2168 in ce25c01
It seems like it explicitly skips building the project if the build is invoked from Visual Studio:
Is there a way to actually accomplish what I am trying to accomplish? I don't want to use a bunch of custom MSBuild stuff for this (e.g. I don't want to do anything along the lines of manually invoking
MSBuildtasks to force-build the project or anything like that).It would be great if I could just do something with the solution configuration mappings so that it always builds both the
x64andAnyCPUplatforms for theCoreproject, but it doesn't seem like that's possible.I can potentially change the
Coreproject so that it always targetsAnyCPU, but it would be deviating from the expectation that ALL of our other projects up to this point have referenced its x64 DLL. Even if that ends up being the route I take, it would be nice to know how to solve the original problem in case I ever encounter this situation again where the other projects must have architecture-specific target platforms (e.g. native AOT or something).All reactions