2009-03-09 2 views
0

표준 0x0 대신 0x4로 응답을 종료하는 서버에 tcp를 통해 연결해야합니다. 일을 단순하게 유지하고 소켓 클래스에서 동기식 보내기/받기를 사용하고 싶습니다. 서버가 0x0으로 메시지를 종료하지 않기 때문에 보내기가 작동하지만 수신은 무기한 차단됩니다. 내가 더 많은 메시지를 보내려면 연결을 열어 두어야하기 때문에 동기식으로 첫 번째 0x4로 읽을 수 없으며 닫을 수 없습니다. BeginReceive를 사용하여 별도의 스레드에서 데이터를 읽을 수는 있지만 여전히 0x0 터미네이터가 필요한 것처럼 보이는 것은 좋을 것입니다. BeginRecieve에 크기 1의 버퍼를 전달하려고 시도했지만 각 char 읽기에 대해 내 대리자를 호출하기를 바라고 있지만 그렇게 작동하지는 않습니다. 첫 번째 문자를 읽고 중지합니다.소켓을 특수 메시지 터미네이터와 비동기 적으로 읽음

어떤 아이디어?

여기를 0x04과 함께 종료가 모호한 것 같다 응용 프로그램

using System; 
using System.Collections.Generic; 
using System.ComponentModel; 
using System.Data; 
using System.Drawing; 
using System.Linq; 
using System.Text; 
using System.Windows.Forms; 
using System.Net; 
using System.Net.Sockets; 


namespace SocketTest 
{ 
    public partial class SocketTestForm : Form 
    { 
     Socket socket; 
     byte[] oneChar = new byte[1]; 

     public SocketTestForm() 
     { 
      InitializeComponent(); 
     } 

     private void GetButton_Click(object sender, EventArgs e) 
     { 
      //connect to google 
      IPHostEntry host = Dns.GetHostEntry("google.com"); 
      IPEndPoint ipe = new IPEndPoint(host.AddressList[0], 80); 
      socket = new Socket(ipe.AddressFamily, SocketType.Stream, ProtocolType.Tcp); 
      socket.Connect(ipe); 
      if(socket.Connected) 
       Console.WriteLine("Connected"); 

      //write an http get header 

      String request = "GET/HTTP/1.1\r\nHost: google.com\r\nConnection: Close\r\n\r\n"; 

      socket.Send(Encoding.ASCII.GetBytes(request)); 

      //read the response syncronously, the easy way... 
      //but this does not work if the server does not return the 0 byte... 

      //byte[] response = new byte[5000]; 
      //socket.Receive(response, response.Length, SocketFlags.None); 
      //string res = Encoding.ASCII.GetString(response); 
      //Console.WriteLine(res); 

      //read the response async 
      AsyncCallback onreceive = ByteReceived; 
      socket.BeginReceive(oneChar, 0, 1, SocketFlags.None, onreceive, null); 
     } 

     public void ByteReceived(IAsyncResult ar) 
     { 
      string res = Encoding.ASCII.GetString(oneChar); 
      if (res[0] == 0x4) ; //fire some event 
     } 
    } 
} 

답변

2

하지만 코드가 한 바이트 후 중지 된 이유는, 당신은 단지 한 바이트를 요구한다는 것입니다. 두 번째 바이트가 필요하면 다시 질문해야합니다.

변경하기 ByteReceived 당신이를 0x04 명중 할 때까지 당신에게 모든 바이트를 받아야 다음과 같이 HTTP 응답은 당신이 헤더의 종결을 명중 할 때까지 바이트를 읽을 수 읽기

public void ByteReceived(IAsyncResult ar) 
{ 
    string res = Encoding.ASCII.GetString(oneChar); 
    if (res[0] == 0x4) 
    { 
     //fire some event 
    } 
    else 
    { 
     AsyncCallback onreceive = ByteReceived; 
     socket.BeginReceive(oneChar, 0, 1, SocketFlags.None, onreceive, null); 
    } 
} 

일반적인 방법을, http 헤더의 content length 필드를 사용하여 읽은 바이트 수를 파악하십시오.

다시 0x04 종료가 의심 스럽습니다.