From 331fec9231eddedef73905e06e537d29550b17d9 Mon Sep 17 00:00:00 2001 From: bparks13 Date: Thu, 13 Mar 2025 10:48:01 -0400 Subject: [PATCH] Gracefully disconnect socket when acquisition stops - If the server was disconnected during acquisition, and the plugin is trying to automatically reconnect, it will now disconnect if acquisition stops to prevent it going into an unrecoverable state - Update the Python script so it waits to initialize the server until after the user provides keyboard input. This prevents the client from connecting, deciding it can't read any data, and disconnecting - Bump version to 0.5.1 --- CMakeLists.txt | 1 + Resources/python-example-tcp.py | 12 +++++++++--- Source/EphysSocket.cpp | 2 ++ Source/OpenEphysLib.cpp | 2 +- Source/SocketThread.cpp | 5 +++++ 5 files changed, 18 insertions(+), 4 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 9e90a0e..1242979 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -65,6 +65,7 @@ if(MSVC) target_compile_options(${PLUGIN_NAME} PRIVATE /sdl- /W0) install(TARGETS ${PLUGIN_NAME} RUNTIME DESTINATION ${GUI_BIN_DIR}/plugins CONFIGURATIONS ${CMAKE_CONFIGURATION_TYPES}) + install(FILES $ DESTINATION ${GUI_BIN_DIR}/plugins OPTIONAL) set(CMAKE_PREFIX_PATH ${CMAKE_CURRENT_SOURCE_DIR}/../libs) elseif(LINUX) diff --git a/Resources/python-example-tcp.py b/Resources/python-example-tcp.py index d54520e..f103fd0 100644 --- a/Resources/python-example-tcp.py +++ b/Resources/python-example-tcp.py @@ -38,14 +38,14 @@ oneCycle = np.concatenate((intList_1, intList_2)) allData = np.tile(oneCycle, (numChannels, totalDuration)).T +# ---- WAIT FOR USER INPUT ---- # +value = input("Press enter key to start...") + # ---- CREATE THE SOCKET SERVER ---- # tcpServer = socket.socket(family=socket.AF_INET, type=socket.SOCK_STREAM) tcpServer.bind(('localhost', 9001)) tcpServer.listen(1) -# ---- WAIT FOR USER INPUT ---- # -value = input("Press enter key to start...") - print("Waiting for external connection to start...") (tcpClient, address) = tcpServer.accept() print("Connected.") @@ -75,3 +75,9 @@ def currentTime(): print("Done") except BrokenPipeError: print("Connection closed by the server. Unable to send data. Exiting...") + +except ConnectionAbortedError: + print("Connection was aborted, unable to send data. Try disconnecting and reconnecting the remote client. Exiting...") + +except ConnectionResetError: + print("Connection was aborted, unable to send data. Try disconnecting and reconnecting the remote client. Exiting...") diff --git a/Source/EphysSocket.cpp b/Source/EphysSocket.cpp index a40d817..b8c353b 100644 --- a/Source/EphysSocket.cpp +++ b/Source/EphysSocket.cpp @@ -46,6 +46,8 @@ void EphysSocket::registerParameters() void EphysSocket::disconnectSocket() { + socket.signalThreadShouldExit(); + socket.waitForThreadToExit(1000); socket.disconnectSocket(); getParameter ("port")->setEnabled (true); diff --git a/Source/OpenEphysLib.cpp b/Source/OpenEphysLib.cpp index 0012d5d..fe452d1 100644 --- a/Source/OpenEphysLib.cpp +++ b/Source/OpenEphysLib.cpp @@ -38,7 +38,7 @@ extern "C" EXPORT void getLibInfo (Plugin::LibraryInfo* info) { info->apiVersion = PLUGIN_API_VER; info->name = "Ephys Socket"; - info->libVersion = "0.5.0"; + info->libVersion = "0.5.1"; info->numPlugins = NUM_PLUGINS; } diff --git a/Source/SocketThread.cpp b/Source/SocketThread.cpp index 4178833..c37c2ef 100644 --- a/Source/SocketThread.cpp +++ b/Source/SocketThread.cpp @@ -47,6 +47,11 @@ void SocketThread::startAcquisition() void SocketThread::stopAcquisition() { acquiring = false; + + if (shouldReconnect) + { + processor->disconnectSocket(); + } } bool SocketThread::connectSocket (int port, bool printOutput)