From 9015f185a2367e3a3ad255b543062abb290908dc Mon Sep 17 00:00:00 2001 From: flykhan Date: Wed, 6 Sep 2023 15:33:01 +0800 Subject: [PATCH] =?UTF-8?q?qq=E7=BE=A4=E8=81=8A?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- day3/qq2/qq2.c | 118 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 118 insertions(+) create mode 100644 day3/qq2/qq2.c diff --git a/day3/qq2/qq2.c b/day3/qq2/qq2.c new file mode 100644 index 0000000..98e33e1 --- /dev/null +++ b/day3/qq2/qq2.c @@ -0,0 +1,118 @@ +// 群聊 +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/* +* ./a.out port +*/ + +void *recv_task(void *arg); +void *send_task(void *arg); + +int bind_port; + +int main(int argc, char const *argv[]) +{ + if (argc < 2) + { + printf("usage: %s port\n", argv[0]); + return -1; + } + + int sock_fd = socket(AF_INET, SOCK_DGRAM, 0); + if (sock_fd < 0) + { + perror("socket"); + return EXIT_FAILURE; // 1 + } + + bind_port = atoi(argv[1]); + + // 绑定端口 + struct sockaddr_in bind_addr; + memset(&bind_addr, 0, sizeof(bind_addr)); + bind_addr.sin_family = AF_INET; + bind_addr.sin_port = htons(bind_port); + bind_addr.sin_addr.s_addr = htonl(INADDR_ANY); + bind(sock_fd, (struct sockaddr *)&bind_addr, sizeof(bind_addr)); // 绑定文件描述符和地址端口 + + // 设置 socket 选项为广播 + int val = 1; + int ret = setsockopt(sock_fd, SOL_SOCKET, SO_BROADCAST, &val, sizeof(val)); + if (ret != 0) + { + perror("setsockopt"); + } + + pthread_t tid1, tid2; + pthread_create(&tid1, NULL, recv_task, &sock_fd); + pthread_create(&tid2, NULL, send_task, &sock_fd); + + pthread_join(tid2, NULL); + pthread_cancel(tid1); + pthread_join(tid1, NULL); + + printf("---over---\n"); + close(sock_fd); + + return 0; +} + +void *recv_task(void *arg) +{ + int sock_fd = *((int *)arg); + + while (1) + { + struct sockaddr_in data_addr; + socklen_t data_addr_len = sizeof(data_addr); + bzero(&data_addr, data_addr_len); + + char buf[128] = ""; + + ssize_t recv_len = recvfrom(sock_fd, buf, 128, 0, (struct sockaddr *)&data_addr, &data_addr_len); + if (recv_len > 0) + { + char ip[16] = ""; + inet_ntop(AF_INET, &data_addr.sin_addr.s_addr, ip, 16); + printf("%s(%d): %s\n", ip, ntohs(data_addr.sin_port), buf); + } + } +} + +void *send_task(void *arg) +{ + int sock_fd = *((int *)arg); + + while (1) + { + char buf[128] = ""; + if (fgets(buf, 128, stdin) != NULL) + { + buf[strlen(buf) - 1] = 0; + + struct sockaddr_in addr; + bzero(&addr, sizeof(addr)); + addr.sin_family = AF_INET; + addr.sin_port = htons(bind_port); + addr.sin_addr.s_addr = inet_addr("10.35.188.255"); // 一定是广播地址 + + sendto(sock_fd, buf, strlen(buf) + 1, 0, (struct sockaddr *)&addr, sizeof(addr)); + if (strncmp(buf, "bye", 3) == 0) + { + break; + } + if (strncmp(buf, "clear", 5) == 0) + { + system("clear"); + } + } + } +} \ No newline at end of file