REDAC HybridController
Firmware for LUCIDAC/REDAC Teensy
Loading...
Searching...
No Matches
native_ethernet_server.cpp
Go to the documentation of this file.
1#include <net/ethernet_client.h>
2
5
6#include <iostream>
7#include <memory>
8#include <string>
9
10namespace net {
11
13 running = true;
14
15 // Create socket
16 server_fd = socket(AF_INET, SOCK_STREAM, 0);
17#ifdef _WIN64
18 if (server_fd == INVALID_SOCKET) {
19#else
20 if (server_fd == -1) {
21#endif
22 std::cerr << "Socket creation failed: " <<
23#ifdef _WIN64
24 WSAGetLastError()
25#else
26 strerror(errno)
27#endif
28 << std::endl;
29 return false;
30 }
31
32 // Set socket options to reuse address and port
33 int opt = 1;
34#ifdef _WIN64
35 if (setsockopt(server_fd, SOL_SOCKET, SO_REUSEADDR, reinterpret_cast<const char *>(&opt), sizeof(opt))) {
36#else
37 if (setsockopt(server_fd, SOL_SOCKET, SO_REUSEPORT, &opt, sizeof(opt))) {
38#endif
39#ifdef _WIN64
40
41#else
42 std::cerr << "setsockopt failed: " << strerror(errno) << std::endl;
43#endif
44
45 return false;
46 }
47
48 // Prepare the sockaddr_in structure
49 sockaddr_in address{};
50 address.sin_family = AF_INET;
51 address.sin_addr.s_addr = INADDR_ANY;
52 address.sin_port = htons(port);
53
54 // Bind the socket
55 if (bind(server_fd, reinterpret_cast<sockaddr *>(&address), sizeof(address)) < 0) {
56#ifdef _WIN64
57#else
58
59 std::cerr << "Bind failed: " << strerror(errno) << std::endl;
60#endif
61
62 return false;
63 }
64
65 // Listen for connections
66 if (listen(server_fd, 8) < 0) {
67#ifdef _WIN64
68#else
69 std::cerr << "Listen failed: " << strerror(errno) << std::endl;
70#endif
71
72 return false;
73 }
74
75// Set non-blocking mode
76#ifdef _WIN64
77 u_long mode = 1;
78 ioctlsocket(server_fd, FIONBIO, &mode);
79#else
80 int flags = fcntl(server_fd, F_GETFL);
81 fcntl(server_fd, F_SETFL, flags | O_NONBLOCK);
82#endif
83
84 std::cout << "Server is listening on port " << port << std::endl;
85 return true;
86}
87
89 sockaddr_in client_addr{};
90#ifdef _WIN64
91 int client_len = sizeof(client_addr);
92#else
93 socklen_t client_len = sizeof(client_addr);
94#endif
95
96 auto client_socket = ::accept(server_fd, reinterpret_cast<struct sockaddr *>(&client_addr), &client_len);
97
98#ifdef _WIN64
99 if (client_socket != INVALID_SOCKET) {
100#else
101 if (client_socket >= 0) {
102#endif
103 char client_ip[INET_ADDRSTRLEN];
104 inet_ntop(AF_INET, &client_addr.sin_addr, client_ip, INET_ADDRSTRLEN);
105 std::cout << "New connection from " << client_ip << ":" << ntohs(client_addr.sin_port) << std::endl;
106 }
107
108 return EthernetClient(std::make_unique<NativeEthernetClientHAL>(client_socket));
109}
110
111// Add destructor to properly clean up
113 if (running) {
114#ifdef _WIN64
115 closesocket(server_fd);
116#else
117 close(server_fd);
118#endif
119 running = false;
120 }
121}
122
123} // namespace net
Definition mode.h:14