Advertisement
rav16783

Untitled

Mar 28th, 2023
26
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 6.94 KB | None | 0 0
  1. #include <arpa/inet.h>
  2. #include <pthread.h>
  3. #include <stdio.h>
  4. #include <stdlib.h>
  5. #include <string.h>
  6. #include <sys/socket.h>
  7. #include <sys/types.h>
  8. #include <unistd.h>
  9.  
  10. #define MAX_LEN 1024
  11. #define NAME_LEN 20
  12. #define MAX_USERS 10
  13. #define USERS_FILE "users.txt"
  14. #define CONN "CONN"
  15. #define LIST "LIST"
  16. #define EXIT "EXIT"
  17. #define HELO "HELO"
  18. #define MESG "MESG"
  19. #define CURR "CURR"
  20. #define ERR "ERR"
  21. #define OK "200 OK"
  22. #define NOT_FOUND "file not found"
  23. #define AVAILABLE "201 AVAILABLE"
  24. #define ASK_NAME "What is your name?"
  25.  
  26. extern void fatal_error(char *msg);
  27. extern void clear_line();
  28. extern void server(int port);
  29. extern void *handle_client(void *param);
  30. extern int send_to(int sock, char *send_buff);
  31. extern int receive_front(int sock, char *recv_buff);
  32. extern int parse(char *tag, char *buffer, char *name);
  33. extern void update_file(int i, char *mesg);
  34.  
  35. struct client_info
  36. {
  37. pthread_t tid;
  38. int sockfd;
  39. int new_sock;
  40. char name[MAX_LEN];
  41. char ip[INET_ADDRSTRLEN];
  42. int port;
  43. struct sockaddr_in addr;
  44. };
  45.  
  46. struct client_info clients[2];
  47. pthread_mutex_t file_mutex;
  48.  
  49. int parse(char *tag, char *buffer, char *remaining)
  50. {
  51. char buffer_copy[MAX_LEN];
  52. strcpy(buffer_copy, buffer);
  53. char *tok = strtok(buffer_copy, " ");
  54.  
  55. if (tok == NULL)
  56. return -1;
  57.  
  58. if (strcmp(tok, tag) != 0)
  59. return -1;
  60.  
  61. // copy the rest of the message ahead to the "remaining" pointer
  62. strcpy(remaining, buffer + strlen(tag) + 1);
  63.  
  64. return 0;
  65. }
  66.  
  67. void fatal_error(char *msg)
  68. {
  69. perror(msg);
  70. exit(1);
  71. }
  72.  
  73. int send_to(int sock, char *send_buff)
  74. {
  75. int send_len = strlen(send_buff);
  76. int bytes_sent = send(sock, send_buff, send_len + 1, 0);
  77. if (bytes_sent < 0)
  78. fatal_error("send error\n");
  79. return bytes_sent;
  80. }
  81. int receive_from(int sock, char *recv_buff)
  82. {
  83. while (1)
  84. {
  85. int bytes_received = recv(sock, recv_buff, MAX_LEN, 0);
  86. if (bytes_received < 0)
  87. fatal_error("receive error\n");
  88. if (bytes_received == 0)
  89. continue;
  90. return bytes_received;
  91. }
  92. }
  93.  
  94. void clear_line()
  95. {
  96. printf("\033[2K"); // clear entire line
  97. printf("\r"); // move cursor to beginning of line
  98. }
  99.  
  100. int main(int argc, char **argv)
  101. {
  102. if (argc != 1)
  103. printf("Usage: <port>\n");
  104.  
  105. int port = atoi(argv[1]);
  106.  
  107. server(port);
  108. return 0;
  109. }
  110.  
  111. void server(int port)
  112. {
  113. FILE *fp = fopen("clientid1_clientid2.txt", "w");
  114. fclose(fp);
  115. printf("<< Starting server session >>\n");
  116.  
  117. struct sockaddr_in my_addr;
  118. my_addr.sin_family = AF_INET;
  119. my_addr.sin_port = htons(port);
  120. // my_addr sin_addr s_addr = htoml(INADDR_ANY);
  121. inet_pton(AF_INET, "127.0.0.1", &my_addr.sin_addr);
  122.  
  123. int sockfd = socket(AF_INET, SOCK_STREAM, 0);
  124.  
  125. if (setsockopt(sockfd, SOL_SOCKET, SO_REUSEADDR, &(int){1}, sizeof(int)) < 0)
  126. fatal_error("setsockopt(SO_REUSEADDR) failed");
  127.  
  128. if (bind(sockfd, (struct sockaddr *)&my_addr, sizeof(my_addr)) == -1)
  129. fatal_error("bind() failed");
  130.  
  131. printf(" << bind successful >>\n");
  132.  
  133. if (listen(sockfd, 0) == -1)
  134. fatal_error("listen() failed");
  135.  
  136. printf("server listening on port %d>>\n", port);
  137. for (int i = 0; i < 2; i++)
  138. {
  139. clients[i].sockfd = sockfd;
  140. clients[i].new_sock = -1;
  141. int *id = (int *)malloc(sizeof(int));
  142. *id = i;
  143. pthread_create(&clients[i].tid, NULL, handle_client, (void *)id);
  144. }
  145.  
  146. for (int i = 0; i < MAX_USERS; i++)
  147. pthread_join(clients[i].tid, NULL);
  148.  
  149. printf("closing server");
  150. }
  151.  
  152. void *handle_client(void *param)
  153. {
  154. char recv_buff[MAX_LEN];
  155. char send_buff[MAX_LEN];
  156.  
  157. int client_num = *(int *)param;
  158.  
  159. free(param);
  160.  
  161. struct client_info *client = &clients[client_num];
  162.  
  163. int sockfd = client->sockfd;
  164. char *name = client->name;
  165. socklen_t slen = sizeof(client->addr);
  166. int new_socket = accept(sockfd, (struct sockaddr *)&client->addr, &slen);
  167. client->new_sock = new_socket;
  168. if (new_socket < 0)
  169. fatal_error("accept() failed");
  170.  
  171. if (client_num == MAX_USERS - 1)
  172. {
  173. printf("<< final client connected, not accepting any more connections >>\n");
  174. close(new_socket);
  175. }
  176.  
  177. inet_ntop(AF_INET, &client->addr.sin_addr, client->ip, INET_ADDRSTRLEN);
  178.  
  179. client->port = ntohs(client->addr.sin_port);
  180. printf("<< client %d connected from %s:%d >>\n", client_num + 1, client->ip, client->port);
  181.  
  182. int bytes_received = receive_from(new_socket, recv_buff);
  183.  
  184. printf("[CLIENT-%d @ SERVER] [%d bytes]\t: %s\n", client_num + 1, bytes_received, recv_buff);
  185.  
  186. if (strcmp(recv_buff, HELO) != 0)
  187. fatal_error("client did not send HELO as the first message");
  188.  
  189. memset(send_buff, 0, MAX_LEN);
  190. sprintf(send_buff, "%s %s", MESG, ASK_NAME);
  191. int bytes_sent = send_to(new_socket, send_buff);
  192. printf("[Server @ CLIENT-%d] [%d bytes]\t: %s\n", client_num + 1, bytes_sent, send_buff);
  193.  
  194. bytes_received = receive_from(new_socket, recv_buff);
  195.  
  196. if (parse(MESG, recv_buff, name) != 0)
  197. fatal_error("client did not send NAME in appropriate format");
  198. printf("name : %s\n", name);
  199.  
  200. printf("[CLIENT-%d @ SERVER] [%d bytes]\t: %s\n", client_num + 1, bytes_received, recv_buff);
  201.  
  202. // update_file();
  203. while (1)
  204. {
  205. bytes_received = receive_from(client->new_sock, recv_buff);
  206. printf("[%s @ SERVER] [%d bytes]\t: %s\n", name, bytes_received, recv_buff);
  207.  
  208. char message[MAX_LEN];
  209. int *chat = 0;
  210. parse(MESG, recv_buff, message);
  211. char sendMesg[MAX_LEN];
  212. strcpy(sendMesg, MESG);
  213. strncat(sendMesg, " ", 1);
  214. strncat(sendMesg, name, strlen(name));
  215. strncat(sendMesg, " ", 1);
  216. strncat(sendMesg, message, strlen(message));
  217. strcpy(send_buff, sendMesg);
  218.  
  219. // strncat(send_buff, " ", 1);
  220.  
  221. // strcat(send_buff, " ");
  222. // strcat(send_buff, clients[1 - client_num].name);
  223. int bytes_sent = send_to(clients[1 - client_num].new_sock, send_buff);
  224. // int bytes_sent = send_to(client->new_sock, send_buff);
  225. printf("[SERVER @ %s] [%d bytes]\t: %s\n", name, bytes_sent, recv_buff);
  226. update_file(client_num, message);
  227.  
  228. if (strcmp(message, EXIT) == 0)
  229. {
  230. printf("<< %s has left the chat >>\n", name);
  231. send_to(clients[client_num].new_sock, send_buff);
  232. break;
  233. }
  234. }
  235. close(client->new_sock);
  236. pthread_exit(NULL);
  237. }
  238.  
  239. void update_file(int i, char message[MAX_LEN])
  240. {
  241. pthread_mutex_lock(&file_mutex);
  242. FILE *fp = fopen("clientid1_clientid2.txt", "a+");
  243. if (fp == NULL)
  244. fatal_error("fopen() failed");
  245.  
  246. printf("updating file\n");
  247. fprintf(fp, "%s: ", clients[i].name);
  248. fprintf(fp, "%s", message);
  249. fprintf(fp, "\n");
  250. fclose(fp);
  251. pthread_mutex_unlock(&file_mutex);
  252. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement