2012-04-24 2 views
1

UDP 소켓을 처리하기위한 기본 클래스에 다음 코드 (아래 제공된 코드)가 있습니다. WinRT (WINRT의 #define에 의해 제어 됨)에 대한 지원을 추가하고 있습니다. 나는 .Net에서 작동하는 모든 것을 가지고 있지만 WinRT 구현에 문제가있다. 데이터를 보내면 서버 측에서 수신되지 않습니다. 어떤 생각이 잘못 되었습니까? 나는 클라이언트 측에서 어떤 에러도 보지 못했고, 서버에는 아무 것도 나타나지 않는다. 비슷한 방식으로 DataWriter를 사용하여 TCP 소켓 클래스를 성공적으로 가져 왔습니다.UDP DatagramSocket의 올바른 사용

 public UdpSocketClient(IPEndPoint remoteEndPoint, int localPort) 
     { 
      this.remoteEndPoint = remoteEndPoint; 
#if WINRT 
      this.socket = new DatagramSocket(); 
      this.socket.MessageReceived += ReceiveCallback; 

      // Bind to any port 
      Logger.Debug("{0}: UdpSocketClient created. Binding to port {1}.", this, (localPort == 0) ? "[any]" : localPort.ToString()); 
      IAsyncAction bindAction = this.socket.BindEndpointAsync(new HostName("localhost"), localPort == 0 ? "0" : localPort.ToString()); 
      bindAction.AsTask().Wait(); 
      Logger.Trace("{0}: Bind Complete to port {1}", this, this.socket.Information.LocalServiceName); 

      // Get IOutputStream 
      Logger.Trace("{0}: Getting output stream to {1}.", this, remoteEndPoint); 
      IAsyncOperation<IOutputStream> asyncOutput = this.socket.GetOutputStreamAsync(remoteEndPoint.address, remoteEndPoint.port.ToString()); 
      asyncOutput.AsTask().Wait(); 
      Logger.Trace("{0}: Got output stream.", this); 

      // Create DataWriter 
      dataWriter = new DataWriter(asyncOutput.GetResults()); 
#else 
      ... 
#endif 
     } 


     public void SendBuffer(ByteBuffer buffer, int wait = 0) 
     { 
#if WINRT 
      Logger.Trace("{0}: Sending buffer. Wait = {1}", this, wait); 
      for (int i = 0; i < buffer.WriteSize(); i++) 
       dataWriter.WriteByte(buffer.Buffer()[i]); 
      DataWriterStoreOperation op = dataWriter.StoreAsync(); 
      if (wait != 0) op.AsTask().Wait(wait); 
      else op.AsTask().Wait(); 
      Logger.Trace("{0}: Sending complete.", this); 
#else 
     ... 
#endif 
     } 

일부 관련 로그 :

04/23 19:08:57.504 DEBUG: Area Sync: UdpSocketClient created. Binding to port [any]. 
04/23 19:08:57.505 TRACE: Area Sync: Bind Complete to port 59518 
04/23 19:08:57.506 TRACE: Area Sync: Getting output stream to 71.227.179.128:1302. 
04/23 19:08:57.507 TRACE: Area Sync: Got output stream. 

04/23 19:08:57.604 TRACE: Area Sync: Sending contact packet. 
04/23 19:08:57.604 TRACE: Area Sync: Sending buffer. Wait = 0 
04/23 19:08:57.605 TRACE: Area Sync: Sending complete. 
+1

클라이언트가 패킷을 실제로 네트워크로 보내는 지 확인하기 위해 패킷 스니퍼를 사용합니다. –

+0

나는 패킷을 보내지 않을 것이라고 확신한다. 동일한 닷넷 코드를 실행하면 작동합니다. –

답변

1

나는 그것을 알아 냈어. 분명히 내 바인딩 코드가 마음에 들지 않습니다. 설명서에서는 바인딩에 null을 전달할 수 있어야한다고 말했지만 항상 예외가 있습니다. 따라서 ConnectAsync API를 사용하면 작동합니다.

 public UdpSocketClient(IPEndPoint remoteEndPoint, int localPort) 
     { 
      this.remoteEndPoint = remoteEndPoint; 
#if WINRT 
      this.socket = new DatagramSocket(); 
      this.socket.MessageReceived += ReceiveCallback; 

      Logger.Trace("{0}: Connecting to {1}.", this, remoteEndPoint); 
      IAsyncAction connectAction = this.socket.ConnectAsync(remoteEndPoint.address, remoteEndPoint.port.ToString()); 
      connectAction.AsTask().Wait(); 
      Logger.Trace("{0}: Connect Complete. Status {1}, ErrorCode {2}", this, connectAction.Status, 
       connectAction.ErrorCode != null ? connectAction.ErrorCode.Message : "None"); 

      dataWriter = new DataWriter(this.socket.OutputStream); 
#else 
      ... 
#endif 
     }