分类

  • 软件天地

  • C#进行点对点通讯和文件传输(通讯基类部分)‖
      using System;                                                    

      using System.Net.Sockets;                            

      using System.Net ;                                          

      using System.IO ;                                            

      using System.Windows.Forms;                        

      using System.Text;                                          

      namespace BaseClass                                        

      {                                                                            

         /// <summary>


         /// 传送信息的
    的长度信息+可变长度的信
    格式为 给定长度的命令部分+给
    息部分
    定长度的命令注释部分+可变长度


         /// </summary>


         public class CommunClass                        

         {                                                                      

           public CommunClass()                            

           {                                                                  

             //                                                            

             // TODO: 在此处添加构造函数逻辑                        

             //                                                            

           }                                                                  

           /// <summary>


           /// 命令部分的长度                                              

           /// </summary>


           private st
    atic readonly int CMDLEN = 5
    0 ;

           /// <summary>


           /// 命令注释部分的长度                                          

           /// </summary>


          rivate st
    atic readonly int DESCLEN =
    100 ;

           /// <summary>


           /// 可变长度的长度信息部分所占的字节数                          

           /// </summary>


           private static readonl
    y int DYNAMICLENGTHLEN = 10 ;

           /// <summary>


           /// 每次处理可变信息部分的长度                                  

           /// </summary>


           private static readonl
    y int DEALLEN = 1024 ;      

           /// <summary>


           /// /应答的最大长度                                            

           /// </summary>


           private st
    atic readonly int RESPONLEN
    = 20 ;

           /// <summary>


           /// 用于填充命令或注筒蛔愠ざ炔糠值淖址?nbsp;                       

           /// </summary>  


           private static readonl
    y char FILLCHAR = '^' ;

           /// <summary>


           /// 成功发
    说还不是)
    送一部分数据后的回调方法(也

    可以认为是触发的事件,但严格来


           /// </summary>


           public del
    egate void OnSend(int iTotal
    ,int iSending) ;

           /// <summary>


           /// 根据给定的服务器和端口号建立连接                            

           /// </summary>


           /// <param name="strHost">服务器名</param>


           /// <param name="iPort">端口号</param>


           /// <returns></returns>


           public stat
    ic Socket ConnectToServer(st
    ring strHost,int iPort)

           {                                                           

             try                                                         

             {                                                              

                IPAddress ipA
    ddress = Dns.Resolve(strHost).AddressList[0];

                IPEndPoint ip
    Point = new IPEndPoint(ipAddress,iPort) ;

                S
    ork,SocketType.Stream,Pr
    ocket s = new Socket(Address
    otocolType.Tcp) ;
    Family.InterNetw


                s.Connect(ipPoint) ;                  

                return s ;                                      

             }                                                             

             catch (Exception e)                         

             {                                                              

                t
    e.Message)) ;
    hrow (new Exception("建立到

    服务器的连接出错" +


             }                                                              

           }                                                                  

           /// <summary>


           /// 将文本写到Socket中                                    

           /// </summary>


           /// <param name="s">要发送信息的Socket</param>


           /// <param name="strInfo">要发送的信息</param>


           /// <returns>是否成功</returns>


           public static bool Writ
    eTextToSocket(Socket s,string strInfo)

           {                                                                  

             byte [
    ] buf = Encoding.UTF8.GetByt
    es(strInfo) ;

             try                                                          

             {                                                              

                s
    .Send(buf,0,buf.Length,Socke
    tFlags.None) ;

                return true ;                                

             }                                                              

             catch(Exception err)                        

             {                                                              

                MessageBox.Sh
    ow("发送文本失败!"+err.Message) ;

                return false ;                              

             }                                                              

           }                                                                  

           /// <summary>


           /// 将命令文本写到Socket中                                

           /// </summary>


           /// <param name="s">要发送命令文本的Socket</param>


           /// <param name="strInfo">要发送的命令文本</param>


           /// <returns>是否成功</returns>


           public stat
    ic bool WriteCommandToSocket
    (Socket s,string strCmd)

           {                                                                  

             if (strCmd == "")                              

                strCmd = "NOP" ;                          

             strCmd = strCmd.Pa
    dRight(CMDLEN,FILLCHAR) ;

             return
    WriteTextToSocket(s,strCmd)
    ;     

           }                                                                  

           /// <summary>


           /// 将命令注释写到Socket中                                

           /// </summary>


           /// <param name="s">要发送命令注释的Socket</param>


           /// <param name="strInfo">要发送的命令注释</param>


           /// <returns>是否成功</returns>


           public stat
    ic bool WriteCommandDescToSo
    cket(Socket s,string strDesc)

           {                                                                  

             if (strDesc == "")                            

                strDesc = "0" ;                            

             strDesc = strDesc.
    PadRight(DESCLEN,FILLCHAR) ;

             return
    WriteTextToSocket(s,strDesc
    ) ;       

           }                                                                  

           /// <summary>


           /// 发送可变信息的字节数                                        

           /// </summary>


           /// <param name="s">要发送字节数的Socket</param>


           /// <param name="iLen">字节数</param>


           /// <returns>是否成功</returns>


           public static bool Writ
    eDynamicLenToSocket(Socket s,int iLen)

           {                                                           

             string strLen = iL
    YNAMICLENGTHLEN,FILLCHAR) ;
    en.ToString().PadRight(D


             return
    WriteTextToSocket(s,strLen)
    ;     

           }                                                                  

           /// <summary>


           /// 将缓存的指定部分发送到Socket                          

           /// </summary>


           /// <param name="s">要发送缓存的Socket</param>


           /// <param name="buf">要发送的缓存</param>


           /// <param name="iStart">要发送缓存的起始位置</param>


           /// <param name="iCount">要发送缓存的字节数</param>


           /// <param name="iBlock">每次发送的字节说</param>


           /// <param name="SendSuccess">每次发送成功后的回调函数</param>


           /// <returns>是否发送成功</returns>


           public stat
    iStart,int iCount,int iB
    ic bool WriteBufToSocket(Soc
    lock,OnSend SendSuccess)
    ket s,byte [] buf,int


           {                                                                

             int iSended = 0 ;                              

             int iSending = 0 ;                            

             while(iSended<iCount)                

             {                                                              

                if (iSended +
    iBlock <= iCount)

                  iSending = iBlock ;                

                else                                                  

                  iSending
    = iCount - iSended ;

                s
             
    .Send(buf,iStart+iSended,iSe

    nding,SocketFlags.None) ;  


                iSended += iSending ;                

                i
    f (ReadResponsionFromSocket(
    s)=="OK")

                  if (SendSuccess != null)      

                
      SendSuccess(iCount,iSend
    ed) ;

                else                                                  

                  return false;                            

             }                                                              

             return true ;                          

           }                                                                  

           /// <summary>


           /// 将长度不固定文本发送到socket                          

           /// </summary>


           /// <param name="s">要发送文本的Socket</param>


           /// <param name="strText">要发送的文本</param>


           /// <param name="OnSendText">成功发送一部分文本后的回调函数</param>


           /// <param name="settextlen">得到文本长度的回调函数</param>


           /// <returns></returns>


           public stat
    ic bool WriteDynamicTextToSo
    cket(Socket s,string strText,

             OnSend OnSendText)                            

           {                                                                  

             byte [
    ] buf = Encoding.UTF8.GetByt
    es(strText) ;

                                                                             

             int iLen = buf.Length ;                  

             try                                                          

             {                                                              

                WriteDynamicL
    enToSocket(s,iLen) ;

                r
    eturn WriteBufToSocket(s,buf
    ,0,iLen,DEALLEN,OnSendText) ;

             }                                                              

             catch(Exception err)                        

             {                                                              

                M
    essageBox.Show("发送文本失败
    !"+err.Message) ;

                return false ;                              

             }                                                              

           }                                                                  

           /// <summary>


           /// 将文件写到Socket                                      

           /// </summary>


           /// <param name="s">要发送文件的Socket</param>


           /// <param name="strFile">要发送的文件</param>


           /// <returns>是否成功</returns>


           public static bool Writ
    eFileToSocket(Socket s,string strFile,

             OnSend OnSendFile)                            

           {                                                                  

             FileSt
    en,FileAccess.Read,FileS
    ream fs = new FileStream(str
    hare.Read) ;
    File,FileMode.Op


             int iLen = (int)fs.Length ;          

             WriteDynamicLenToS
    ocket(s,iLen) ;

             byte [] buf = new byte[iLen] ;    

             try                                                          

             {                                                              

                fs.Read(buf,0,iLen) ;                

                r
    eturn WriteBufToSocket(s,buf
    ,0,iLen,DEALLEN,OnSendFile) ;

             }                                                              

             catch(Exception err)                        

             {                                                              

                M
    essageBox.Show("发送文件失败
    !"+err.Message) ;

                return false ;                              

             }                                                              

             finally                                                  

             {                                                              

                fs.Close() ;                                  

             }                                                       

           }                                                                  

           /// <summary>


           /// 对方对自己消息的简单回应                                    

           /// </summary>


           /// <param name="s"></param>


           /// <returns></returns>


           public static string Re
    adResponsionFromSocket( Socket s)

           {                                                                  

             byte [
    ] bufCmd = new byte[RESPONLE
    N] ;

             int iCount = s.Receive(bufCmd) ;

             string strRespon =
    Encoding.UTF8.GetString(bufCmd,0,iCount) ;

             return strRespon ;                            

           }                                                                  

           /// <summary>


           /// 从Socket读取命令                                      

           /// </summary>


           /// <param name="s">要读取命令的Socket</param>


           /// <returns>读取的命令</returns>


           public static string Re
    adCommandFromSocket( Socket s)

           {                                                         

             byte [
    ] bufCmd = new byte[CMDLEN]
    ;

             int iCount = s.Rec
    eive(bufCmd,0,CMDLEN,SocketFlags.Partial) ;

             string strCommand
    = Encoding.UTF8.GetString(bufCmd,0,CMDLEN) ;

             return strCommand
    = strCommand.TrimEnd(FILLCHAR) ;

           }                                                                  

           /// <summary>


           /// 读取命令注释                                                

           /// </summary>


           /// <param name="s">要读取命令注释的Socket</param>


           /// <returns>读取的命令注释</returns>


           public static string Re
    adCommandDescFromSocket( Socket s)

           {                                                         

             byte [] bufCmd = n
    ew byte[DESCLEN] ;

             int iC
    ount = s.Receive(bufCmd,0,DE
    SCLEN,SocketFlags.Partial) ;

             string
    strCommand = Encoding.UTF8.
    GetString(bufCmd,0,DESCLEN) ;

             return strCommand
    = strCommand.TrimEnd(FILLCHAR) ;

           }                                                                  

           /// <summary>


           /// 读取可变部分的长度                                          

           /// </summary>


           /// <param name="s">要读取可变部分长度的Socket</param>


           /// <returns>读取的可变部分的长度</returns>


           public static int ReadD
    ynamicLenFromSocket( Socket s)

           {                                                         

             byte [] bufCmd = n
    ew byte[DYNAMICLENGTHLEN] ;

             int iCount = s.Rec
    GTHLEN,SocketFlags.Partial) ;
    eive(bufCmd,0,DYNAMICLEN


             string
    ,0,DYNAMICLENGTHLEN) ;
    strCommand = Encoding.UTF8.

    GetString(bufCmd


             return int.Parse(s
    trCommand.TrimEnd(FILLCHAR)) ;

           }                                                                  

           /// <summary>


           /// 读取文本形式的可变信息                                      

           /// </summary>


           /// <param name="s">要读取可变信息的Socket</param>


           /// <returns>读取的可变信息</returns>


           public static string Re
    adDynamicTextFromSocket( Socket s)

           {                                                           

             int iL
    en = ReadDynamicLenFromSock
    et(s) ;

                                                                                   

             byte [] buf = new byte[iLen] ;    

             string strInfo = "" ;                      

             int iReceiveded = 0 ;                      

             int iReceiveing = 0 ;                      

             while(iReceiveded<iLen)            

             {                                                              

                if (iReceived
    ed + DEALLEN <= iLen)

                  iReceiveing = DEALLEN ;        

                else                                                  

                
      iReceiveing = iLen - iRe
    ceiveded ;          

                s.Receive(buf
     
    ,iReceiveded,iReceiveing,SocketFlags.None) ; 


                CommunClass.W
    riteTextToSocket(s,"OK") ;

                iReceiveded+= iReceiveing ;    

             }                                                              

             strInf
    o = Encoding.UTF8.GetString(
    buf,0,iLen) ;

             return strInfo ;                                

           }                                                                  

           /// <summary>


           /// 读取文件形式的可变信息                                      

           /// </summary>


           /// <param name="s">要读取可变信息的Socket</param>


           /// <param name="strFile">读出后的文件保存位置</param>


           /// <returns>是否读取成功</returns>


           public static bool Read
    )
    DynamicFileFromSocket( Socket s,string strFile


           {                                                           

             int iLen = ReadDy
    namicLenFromSocket(s) ;

             byte [] buf = new byte[iLen] ;    

             FileSt
    eate,FileAccess.Write) ;
    ream fs = new FileStream(str

    File,FileMode.Cr


             try                                                          

             {                                                              

                int iReceiveded = 0 ;                

                int iReceiveing = 0 ;                

                while(iReceiveded<iLen)      

                {                                                        

                  if (iRece
    iveded + DEALLEN <= iLen)

                    iReceiveing = DEALLEN ;    

                  else                                              

                
      
        iReceiveing = iLen -

    iReceiveded ;        


                  s.Receiv
    veing,SocketFlags.None) ;  
    e(buf,iReceiveded,iRecei


                  CommunCl
    ass.WriteTextToSocket(s,"OK") ;

                  iReceiveded+= iReceiveing ;

                }                                                        

                fs.Write(buf,0,iLen) ;              

                return true ;                                

             }                                                              

             catch(Exception err)                        

             {                                                              

                M
    essageBox.Show("接收文件失败
    "+err.Message) ;

                return false ;                              

             }                                                              

             finally                                                  

             {                                                              

                fs.Close() ;                                  

             }                                                       

           }                                                                  

         }//end class                                                

      }//end namespace                                              




    上一页 下一页




    map