Coverage Report

Created: 2023-06-07 06:06

/src/open62541/arch/eventloop_posix.h
Line
Count
Source (jump to first uncovered line)
1
/* This Source Code Form is subject to the terms of the Mozilla Public
2
 * License, v. 2.0. If a copy of the MPL was not distributed with this
3
 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
4
 *
5
 *    Copyright 2021 (c) Fraunhofer IOSB (Author: Julius Pfrommer)
6
 *    Copyright 2021 (c) Fraunhofer IOSB (Author: Jan Hermes)
7
 */
8
9
#ifndef UA_EVENTLOOP_POSIX_H_
10
#define UA_EVENTLOOP_POSIX_H_
11
12
#include <open62541/config.h>
13
#include <open62541/plugin/eventloop.h>
14
15
#if defined(UA_ARCHITECTURE_POSIX) || defined(UA_ARCHITECTURE_WIN32)
16
17
#include "common/ua_timer.h"
18
#include "open62541_queue.h"
19
20
/* epoll_pwait returns bogus data with the tc compiler */
21
#if defined(__linux__) && !defined(__TINYC__)
22
# define UA_HAVE_EPOLL
23
# include <sys/epoll.h>
24
#endif
25
26
0
#define UA_MAXBACKLOG 100
27
0
#define UA_MAXHOSTNAME_LENGTH 256
28
0
#define UA_MAXPORTSTR_LENGTH 6
29
30
#ifndef MSG_NOSIGNAL
31
#define MSG_NOSIGNAL 0
32
#endif
33
34
#ifndef MSG_DONTWAIT
35
#define MSG_DONTWAIT 0
36
#endif
37
38
_UA_BEGIN_DECLS
39
40
/* POSIX events are based on sockets / file descriptors. The EventSources can
41
 * register their fd in the EventLoop so that they are considered by the
42
 * EventLoop dropping into "poll" to wait for events. */
43
44
/* TODO: Move the macro-forest from /arch/<arch>/ua_architecture.h */
45
46
0
#define UA_FD UA_SOCKET
47
0
#define UA_INVALID_FD UA_INVALID_SOCKET
48
49
struct UA_RegisteredFD;
50
typedef struct UA_RegisteredFD UA_RegisteredFD;
51
52
/* Bitmask to be used for the UA_FDCallback event argument */
53
0
#define UA_FDEVENT_IN 1
54
0
#define UA_FDEVENT_OUT 2
55
0
#define UA_FDEVENT_ERR 4
56
57
typedef void (*UA_FDCallback)(UA_EventSource *es, UA_RegisteredFD *rfd, short event);
58
59
struct UA_RegisteredFD {
60
    UA_DelayedCallback dc; /* Used for async closing. Must be the first member
61
                            * because the rfd is freed by the delayed callback
62
                            * mechanism. */
63
64
    ZIP_ENTRY(UA_RegisteredFD) zipPointers; /* Register FD in the EventSource */
65
    UA_FD fd;
66
    short listenEvents; /* UA_FDEVENT_IN | UA_FDEVENT_OUT*/
67
68
    UA_EventSource *es; /* Backpointer to the EventSource */
69
    UA_FDCallback eventSourceCB;
70
};
71
72
enum ZIP_CMP cmpFD(const UA_FD *a, const UA_FD *b);
73
typedef ZIP_HEAD(UA_FDTree, UA_RegisteredFD) UA_FDTree;
74
ZIP_FUNCTIONS(UA_FDTree, UA_RegisteredFD, zipPointers, UA_FD, fd, cmpFD)
75
76
/* All ConnectionManager in the POSIX EventLoop can be cast to
77
 * UA_ConnectionManagerPOSIX. They carry a sorted tree of their open
78
 * sockets/file-descriptors. */
79
typedef struct {
80
    UA_ConnectionManager cm;
81
82
    /* Reused receive buffer. The size is configured via
83
     * the recv-bufsize parameter.*/
84
    UA_ByteString rxBuffer;
85
86
    /* Sorted tree of the FDs */
87
    size_t fdsSize;
88
    UA_FDTree fds;
89
} UA_POSIXConnectionManager;
90
91
typedef struct {
92
    UA_EventLoop eventLoop;
93
94
    /* Timer */
95
    UA_Timer timer;
96
97
    /* Linked List of Delayed Callbacks */
98
    UA_DelayedCallback *delayedCallbacks;
99
100
    /* Flag determining whether the eventloop is currently within the
101
     * "run" method */
102
    UA_Boolean executing;
103
104
#if defined(UA_HAVE_EPOLL)
105
    UA_FD epollfd;
106
#else
107
    UA_RegisteredFD **fds;
108
    size_t fdsSize;
109
#endif
110
111
#if UA_MULTITHREADING >= 100
112
    UA_Lock elMutex;
113
#endif
114
} UA_EventLoopPOSIX;
115
116
/*
117
 * The following functions differ between epoll and normal select
118
 */
119
120
/* Register to start receiving events */
121
UA_StatusCode
122
UA_EventLoopPOSIX_registerFD(UA_EventLoopPOSIX *el, UA_RegisteredFD *rfd);
123
124
/* Modify the events that the fd listens on */
125
UA_StatusCode
126
UA_EventLoopPOSIX_modifyFD(UA_EventLoopPOSIX *el, UA_RegisteredFD *rfd);
127
128
/* Deregister but do not close the fd. No further events are received. */
129
void
130
UA_EventLoopPOSIX_deregisterFD(UA_EventLoopPOSIX *el, UA_RegisteredFD *rfd);
131
132
UA_StatusCode
133
UA_EventLoopPOSIX_pollFDs(UA_EventLoopPOSIX *el, UA_DateTime listenTimeout);
134
135
/* Helper functions between EventSources */
136
137
UA_StatusCode
138
UA_EventLoopPOSIX_allocateRXBuffer(UA_POSIXConnectionManager *pcm);
139
140
UA_StatusCode
141
UA_EventLoopPOSIX_allocNetworkBuffer(UA_ConnectionManager *cm,
142
                                     uintptr_t connectionId,
143
                                     UA_ByteString *buf,
144
                                     size_t bufSize);
145
146
void
147
UA_EventLoopPOSIX_freeNetworkBuffer(UA_ConnectionManager *cm,
148
                                    uintptr_t connectionId,
149
                                    UA_ByteString *buf);
150
151
/*
152
 * Helper functions to be used across protocols
153
 */
154
155
/* Set the socket non-blocking. If the listen-socket is nonblocking, incoming
156
 * connections inherit this state. */
157
UA_StatusCode
158
UA_EventLoopPOSIX_setNonBlocking(UA_FD sockfd);
159
160
/* Don't have the socket create interrupt signals */
161
UA_StatusCode
162
UA_EventLoopPOSIX_setNoSigPipe(UA_FD sockfd);
163
164
/* Enables sharing of the same listening address on different sockets */
165
UA_StatusCode
166
UA_EventLoopPOSIX_setReusable(UA_FD sockfd);
167
168
_UA_END_DECLS
169
170
#endif /* defined(UA_ARCHITECTURE_POSIX) || defined(UA_ARCHITECTURE_WIN32) */
171
172
#endif /* UA_EVENTLOOP_POSIX_H_ */