skindervik

TCP-MULTI-THREADED-SERVER

Jul 4th, 2020 (edited)
2,719
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 3.80 KB | None | 0 0
  1. //MY CRAPPY YOUTUBE https://www.youtube.com/channel/UC9kD0oE90HfCZvMAPzRLf3w
  2.  
  3. #include<iostream>
  4. #include<WS2tcpip.h>
  5. #include<thread>
  6. #include<sstream>
  7. #include<vector>
  8. #pragma comment (lib, "Ws2_32.lib")
  9. int main() {
  10.     //INITIALIZE THE WINSOCK
  11.     WSADATA some_kind_of_data;
  12.     WSAStartup(MAKEWORD(2,2), &some_kind_of_data);
  13.  
  14.     //CLIENT OBJECT
  15.     struct CLIENT{
  16.         char client_ip[256];
  17.         SOCKET sock;
  18.     };
  19.  
  20.     //CREATE A LIST OF CLIENTS
  21.     std::vector<CLIENT> clients;
  22.  
  23.     //ACCEPT CONNECTION - THREAD 01
  24.     std::thread accepter([&clients]() {
  25.         ///CREATE LISTENING SOCKET
  26.         sockaddr_in listen_address;
  27.         listen_address.sin_family = AF_INET;
  28.         listen_address.sin_port = htons(666);
  29.         listen_address.sin_addr.S_un.S_addr = INADDR_ANY;
  30.         //CREATE THE SOCKET ITSELF
  31.         SOCKET listen_socket = socket(AF_INET, SOCK_STREAM, 0);
  32.         //BIND THE ADRESS TO THE SOCKET
  33.         bind(listen_socket, (sockaddr*)&listen_address, sizeof(listen_address));
  34.         //SET THE SOCKET TO LISTENING MODE
  35.         listen(listen_socket, SOMAXCONN);
  36.         //STORE CLIENT IP
  37.         sockaddr_in client_address;
  38.         int client_address_size = sizeof(client_address);
  39.         //TEMPORARY CLIENT SOCKET
  40.         SOCKET client_socket;
  41.         //USED FOR CHANGING SOCKETS TO NON_BLOCKING
  42.         u_long non_blocking = true;
  43.  
  44.         while (true){
  45.             //CREATE TEMPORARY SOCKET
  46.             client_socket = accept(listen_socket, (sockaddr*)&client_address, &client_address_size);
  47.             if (client_socket != INVALID_SOCKET) { //IF CLIENT CONNECTED CORRECTLLY
  48.                 //SET THE TEMPORARY SOCKET TO NON_BLOCKING
  49.                 ioctlsocket(client_socket, FIONBIO, &non_blocking);
  50.                 //CREATE NEW CLIENT OBJECT
  51.                 CLIENT new_client;
  52.                 //PUT SOCKET AND IP FROM TEMPORARY SOCKET TO NEW CLIENT OBJECT
  53.                 new_client.sock = client_socket;
  54.                 inet_ntop(AF_INET, &client_address.sin_addr, new_client.client_ip, 256);
  55.                 //ADD THE NEW CLIENT OBJECT TO THE LIST OF CLIENTS
  56.                 clients.push_back(new_client);
  57.                 //PRINT OUT THAT SOMEONE HAS CONNECTED
  58.                 std::cout << "Client " << new_client.client_ip << ":" << clients.size() - 1 << " Connected!" << std::endl;
  59.             }}});
  60.  
  61.     //CHECK CONNECTIONS - THREAD 02
  62.     std::thread checker([&clients]() {
  63.         while (true) {
  64.             //CYCKLE TROUGH ALL THE CLIENTS
  65.             for (int i = 0; i < clients.size(); i++){
  66.                 //SEND EMPTY MESSAGE TO ALL CLIENTS
  67.                 if (send(clients[i].sock, "", 1, 0) < 0) {
  68.                     //IF CLIENT FAILS TO RECEIVE THE MESSAGE
  69.                     //PRINT OUT MESSAGE THAT THAT CLIENT HAS DISCONNECTED
  70.                     std::cout << "Client " << clients[i].client_ip << ":" << i << " Disconnected!" << std::endl;
  71.                     //ERASE THE CLIENT FROM THE LIST
  72.                     clients.erase(clients.begin()+i);
  73.                 }}
  74.             //WAIT ONE SECOND BEFORE CHECKING CONNECTION AGAIN
  75.             std::this_thread::sleep_for(std::chrono::seconds(1));
  76.         }});
  77.  
  78.      
  79.     //RECEIVE MESSAGE - THREAD 03
  80.     std::thread receiver([&clients]() {
  81.         //BUFFER THAT STORES THE RECEIVED MESSAGE
  82.         char buffer[1024];
  83.  
  84.         while (true){
  85.             //CYCKLE TROUGH ALL THE CLIENTS
  86.             for (int i = 0; i < clients.size(); i++){
  87.                 //DELETE THE OLD RECEIVED MESSAGE
  88.                 memset(buffer, 0, sizeof(buffer));
  89.  
  90.                 //IF RECEIVED MESSAGE IS LONGER THEN ONE CHARACTER
  91.                 if (recv(clients[i].sock, buffer, sizeof(buffer), 0) > 1) {
  92.                     //CYCKLE TROUGH ALL THE CLIENTS
  93.                     //SENDS RECEIVED MESSAGE TO ALL CONNECTED CLIENTS
  94.                     for (int y = 0; y < clients.size(); y++)
  95.                         //SEND MESSAGE TO ALL CLIENTS EXCEPT TO THE CLIENT THAT SEND THE MESSAGE
  96.                         if (i != y) {
  97.                             std::stringstream msg;
  98.                             //CONSTRUCT THE MESSAGE
  99.                             msg << clients[i].client_ip << ":" << i << " " << buffer;
  100.                             //SEND THE MESSAGE
  101.                             send(clients[y].sock, msg.str().c_str(), msg.str().size(), 0);
  102.                         }}}}});
  103.    
  104.     //CONTROLL THE SERVER - MAIN THREAD
  105.     std::string msg;
  106.     while (true) {
  107.         std::getline(std::cin, msg);
  108.         if (msg == "stop") {
  109.             break;
  110.         }}
  111.     WSACleanup();
  112.     system("pause");
  113.     quick_exit(0);
  114. }
Advertisement
Add Comment
Please, Sign In to add comment