ducky.reactor module

This module provides simple reactor core that runs each of registered tasks at least once during one iteration of its internal loop.

There are two different kinds of objects that reactor manages:

  • task - it’s called periodicaly, at least once in each reactor loop iteration
  • event - asynchronous events are queued and executed before running any tasks. If there are no runnable tasks, reactor loop waits for incomming events.
class ducky.reactor.CallInReactorTask(fn, *args, **kwargs)[source]

Bases: ducky.interfaces.IReactorTask

This task request running particular function during the reactor loop. Useful for planning future work, and for running tasks in reactor’s thread.

Parameters:
  • fn – callback to fire.
  • args – arguments for callback.
  • kwargs – keyword arguments for callback.
run()[source]
class ducky.reactor.FDCallbacks(on_read, on_write, on_error)

Bases: tuple

_asdict()

Return a new OrderedDict which maps field names to their values

_fields = ('on_read', 'on_write', 'on_error')
classmethod _make(iterable, new=<built-in method __new__ of type object at 0x906d60>, len=<built-in function len>)

Make a new FDCallbacks object from a sequence or iterable

_replace(_self, **kwds)

Return a new FDCallbacks object replacing specified fields with new values

on_error

Alias for field number 2

on_read

Alias for field number 0

on_write

Alias for field number 1

class ducky.reactor.Reactor(machine)[source]

Bases: object

Main reactor class.

add_call(fn, *args, **kwargs)[source]

Enqueue function call. Function will be called in reactor loop.

add_event(event)[source]

Enqueue asynchronous event.

add_fd(fd, on_read=None, on_write=None, on_error=None)[source]

Register file descriptor with reactor. File descriptor will be checked for read/write/error posibilities, and appropriate callbacks will be fired.

No arguments are passed to callbacks.

Parameters:
  • fd (int) – file descriptor.
  • on_read – function that will be called when file descriptor is available for reading.
  • on_write – function that will be called when file descriptor is available for write.
  • on_error – function that will be called when error state raised on file descriptor.
add_task(task)[source]

Register task with reactor’s main loop.

remove_fd(fd)[source]

Unregister file descriptor. It will no longer be checked by its main loop.

Parameters:fd (int) – previously registered file descriptor.
remove_task(task)[source]

Unregister task, it will never be ran again.

run()[source]

Starts reactor loop. Enters endless loop, calling runnable tasks and events, and - in case there are no runnable tasks - waits for new events.

When there are no tasks managed by reactor, loop quits.

task_runnable(task)[source]

If not yet marked as such, task is marked as runnable, and its run() method will be called every iteration of reactor’s main loop.

task_suspended(task)[source]

If runnable, task is marked as suspended, not runnable, and it will no longer be ran by reactor. It’s still registered, so reactor’s main loop will not quit, and task can be later easily re-enabled by calling ducky.reactor.Reactor.task_runnable().

class ducky.reactor.RunInIntervalTask(ticks, fn, *args, **kwargs)[source]

Bases: ducky.interfaces.IReactorTask

This task will run its callback every ticks iterations of reactor’s main loop.

Parameters:
  • ticks (int) – number of main loop iterations between two callback calls.
  • args – arguments for callback.
  • kwargs – keyword arguments for callback.
run()[source]
class ducky.reactor.SelectTask(machine, fds, *args, **kwargs)[source]

Bases: ducky.interfaces.IReactorTask

Private task, serving as a single point where select syscall is being executed. When a subsystem is interested in IO on a file descriptor, such file descriptor should be set as non-blocking, and then registered with reactor - it’s not viable to place select calls everywhere in different drivers. This task takes list of registered file descriptors, checks for possible IO oportunities, and fires callbacks accordingly.

Parameters:
  • machine (ducky.machine.Machine) – VM this task (and reactor) belongs to.
  • fds (dict) – dictionary, where keys are descriptors, and values are lists of their callbacks.
add_fd(fd, on_read=None, on_write=None, on_error=None)[source]

Register file descriptor with reactor. File descriptor will be checked for read/write/error posibilities, and appropriate callbacks will be fired.

No arguments are passed to callbacks.

Parameters:
  • fd (int) – file descriptor.
  • on_read – function that will be called when file descriptor is available for reading.
  • on_write – function that will be called when file descriptor is available for write.
  • on_error – function that will be called when error state raised on file descriptor.
remove_fd(fd)[source]

Unregister file descriptor. It will no longer be checked by its main loop.

Parameters:fd (int) – previously registered file descriptor.
run()[source]