c#程序打包、機器代碼生成(Ngen.exe)

深刻本機影像生成器(Ngen.exe)工具使用方法詳解

先介紹一點背景知識;.Net程序在運行時會實時(JIT)編譯,將.Net程序文件編譯成cpu認識的彙編機器碼。實時編譯須要消耗額外的cpu和內存資源,這對於服務器端程序是可有可無的,由於實時編譯只在程序第一次運行時編譯,以後就不須要再作了;若是你在作的是一個較大的winform程序或者silverlight等客戶端程序時就須要考慮提早編譯了。
.Net framework安裝目錄下(相似C:\Windows\Microsoft.NET\Framework\v4.0.30319)有一個ngen.exe工具,就是作這件事兒的。這個程序是一個控制檯程序,最經常使用的使用方法以下:
生成文件filepath的native code使用下面命令:

  複製代碼 代碼以下:php

  ngen install filepath 服務器


卸載文件filepath的native code使用下面命令

  複製代碼 代碼以下:app

  Ngen uninstall filepath ide


本文主要就用這兩種用法,有關這個工具更多的參數和介紹,請參考 msdn
客戶端程序咱們必然要製做安裝包,個人思路是在安裝程序時就作本機映象的生成操做;咱們能夠在安裝程序中添加一步自定義操做來作這件事情。
若是你對本文的話題感興趣,不妨按照下面步驟試一下。
1. 新建解決方案,名字隨意
2. 在新解決方案中添加一個winform項目,假定咱們要對這個winform項目生成的可執行文件作本機映象生成操做;這只是一個演示,因此這個項目什麼都不作
3. 在這個解決方案中添加一個名字爲NgenInstaller的類庫項目,並新建一個Installer Class;

  

在新建的NgenInstaller類中添加在安裝時使用ngen安裝程序的功能代碼。
4. 代碼實現很簡單就是使用Process執行ngen程序來完成安裝。須要注意的時,具體讓ngen安裝那些文件時經過Context.Parameters[「ngen1|2|3」]傳進來的,這個參數須要在製做安裝包的自定義步驟中設置。
實現代碼:

  複製代碼 代碼以下:工具

  using System; 
using System.Collections; 
using System.Collections.Generic; 
using System.ComponentModel; 
using System.Configuration.Install; 
using System.Linq; 
using System.Runtime.InteropServices; 
using System.IO; 
using System.Diagnostics; 

  
namespace NgenInstaller 

    [RunInstaller(true)] 
    public partial class NgenInstaller : System.Configuration.Install.Installer 
    { 
        public NgenInstaller() 
        { 
            InitializeComponent(); 
        } 

        public override void Install(IDictionary stateSaver) 
        { 
            NgenFile(InstallTypes.Install); 
        } 

  
        public override void Uninstall(IDictionary savedState) 
        { 
            NgenFile(InstallTypes.Uninstall); 
        } 

        private enum InstallTypes 
        { 
            Install, 
            Uninstall 
        } 

        private void NgenFile(InstallTypes options) 
        { 
            string envDir = RuntimeEnvironment.GetRuntimeDirectory(); 
            string ngenPath = Path.Combine(envDir, "ngen.exe"); 
            string exePath = Context.Parameters["assemblypath"];             
            string appDir = Path.GetDirectoryName(exePath); 

            int i = 1; 

            do { 
                string fileKey = "ngen" + i; 
                //須要生成本機映象的程序集名字,配置在ngen1...5,6的配置中 
                if (Context.Parameters.ContainsKey(fileKey)) 
                { 
                    string ngenFileName = Context.Parameters["ngen" + i]; 
                    string fileFullName = Path.Combine(appDir, ngenFileName); 
                    string argument = (options == InstallTypes.Install ? "install" : "uninstall") + " \"" + fileFullName + "\""; 

                    Process ngenProcess = new Process(); 
                    ngenProcess.StartInfo.FileName = ngenPath; 
                    ngenProcess.StartInfo.Arguments = argument; 
                    ngenProcess.StartInfo.CreateNoWindow = true; 
                    ngenProcess.StartInfo.WindowStyle = ProcessWindowStyle.Hidden; 
                    ngenProcess.Start(); 

                    ngenProcess.WaitForExit(); 
                    i++; 
                } 
                else { 
                    break; 
                } 
            } 
            while (true); 
        } 
    } 
}測試


這個類庫中只有這一個類,完成咱們要的操做
5. 最後一步是製做安裝程序,在解決方案中添加安裝項目

  

  添加安裝程序以後右擊安裝項目添加項目輸出,以下圖所示spa

  

  在添加項目輸出的對話框中選擇Winforms項目和剛建的類庫。
而後右擊安裝項目選擇視圖---自定操做打開自定義操做窗口,添加一個名字爲「Ngen生成本機映象」的自定義操做,在添加操做時要選擇NgenInstaller項目輸出 以下圖:命令行

  

  而後將自定義操做的名字修改成「Ngen生成本機代碼」,以下圖所示code

  

  而後右擊新建的自定義操做,選擇屬性窗口,在屬性窗口的CustomActionData屬性中添加須要操做的程序集,注意CustomActionData是一個鍵值對,每一個鍵值對以/開始orm

  

  完成這一步就差很少了,你能夠編譯一下整個解決方案。運行安裝項目生成的安裝包。
6. 運行安裝包,若是一切正常的話就作了本機映象生成了,能夠經過ngen display filePath命令來驗證native本機影響是否安裝正常,以下命令行輸出

  

附件中是測試項目源碼。但願這篇文章有用。
標籤:  工具  Ngen.exe
相關文章
相關標籤/搜索