Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- // cn-lab4-server.cpp: определяет точку входа для консольного приложения.
- //
- #include "stdafx.h"
- #include <iostream>
- #include <set>
- #include <sstream>
- #include <string>
- #include <thread>
- #include <vector>
- #include <winsock2.h>
- #pragma comment(lib, "ws2_32.lib")
- using namespace std;
- vector<thread> client_list;
- set<SOCKET> open_socks;
- int client_process(SOCKET client_sock, const int client_id) {
- SECURITY_DESCRIPTOR sd;
- InitializeSecurityDescriptor(&sd, SECURITY_DESCRIPTOR_REVISION);
- SetSecurityDescriptorDacl(&sd, true, 0, false);
- SECURITY_ATTRIBUTES sa;
- sa.lpSecurityDescriptor = &sd;
- sa.nLength = sizeof(sa);
- sa.bInheritHandle = true;
- HANDLE newstdin, newstdout, read_stdout, write_stdin;
- CreatePipe(&newstdin, &write_stdin, &sa, 0);
- CreatePipe(&read_stdout, &newstdout, &sa, 0);
- STARTUPINFO si;
- GetStartupInfo(&si);
- si.dwFlags = STARTF_USESTDHANDLES | STARTF_USESHOWWINDOW;
- si.wShowWindow = SW_HIDE;
- si.hStdOutput = newstdout;
- si.hStdError = newstdout;
- si.hStdInput = newstdin;
- PROCESS_INFORMATION pi;
- int len = 0;
- char buffer[65536];
- auto cp = CreateProcess(L"C:\\Study\\CN\\cn-lab4-server-rp\\Debug\\cn-lab4-server-rp.exe", 0, 0, 0, true, CREATE_NEW_CONSOLE, 0, 0, &si, &pi);
- if (cp == 0)
- cout << GetLastError() << endl;
- WSAPROTOCOL_INFO protocol_info;
- WSADuplicateSocket(client_sock, pi.dwProcessId, &protocol_info);
- closesocket(client_sock);
- WriteFile(write_stdin, &protocol_info, sizeof(protocol_info), 0, 0);
- for (int request_id = 1;;) {
- long avail = 0;
- while (!avail) {
- char buff[65536];
- auto ret = PeekNamedPipe(read_stdout, &buff[0], 65536, 0, (DWORD *)&avail, 0);
- if (ret == false) {
- avail = -1;
- }
- Sleep(1);
- }
- char buff[65536];
- ReadFile(&read_stdout, &buff, avail + 2, 0, 0);
- buff[avail + 1] = 0;
- string s = buff;
- if (s == "&request_received") {
- cout << "Recieved request #" << request_id << " from client #" << client_id << endl;
- continue;
- }
- if (s == "&answer_sent") {
- cout << "Answer for request #" << request_id << " from client #" << client_id << " was sent" << endl;
- request_id++;
- continue;
- }
- if (s == "&client_exit") {
- cout << "Client #" << client_id << " disconnected" << endl;
- break;
- }
- }
- return 0;
- }
- int port_listen(const SOCKET &main_sock) {
- for (int client_id = 1;; client_id++) {
- sockaddr_in addr_client;
- int client_addr_size = sizeof(addr_client);
- SOCKET client_sock = accept(main_sock, (sockaddr *)&addr_client, &client_addr_size);
- if (client_sock == INVALID_SOCKET) {
- auto wsa_error = WSAGetLastError();
- if (wsa_error != 10004)
- cout << "Accept error " << wsa_error << endl;
- return 1;
- }
- cout << "Client " << client_id << " connected" << endl;
- client_list.emplace_back(client_process, client_sock, client_id);
- }
- return 0;
- }
- int main()
- {
- cout << "cn-lab4 var10 server start" << endl;
- WSAData wsadata;
- WSAStartup(0x0202, &wsadata);
- cout << "Windows Sockets API initialized" << endl;
- SOCKET main_sock;
- main_sock = socket(AF_INET, SOCK_STREAM, 0);
- if (main_sock == INVALID_SOCKET) {
- cout << "Main socket create error " << WSAGetLastError() << endl;
- WSACleanup();
- return 1;
- }
- cout << "Main socket created successfully" << endl;
- sockaddr_in addr_local;
- addr_local.sin_family = AF_INET;
- addr_local.sin_addr.S_un.S_addr = 0;
- addr_local.sin_port = htons(5004);
- if (::bind(main_sock, (sockaddr *)&addr_local, sizeof(addr_local))) {
- cout << "Bind error " << WSAGetLastError() << endl;
- closesocket(main_sock);
- WSACleanup();
- return 2;
- }
- cout << "Port " << ntohs(addr_local.sin_port) << " bound successful" << endl;
- if (listen(main_sock, 16))
- {
- cout << "Listen error " << WSAGetLastError() << endl;
- closesocket(main_sock);
- WSACleanup();
- return 3;
- }
- cout << "Listening port 5004" << endl;
- thread listen(port_listen, main_sock);
- string s;
- do {
- cin >> s;
- } while (s != "stop" && s != "exit");
- closesocket(main_sock);
- for (auto client_sock : open_socks) {
- send(client_sock, "&stop", sizeof("&stop"), 0);
- closesocket(client_sock);
- }
- if (listen.joinable())
- listen.join();
- for (unsigned int i = 0; i < client_list.size(); i++)
- if (client_list.at(i).joinable())
- client_list.at(i).join();
- WSACleanup();
- cout << "cn-lab4 var10 server was stopped" << endl;
- return 0;
- }
Advertisement
Add Comment
Please, Sign In to add comment