2015-12-10 158 views
2
 Socket A(local_address); 

    void enviar(sockaddr_in remote_address, std::atomic<bool>& quit){ 
     std::string message_text; 
     Message message; 
     while(!quit){ 
      std::getline(std::cin, message_text); 
      if (message_text != "/quit"){ 
       memset(message.text, 0, 1024); 
       message_text.copy(message.text, sizeof(message.text) - 1, 0); 
       A.send_to(message, remote_address); 
      } 
      else { 
       quit = true; 
      } 
     } 
    } 

    void recibir(sockaddr_in local_address, std::atomic<bool>& quit){ 
     Message messager; 
     while(!quit){ 
      A.receive_from(messager, local_address); 
     } 
    } 

    int main(void){ 
     std::atomic<bool> quit(false); 
     sockaddr_in remote_address = make_ip_address("127.0.0.1",6000); 

     std::thread hilorec(&recibir,local_address, std::ref(quit)); 
     std::thread hiloenv(&enviar,remote_address, std::ref(quit)); 

     hiloenv.join(); 
     hilorec.join(); 
    } 

嗨!我正在嘗試與套接字進行簡單的聊天。我希望程序在寫入「/ quit」時完成。我用一個叫做quit的原子布爾變量來試試這個。問題是,當我寫入「/退出」退出將是'真',hiloenv線程將完成,但接收消息的hilorec將被阻止,直到我收到一條消息,因爲recvfrom()函數。我如何解決這個問題?C++ - 套接字和多線程

對不起,我的英語和謝謝!

+0

你使用什麼套接字庫? – Nick

+0

這是在什麼平臺上運行的? –

+0

在'hiloenv'完成之前添加一個延遲,或者在發送'/ quit'之後等待完成'hilorec'而不等待響應 –

回答

0

如果要創建單個線程應用程序,請使用epoll或選擇apis。如果你想堅持你當前的設計,那麼你可以創建你的套接字,並設置超時時間。詳情請參閱How to set socket timeout in C when making multiple connections?。所以當你退出時,等待的線程會在recout或timout後發送,然後線程將加入,你的應用程序可以正常退出。

3

關閉輸入插座。這將導致recvfrom()返回零,就好像對方關閉了連接一樣,這會導致該線程退出。

1

當檢測到退出時,我會向主線程發送一些特殊的(例如空的)消息到套接字。在這種情況下,您的while(!quit) ...循環將完成,因此線程。

0

感謝您的答案。我設法修復它,如果任何人有興趣如何:

 std::thread hilorec(&recibir,local_address); 
    std::thread hiloenv(&enviar,remote_address); 

    while(!quit){} 

    pthread_cancel(hilorec.native_handle()); 
    pthread_cancel(hiloenv.native_handle()); 

    hilorec.join(); 
    hiloenv.join();