]>
git.proxmox.com Git - mirror_frr.git/blob - lib/frr_zmq.h
1 // SPDX-License-Identifier: GPL-2.0-or-later
3 * libzebra ZeroMQ bindings
4 * Copyright (C) 2015 David Lamparter
17 /* linking/packaging note: this is a separate library that needs to be
18 * linked into any daemon/library/module that wishes to use its
19 * functionality. The purpose of this is to encapsulate the libzmq
20 * dependency and not make libfrr/FRR itself depend on libzmq.
22 * libfrrzmq should be put in LDFLAGS/LIBADD *before* either libfrr or
23 * libzmq, and both of these should always be listed, e.g.
24 * foo_LDFLAGS = libfrrzmq.la libfrr.la $(ZEROMQ_LIBS)
27 /* callback integration */
34 void (*cb_msg
)(void *arg
, void *zmqsock
);
35 void (*cb_part
)(void *arg
, void *zmqsock
, zmq_msg_t
*msg
,
37 void (*cb_error
)(void *arg
, void *zmqsock
);
44 bool in_cb
; /* This context is in a read or write callback. */
52 * this is mostly here as a convenience, it has IPv6 enabled but nothing
53 * else is tied to it; you can use a separate context without problems
55 extern void *frrzmq_context
;
57 extern void frrzmq_init(void);
58 extern void frrzmq_finish(void);
60 #define _xref_zmq_a(type, f, d, call) \
62 static const struct xref_eventsched _xref __attribute__( \
64 .xref = XREF_INIT(XREFT_EVENTSCHED, NULL, __func__), \
67 .event_type = EVENT_##type, \
69 XREF_LINK(_xref.xref); \
73 /* core event registration, one of these 2 macros should be used */
74 #define frrzmq_event_add_read_msg(m, f, e, a, z, d) \
75 _xref_zmq_a(READ, f, d, \
76 _frrzmq_event_add_read(&_xref, m, f, NULL, e, a, z, d))
78 #define frrzmq_event_add_read_part(m, f, e, a, z, d) \
79 _xref_zmq_a(READ, f, d, \
80 _frrzmq_event_add_read(&_xref, m, NULL, f, e, a, z, d))
82 #define frrzmq_event_add_write_msg(m, f, e, a, z, d) \
83 _xref_zmq_a(WRITE, f, d, \
84 _frrzmq_event_add_write(&_xref, m, f, e, a, z, d))
89 /* Set up a POLLIN or POLLOUT notification to be called from the libfrr main
90 * loop. This has the following properties:
92 * - since ZeroMQ works with edge triggered notifications, it will loop and
93 * dispatch as many events as ZeroMQ has pending at the time libfrr calls
95 * - due to this looping (which means it non-single-issue), the callback is
96 * also persistent. Do _NOT_ re-register the event inside of your
98 * - either msgfunc or partfunc will be called (only one can be specified)
99 * - msgfunc is called once for each incoming message
100 * - if partfunc is specified, the message is read and partfunc is called
101 * for each ZeroMQ multi-part subpart. Note that you can't send replies
102 * before all parts have been read because that violates the ZeroMQ FSM.
103 * - write version doesn't allow for partial callback, you must handle the
104 * whole message (all parts) in msgfunc callback
105 * - you can safely cancel the callback from within itself
106 * - installing a callback will check for pending events (ZMQ_EVENTS) and
107 * may schedule the event to run as soon as libfrr is back in its main
111 _frrzmq_event_add_read(const struct xref_eventsched
*xref
,
112 struct event_loop
*master
,
113 void (*msgfunc
)(void *arg
, void *zmqsock
),
114 void (*partfunc
)(void *arg
, void *zmqsock
,
115 zmq_msg_t
*msg
, unsigned partnum
),
116 void (*errfunc
)(void *arg
, void *zmqsock
), void *arg
,
117 void *zmqsock
, struct frrzmq_cb
**cb
);
118 extern int _frrzmq_event_add_write(const struct xref_eventsched
*xref
,
119 struct event_loop
*master
,
120 void (*msgfunc
)(void *arg
, void *zmqsock
),
121 void (*errfunc
)(void *arg
, void *zmqsock
),
122 void *arg
, void *zmqsock
,
123 struct frrzmq_cb
**cb
);
125 extern void frrzmq_thread_cancel(struct frrzmq_cb
**cb
, struct cb_core
*core
);
128 * http://api.zeromq.org/4-2:zmq-getsockopt#toc10
130 * As the descriptor is edge triggered, applications must update the state of
131 * ZMQ_EVENTS after each invocation of zmq_send or zmq_recv.To be more explicit:
132 * after calling zmq_send the socket may become readable (and vice versa)
133 * without triggering a read event on the file descriptor.
135 extern void frrzmq_check_events(struct frrzmq_cb
**cbp
, struct cb_core
*core
,
142 #endif /* _FRRZMQ_H */