开发者

How to properly NGen .NET application during installation

I'm using Inno Setup to generate setup program for my application, and I would like to write a script to NGen my application during installation. I want the code to be able to NGen files targeting x86, x64, or AnyCPU. I want to be able to NGen on 32bit and 64bit systems. How can I achieve this?

I've found a couple of helpful links:

Getting the .NET Framework directory path

http://nsis.sourceforge.net/Get_directory_of_installed_.NET_runtime

Where I've found it is a quite complex problem - there can be up to 4 different versions of NGen application:

  1. for CLR 2.0 and 32bit systems
  2. for CLR 2.0 and 64bit systems
  3. for CLR 4.0 and 32bit systems
  4. for CLR 4.0 and 64bit systems

And it is even more complicated开发者_JAVA技巧 by the fact the application can target 32bit CPU and run on 64bit system.


So what came to my mind was a function looking like this:

function NGenFile(file: String; targetCPU: TTargetCPU; targetCLR: TTargetCLR): Boolean;

and call it somewhere in [Code] after successful isntallation:

NGenFile(ExpandConstant('{app}\application.exe'), tcpu64, tclr20);
NGenFile(ExpandConstant('{app}\library1.dll'), tcpu64, tclr40);
NGenFile(ExpandConstant('{app}\library2.dll'), tcpu32, tclr20);
NGenFile(ExpandConstant('{app}\library3.dll'), tcpu32, tclr40);
NGenFile(ExpandConstant('{app}\library4.dll'), tcpuAny, tclr20);
NGenFile(ExpandConstant('{app}\library5.dll'), tcpuAny, tclr40);

And it would work like this:

  1. application.exe (tcpu64, tclr20)

    On 64bit system it would generate native image targeting 64bit CPU and CLR 2.0, Result := True

    On 32bit system it wouldn't do anything, Result := False

  2. library1.dll (tcpu64, tclr40)

    On 64bit system it would generate native image targeting 64bit CPU and CLR 4.0, Result := True

    On 32bit system it wouldn't do anything, Result := False

  3. library2.dll (tcpu32, tclr20)

    On 64bit system it would generate native image targeting 32bit CPU and CLR 2.0, Result := True

    On 32bit system it would do the same as on 64bit system

  4. library3.dll (tcpu32, tclr40)

    On 64bit system it would generate native image targeting 32bit CPU and CLR 4.0, Result := True

    On 32bit system it would do the same as on 64bit system

  5. library4.dll (tcpuAny, tclr20)

    On 64bit system it would generate native image targeting 64bit CPU and CLR 2.0, Result := True

    On 32bit system it would generate native image targeting 32bit CPU and CLR 2.0, Result := True

  6. library5.dll (tcpuAny, tclr40)

    On 64bit system it would generate native image targeting 64bit CPU and CLR 4.0, Result := True

    On 32bit system it would generate native image targeting 32bit CPU and CLR 4.0, Result := True


So to make it work, I need to know 4 different paths to .NET runtime directory. This is what I've found:

  1. 32bit system CLR 2.0

    Get value of "InstallRoot" in "HKLM\Software\Microsoft\.NETFramework", save to value1

    Get name of first value in "HKLM\Software\Microsoft\.NETFramework\Policy\v2.0", save to value2

    value1 + "v2.0." + value2 + "\ngen.exe" => win

    Example: "c:\Windows\Microsoft.NET\Framework\v2.0.50727\ngen.exe"

    I assume this will work the same on 32bit and 64bit systems

  2. 32bit system CLR 4.0

    Get value of "InstallRoot" in "HKLM\Software\Microsoft\.NETFramework", save to value1

    Get name of first value in "HKLM\Software\Microsoft\.NETFramework\Policy\v4.0", save to value2

    value1 + "v4.0." + value2 + "\ngen.exe" => win

    Example: "c:\Windows\Microsoft.NET\Framework\v4.0.30319\ngen.exe"

    I assume this will work the same on 32bit and 64bit systems

  3. 64bit system CLR 2.0

    How to get InstallRoot for 64bit .NET Framework?

    Example: "c:\Windows\Microsoft.NET\Framework64\v2.0.50727\ngen.exe"

  4. 64bit system CLR 4.0

    How to get InstallRoot for 64bit .NET Framework?

    Example: "c:\Windows\Microsoft.NET\Framework64\v4.0.30319\ngen.exe"

I'm actually not sure if the "InstallRoot" value on 64bit systems would point to InstallRoot of 32bit .NET, or 64bit .NET, so are the first 2 methods reliable for any system? And how would look like the second 2 methods? Is there any simpler way to achieve all of this?


What version of InnoSetup are you using? In the version I use (5.4.0a), there are already constants for to find the .NET root directory. From the InnoSetup help:

{dotnet20} .NET Framework version 2.0 root directory. {dotnet20} is equivalent to {dotnet2032} unless the install is running in 64-bit mode, in which case it is equivalent to {dotnet2064}.

An exception will be raised if an attempt is made to expand this constant on a system with no .NET Framework version 2.0 present.

{dotnet2032} 32-bit .NET Framework version 2.0 root directory.

An exception will be raised if an attempt is made to expand this constant on a system with no .NET Framework version 2.0 present.

{dotnet2064} 64-bit Windows only: 64-bit .NET Framework version 2.0 root directory.

An exception will be raised if an attempt is made to expand this constant on a system with no .NET Framework version 2.0 present.

{dotnet40} .NET Framework version 4.0 root directory. {dotnet40} is equivalent to {dotnet4032} unless the install is running in 64-bit mode, in which case it is equivalent to {dotnet4064}.

An exception will be raised if an attempt is made to expand this constant on a system with no .NET Framework version 4.0 present.

{dotnet4032} 32-bit .NET Framework version 4.0 root directory.

An exception will be raised if an attempt is made to expand this constant on a system with no .NET Framework version 4.0 present.

{dotnet4064} 64-bit Windows only: 64-bit .NET Framework version 4.0 root directory.

An exception will be raised if an attempt is made to expand this constant on a system with no .NET Framework version 4.0 present.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜