使用C#製做進程監視器

來源:互聯網
上載者:User

1)可以查看進程的各項基本資料,如cpu,記憶體,父進程,執行路徑,建立者等

2)可以中止進程,建立新進程

3)可以配置目標進程,配置重新整理速度

最終:

(以下給出部分代碼,其餘像進程的建立、中止等,使用process類將很容易實現)

1)使用wmi擷取父進程id,進程建立者

(注意,使用wmi獲得的內容,不宜迴圈重新整理,這樣代價比較大)

添加命名空間:

using System.Management;

        /**//// <summary>
        /// 使用Wmi擷取指定進程的建立者等資訊
        /// </summary>
        /// <param name="pID">進程ID</param>
        private void FillDetailUseWmi(int pID)
        {
            ManagementObjectSearcher searcher = new ManagementObjectSearcher("Select * From Win32_Process Where ProcessID=" + pID);
            ManagementObjectCollection moc = searcher.Get();

            ManagementOperationObserver observer = new ManagementOperationObserver();
            HandleObjectReady hor = new HandleObjectReady();
            //監測非同步方法呼叫是否已成功返回
            observer.ObjectReady += new ObjectReadyEventHandler(hor.Done);

            foreach (ManagementObject mo in moc)
            {
                //非同步呼叫該對象的GetOwner方法,擷取進程建立者
                mo.InvokeMethod(observer, "GetOwner", null);
                //等待非同步呼叫返回
                while (!hor.Complete)
                {
                    System.Threading.Thread.Sleep(500);
                }

                string user = "";
                //判斷擷取使用者名稱的操作是否成功
                if (hor.Obj["returnValue"].ToString() == "0")
                {
                    user = hor.Obj.Properties["User"].Value.ToString();
                }
                //判斷字典中是否已移除該項
                if (!this.mDict.ContainsKey(pID))
                {
                    return;
                }
                if (mo["ParentProcessID"] != null && this.mDict.ContainsKey(Convert.ToInt32(mo["ParentProcessID"])))
                {
                    //根據父進程ID擷取父進程名稱
                    this.mDict[pID].ParentProce = this.mDict[Convert.ToInt32(mo["ParentProcessID"])].ProceName;
                }
                this.mDict[pID].Creator = user;

                //觸發重新整理進程詳細資料事件
                if (this.HandleDetailList != null)
                {
                    this.HandleDetailList(this.mDict[pID]);
                }
            }

            //釋放資源
            searcher.Dispose();
            searcher = null;
            moc.Dispose();
            moc = null;
            observer = null;
            hor = null;
        }

    /**//// <summary>
    /// 該類用於監測Wmi非同步呼叫方法是否已經返回
    /// </summary>
    public class HandleObjectReady
    {
        private bool complete = false;
        private ManagementBaseObject obj;

        public void Done(object sender, ObjectReadyEventArgs e)
        {
            complete = true;
            obj = e.NewObject;
        }

        public bool Complete
        {
            get
            {
                return complete;
            }
        }

        public ManagementBaseObject Obj
        {
            get
            {
                return obj;
            }
        }
    }

2)使用效能計數器計算cpu利用率

2.1)計算過程

//通過計數器擷取idle空閑進程cpu佔用率r1;

//通過process類的TotalProcessorTime屬性擷取各進程的cpu時間,求和,得各進程(除空閑進程idle,該進程無法通過process類獲得cpu時間)cpu時間和t1;

//通過t1/(100-r1)得到總cpu時間t;

//對各進程,通過TotalProcessorTime獲得進程cpu時間tnew,計算:

(Tnew-told)/t,即得該進程的cpu佔用率,其中told是程式中記錄的該進程上一次的TotalProcessorTime。

2.2)關於效能計數器

系統會為每個進程分配一個計數器,通過

new PerformanceCounter("Process", "% Processor Time", "進程名稱")執行個體化該計數器,使用計數器對象的NextValue方法可以得到進程佔用cpu的百分比(第一次調用NextValue擷取的值都為0,之後就沒問題了,這個要注意)。

2.3)Idle進程的含義

Idle意為懶散的、無所事事。事實上,idle不能算著一個進程,它用於表示cpu空閑資源,它所佔的比率越高,表示你的機器越空閑。

2.4)多核CPU或使用超執行緒技術的CPU

對於多核或使用超執行緒技術的cpu,根據計數器求得的idle進程cpu佔用比率將超過100%,此時應將idle的cpu利用率/總的cpu利用率,所得作為真正的idle的cpu利用率。

添加命名空間:

using System.Diagnostics;

        /**//// <summary>
        /// 效能計數器,用於擷取CPU空閑百分比
        /// </summary>
        private static PerformanceCounter mIdle = new PerformanceCounter("Process", "% Processor Time", "Idle");
        /**//// <summary>
        /// 效能計數器,用於擷取CPU總利用率
        /// </summary>
        private static PerformanceCounter mTotal = new PerformanceCounter("Process", "% Processor Time", "_Total");

        private void FillNeedRefreshInfo(params Process[] pCurrentAll)
        {www.elivn.com
            …………
            //以下計算CPU利用率
            this.mCurrentTotalCpuTime = this.CalCurrentTotalCpuTime();
            for (int i = 0; i < pCurrentAll.Length; i++)
            {
                //空閑進程idle
                if (pCurrentAll[i].Id == 0)
                {
                    this.mDict[pCurrentAll[i].Id].CpuPercent = this.mIdleCpuPercent;
                }
                else
                {
                    try
                    {
                        //無法保證進程不會中途退出,此時無法擷取其Cpu時間
                        long ms = (long)pCurrentAll[i].TotalProcessorTime.TotalMilliseconds;
                        double d = (ms - this.mDict[pCurrentAll[i].Id].OldCpuTime) * 1.0 / this.mCurrentTotalCpuTime;
                        this.mDict[pCurrentAll[i].Id].CpuPercent = d;
                        this.mDict[pCurrentAll[i].Id].OldCpuTime = ms;
                    }
                    catch
                    {
                    }
                }

                //調用重新整理事件
                if (this.HandleProceRefresh != null)
                {
                    this.HandleProceRefresh(this.mDict[pCurrentAll[i].Id], 100 - this.mIdleCpuPercent);
                }
            }
        }

        private double CalCurrentTotalCpuTime()
        {
            double d = 0;
            //擷取效能計數器值
            double idlePercent = mIdle.NextValue();
            double totalPercent = mTotal.NextValue();
            //避免除0異常
            if (totalPercent == 0)
            {
                this.mIdleCpuPercent = 0;
            }
            else
            {
                //可能遇到多核或超執行緒CPU,CPU空閑進程比率不能直接使用計數器的值
                this.mIdleCpuPercent = idlePercent * 100 / totalPercent;
            }

            //以下擷取上一次計算至當前總的非空閑CPU時間
            foreach (Process p in this.mCurrentAll)
            {
                //對空閑進程及中途退出的進程不做處理
                if (p.Id == 0 || p.HasExited)
                {
                    continue;
                }

                if (this.mDict ==null || !this.mDict.ContainsKey(p.Id))
                {
                    d += p.TotalProcessorTime.TotalMilliseconds;
                }
                else
                {
                    d += p.TotalProcessorTime.TotalMilliseconds - this.mDict[p.Id].OldCpuTime;
                }
            }

            //當前非空閑CPU時間/當前非空閑時間所佔比率=當前總CPU時間
            //return d / (totalPercent - idlePercent);
            return d / (100 - mIdleCpuPercent);
        }

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.