1 /*
2  *  Copyright (c) 2016, The OpenThread Authors.
3  *  All rights reserved.
4  *
5  *  Redistribution and use in source and binary forms, with or without
6  *  modification, are permitted provided that the following conditions are met:
7  *  1. Redistributions of source code must retain the above copyright
8  *     notice, this list of conditions and the following disclaimer.
9  *  2. Redistributions in binary form must reproduce the above copyright
10  *     notice, this list of conditions and the following disclaimer in the
11  *     documentation and/or other materials provided with the distribution.
12  *  3. Neither the name of the copyright holder nor the
13  *     names of its contributors may be used to endorse or promote products
14  *     derived from this software without specific prior written permission.
15  *
16  *  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17  *  AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18  *  IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19  *  ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
20  *  LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21  *  CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22  *  SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
23  *  INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
24  *  CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
25  *  ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26  *  POSSIBILITY OF SUCH DAMAGE.
27  */
28 
29 /**
30  * @file
31  * @brief
32  *  This file defines the OpenThread UDP API.
33  *
34  */
35 
36 #ifndef OPENTHREAD_UDP_H_
37 #define OPENTHREAD_UDP_H_
38 
39 #include <openthread/ip6.h>
40 #include <openthread/message.h>
41 
42 #ifdef __cplusplus
43 extern "C" {
44 #endif
45 
46 /**
47  * @addtogroup api-udp
48  *
49  * @brief
50  *   This module includes functions that control UDP communication.
51  *
52  * @{
53  *
54  */
55 
56 /**
57  * This callback allows OpenThread to provide specific handlers for certain UDP messages.
58  *
59  * @retval  true    The message is handled by this receiver and should not be further processed.
60  * @retval  false   The message is not handled by this receiver.
61  *
62  */
63 typedef bool (*otUdpHandler)(void *aContext, const otMessage *aMessage, const otMessageInfo *aMessageInfo);
64 
65 /**
66  * Represents a UDP receiver.
67  *
68  */
69 typedef struct otUdpReceiver
70 {
71     struct otUdpReceiver *mNext;    ///< A pointer to the next UDP receiver (internal use only).
72     otUdpHandler          mHandler; ///< A function pointer to the receiver callback.
73     void                 *mContext; ///< A pointer to application-specific context.
74 } otUdpReceiver;
75 
76 /**
77  * Adds a UDP receiver.
78  *
79  * @param[in]   aInstance       A pointer to an OpenThread instance.
80  * @param[in]   aUdpReceiver    A pointer to the UDP receiver.
81  *
82  * @retval  OT_ERROR_NONE       The receiver is successfully added.
83  * @retval  OT_ERROR_ALREADY    The UDP receiver was already added.
84  *
85  */
86 otError otUdpAddReceiver(otInstance *aInstance, otUdpReceiver *aUdpReceiver);
87 
88 /**
89  * Removes a UDP receiver.
90  *
91  * @param[in]   aInstance       A pointer to an OpenThread instance.
92  * @param[in]   aUdpReceiver    A pointer to the UDP receiver.
93  *
94  * @retval  OT_ERROR_NONE       The receiver is successfully removed.
95  * @retval  OT_ERROR_NOT_FOUND  The UDP receiver was not added.
96  *
97  */
98 otError otUdpRemoveReceiver(otInstance *aInstance, otUdpReceiver *aUdpReceiver);
99 
100 /**
101  * Sends a UDP message without socket.
102  *
103  * @param[in]  aInstance     A pointer to an OpenThread instance.
104  * @param[in]  aMessage      A pointer to a message without UDP header.
105  * @param[in]  aMessageInfo  A pointer to a message info associated with @p aMessage.
106  *
107  * @retval OT_ERROR_NONE     Successfully enqueued the message into an output interface.
108  * @retval OT_ERROR_NO_BUFS  Insufficient available buffer to add the IPv6 headers.
109  *
110  */
111 otError otUdpSendDatagram(otInstance *aInstance, otMessage *aMessage, otMessageInfo *aMessageInfo);
112 
113 /**
114  * This callback allows OpenThread to inform the application of a received UDP message.
115  *
116  */
117 typedef void (*otUdpReceive)(void *aContext, otMessage *aMessage, const otMessageInfo *aMessageInfo);
118 
119 /**
120  * Represents a UDP socket.
121  *
122  */
123 typedef struct otUdpSocket
124 {
125     otSockAddr          mSockName; ///< The local IPv6 socket address.
126     otSockAddr          mPeerName; ///< The peer IPv6 socket address.
127     otUdpReceive        mHandler;  ///< A function pointer to the application callback.
128     void               *mContext;  ///< A pointer to application-specific context.
129     void               *mHandle;   ///< A handle to platform's UDP.
130     struct otUdpSocket *mNext;     ///< A pointer to the next UDP socket (internal use only).
131 } otUdpSocket;
132 
133 /**
134  * Defines the OpenThread network interface identifiers.
135  *
136  */
137 typedef enum otNetifIdentifier
138 {
139     OT_NETIF_UNSPECIFIED = 0, ///< Unspecified network interface.
140     OT_NETIF_THREAD,          ///< The Thread interface.
141     OT_NETIF_BACKBONE,        ///< The Backbone interface.
142 } otNetifIdentifier;
143 
144 /**
145  * Allocate a new message buffer for sending a UDP message.
146  *
147  * @note If @p aSettings is 'NULL', the link layer security is enabled and the message priority is set to
148  * OT_MESSAGE_PRIORITY_NORMAL by default.
149  *
150  * @param[in]  aInstance  A pointer to an OpenThread instance.
151  * @param[in]  aSettings  A pointer to the message settings or NULL to use default settings.
152  *
153  * @returns A pointer to the message buffer or NULL if no message buffers are available or parameters are invalid.
154  *
155  * @sa otMessageFree
156  *
157  */
158 otMessage *otUdpNewMessage(otInstance *aInstance, const otMessageSettings *aSettings);
159 
160 /**
161  * Open a UDP/IPv6 socket.
162  *
163  * @param[in]  aInstance  A pointer to an OpenThread instance.
164  * @param[in]  aSocket    A pointer to a UDP socket structure.
165  * @param[in]  aCallback  A pointer to the application callback function.
166  * @param[in]  aContext   A pointer to application-specific context.
167  *
168  * @retval OT_ERROR_NONE    Successfully opened the socket.
169  * @retval OT_ERROR_FAILED  Failed to open the socket.
170  *
171  */
172 otError otUdpOpen(otInstance *aInstance, otUdpSocket *aSocket, otUdpReceive aCallback, void *aContext);
173 
174 /**
175  * Check if a UDP socket is open.
176  *
177  * @param[in]  aInstance  A pointer to an OpenThread instance.
178  * @param[in]  aSocket    A pointer to a UDP socket structure.
179  *
180  * @returns Whether the UDP socket is open.
181  *
182  */
183 bool otUdpIsOpen(otInstance *aInstance, const otUdpSocket *aSocket);
184 
185 /**
186  * Close a UDP/IPv6 socket.
187  *
188  * @param[in]  aInstance  A pointer to an OpenThread instance.
189  * @param[in]  aSocket    A pointer to a UDP socket structure.
190  *
191  * @retval OT_ERROR_NONE   Successfully closed the socket.
192  * @retval OT_ERROR_FAILED Failed to close UDP Socket.
193  *
194  */
195 otError otUdpClose(otInstance *aInstance, otUdpSocket *aSocket);
196 
197 /**
198  * Bind a UDP/IPv6 socket.
199  *
200  * @param[in]  aInstance  A pointer to an OpenThread instance.
201  * @param[in]  aSocket    A pointer to a UDP socket structure.
202  * @param[in]  aSockName  A pointer to an IPv6 socket address structure.
203  * @param[in]  aNetif     The network interface to bind.
204  *
205  * @retval OT_ERROR_NONE   Bind operation was successful.
206  * @retval OT_ERROR_FAILED Failed to bind UDP socket.
207  *
208  */
209 otError otUdpBind(otInstance *aInstance, otUdpSocket *aSocket, const otSockAddr *aSockName, otNetifIdentifier aNetif);
210 
211 /**
212  * Connect a UDP/IPv6 socket.
213  *
214  * @param[in]  aInstance  A pointer to an OpenThread instance.
215  * @param[in]  aSocket    A pointer to a UDP socket structure.
216  * @param[in]  aSockName  A pointer to an IPv6 socket address structure.
217  *
218  * @retval OT_ERROR_NONE   Connect operation was successful.
219  * @retval OT_ERROR_FAILED Failed to connect UDP socket.
220  *
221  */
222 otError otUdpConnect(otInstance *aInstance, otUdpSocket *aSocket, const otSockAddr *aSockName);
223 
224 /**
225  * Send a UDP/IPv6 message.
226  *
227  * @param[in]  aInstance     A pointer to an OpenThread instance.
228  * @param[in]  aSocket       A pointer to a UDP socket structure.
229  * @param[in]  aMessage      A pointer to a message buffer.
230  * @param[in]  aMessageInfo  A pointer to a message info structure.
231  *
232  * If the return value is OT_ERROR_NONE, OpenThread takes ownership of @p aMessage, and the caller should no longer
233  * reference @p aMessage. If the return value is not OT_ERROR_NONE, the caller retains ownership of @p aMessage,
234  * including freeing @p aMessage if the message buffer is no longer needed.
235  *
236  * @retval OT_ERROR_NONE           The message is successfully scheduled for sending.
237  * @retval OT_ERROR_INVALID_ARGS   Invalid arguments are given.
238  * @retval OT_ERROR_NO_BUFS        Insufficient available buffer to add the UDP and IPv6 headers.
239  *
240  */
241 otError otUdpSend(otInstance *aInstance, otUdpSocket *aSocket, otMessage *aMessage, const otMessageInfo *aMessageInfo);
242 
243 /**
244  * Gets the head of linked list of UDP Sockets.
245  *
246  * @param[in]  aInstance  A pointer to an OpenThread instance.
247  *
248  * @returns A pointer to the head of UDP Socket linked list.
249  *
250  */
251 otUdpSocket *otUdpGetSockets(otInstance *aInstance);
252 
253 /**
254  * @}
255  *
256  */
257 
258 /**
259  * @addtogroup api-udp-forward
260  *
261  * @brief
262  *   This module includes functions for UDP forward feature.
263  *
264  *   The functions in this module are available when udp-forward feature (`OPENTHREAD_CONFIG_UDP_FORWARD_ENABLE`) is
265  *   enabled.
266  *
267  * @{
268  *
269  */
270 
271 /**
272  * Pointer delivers the UDP packet to host and host should send the packet through its own network stack.
273  *
274  * @param[in]  aMessage   A pointer to the UDP Message.
275  * @param[in]  aPeerPort  The destination UDP port.
276  * @param[in]  aPeerAddr  A pointer to the destination IPv6 address.
277  * @param[in]  aSockPort  The source UDP port.
278  * @param[in]  aContext   A pointer to application-specific context.
279  *
280  */
281 typedef void (*otUdpForwarder)(otMessage    *aMessage,
282                                uint16_t      aPeerPort,
283                                otIp6Address *aPeerAddr,
284                                uint16_t      aSockPort,
285                                void         *aContext);
286 
287 /**
288  * Set UDP forward callback to deliver UDP packets to host.
289  *
290  * @param[in]  aInstance            A pointer to an OpenThread instance.
291  * @param[in]  aForwarder           A pointer to a function called to forward UDP packet to host.
292  * @param[in]  aContext             A pointer to application-specific context.
293  *
294  */
295 void otUdpForwardSetForwarder(otInstance *aInstance, otUdpForwarder aForwarder, void *aContext);
296 
297 /**
298  * Handle a UDP packet received from host.
299  *
300  * @param[in]  aInstance            A pointer to an OpenThread instance.
301  * @param[in]  aMessage             A pointer to the UDP Message.
302  * @param[in]  aPeerPort            The source UDP port.
303  * @param[in]  aPeerAddr            A pointer to the source address.
304  * @param[in]  aSockPort            The destination UDP port.
305  *
306  * @warning No matter the call success or fail, the message is freed.
307  *
308  */
309 void otUdpForwardReceive(otInstance         *aInstance,
310                          otMessage          *aMessage,
311                          uint16_t            aPeerPort,
312                          const otIp6Address *aPeerAddr,
313                          uint16_t            aSockPort);
314 
315 /**
316  * Determines if the given UDP port is exclusively opened by OpenThread API.
317  *
318  * @param[in]  aInstance            A pointer to an OpenThread instance.
319  * @param[in]  port                 UDP port number to verify.
320  *
321  * @retval true    The port is being used exclusively by OpenThread.
322  * @retval false   The port is not used by any of the OpenThread API or is shared (e.g. is Backbone socket).
323  *
324  */
325 bool otUdpIsPortInUse(otInstance *aInstance, uint16_t port);
326 
327 /**
328  * @}
329  *
330  */
331 
332 #ifdef __cplusplus
333 } // extern "C"
334 #endif
335 
336 #endif // OPENTHREAD_UDP_H_
337