diff --git a/lib/runcpm/abstraction_fujinet.h b/lib/runcpm/abstraction_fujinet.h index 4460b781a..257bced8d 100644 --- a/lib/runcpm/abstraction_fujinet.h +++ b/lib/runcpm/abstraction_fujinet.h @@ -643,10 +643,18 @@ uint8_t bios_tcpListen(uint16_t port) } server = new fnTcpServer(port,1); - server->begin(port); - Debug_printf("bios_tcpListen - Now listening on port %u\r\n", port); - return server != nullptr; + int res = server->begin(port); + if (res == 0) + { + Debug_printf("bios_tcpListen - failed to open port %u\nError (%d): %s\r\n", port, errno, strerror(errno)); + return true; + } + else + { + Debug_printf("bios_tcpListen - Now listening on port %u\r\n", port); + return false; + } } uint8_t bios_tcpAvailable(void) diff --git a/lib/runcpm/abstraction_fujinet_apple2.h b/lib/runcpm/abstraction_fujinet_apple2.h index 8a0476487..df37dccf0 100644 --- a/lib/runcpm/abstraction_fujinet_apple2.h +++ b/lib/runcpm/abstraction_fujinet_apple2.h @@ -639,10 +639,17 @@ uint8_t bios_tcpListen(uint16_t port) } server = new fnTcpServer(port,1); - server->begin(port); - - Debug_printf("bios_tcpListen - Now listening on port %u\r\n", port); - return server != nullptr; + int res = server->begin(port); + if (res == 0) + { + Debug_printf("bios_tcpListen - failed to open port %u\nError (%d): %s\r\n", port, errno, strerror(errno)); + return true; + } + else + { + Debug_printf("bios_tcpListen - Now listening on port %u\r\n", port); + return false; + } } uint8_t bios_tcpAvailable(void) diff --git a/lib/tcpip/fnTcpServer.cpp b/lib/tcpip/fnTcpServer.cpp index 907822a44..126ff6ef8 100644 --- a/lib/tcpip/fnTcpServer.cpp +++ b/lib/tcpip/fnTcpServer.cpp @@ -8,10 +8,13 @@ // Configures a listening TCP socket on given port -void fnTcpServer::begin(uint16_t port) +// Returns 0 for error, 1 for success. +int fnTcpServer::begin(uint16_t port) { - if (_listening) - return; + if (_listening) { + Debug_println("TCP Server already listening. Aborting."); + return 0; + } if (port) _port = port; @@ -21,7 +24,7 @@ void fnTcpServer::begin(uint16_t port) if (_sockfd < 0) { Debug_printf("fnTcpServer::begin failed to allocate socket, err %d\r\n", errno); - return; + return 0; } // Bind socket to our interface @@ -32,13 +35,14 @@ void fnTcpServer::begin(uint16_t port) if (bind(_sockfd, (struct sockaddr *)&server, sizeof(server)) < 0) { Debug_printf("fnTcpServer::begin failed to bind socket, err %d\r\n", errno); - return; + return 0; } int enable = 1; if (setsockopt(_sockfd, SOL_SOCKET, SO_REUSEADDR, &enable, sizeof(int)) < 0) { - Debug_printf("fnTcpServer::begin failed to set SO_REUSEADDR, err %d", errno); + Debug_printf("fnTcpServer::begin failed to set SO_REUSEADDR, err %d\r\n", errno); + return 0; } Debug_printf("Max clients is currently %u\r\n",_max_clients); @@ -47,15 +51,22 @@ void fnTcpServer::begin(uint16_t port) if (listen(_sockfd, _max_clients) < 0) { Debug_printf("fnTcpServer::begin failed to listen on socket, err %d\r\n", errno); - return; + return 0; } // Switch to non-blocking mode - fcntl(_sockfd, F_SETFL, O_NONBLOCK); + if (fcntl(_sockfd, F_SETFL, O_NONBLOCK) < 0) + { + Debug_printf("fnTcpServer::begin failed to set non-blocking mode. Closing down server. err %d\n", errno); + stop(); + return 0; + } _listening = true; _noDelay = false; _accepted_sockfd = -1; + Debug_printf("TCP Server now listening on port %d.\n", _port); + return 1; } // Returns true if a client has connected to the socket diff --git a/lib/tcpip/fnTcpServer.h b/lib/tcpip/fnTcpServer.h index f850aadc0..9ec638145 100644 --- a/lib/tcpip/fnTcpServer.h +++ b/lib/tcpip/fnTcpServer.h @@ -21,7 +21,7 @@ class fnTcpServer fnTcpServer(uint16_t port=80, uint8_t max_clients=4): _port(port), _max_clients(max_clients){} ~fnTcpServer(){ stop(); } - void begin(uint16_t port=0); + int begin(uint16_t port=0); fnTcpClient accept(){ return available(); } void setNoDelay(bool nodelay) { _noDelay = nodelay; };