Следите за новинками
в нашем Telegram канале. Жми, чтобы подписаться:)
⊗cpSpSoExc 678 of 696 menu
◀ ▶

Обмен в одном запуске в C++

Полный цикл в одном процессе требует двух потоков: один ждет accept, другой вызывает connect к 127.0.0.1 и порту 18080.

Сначала клиент пишет строку, затем читает ответ - порядок важен, иначе стороны ждут друг друга. Ответ сервера выведем на клиенте после recv в буфер с явным размером. Оба потока свяжем через join, каждый дескриптор закроем через close:

#include <arpa/inet.h> #include <chrono> #include <cstring> #include <cstdlib> #include <iostream> #include <netinet/in.h> #include <string> #include <sys/socket.h> #include <thread> #include <unistd.h> int main() { std::thread server([]() { int listen_fd = socket(AF_INET, SOCK_STREAM, 0); if (listen_fd == -1) { return; } sockaddr_in addr{}; addr.sin_family = AF_INET; addr.sin_port = htons(18080); if (inet_pton(AF_INET, "127.0.0.1", &addr.sin_addr) != 1) { close(listen_fd); return; } if (bind(listen_fd, reinterpret_cast<sockaddr*>(&addr), sizeof(addr)) == -1) { close(listen_fd); return; } if (listen(listen_fd, 1) == -1) { close(listen_fd); return; } int peer_fd = accept(listen_fd, nullptr, nullptr); if (peer_fd == -1) { close(listen_fd); return; } char buf[128]; ssize_t got = recv(peer_fd, buf, sizeof(buf) - 1, 0); if (got != -1) { buf[got] = '\0'; std::string reply = "status: done\n"; send(peer_fd, reply.c_str(), reply.size(), 0); } close(peer_fd); close(listen_fd); }); std::thread client([]() { std::this_thread::sleep_for(std::chrono::milliseconds(50)); int fd = socket(AF_INET, SOCK_STREAM, 0); if (fd == -1) { return; } sockaddr_in addr{}; addr.sin_family = AF_INET; addr.sin_port = htons(18080); if (inet_pton(AF_INET, "127.0.0.1", &addr.sin_addr) != 1) { close(fd); return; } if (connect(fd, reinterpret_cast<sockaddr*>(&addr), sizeof(addr)) == -1) { close(fd); return; } const char* line = "go\n"; if (send(fd, line, std::strlen(line), 0) == -1) { close(fd); return; } char buf[128]; ssize_t got = recv(fd, buf, sizeof(buf) - 1, 0); if (got != -1) { buf[got] = '\0'; std::cout << buf; } close(fd); }); server.join(); client.join(); return 0; }

Сервер может добавить к ответу прочитанный текст. Клиент печатает готовую строку целиком - так видно, что обмен завершился в рамках одного запуска:

#include <arpa/inet.h> #include <chrono> #include <cstring> #include <cstdlib> #include <iostream> #include <netinet/in.h> #include <string> #include <sys/socket.h> #include <thread> #include <unistd.h> int main() { std::thread server([]() { int listen_fd = socket(AF_INET, SOCK_STREAM, 0); if (listen_fd == -1) { return; } sockaddr_in addr{}; addr.sin_family = AF_INET; addr.sin_port = htons(18080); if (inet_pton(AF_INET, "127.0.0.1", &addr.sin_addr) != 1) { close(listen_fd); return; } if (bind(listen_fd, reinterpret_cast<sockaddr*>(&addr), sizeof(addr)) == -1) { close(listen_fd); return; } if (listen(listen_fd, 1) == -1) { close(listen_fd); return; } int peer_fd = accept(listen_fd, nullptr, nullptr); if (peer_fd == -1) { close(listen_fd); return; } char buf[128]; ssize_t got = recv(peer_fd, buf, sizeof(buf) - 1, 0); if (got != -1) { buf[got] = '\0'; std::string reply = std::string("heard: ") + buf; send(peer_fd, reply.c_str(), reply.size(), 0); } close(peer_fd); close(listen_fd); }); std::thread client([]() { std::this_thread::sleep_for(std::chrono::milliseconds(50)); int fd = socket(AF_INET, SOCK_STREAM, 0); if (fd == -1) { return; } sockaddr_in addr{}; addr.sin_family = AF_INET; addr.sin_port = htons(18080); if (inet_pton(AF_INET, "127.0.0.1", &addr.sin_addr) != 1) { close(fd); return; } if (connect(fd, reinterpret_cast<sockaddr*>(&addr), sizeof(addr)) == -1) { close(fd); return; } const char* line = "wave\n"; if (send(fd, line, std::strlen(line), 0) == -1) { close(fd); return; } char buf[128]; ssize_t got = recv(fd, buf, sizeof(buf) - 1, 0); if (got != -1) { buf[got] = '\0'; std::cout << buf; } close(fd); }); server.join(); client.join(); return 0; }

Клиент отправляет "start\n" на 127.0.0.1 и печатает ответ "begin: start", который формирует сервер.

В консоли клиента после обмена должна быть строка "ok", если сервер получил "check".

← →
↑
Мы используем cookie для работы сайта, аналитики и персонализации. Обработка данных происходит согласно Политике конфиденциальности.
принять все настроить отклонить