コード例 #1
0
ファイル: P2PChatClient_Create.cs プロジェクト: bssthu/CSP2P
 /// <summary>
 /// 接受方:
 /// 收到的1次确认为私聊,记录对方的身份信息
 /// 此时确定owner
 /// 发送2次确认
 /// </summary>
 /// <param name="protocalHandler">接收到的协议的封装</param>
 public void newSocketChatNameReceived(ProtocalHandler protocalHandler)
 {
     try
     {
         // 对方用户名
         string targetNameBase64 =
             protocalHandler.GetElementTextByTag("name");
         string targetName =
             protocalHandler.Base64stringToString(targetNameBase64);
         // 打开私聊窗口
         main.SetChatFormClient(this, targetName);
         // 2次确认,发送you = 对方(发起方)用户名
         string protocalText = protocalHandler.Pack("init_chat_ok");
         protocalText = protocalHandler.Append(
             protocalText, "you", targetNameBase64);
         byte[] sendbuf            = Encoding.ASCII.GetBytes(protocalText);
         SocketAsyncEventArgs saEA = new SocketAsyncEventArgs();
         saEA.Completed +=
             new EventHandler <SocketAsyncEventArgs>(
                 newSocketUsernameSendEventHandler);
         saEA.SetBuffer(sendbuf, 0, sendbuf.Length);
         socket.SendAsync(saEA);
     }
     catch (Exception ex)
     {
         Trace.WriteLine("异常位置:" +
                         "newSocketChatNameReceived");
         Trace.WriteLine(ex.Message);
         CloseSocket();
     }
 }
コード例 #2
0
 /// <summary>
 /// 发起方:
 /// 收到2次确认,核对对方的身份信息
 /// </summary>
 /// <param name="sender"></param>
 /// <param name="ea"></param>
 private void createSocketNameReceivedEventHandler(
     object sender, EventArgs ea)
 {
     try
     {
         SocketAsyncEventArgs socketAsyncEA =
             (SocketAsyncEventArgs)ea;
         // 获取文本
         string rcvString =
             Encoding.ASCII.GetString(socketAsyncEA.Buffer);
         ProtocalHandler protocalHandler =
             new ProtocalHandler(main.MyName);
         // 判断是否是协议
         if (!protocalHandler.SetXmlText(rcvString))
         {
             throw new MyProtocalException(
                       "不是有效的协议文本,找不到CSP2P标签");
         }
         // 数据包类型
         string type = protocalHandler.GetElementTextByTag("type");
         if (type.Equals("closesocket"))     // 对方要求关闭Socket
         {
             closeSocketWithoutSend();
         }
         if (!type.Equals("init_gp_ok"))
         {
             throw new MyProtocalException(
                       "不是有效的2次确认," +
                       "找不到type标签或type不为init_gp_ok");
         }
         // 对方用户名
         string key = protocalHandler.GetElementTextByTag("name");
         key = protocalHandler.Base64stringToString(key);
         if (!key.Equals(targetName))
         {
             throw new MyProtocalException(
                       "不是有效的2次确认," +
                       "找不到name标签或接受方用户名不符");
         }
         // 己方用户名
         string myName = protocalHandler.GetElementTextByTag("you");
         myName = protocalHandler.Base64stringToString(myName);
         if (!myName.Equals(main.MyName))
         {
             throw new MyProtocalException(
                       "2次确认发现错误,找不到you标签" +
                       "或接受方返回的发送方用户名不符");
         }
         // 开始通信
         owner.BeginInvoke(owner.sendRTFDelegate, rtfToSend);
         rtfToSend = null;
         beginReceive();
     }
     catch (Exception ex)
     {
         Trace.WriteLine("异常位置:" +
                         "createSocketNameReceivedEventHandler");
         Trace.WriteLine(ex.Message);
         CloseSocket();
     }
 }
コード例 #3
0
ファイル: P2PGroupClient.cs プロジェクト: bssthu/CSP2P
        /// <summary>
        /// 收到一条数据
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="ea"></param>
        private void receiveOneEventHandler(object sender, EventArgs ea)
        {
            try
            {
                SocketAsyncEventArgs socketAsyncEA =
                    (SocketAsyncEventArgs)ea;
                // 获取文本
                string rcvString =
                    Encoding.ASCII.GetString(socketAsyncEA.Buffer);
                ProtocalHandler protocalHandler = new ProtocalHandler();
                // 判断是否是协议
                protocalHandler.SetXmlText(rcvString);
                // 对方用户名
                string targetNameBase64 =
                    protocalHandler.GetElementTextByTag("name");
                string targetName =
                    protocalHandler.Base64stringToString(targetNameBase64);
                if (targetName == null)
                {
                    throw new MyProtocalException(
                              "不是有效协议," +
                              "找不到name标签或无法解码");
                }
                // 类型
                string type = protocalHandler.GetElementTextByTag("type");
                if (type == null)
                {
                    throw new MyProtocalException(
                              "不是有效的协议文本,找不到type标签");
                }
                else
                {
                    switch (type)
                    {
                    case "ctl_closesocket":         // 对方要求关闭Socket
                        closeSocketWithoutSend();
                        break;

                    case "gp_rtf":         // 收到聊天消息(RTF文本)
                        string rtfText = protocalHandler.GetElementTextByTag("data");
                        if (rtfText == null)
                        {
                            throw new MyProtocalException(
                                      "不是有效的协议文本,type为gp_rtf但找不到data标签");
                        }
                        rtfText = protocalHandler.Base64stringToString(rtfText);
                        if (rtfText == null)
                        {
                            throw new MyProtocalException(
                                      "不是有效的协议文本,rtf文本解码错误");
                        }
                        // 显示收到的消息
                        owner.BeginInvoke(owner.receiveRTFDelegate,
                                          new object[] { rtfText });
                        break;

                    default:
                        throw new MyProtocalException("type类型未知: " + type);
                    }   // End Switch
                }
            }
            catch (Exception ex)
            {
                Trace.WriteLine("异常位置:P2PGroupClient.receiveOneEventHandler");
                Trace.WriteLine(ex.Message);
            }
            finally
            {
                // 继续接收数据
                if (socket != null)
                {
                    beginReceive();
                }
            }
        }
コード例 #4
0
ファイル: P2PChatClient_File.cs プロジェクト: bssthu/CSP2P
        /// <summary>
        /// 收到的协议是file类型时的判断
        /// </summary>
        /// <param name="type">类型</param>
        /// <param name="protocalHandler">协议处理类</param>
        protected void ReceivedTypeFile(string type, ProtocalHandler protocalHandler)
        {
            // 文件收发时接收到的文件名
            string receivedSafeFileNameBase64 =
                protocalHandler.GetElementTextByTag("file");

            try
            {
                switch (type)
                {
                case "file_requesttosend":         // 收到接收文件的请求
                    if (owner.showPanelFile)
                    {
                        // 直接拒收
                        DeniedToFile();
                        break;
                    }
                    if (receivedSafeFileNameBase64 == null)
                    {
                        throw new MyProtocalException(
                                  "不是有效的协议文本,type为file但找不到file标签");
                    }
                    string receivedSafeFileName =
                        protocalHandler.Base64stringToString(receivedSafeFileNameBase64);
                    if (receivedSafeFileName == null)
                    {
                        throw new MyProtocalException(
                                  "不是有效的协议文本,文件名解码错误");
                    }
                    safeFileNameBase64 = receivedSafeFileNameBase64;
                    maxSeq             = Convert.ToUInt32(
                        protocalHandler.GetElementTextByTag("maxseq"));
                    owner.BeginInvoke(owner.setProgressDelegate, (int)maxSeq);
                    currentSeq = 0;
                    // 让用户选择是否接收文件
                    owner.BeginInvoke(owner.askedForReceivingFileDelegate,
                                      receivedSafeFileName);
                    break;

                case "file_cleartosend":
                    if (!owner.showPanelFile)
                    {
                        // 拒收
                        StopToSendFile();
                        break;
                    }
                    // 检查文件名匹配情况
                    CheckFileName(receivedSafeFileNameBase64);
                    // 开始发送
                    try
                    {
                        owner.sendingOrReceivingFile = true;
                        owner.BeginInvoke(owner.startTimingDelegate);
                        sendingFilePack(0);
                    }
                    catch (Exception ex)
                    {
                        Trace.WriteLine("无法开始发送文件。");
                        throw ex;
                    }
                    break;

                case "file_denied":          // 发文件的请求被拒绝
                    if (!owner.showPanelFile)
                    {
                        // 没有在准备收发文件的状态
                        break;
                    }
                    if (owner.sendingOrReceivingFile)
                    {
                        // 已经在收发文件,取消的type应该为file_abort
                        StopToSendFile();
                        break;
                    }
                    // 检查文件名匹配情况
                    CheckFileName(receivedSafeFileNameBase64);
                    // 取消文件发送
                    fileDenied();
                    break;

                case "file_data":
                    // 检查是否正在收发文件
                    CheckWhileSendingOrReceiving();
                    // 超时定时器重置
                    sendTimeOutTimer.Start();
                    // 检查文件名匹配情况
                    CheckFileName(receivedSafeFileNameBase64);
                    string seqString   = protocalHandler.GetElementTextByTag("seq");
                    uint   receivedSeq = Convert.ToUInt32(seqString);
                    string data        = protocalHandler.GetElementTextByTag("data");
                    byte[] buf         = Convert.FromBase64String(data);
                    // 检查checksum
                    uint len = Convert.ToUInt32(
                        protocalHandler.GetElementTextByTag("len"));
                    int checksum = Convert.ToInt32(
                        protocalHandler.GetElementTextByTag("checksum"));
                    for (uint i = 0; i < len; i++)
                    {
                        checksum += buf[i];
                    }
                    // 顺序正确 && 校验正确
                    if (receivedSeq == currentSeq && checksum == 0)
                    {
                        owner.BeginInvoke(owner.showProgressDelegate, (int)currentSeq);
                        fileWriter.WriteBytes(currentSeq, buf, len);
                        sendAck(++currentSeq);
                        if (currentSeq >= maxSeq)
                        {
                            finishSendingOrReceivingFile();
                        }
                    }
                    else
                    {
                        sendAck(currentSeq);
                    }
                    break;

                case "file_ack":
                    // 检查是否正在收发文件
                    CheckWhileSendingOrReceiving();
                    // 检查文件名匹配情况
                    CheckFileName(receivedSafeFileNameBase64);
                    string ackString = protocalHandler.GetElementTextByTag("ack");
                    receivedAck(Convert.ToUInt32(ackString));
                    break;

                case "file_abort":
                    if (!owner.showPanelFile)
                    {
                        // 没有在准备收发文件的状态
                        break;
                    }
                    if (!owner.sendingOrReceivingFile)
                    {
                        // 没有正在收发文件
                        break;
                    }
                    // 取消文件发送
                    owner.BeginInvoke(owner.stopSendingOrReceivingFileDelegate,
                                      String.Format("文件{0}的收发已被取消。",
                                                    protocalHandler.Base64stringToString(safeFileNameBase64)));
                    fileAborted();
                    break;

                default:
                    throw new MyProtocalException("协议类型未知");
                    //break;
                }
            }
            catch (Exception ex)
            {
                Trace.WriteLine("异常位置:ReceivedTypeFile");
                Trace.WriteLine(ex.Message);
                sendErrCount++;
                if (owner.sendingOrReceivingFile)
                {
                    sendAck(currentSeq);
                }

                //StopToSendFile();
            }
        }
コード例 #5
0
        /// <summary>
        /// 接受方
        /// 收到1次确认,判断连接的类型
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="ea"></param>
        private void firstAckReceivedEventHandler(
            object sender, EventArgs ea)
        {
            Socket rcvSocket = sender as Socket;

            try
            {
                // 接收到的异步Socket事件参数
                SocketAsyncEventArgs socketAsyncEA = (SocketAsyncEventArgs)ea;
                // 提取接收到的文本
                string rcvString =
                    Encoding.ASCII.GetString(socketAsyncEA.Buffer);
                ProtocalHandler protocalHandler =
                    new ProtocalHandler(MyName);
                // 是否是协议
                if (!protocalHandler.SetXmlText(rcvString))
                {
                    throw new MyProtocalException(
                              "不是有效的协议文本,找不到CSP2P标签");
                }
                // 数据包类型
                string type = protocalHandler.GetElementTextByTag("type");
                if (type == null)
                {
                    throw new MyProtocalException(
                              "不是有效的1次确认,找不到type标签");
                }
                if (type.Equals("closesocket"))     // 对方要求关闭Socket
                {
                    rcvSocket.Close();
                }
                // 对方用户名
                string targetNameBase64 =
                    protocalHandler.GetElementTextByTag("name");
                string targetName =
                    protocalHandler.Base64stringToString(targetNameBase64);
                if (targetName == null)
                {
                    throw new MyProtocalException(
                              "不是有效的1次确认," +
                              "找不到name标签");
                }
                if (type.Equals("init_chat_request"))   // 私聊
                {
                    P2PChatClient socketHandler =
                        new P2PChatClient(this, rcvSocket);
                    socketHandler.newSocketChatNameReceived(protocalHandler);
                }
                else if (type.Equals("init_gp_request"))     // 群聊
                {
                    P2PGroupClient socketHandler =
                        new P2PGroupClient(this, rcvSocket);
                    socketHandler.newSocketGroupNamesReceived(protocalHandler);
                }
                else
                {
                    throw new MyProtocalException(
                              "不是有效的1次确认," +
                              "type不为init_chat_request或init_gp_request");
                }
                // 记录对方地址
                if (remoteIPaddress.ContainsKey(targetName))
                {
                    remoteIPaddress[targetName] =
                        new IPInfo((IPEndPoint)rcvSocket.RemoteEndPoint);
                }
                else
                {
                    remoteIPaddress.Add(targetName,
                                        new IPInfo((IPEndPoint)rcvSocket.RemoteEndPoint));
                }
            }
            catch (Exception ex)
            {
                Trace.WriteLine("异常位置:" +
                                "firstAckReceivedEventHandler");
                Trace.WriteLine(ex.Message);
                // 直接关闭socket
                try
                {
                    rcvSocket.Close();
                }
                catch (Exception ex2)
                {
                    Trace.WriteLine("异常位置:" +
                                    "firstAckReceivedEventHandler出错关闭rcvSocket时");
                    Trace.WriteLine(ex2.Message);
                }
            }
        }