ithewei 1 год назад
Родитель
Сommit
67139ab316
3 измененных файлов с 38 добавлено и 6 удалено
  1. 3 1
      evpp/Channel.h
  2. 8 1
      evpp/TcpClient.h
  3. 27 4
      evpp/TcpClientEventLoop_test.cpp

+ 3 - 1
evpp/Channel.h

@@ -4,6 +4,7 @@
 #include <string>
 #include <functional>
 #include <memory>
+#include <atomic>
 
 #include "hloop.h"
 #include "hsocket.h"
@@ -193,7 +194,8 @@ public:
         CONNECTED,
         DISCONNECTED,
         CLOSED,
-    } status;
+    };
+    std::atomic<Status>          status;
     std::function<void(Buffer*)> onread;
     // NOTE: Use Channel::isWriteComplete in onwrite callback to determine whether all data has been written.
     std::function<void(Buffer*)> onwrite;

+ 8 - 1
evpp/TcpClient.h

@@ -35,6 +35,13 @@ public:
         return loop_;
     }
 
+    // delete thread-safe
+    void deleteInLoop() {
+        loop_->runInLoop([this](){
+            delete this;
+        });
+    }
+
     // NOTE: By default, not bind local port. If necessary, you can call bind() after createsocket().
     // @retval >=0 connfd, <0 error
     int createsocket(int remote_port, const char* remote_host = "127.0.0.1") {
@@ -86,7 +93,7 @@ public:
 
     // closesocket thread-safe
     void closesocket() {
-        if (channel) {
+        if (channel && channel->status != SocketChannel::CLOSED) {
             loop_->runInLoop([this](){
                 if (channel) {
                     setReconnect(NULL);

+ 27 - 4
evpp/TcpClientEventLoop_test.cpp

@@ -7,6 +7,8 @@
  *
  */
 
+#include <iostream>
+
 #include "TcpClient.h"
 #include "htime.h"
 
@@ -77,14 +79,35 @@ int TestMultiClientsRunInOneEventLoop(int port, int nclients) {
     auto loop_thread = std::make_shared<EventLoopThread>();
     loop_thread->start();
 
-    std::map<int, MyTcpClientPtr> clients;
+    std::map<int, MyTcpClient*> clients;
     for (int i = 0; i < nclients; ++i) {
         MyTcpClient* client = new MyTcpClient(loop_thread->loop());
         client->connect(port);
-        clients[i] = MyTcpClientPtr(client);
+        clients[i] = client;
+    }
+
+    std::string str;
+    while (std::getline(std::cin, str)) {
+        if (str == "close") {
+            for (auto& pair : clients) {
+                MyTcpClient* client = pair.second;
+                client->closesocket();
+            }
+        } else if (str == "delete") {
+            for (auto& pair : clients) {
+                MyTcpClient* client = pair.second;
+                client->deleteInLoop();
+            }
+            break;
+        } else {
+            for (auto& pair : clients) {
+                MyTcpClient* client = pair.second;
+                client->send(str);
+            }
+        }
     }
 
-    // press Enter to stop
+    printf("Press Enter key to exit loop.\n");
     while (getchar() != '\n');
     loop_thread->stop();
     loop_thread->join();
@@ -94,7 +117,7 @@ int TestMultiClientsRunInOneEventLoop(int port, int nclients) {
 
 int main(int argc, char* argv[]) {
     if (argc < 2) {
-        printf("Usage: %s port\n", argv[0]);
+        printf("Usage: %s port [nclients]\n", argv[0]);
         return -10;
     }
     int port = atoi(argv[1]);