mirror of
https://github.com/RIOT-OS/RIOT.git
synced 2025-12-25 06:23:53 +01:00
Merge pull request #5758 from miri64/sock/api/initial
sock: Introduction of new application layer API
This commit is contained in:
commit
526917b8cc
209
sys/include/net/sock.h
Normal file
209
sys/include/net/sock.h
Normal file
@ -0,0 +1,209 @@
|
||||
/*
|
||||
* Copyright (C) 2016 Alexander Aring <aar@pengutronix.de>
|
||||
* Freie Universität Berlin
|
||||
* HAW Hamburg
|
||||
* Kaspar Schleiser <kaspar@schleiser.de>
|
||||
*
|
||||
* This file is subject to the terms and conditions of the GNU Lesser
|
||||
* General Public License v2.1. See the file LICENSE in the top level
|
||||
* directory for more details.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @defgroup net_sock Sock API
|
||||
* @ingroup net
|
||||
* @brief Provides a minimal common API for applications to connect to the
|
||||
* different network stacks
|
||||
*
|
||||
* About
|
||||
* =====
|
||||
*
|
||||
* ~~~~~~~~~~~~~~~~~~~~
|
||||
* +---------------+
|
||||
* | Application |
|
||||
* +---------------+
|
||||
* ^
|
||||
* |
|
||||
* v
|
||||
* sock
|
||||
* ^
|
||||
* |
|
||||
* v
|
||||
* +---------------+
|
||||
* | Network Stack |
|
||||
* +---------------+
|
||||
* ~~~~~~~~~~~~~~~~~~~~
|
||||
*
|
||||
* This module provides a minimal set of functions to establish connections or
|
||||
* send and receives datagrams using different types of communication. Together,
|
||||
* they serve as a common API that connects application- and network stack code.
|
||||
*
|
||||
* Currently the following sock types are defined:
|
||||
*
|
||||
* * @ref sock_ip_t (net/sock/ip.h): raw IP sock
|
||||
* * @ref sock_tcp_t (net/sock/tcp.h): TCP sock
|
||||
* * @ref sock_udp_t (net/sock/udp.h): UDP sock
|
||||
*
|
||||
* Each network stack must implement at least one sock type.
|
||||
*
|
||||
* Note that there might be no relation between the different sock types.
|
||||
* For simplicity and modularity this API doesn't put any restriction of the
|
||||
* actual implementation of the type. For example, one implementation might
|
||||
* choose to have all sock types have a common base class or use the raw IP
|
||||
* sock type to send e.g. UDP packets, while others will keep them
|
||||
* completely separate from each other.
|
||||
*
|
||||
* How To Use
|
||||
* ==========
|
||||
*
|
||||
* A RIOT application uses the functions provided by one or more of the
|
||||
* sock type headers (for example @ref sock_udp), regardless of the
|
||||
* network stack it uses.
|
||||
* The network stack used under the bonnet is specified by including the
|
||||
* appropriate module (for example USEMODULE += gnrc_sock_udp)
|
||||
*
|
||||
* This allows for network stack agnostic code on the application layer.
|
||||
* The application code to establish a connection is always the same, allowing
|
||||
* the network stack underneath to be switched simply by changing the
|
||||
* `USEMODULE` definitions in the application's Makefile.
|
||||
*
|
||||
* @author Alexander Aring <aar@pengutronix.de>
|
||||
* @author Simon Brummer <simon.brummer@haw-hamburg.de>
|
||||
* @author Cenk Gündoğan <mail@cgundogan.de>
|
||||
* @author Peter Kietzmann <peter.kietzmann@haw-hamburg.de>
|
||||
* @author Martine Lenders <m.lenders@fu-berlin.de>
|
||||
* @author Kaspar Schleiser <kaspar@schleiser.de>
|
||||
*
|
||||
* @{
|
||||
*
|
||||
* @file
|
||||
* @brief Common sock API definitions
|
||||
*
|
||||
* @author Martine Lenders <m.lenders@fu-berlin.de>
|
||||
* @author Kaspar Schleiser <kaspar@schleiser.de>
|
||||
*/
|
||||
|
||||
#ifndef NET_SOCK_H_
|
||||
#define NET_SOCK_H_
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#if defined(DOXYGEN)
|
||||
/**
|
||||
* @brief compile flag to activate IPv6 support for sock
|
||||
*/
|
||||
#define SOCK_HAS_IPV6
|
||||
#endif
|
||||
|
||||
/**
|
||||
* @brief Common flags for @ref net_conn
|
||||
* @name net_sock_flags
|
||||
* @{
|
||||
*/
|
||||
#define SOCK_FLAGS_REUSE_EP (0x0001) /**< allow to reuse end point on bind */
|
||||
/** @} */
|
||||
|
||||
|
||||
/**
|
||||
* @brief Special netif ID for "any interface"
|
||||
* @todo Use an equivalent defintion from PR #5511
|
||||
*/
|
||||
#define SOCK_ADDR_ANY_NETIF (0)
|
||||
|
||||
/**
|
||||
* @brief Address to bind to any IPv4 address
|
||||
*/
|
||||
#define SOCK_IPV4_EP_ANY { .family = AF_INET, \
|
||||
.netif = SOCK_ADDR_ANY_NETIF }
|
||||
|
||||
#if defined(SOCK_HAS_IPV6) || defined(DOXYGEN)
|
||||
/**
|
||||
* @brief Address to bind to any IPv6 address
|
||||
*/
|
||||
#define SOCK_IPV6_EP_ANY { .family = AF_INET6, \
|
||||
.netif = SOCK_ADDR_ANY_NETIF }
|
||||
#endif
|
||||
|
||||
/**
|
||||
* @brief Abstract IP end point and end point for a raw IP sock object
|
||||
*/
|
||||
typedef struct {
|
||||
/**
|
||||
* @brief family of sock_ip_ep_t::addr
|
||||
*
|
||||
* @see @ref net_af
|
||||
*/
|
||||
int family;
|
||||
|
||||
union {
|
||||
#if defined(SOCK_HAS_IPV6) || defined(DOXYGEN)
|
||||
/**
|
||||
* @brief IPv6 address mode
|
||||
*
|
||||
* @note only available if @ref SOCK_HAS_IPV6 is defined.
|
||||
*/
|
||||
uint8_t ipv6[16];
|
||||
#endif
|
||||
uint32_t ipv4; /**< IPv4 address mode */
|
||||
} addr; /**< address */
|
||||
|
||||
/**
|
||||
* @brief stack-specific network interface ID
|
||||
*
|
||||
* @todo port to common network interface identifiers in PR #5511.
|
||||
*
|
||||
* Use @ref SOCK_ADDR_ANY_NETIF for any interface.
|
||||
* For reception this is the local interface the message came over,
|
||||
* for transmission, this is the local interface the message should be send
|
||||
* over
|
||||
*/
|
||||
uint16_t netif;
|
||||
} sock_ip_ep_t;
|
||||
|
||||
/**
|
||||
* @brief Common IP-based transport layer end point
|
||||
*/
|
||||
struct _sock_tl_ep {
|
||||
/**
|
||||
* @brief family of sock_ip_ep_t::addr
|
||||
*
|
||||
* @see @ref net_af
|
||||
*/
|
||||
int family;
|
||||
|
||||
union {
|
||||
#if defined(SOCK_HAS_IPV6) || defined(DOXYGEN)
|
||||
/**
|
||||
* @brief IPv6 address mode
|
||||
*
|
||||
* @note only available if @ref SOCK_HAS_IPV6 is defined.
|
||||
*/
|
||||
uint8_t ipv6[16];
|
||||
#endif
|
||||
uint32_t ipv4; /**< IPv4 address mode */
|
||||
} addr; /**< address */
|
||||
|
||||
/**
|
||||
* @brief stack-specific network interface ID
|
||||
*
|
||||
* @todo port to common network interface identifiers in PR #5511.
|
||||
*
|
||||
* Use @ref SOCK_ADDR_ANY_NETIF for any interface.
|
||||
* For reception this is the local interface the message came over,
|
||||
* for transmission, this is the local interface the message should be send
|
||||
* over
|
||||
*/
|
||||
uint16_t netif;
|
||||
uint16_t port; /**< transport layer port */
|
||||
};
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* NET_SOCK_H_ */
|
||||
/** @} */
|
||||
204
sys/include/net/sock/ip.h
Normal file
204
sys/include/net/sock/ip.h
Normal file
@ -0,0 +1,204 @@
|
||||
/*
|
||||
* Copyright (C) 2016 Alexander Aring <aar@pengutronix.de>
|
||||
* Freie Universität Berlin
|
||||
* HAW Hamburg
|
||||
* Kaspar Schleiser <kaspar@schleiser.de>
|
||||
*
|
||||
* This file is subject to the terms and conditions of the GNU Lesser
|
||||
* General Public License v2.1. See the file LICENSE in the top level
|
||||
* directory for more details.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @defgroup net_sock_ip Raw IPv4/IPv6 sock API
|
||||
* @ingroup net_sock
|
||||
* @brief Sock Submodule for raw IPv4/IPv6
|
||||
* @{
|
||||
*
|
||||
* @file
|
||||
* @brief Raw IPv4/IPv6 sock definitions
|
||||
*
|
||||
* @author Alexander Aring <aar@pengutronix.de>
|
||||
* @author Simon Brummer <simon.brummer@haw-hamburg.de>
|
||||
* @author Cenk Gündoğan <mail@cgundogan.de>
|
||||
* @author Peter Kietzmann <peter.kietzmann@haw-hamburg.de>
|
||||
* @author Martine Lenders <m.lenders@fu-berlin.de>
|
||||
* @author Kaspar Schleiser <kaspar@schleiser.de>
|
||||
*/
|
||||
#ifndef NET_SOCK_IP_H_
|
||||
#define NET_SOCK_IP_H_
|
||||
|
||||
#include <assert.h>
|
||||
#include <stdint.h>
|
||||
#include <stdlib.h>
|
||||
#include <sys/types.h>
|
||||
|
||||
#include "net/sock.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/**
|
||||
* @brief Implementation-specific type of a raw IPv4/IPv6 sock object
|
||||
*
|
||||
* `struct sock_ip` needs to be defined by stack-specific `sock_types.h`.
|
||||
*/
|
||||
typedef struct sock_ip sock_ip_t;
|
||||
|
||||
/**
|
||||
* @brief Creates a new raw IPv4/IPv6 sock object
|
||||
*
|
||||
* @pre `(sock != NULL)`
|
||||
*
|
||||
* @param[out] sock The resulting sock object.
|
||||
* @param[in] local Local end point for the sock object.
|
||||
* May be NULL to solicit implicit bind on
|
||||
* @ref sock_ip_send().
|
||||
* sock_ip_ep_t::netif must either be
|
||||
* @ref SOCK_ADDR_ANY_NETIF or equal to sock_ip_ep_t::netif
|
||||
* of @p remote if `remote != NULL`.
|
||||
* @param[in] remote Remote end point for the sock object.
|
||||
* May be `NULL` but then the `remote` parameter of
|
||||
* @ref sock_ip_send() may not be `NULL` or it will always
|
||||
* error with return value -ENOTCONN.
|
||||
* sock_ip_ep_t::port may not be 0 if `remote != NULL`.
|
||||
* sock_ip_ep_t::netif must either be
|
||||
* @ref SOCK_ADDR_ANY_NETIF or equal to sock_ip_ep_t::netif
|
||||
* of @p local if `local != NULL`.
|
||||
* @param[in] proto Protocol to use in the raw IPv4/IPv6 sock object
|
||||
* (the `protocol` header field in IPv4 and the `next_header`
|
||||
* field in IPv6).
|
||||
* @param[in] flags Flags for the sock object. See also @ref net_sock_flags.
|
||||
* May be 0.
|
||||
*
|
||||
* @return 0 on success.
|
||||
* @return -EADDRINUSE, if `local != NULL` and the stack reports that @p local
|
||||
* is already used elsewhere
|
||||
* @return -EAFNOSUPPORT, if `local != NULL` or `remote != NULL` and
|
||||
* sock_ip_ep_t::family of @p local or @p remote is not supported.
|
||||
* @return -EINVAL, if `proto` is not supported or if sock_ip_ep_t::netif of
|
||||
* @p local or @p remote is not a valid interface or contradict each
|
||||
* other (i.e. `(local->netif != remote->netif) &&
|
||||
* ((local->netif != SOCK_ADDR_ANY_NETIF) ||
|
||||
* (remote->netif != SOCK_ADDR_ANY_NETIF))` if neither is `NULL`).
|
||||
* @return -ENOMEM, if the stack can't provide enough resources for `sock` to
|
||||
* be created.
|
||||
* @return -EPROTONOSUPPORT, if `local != NULL` or `remote != NULL` and
|
||||
* proto is not supported by sock_ip_ep_t::family of @p local or @p
|
||||
* remote.
|
||||
*/
|
||||
int sock_ip_create(sock_ip_t *sock, const sock_ip_ep_t *local,
|
||||
const sock_ip_ep_t *remote, uint8_t proto, uint16_t flags);
|
||||
|
||||
/**
|
||||
* @brief Closes a raw IPv4/IPv6 sock object
|
||||
*
|
||||
* @pre `(sock != NULL)`
|
||||
*
|
||||
* @param[in] sock A raw IPv4/IPv6 sock object.
|
||||
*/
|
||||
void sock_ip_close(sock_ip_t *sock);
|
||||
|
||||
/**
|
||||
* @brief Gets the local end point of a raw IPv4/IPv6 sock object
|
||||
*
|
||||
* @pre `(sock != NULL) && (ep != NULL)`
|
||||
*
|
||||
* @param[in] sock A raw IPv4/IPv6 sock object.
|
||||
* @param[out] ep The local end point.
|
||||
*
|
||||
* @return 0 on success.
|
||||
* @return -EADDRNOTAVAIL, when @p sock has no end point bound to it.
|
||||
*/
|
||||
int sock_ip_get_local(sock_ip_t *sock, sock_ip_ep_t *ep);
|
||||
|
||||
/**
|
||||
* @brief Gets the remote end point of a UDP sock object
|
||||
*
|
||||
* @pre `(sock != NULL) && (ep != NULL)`
|
||||
*
|
||||
* @param[in] sock A UDP sock object.
|
||||
* @param[out] ep The remote end point.
|
||||
*
|
||||
* @return 0 on success.
|
||||
* @return -ENOTCONN, when @p sock has no remote end point bound to it.
|
||||
*/
|
||||
int sock_ip_get_remote(sock_ip_t *sock, sock_ip_ep_t *ep);
|
||||
|
||||
/**
|
||||
* @brief Receives a message over IPv4/IPv6 from remote end point
|
||||
*
|
||||
* @pre `(sock != NULL) && (data != NULL) && (max_len > 0)`
|
||||
*
|
||||
* @param[in] sock A raw IPv4/IPv6 sock object.
|
||||
* @param[out] data Pointer where the received data should be stored.
|
||||
* @param[in] max_len Maximum space available at @p data.
|
||||
* If received data exceeds @p max_len the data is
|
||||
* truncated and the remaining data can be retrieved
|
||||
* later on.
|
||||
* @param[in] timeout Timeout for receive in microseconds.
|
||||
* This value can be ignored (no timeout) if the
|
||||
* @ref sys_xtimer module is not present and the stack does
|
||||
* not support timeouts on its own.
|
||||
* May be 0 for no timeout.
|
||||
* @param[out] remote Remote end point of the received data.
|
||||
* May be NULL, if it is not required by the application.
|
||||
*
|
||||
* @note Function blocks if no packet is currently waiting.
|
||||
*
|
||||
* @return The number of bytes received on success.
|
||||
* @return 0, if no received data is available, but everything is in order.
|
||||
* @return -EADDRNOTAVAIL, if local of @p sock is not given.
|
||||
* @return -ENOBUFS, if buffer space is not large enough to store received
|
||||
* data.
|
||||
* @return -ENOMEM, if no memory was available to receive @p data.
|
||||
* @return -EPROTO, if source address of received packet did not equal
|
||||
* the remote of @p sock.
|
||||
* @return -ETIMEDOUT, if @p timeout expired.
|
||||
*/
|
||||
ssize_t sock_ip_recv(sock_ip_t *sock, void *data, size_t max_len,
|
||||
uint32_t timeout, sock_ip_ep_t *remote);
|
||||
|
||||
/**
|
||||
* @brief Sends a message over IPv4/IPv6 to remote end point
|
||||
*
|
||||
* @pre `((sock != NULL || remote != NULL)) && (if (len != 0): (data != NULL))`
|
||||
*
|
||||
* @param[in] sock A raw IPv4/IPv6 sock object. May be NULL.
|
||||
* A sensible local end point should be selected by the
|
||||
* stack in that case.
|
||||
* @param[in] data Pointer where the received data should be stored.
|
||||
* May be `NULL` if `len == 0`.
|
||||
* @param[in] len Maximum space available at @p data.
|
||||
* @param[in] proto Protocol to use in the packet send, in case
|
||||
* `sock == NULL`. If `sock != NULL` this parameter will be
|
||||
* ignored.
|
||||
* @param[in] remote Remote end point for the send data.
|
||||
* May be `NULL`, if @p sock has a remote end point.
|
||||
* sock_ip_ep_t::family may be AF_UNSPEC, if local
|
||||
* end point of @p sock provides this information.
|
||||
*
|
||||
* @note Function blocks until packet is handed to the stack.
|
||||
*
|
||||
* @return The number of bytes send on success.
|
||||
* @return -EAFNOSUPPORT, if `remote != NULL` and sock_ip_ep_t::family of
|
||||
* @p remote is != AF_UNSPEC and not supported.
|
||||
* @return -EHOSTUNREACH, if @p remote or remote end point of @p sock is not
|
||||
* reachable.
|
||||
* @return -ENOMEM, if no memory was available to send @p data.
|
||||
* @return -ENOTCONN, if `remote == NULL`, but @p sock has no remote end point.
|
||||
* @return -EPROTOTYPE, if `sock == NULL` and @p proto is not by
|
||||
* sock_ip_ep_t::family of @p remote.
|
||||
*/
|
||||
ssize_t sock_ip_send(sock_ip_t *sock, const void *data, size_t len,
|
||||
uint8_t proto, const sock_ip_ep_t *remote);
|
||||
|
||||
#include "sock_types.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* NET_SOCK_IP_H_ */
|
||||
/** @} */
|
||||
231
sys/include/net/sock/tcp.h
Normal file
231
sys/include/net/sock/tcp.h
Normal file
@ -0,0 +1,231 @@
|
||||
/*
|
||||
* Copyright (C) 2016 Alexander Aring <aar@pengutronix.de>
|
||||
* Freie Universität Berlin
|
||||
* HAW Hamburg
|
||||
* Kaspar Schleiser <kaspar@schleiser.de>
|
||||
*
|
||||
* This file is subject to the terms and conditions of the GNU Lesser
|
||||
* General Public License v2.1. See the file LICENSE in the top level
|
||||
* directory for more details.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @defgroup net_sock_tcp TCP sock API
|
||||
* @ingroup net_sock
|
||||
* @brief Sock submodule for TCP
|
||||
* @{
|
||||
*
|
||||
* @file
|
||||
* @brief TCP sock definitions
|
||||
*
|
||||
* @author Alexander Aring <aar@pengutronix.de>
|
||||
* @author Simon Brummer <simon.brummer@haw-hamburg.de>
|
||||
* @author Cenk Gündoğan <mail@cgundogan.de>
|
||||
* @author Peter Kietzmann <peter.kietzmann@haw-hamburg.de>
|
||||
* @author Martine Lenders <m.lenders@fu-berlin.de>
|
||||
* @author Kaspar Schleiser <kaspar@schleiser.de>
|
||||
*/
|
||||
#ifndef NET_SOCK_TCP_H_
|
||||
#define NET_SOCK_TCP_H_
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stdlib.h>
|
||||
#include <sys/types.h>
|
||||
|
||||
#include "net/sock.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
typedef struct _sock_tl_ep sock_tcp_ep_t; /**< An end point for a TCP sock object */
|
||||
|
||||
/**
|
||||
* @brief Implementation-specific type of a TCP sock object
|
||||
*
|
||||
* `struct sock_tcp` needs to be defined by stack-specific `sock_types.h`.
|
||||
*/
|
||||
typedef struct sock_tcp sock_tcp_t;
|
||||
|
||||
/**
|
||||
* @brief Implementation-specific type of a TCP listening queue
|
||||
*
|
||||
* `struct sock_tcp_queue` needs to be defined by stack-specific
|
||||
* `sock_types.h`.
|
||||
*/
|
||||
typedef struct sock_tcp_queue sock_tcp_queue_t;
|
||||
|
||||
/**
|
||||
* @brief Establishes a new TCP sock connection
|
||||
*
|
||||
* @pre `sock != NULL`
|
||||
* @pre `remote != NULL`
|
||||
* @pre `local_port != 0`
|
||||
*
|
||||
* @param[out] sock The resulting sock object.
|
||||
* @param[in] remote Remote end point for the sock object.
|
||||
* @param[in] flags Flags for the sock object. See also @ref net_sock_flags.
|
||||
* May be 0.
|
||||
*
|
||||
* @return 0 on success.
|
||||
* @return -EADDRINUSE, if `(flags & SOCK_FLAGS_REUSE_EP) == 0` and
|
||||
* @p local_port is already used elsewhere
|
||||
* @return -EAFNOSUPPORT, if sock_tcp_ep_t::family of @p remote is not
|
||||
* supported.
|
||||
* @return -ECONNREFUSED, if no-one is listening on the @p remote end point.
|
||||
* @return -EINVAL, if sock_tcp_ep_t::netif of @p remote is not a valid
|
||||
* interface.
|
||||
* @return -ENETUNREACH, if network defined by @p remote is not reachable.
|
||||
* @return -ENOMEM, if system was not able to allocate sufficient memory to
|
||||
* establish connection.
|
||||
* @return -EPERM, if connections to @p remote are not permitted on the system
|
||||
* (e.g. by firewall rules).
|
||||
* @return -ETIMEDOUT, if the connection attempt to @p remote timed out.
|
||||
*/
|
||||
int sock_tcp_connect(sock_tcp_t *sock, const sock_tcp_ep_t *remote,
|
||||
uint16_t local_port, uint16_t flags);
|
||||
|
||||
/**
|
||||
* @brief Listen for an incoming connection request on @p local end point
|
||||
*
|
||||
* @param[in] queue The resulting listening queue.
|
||||
* @param[in] remote Local end point to listen on.
|
||||
* @param[in] queue_array Array of sock objects.
|
||||
* @param[in] queue_len Length of @p queue_array.
|
||||
* @param[in] flags Flags for the listening queue. See also
|
||||
* @ref net_sock_flags. May be 0.
|
||||
*
|
||||
* @return 0 on success.
|
||||
* @return -EADDRINUSE, if `(flags & SOCK_FLAGS_REUSE_EP) == 0` and
|
||||
* @p local is already used elsewhere
|
||||
* @return -EAFNOSUPPORT, if sock_tcp_ep_t::family of @p local is not
|
||||
* supported.
|
||||
* @return -EINVAL, if sock_tcp_ep_t::netif of @p local is not a valid
|
||||
* interface.
|
||||
* @return -ENOMEM, if no memory was available to listen on @p queue.
|
||||
*/
|
||||
int sock_tcp_listen(sock_tcp_queue_t *queue, const sock_tcp_ep_t *local,
|
||||
sock_tcp_t[] queue_array, unsigned queue_len,
|
||||
uint16_t flags);
|
||||
|
||||
/**
|
||||
* @brief Disconnects a TCP connection
|
||||
*
|
||||
* @pre `(sock != NULL)`
|
||||
*
|
||||
* @param[in] sock A TCP sock object.
|
||||
*/
|
||||
void sock_tcp_disconnect(sock_tcp_t *sock);
|
||||
|
||||
/**
|
||||
* @brief Stops listening on TCP listening queue
|
||||
*
|
||||
* @param[in] queue A TCP listening queue.
|
||||
*/
|
||||
void sock_tcp_stop_listen(sock_tcp_queue_t *queue);
|
||||
|
||||
/**
|
||||
* @brief Gets the local end point of a TCP sock object
|
||||
*
|
||||
* @pre `(sock != NULL) && (ep != NULL)`
|
||||
*
|
||||
* @param[in] sock A TCP sock object.
|
||||
* @param[out] ep The local end point.
|
||||
*
|
||||
* @return 0 on success.
|
||||
* @return -EADDRNOTAVAIL, when @p sock has no local end point.
|
||||
*/
|
||||
int sock_tcp_get_local(sock_tcp_t *sock, sock_tcp_ep_t *ep);
|
||||
|
||||
/**
|
||||
* @brief Gets the remote end point of a TCP sock object
|
||||
*
|
||||
* @pre `(sock != NULL) && (ep != NULL)`
|
||||
*
|
||||
* @param[in] sock A TCP sock object.
|
||||
* @param[out] ep The remote end point.
|
||||
*
|
||||
* @return 0 on success.
|
||||
* @return -ENOTCONN, when @p sock is not connected to a remote end point.
|
||||
*/
|
||||
int sock_tcp_get_remote(sock_tcp_t *sock, sock_tcp_ep_t *ep);
|
||||
|
||||
/**
|
||||
* @brief Receives and handles TCP connection requests from other peers
|
||||
*
|
||||
* @pre `(queue != NULL) && (sock != NULL)`
|
||||
*
|
||||
* @param[in] sock A TCP listening queue.
|
||||
* @param[out] out_sock A new TCP sock object for the established
|
||||
* sock object.
|
||||
*
|
||||
* @return 0 on success.
|
||||
* @return -ENOMEM, if system was not able to allocate sufficient memory to
|
||||
* establish connection.
|
||||
* @return -EPERM, if connections on local end point of @p queue are not
|
||||
* permitted on this system (e.g. by firewall rules).
|
||||
* @return -ETIMEDOUT, if the operation timed out stack-internally.
|
||||
*/
|
||||
int sock_tcp_accept(sock_tcp_queue_t *queue, sock_tcp_t **sock);
|
||||
|
||||
/**
|
||||
* @brief Reads data from an established TCP stream
|
||||
*
|
||||
* @pre `(sock != NULL) && (data != NULL) && (max_len > 0)`
|
||||
*
|
||||
* @param[in] sock A TCP sock object.
|
||||
* @param[out] data Pointer where the read data should be stored.
|
||||
* @param[in] max_len Maximum space available at @p data.
|
||||
* If read data exceeds @p max_len the data is
|
||||
* truncated and the remaining data can be retrieved
|
||||
* later on.
|
||||
* @param[in] timeout Timeout for receive in microseconds.
|
||||
* This value can be ignored (no timeout) if the
|
||||
* @ref sys_xtimer module is not present and the stack does
|
||||
* not support timeouts on its own.
|
||||
* May be 0 for no timeout.
|
||||
*
|
||||
* @note Function may block.
|
||||
*
|
||||
* @return The number of bytes read on success.
|
||||
* @return 0, if no read data is available, but everything is in order.
|
||||
* @return -EADDRNOTAVAIL, if local of @p sock is not given.
|
||||
* @return -ECONNABORTED, if the connection is aborted while waiting for the
|
||||
* next data.
|
||||
* @return -ECONNRESET, if the connection was forcibly closed by remote end
|
||||
* point of @p sock.
|
||||
* @return -ENOTCONN, when @p sock is not connected to a remote end point.
|
||||
* @return -ETIMEDOUT, if @p timeout expired.
|
||||
*/
|
||||
ssize_t sock_tcp_read(sock_tcp_t *sock, void *data, size_t max_len,
|
||||
uint32_t timeout);
|
||||
|
||||
/**
|
||||
* @brief Writes data to an established TCP stream
|
||||
*
|
||||
* @pre `(sock != NULL) && (data != NULL) && (max > 0)`
|
||||
*
|
||||
* @param[in] sock A TCP sock object.
|
||||
* @param[in] data Pointer to the data to be written to the stream.
|
||||
* @param[in] len Maximum space available at @p data.
|
||||
*
|
||||
* @note Function may block.
|
||||
*
|
||||
* @return The number of bytes written on success.
|
||||
* @return -ECONNABORTED, if the connection is aborted while waiting for the
|
||||
* next data.
|
||||
* @return -ECONNRESET, if the connection was forcibly closed by remote end
|
||||
* point of @p sock.
|
||||
* @return -ENOMEM, if no memory was available to written @p data.
|
||||
* @return -ENOTCONN, if @p sock is not connected to a remote end point.
|
||||
*/
|
||||
ssize_t sock_tcp_write(sock_tcp_t *sock, const void *data, size_t len);
|
||||
|
||||
#include "sock_types.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* NET_SOCK_TCP_H_ */
|
||||
/** @} */
|
||||
205
sys/include/net/sock/udp.h
Normal file
205
sys/include/net/sock/udp.h
Normal file
@ -0,0 +1,205 @@
|
||||
/*
|
||||
* Copyright (C) 2016 Alexander Aring <aar@pengutronix.de>
|
||||
* Freie Universität Berlin
|
||||
* HAW Hamburg
|
||||
* Kaspar Schleiser <kaspar@schleiser.de>
|
||||
*
|
||||
* This file is subject to the terms and conditions of the GNU Lesser
|
||||
* General Public License v2.1. See the file LICENSE in the top level
|
||||
* directory for more details.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @defgroup net_sock_udp UDP sock API
|
||||
* @ingroup net_sock
|
||||
* @brief Sock submodule for UDP
|
||||
* @{
|
||||
*
|
||||
* @file
|
||||
* @brief UDP sock definitions
|
||||
*
|
||||
* @author Alexander Aring <aar@pengutronix.de>
|
||||
* @author Simon Brummer <simon.brummer@haw-hamburg.de>
|
||||
* @author Cenk Gündoğan <mail@cgundogan.de>
|
||||
* @author Peter Kietzmann <peter.kietzmann@haw-hamburg.de>
|
||||
* @author Martine Lenders <m.lenders@fu-berlin.de>
|
||||
* @author Kaspar Schleiser <kaspar@schleiser.de>
|
||||
*/
|
||||
#ifndef NET_SOCK_UDP_H_
|
||||
#define NET_SOCK_UDP_H_
|
||||
|
||||
#include <assert.h>
|
||||
#include <stdint.h>
|
||||
#include <stdlib.h>
|
||||
#include <sys/types.h>
|
||||
|
||||
#include "net/sock.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
typedef struct _sock_tl_ep sock_udp_ep_t; /**< An end point for a UDP sock object */
|
||||
|
||||
/**
|
||||
* @brief Implementation-specific type of a UDP sock object
|
||||
*
|
||||
* `struct sock_udp` needs to be defined by stack-specific `sock_types.h`.
|
||||
*/
|
||||
typedef struct sock_udp sock_udp_t;
|
||||
|
||||
/**
|
||||
* @brief Creates a new UDP sock object
|
||||
*
|
||||
* @pre `(sock != NULL)`
|
||||
* @pre `(local == NULL) || (local->port != 0)`
|
||||
* @pre `(remote == NULL) || (remote->port != 0)`
|
||||
*
|
||||
* @param[out] sock The resulting sock object.
|
||||
* @param[in] local Local end point for the sock object.
|
||||
* May be `NULL` to solicit implicit bind on
|
||||
* @ref sock_udp_send().
|
||||
* sock_udp_ep_t::port may not be 0 if `local != NULL`.
|
||||
* sock_udp_ep_t::netif must either be
|
||||
* @ref SOCK_ADDR_ANY_NETIF or equal to sock_udp_ep_t::netif
|
||||
* of @p remote if `remote != NULL`.
|
||||
* @param[in] remote Remote end point for the sock object.
|
||||
* May be `NULL` but then the `remote` parameter of
|
||||
* @ref sock_udp_send() may not be `NULL` and or it will
|
||||
* always error with return value -ENOTCONN.
|
||||
* sock_udp_ep_t::port may not be 0 if `remote != NULL`.
|
||||
* sock_udp_ep_t::netif must either be
|
||||
* @ref SOCK_ADDR_ANY_NETIF or equal to sock_udp_ep_t::netif
|
||||
* of @p local if `local != NULL`.
|
||||
* @param[in] flags Flags for the sock object. See also @ref net_sock_flags.
|
||||
* May be 0.
|
||||
*
|
||||
* @return 0 on success.
|
||||
* @return -EADDRINUSE, if `local != NULL` and the stack reports that @p local
|
||||
* is already used elsewhere
|
||||
* @return -EAFNOSUPPORT, if `local != NULL` or `remote != NULL` and
|
||||
* sock_udp_ep_t::family of @p local or @p remote is not supported.
|
||||
* @return -EINVAL, if sock_udp_ep_t::netif of @p local or @p remote is not a
|
||||
* valid interface or contradict each other (i.e.
|
||||
* `(local->netif != remote->netif) &&
|
||||
* ((local->netif != SOCK_ADDR_ANY_NETIF) ||
|
||||
* (remote->netif != SOCK_ADDR_ANY_NETIF))` if neither is `NULL`).
|
||||
* @return -ENOMEM, if the stack can't provide enough resources for `sock` to
|
||||
* be created.
|
||||
*/
|
||||
int sock_udp_create(sock_udp_t *sock, const sock_udp_ep_t *local,
|
||||
const sock_udp_ep_t *remote, uint16_t flags);
|
||||
|
||||
/**
|
||||
* @brief Closes a UDP sock object
|
||||
*
|
||||
* @pre `(sock != NULL)`
|
||||
*
|
||||
* @param[in] sock A UDP sock object.
|
||||
*/
|
||||
void sock_udp_close(sock_udp_t *sock);
|
||||
|
||||
/**
|
||||
* @brief Gets the local end point of a UDP sock object
|
||||
*
|
||||
* @pre `(sock != NULL) && (ep != NULL)`
|
||||
*
|
||||
* @param[in] sock A UDP sock object.
|
||||
* @param[out] ep The local end point.
|
||||
*
|
||||
* @return 0 on success.
|
||||
* @return -EADDRNOTAVAIL, when @p sock has no local end point.
|
||||
*/
|
||||
int sock_udp_get_local(sock_udp_t *sock, sock_udp_ep_t *ep);
|
||||
|
||||
/**
|
||||
* @brief Gets the remote end point of a UDP sock object
|
||||
*
|
||||
* @pre `(sock != NULL) && (ep != NULL)`
|
||||
*
|
||||
* @param[in] sock A UDP sock object.
|
||||
* @param[out] ep The remote end point.
|
||||
*
|
||||
* @return 0 on success.
|
||||
* @return -ENOTCONN, when @p sock has no remote end point bound to it.
|
||||
*/
|
||||
int sock_udp_get_remote(sock_udp_t *sock, sock_udp_ep_t *ep);
|
||||
|
||||
/**
|
||||
* @brief Receives a UDP message from a remote end point
|
||||
*
|
||||
* @pre `(sock != NULL) && (data != NULL) && (max_len > 0)`
|
||||
*
|
||||
* @param[in] sock A raw IPv4/IPv6 sock object.
|
||||
* @param[out] data Pointer where the received data should be stored.
|
||||
* @param[in] max_len Maximum space available at @p data.
|
||||
* If received data exceeds @p max_len the data is
|
||||
* truncated and the remaining data can be retrieved
|
||||
* later on.
|
||||
* @param[in] timeout Timeout for receive in microseconds.
|
||||
* This value can be ignored (no timeout) if the
|
||||
* @ref sys_xtimer module is not present and the stack does
|
||||
* not support timeouts on its own.
|
||||
* May be 0 for no timeout.
|
||||
* Must be 0 if @ref sys_xtimer module is not present.
|
||||
* @param[out] remote Remote end point of the received data.
|
||||
* May be `NULL`, if it is not required by the application.
|
||||
*
|
||||
* @note Function blocks if no packet is currently waiting.
|
||||
*
|
||||
* @return The number of bytes received on success.
|
||||
* @return 0, if no received data is available, but everything is in order.
|
||||
* @return -EADDRNOTAVAIL, if local of @p sock is not given.
|
||||
* @return -ENOBUFS, if buffer space is not large enough to store received
|
||||
* data.
|
||||
* @return -ENOMEM, if no memory was available to receive @p data.
|
||||
* @return -EPROTO, if source address of received packet did not equal
|
||||
* the remote of @p sock.
|
||||
* @return -ETIMEDOUT, if @p timeout expired.
|
||||
*/
|
||||
ssize_t sock_udp_recv(sock_udp_t *sock, void *data, size_t max_len,
|
||||
uint32_t timeout, sock_udp_ep_t *remote);
|
||||
|
||||
/**
|
||||
* @brief Sends a UDP message to remote end point
|
||||
*
|
||||
* @pre `((sock != NULL || remote != NULL)) && (if (len != 0): (data != NULL))`
|
||||
*
|
||||
* @param[in] sock A raw IPv4/IPv6 sock object. May be `NULL`.
|
||||
* A sensible local end point should be selected by the
|
||||
* stack in that case.
|
||||
* @param[in] data Pointer where the received data should be stored.
|
||||
* May be `NULL` if `len == 0`.
|
||||
* @param[in] len Maximum space available at @p data.
|
||||
* @param[in] remote Remote end point for the send data.
|
||||
* May be `NULL`, if @p sock has a remote end point.
|
||||
* sock_udp_ep_t::family may be AF_UNSPEC, if local
|
||||
* end point of @p sock provides this information.
|
||||
* sock_udp_ep_t::port may not be 0.
|
||||
*
|
||||
* @note Function blocks until packet is handed to the stack.
|
||||
*
|
||||
* @return The number of bytes sent on success.
|
||||
* @return -EAFNOSUPPORT, if `remote != NULL` and sock_udp_ep_t::family of
|
||||
* @p remote is != AF_UNSPEC and not supported.
|
||||
* @return -EHOSTUNREACH, if @p remote or remote end point of @p sock is not
|
||||
* reachable.
|
||||
* @return -EINVAL, if sock_udp_ep_t::netif of @p remote is not a valid
|
||||
* interface or contradicts the given local interface (i.e.
|
||||
* neither the local end point of `sock` nor remote are assigned to
|
||||
* `SOCK_ADDR_ANY_NETIF` but are nevertheless different.
|
||||
* @return -EINVAL, if sock_udp_ep_t::port of @p remote is 0.
|
||||
* @return -ENOMEM, if no memory was available to send @p data.
|
||||
* @return -ENOTCONN, if `remote == NULL`, but @p sock has no remote end point.
|
||||
*/
|
||||
ssize_t sock_udp_send(sock_udp_t *sock, const void *data, size_t len,
|
||||
const sock_udp_ep_t *remote);
|
||||
|
||||
#include "sock_types.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* NET_SOCK_UDP_H_ */
|
||||
/** @} */
|
||||
Loading…
x
Reference in New Issue
Block a user