Skip to content

Commit

Permalink
Add non_interactive_ioc() function
Browse files Browse the repository at this point in the history
Resolves PR #156
  • Loading branch information
Xavier GOIZIOU authored and Araneidae committed Apr 24, 2024
1 parent 4388c69 commit 4bbc933
Show file tree
Hide file tree
Showing 5 changed files with 31 additions and 0 deletions.
2 changes: 2 additions & 0 deletions CHANGELOG.rst
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,9 @@ Unreleased_
-----------

Added:

- `Enable setting alarm status of Out records <../../pull/157>`_
- `Adding the non_interactive_ioc function <../../pull/156>`_

Removed:

Expand Down
6 changes: 6 additions & 0 deletions docs/reference/api.rst
Original file line number Diff line number Diff line change
Expand Up @@ -120,6 +120,12 @@ Test Facilities`_ documentation for more details of each function.
.. autofunction:: generalTimeReport
.. autofunction:: eltc

.. autofunction:: non_interactive_ioc

When used with a service manager, use python's -u option or the environment
variable PYTHONUNBUFFERED=TRUE. This ensures that python output, i.e. stdout
and stderr streams, is sent directly to the terminal.

.. attribute:: exit

Displaying this value will invoke ``epicsExit()`` causing the IOC to
Expand Down
12 changes: 12 additions & 0 deletions softioc/asyncio_dispatcher.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
import logging
import threading
import atexit
import signal

class AsyncioDispatcher:
def __init__(self, loop=None, debug=False):
Expand Down Expand Up @@ -48,6 +49,17 @@ def close(self):

self.__shutdown()

def wait_for_quit(self):
stop_event = threading.Event()

def signal_handler(signum, frame):
stop_event.set()

signal.signal(signal.SIGINT, signal_handler)
signal.signal(signal.SIGTERM, signal_handler)

stop_event.wait()

async def __inloop(self, started):
self.loop = asyncio.get_running_loop()
self.__interrupt = asyncio.Event()
Expand Down
2 changes: 2 additions & 0 deletions softioc/cothread_dispatcher.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,8 @@ def __init__(self, dispatcher = None):
else:
self.__dispatcher = dispatcher

self.wait_for_quit = cothread.WaitForQuit

def __call__(
self,
func,
Expand Down
9 changes: 9 additions & 0 deletions softioc/softioc.py
Original file line number Diff line number Diff line change
Expand Up @@ -352,3 +352,12 @@ def interactive_ioc(context = {}, call_exit = True):

if call_exit:
safeEpicsExit(0)


def non_interactive_ioc():
'''Function to run the IOC in non-interactive mode. This mode is useful for
running the IOC as a background process without user interaction.
This function expects a stop signal. When it receives one, the IOC stops.
'''
device.dispatcher.wait_for_quit()
safeEpicsExit(0)

0 comments on commit 4bbc933

Please sign in to comment.