随笔-116  评论-486  文章-1 

在C#中调用API获取网络信息和流量

最近一项目中要求显示网络流量,而且必须使用C#。

事实上,调用 IpHlpApi.dll 的 GetIfTable API 可以轻易获得网络信息和网络流量。只是要在C#中实现还是比较复杂。

先看看怎么定义该 API

[DllImport("IpHlpApi.dll")]
        
extern static public uint GetIfTable(byte[] pIfTable, ref uint pdwSize, bool bOrder);

本来想把 pIfTable 定义为 IntPtr,但是这样的结果是,获取的信息是错误的(直到现在都不知是什么原因)。

但显然定义为 byte[] 是不能直接使用的。幸好在 Google Code Search 找到了三个类:

CustomtMarshaler.cs

MIB_IFROW.cs

MIB_IFTABLE.cs

再定义一个 NetInfo 类,存储网络信息

NetInfo.cs

OK,现在可以获取网络信息了

        /// <summary>
        
/// Get IFTable
        
/// </summary>
        
/// <returns>MIB_IFTABLE Class</returns>

        private static MIB_IFTABLE GetAllIfTable()
        
{
            
//缓冲区大小
            uint dwSize = 0;

            
//获取缓冲区大小
            uint ret = GetIfTable(nullref dwSize, false);
            
if (ret == 50)
            
{
                
//此函数仅支持于 win98/nt 系统
                return null;
            }


            
//定义,获取 MIB_IFTABLE 对象
            MIB_IFTABLE tbl = new MIB_IFTABLE((int)dwSize);
            ret 
= GetIfTable(tbl.ByteArray, ref dwSize, false);

            
//如果不成功
            if (ret != 0)
            
{
                
return null;
            }


            
return tbl;
        }


        
/// <summary>
        
/// Get NetInfo Class
        
/// </summary>
        
/// <param name="row">MIB_IFROW Class</param>
        
/// <returns>NetInfo Class</returns>

        private static NetInfo GetNetInfo(MIB_IFROW row)
        
{
            NetInfo ninfo 
= new NetInfo();
            ninfo.Index 
= row.dwIndex;
            ninfo.Name 
= Encoding.ASCII.GetString(row.bDescr, 0, (int)row.dwDescrLen);
            ninfo.PhysAddr 
= GetPhysAddr(row.bPhysAddr, (int)row.dwPhysAddrLen);
            ninfo.Type 
= (NetType)row.dwType;
            ninfo.Status 
= (NetState)row.dwOperStatus;
            ninfo.Speed 
= row.dwSpeed;
            ninfo.InErrors 
= row.dwInErrors;
            ninfo.InOctets 
= row.dwInOctets;
            ninfo.InUnknownProtos 
= row.dwInUnknownProtos;
            ninfo.OutErrors 
= row.dwOutErrors;
            ninfo.OutOctets 
= row.dwOutOctets;
            
return ninfo;
        }

/// <summary>
        
/// 获取所有的网络信息
        
/// </summary>
        
/// <returns>NetInfo 网络信息范型</returns>

        public static List<NetInfo> GetAllNetInfo()
        
{
            
//定义范型
            List<NetInfo> ninfos = new List<NetInfo>();

            
//定义,获取 MIB_IFTABLE 对象
            MIB_IFTABLE tbl = GetAllIfTable();

            
//如果成功
            if (tbl != null)
            
{
                tbl.Deserialize();
                
for (int i = 0; i < tbl.Table.Length; i++)
                
{
                    ninfos.Add(GetNetInfo(tbl.Table[i]));
                }

            }


            
return ninfos;
        }

PS:事实上,我把获取网络、CPU、内存、磁盘、进程信息等功能封装起来,并做了一个比较完善的 Windows 任务管理器,整理完后发布源码。
 
posted on 2007-03-29 16:43 柠檬隐士 阅读(...) 评论(...) 编辑 收藏