Search code examples
.netmultiplatform.net-core

.NET Core CLI running non-Core App, how does it work?


I'm learning the dotnet CLI (as well as .NET Core) and one thing is not clear regarding multi platform targeting. Suppose my project has following section:

  "frameworks": {
    "netcoreapp1.0": {
       ...
    },
    "net451": { }
  }

And I have net451 installed on my PC. Then I run it:

dotnet run -f net451

What is used to compile and run the project? Does it call the msbuild from net451 sdk? Can the running app be still considered as .NET Core App?

Some useful link:

Running .NET Core apps on multiple frameworks and What the Target Framework Monikers (TFMs) are about


Solution

  • What is used to compile and run the project? Does it call the msbuild from net451 sdk?

    You can find out yourself if you add the -v flag to dotnet:

    > dotnet -v run -f net451
    
    Project hwapp (.NETFramework,Version=v4.5.1) will be compiled because expected outputs are missing
            C:\code\hwapp\bin\Debug\net451\rtmapp.exe
            C:\code\hwapp\bin\Debug\net451\rtmapp.pdb
            C:\code\hwapp\bin\Debug\net451\win7-x64\rtmapp.exe
            C:\code\hwapp\bin\Debug\net451\win7-x64\rtmapp.pdb
    Compiling hwapp for .NETFramework,Version=v4.5.1
    Running C:\Program Files\dotnet\dotnet.exe "C:\Program Files\dotnet\sdk\1.0.0-preview2-003121\csc.dll" -noconfig @C:\code\hwapp\obj\Debug\net451\dotnet-compile-csc.rsp
    Process ID: 4900
    
    Compilation succeeded.
        0 Warning(s)
        0 Error(s)
    
    Time elapsed 00:00:01.4136972
    
    
    Running C:\code\hwapp\bin\Debug\net451\win7-x64\rtmapp.exe
    Process ID: 12208
    Hello World!
    
    > dotnet -v run -f netcoreapp1.0
    
    Project hwapp (.NETCoreApp,Version=v1.0) will be compiled because expected outputs are missing
            C:\code\hwapp\bin\Debug\netcoreapp1.0\rtmapp.dll
            C:\code\hwapp\bin\Debug\netcoreapp1.0\rtmapp.pdb
            C:\code\hwapp\bin\Debug\netcoreapp1.0\rtmapp.deps.json
            C:\code\hwapp\bin\Debug\netcoreapp1.0\rtmapp.runtimeconfig.json
    Compiling hwapp for .NETCoreApp,Version=v1.0
    Running C:\Program Files\dotnet\dotnet.exe "C:\Program Files\dotnet\sdk\1.0.0-preview2-003121\csc.dll" -noconfig @C:\code\hwapp\obj\Debug\netcoreapp1.0\dotnet-compile-csc.rsp
    Process ID: 12084
    
    Compilation succeeded.
        0 Warning(s)
        0 Error(s)
    
    Time elapsed 00:00:01.6766971
    
    
    Running C:\Program Files\dotnet\dotnet.exe exec --additionalprobingpath C:\Users\Svick\.nuget\packages C:\code\hwapp\bin\Debug\netcoreapp1.0\rtmapp.dll
    Process ID: 9068
    Hello World!
    

    Notice that in both cases, csc, the C# compiler, is used directly (it's the .Net Core version of csc, so it's run using dotnet csc.dll). The main difference between the two is the .rsp file, which contains additional arguments for csc.

    In the net451 version, the interesting part of it looks like this:

    -out:"C:\code\hwapp\bin\Debug\net451\hwapp.exe"
    -r:"C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETFramework\v4.5.1\mscorlib.dll"
    -r:"C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETFramework\v4.5.1\System.dll"
    -r:"C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETFramework\v4.5.1\System.Core.dll"
    -r:"C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETFramework\v4.5.1\Microsoft.CSharp.dll"
    

    This is what it means to use net451: that reference assemblies for .Net Framework 4.5.1 are used to compile the application.

    In the netcoreapp1.0 version, it looks like this (truncated):

    -out:"C:\code\hwapp\bin\Debug\netcoreapp1.0\hwapp.dll"
    -r:"C:\Users\Svick\.nuget\packages\Microsoft.CSharp\4.0.1\ref\netstandard1.0\Microsoft.CSharp.dll"
    -r:"C:\Users\Svick\.nuget\packages\Microsoft.VisualBasic\10.0.1\ref\netstandard1.1\Microsoft.VisualBasic.dll"
    -r:"C:\Users\Svick\.nuget\packages\Microsoft.Win32.Primitives\4.0.1\ref\netstandard1.3\Microsoft.Win32.Primitives.dll"
    -r:"C:\Users\Svick\.nuget\packages\System.AppContext\4.1.0\ref\netstandard1.6\System.AppContext.dll"
    -r:"C:\Users\Svick\.nuget\packages\System.Buffers\4.0.0\lib\netstandard1.1\System.Buffers.dll"
    -r:"C:\Users\Svick\.nuget\packages\System.Collections\4.0.11\ref\netstandard1.3\System.Collections.dll"
    -r:"C:\Users\Svick\.nuget\packages\System.Collections.Concurrent\4.0.12\ref\netstandard1.3\System.Collections.Concurrent.dll"
    

    Notice that .Net Standard Library reference assemblies are used instead.

    In either case, msbuild is not used at all.

    Can the running app be still considered as .NET Core App?

    I don't think so. I'd say it's a .Net Framework app, created using the .Net Core CLI/SDK. Yes, it's confusing.