1
0
mirror of https://github.com/RIOT-OS/RIOT.git synced 2024-12-29 04:50:03 +01:00

pkg/wakaama/client_connection: cleanup

Use URI parser and common resource access functions.
This commit is contained in:
Leandro Lanzieri 2021-03-12 18:54:23 +01:00
parent e0896afddc
commit 327da03314
No known key found for this signature in database
GPG Key ID: F4E9A721761C7593
3 changed files with 56 additions and 154 deletions

View File

@ -2,6 +2,7 @@ USEMODULE += wakaama_core wakaama_core_coap13 wakaama_client
# include contrib code (platform adaption and client implementation) # include contrib code (platform adaption and client implementation)
USEMODULE += wakaama_contrib USEMODULE += wakaama_contrib
USEMODULE += uri_parser
# this allows us to include our own objects, implemented in the 'objects' # this allows us to include our own objects, implemented in the 'objects'
# folder, by adding 'wakaama_objects_<objectName>' modules # folder, by adding 'wakaama_objects_<objectName>' modules

View File

@ -41,16 +41,18 @@
#include <stddef.h> #include <stddef.h>
#include "kernel_defines.h" #include "kernel_defines.h"
#include "net/netif.h" #include "net/netif.h"
#include "uri_parser.h"
#include "liblwm2m.h" #include "liblwm2m.h"
#include "lwm2m_client.h" #include "lwm2m_client.h"
#include "lwm2m_client_config.h" #include "lwm2m_client_config.h"
#include "lwm2m_client_connection.h" #include "lwm2m_client_connection.h"
#include "objects/common.h"
#define ENABLE_DEBUG 0 #define ENABLE_DEBUG 0
#include "debug.h" #include "debug.h"
#define URI_LENGTH 256 #define MAX_URI_LENGTH 256
/** /**
* @brief Creates a new connection object based on the security instance * @brief Creates a new connection object based on the security instance
@ -61,22 +63,8 @@
* *
* @return Pointer to the new connection * @return Pointer to the new connection
*/ */
static lwm2m_client_connection_t *_connection_create(int instance_id, static lwm2m_client_connection_t *_connection_create(uint16_t sec_obj_inst_id,
lwm2m_client_data_t *client_data); lwm2m_client_data_t *client_data);
/**
* @brief Gets the URI from an @p instance_id of a @p obj security object
*
* @param[in] obj security object
* @param[in] instance_id ID number of the instance of security object
* @param[out] uri_buffer buffer to place the URI
* @param[in] buffer_size size of @p uri_buffer
*
* @return Pointer to the URI in success
* @return NULL otherwise
*/
static char *_get_uri_from_security_obj(lwm2m_object_t *obj, int instance_id,
char *uri_buffer, int buffer_size);
/** /**
* @brief Sends data with a specified connection @p conn * @brief Sends data with a specified connection @p conn
@ -93,27 +81,6 @@ static int _connection_send(lwm2m_client_connection_t *conn, uint8_t *buffer,
size_t buffer_size, size_t buffer_size,
lwm2m_client_data_t *client_data); lwm2m_client_data_t *client_data);
/**
* @brief Parses the schema of a given URI and sets the default port for the
* found valid schema
* @param[in] uri URI string to parse
* @param[out] port will point to the default port string
* @param[in] instance_id instance ID of the connection
*
* @return pointer to the character after the schema, if found
* @return NULL if no valid schema found
*/
static char *_parse_schema(char *uri, char **port, int instance_id);
/**
* @brief Parses the host and the port part after the schema
*
* @param[in, out] host pointer to the beginning of the host
* @param[out] port pointer to store the position of the port
* @param[in] default_port default port
*/
static void _parse_host_and_port(char **host, char **port, char *default_port);
/** /**
* @brief Tries to find an interface in the host string. If not, it will check * @brief Tries to find an interface in the host string. If not, it will check
* if there only exists one interface, and will use it * if there only exists one interface, and will use it
@ -127,25 +94,11 @@ static netif_t *_get_interface(char *host);
void *lwm2m_connect_server(uint16_t sec_obj_inst_id, void *user_data) void *lwm2m_connect_server(uint16_t sec_obj_inst_id, void *user_data)
{ {
lwm2m_client_data_t *client_data = (lwm2m_client_data_t *)user_data; lwm2m_client_data_t *client_data = (lwm2m_client_data_t *)user_data;
lwm2m_client_connection_t *new_conn = NULL; lwm2m_client_connection_t *new_conn;
/* get the security object list */ DEBUG("[lwm2m_connect_server] Connecting to server in security instance %d\n", sec_obj_inst_id);
lwm2m_object_t *security_objects = (lwm2m_object_t *)LWM2M_LIST_FIND(
client_data->lwm2m_ctx->objectList,
LWM2M_SECURITY_OBJECT_ID);
if (!security_objects) {
DEBUG("[lwm2m_connect_server] Could not find sec object\n");
return NULL;
}
/* get the security object instance */ new_conn = _connection_create(sec_obj_inst_id, client_data);
lwm2m_list_t *instance = LWM2M_LIST_FIND(security_objects, sec_obj_inst_id);
if (instance == NULL) {
DEBUG("[lwm2m_connect_server] Could not find sec object instance\n");
return NULL;
}
new_conn = _connection_create(instance->id, client_data);
if (new_conn) { if (new_conn) {
DEBUG("[lwm2m_connect_server] Connection created\n"); DEBUG("[lwm2m_connect_server] Connection created\n");
/* if the connections list is empty this is the first node, if not /* if the connections list is empty this is the first node, if not
@ -176,7 +129,7 @@ void lwm2m_close_connection(void *sessionH, void *user_data)
else { else {
lwm2m_client_connection_t *prev = client_data->conn_list; lwm2m_client_connection_t *prev = client_data->conn_list;
while(prev != NULL && prev->next != conn) { while (prev != NULL && prev->next != conn) {
prev = prev->next; prev = prev->next;
} }
if (prev != NULL) { if (prev != NULL) {
@ -232,7 +185,7 @@ lwm2m_client_connection_t *lwm2m_client_connection_find(
DEBUG("Conn list is null!"); DEBUG("Conn list is null!");
} }
while(conn != NULL) { while (conn != NULL) {
ipv6_addr_to_str(ip, (ipv6_addr_t *)&conn->remote.addr.ipv6, ip_len); ipv6_addr_to_str(ip, (ipv6_addr_t *)&conn->remote.addr.ipv6, ip_len);
DEBUG("Comparing to [%s]:%d\n", ip, conn->remote.port); DEBUG("Comparing to [%s]:%d\n", ip, conn->remote.port);
if ((conn->remote.port == remote->port) && if ((conn->remote.port == remote->port) &&
@ -267,51 +220,6 @@ static int _connection_send(lwm2m_client_connection_t *conn, uint8_t *buffer,
return 0; return 0;
} }
static char *_parse_schema(char *uri, char **port, int instance_id)
{
char *host = NULL;
if (!uri) {
DEBUG("[_parse_schema] Could not get URI of instance\n");
goto out;
}
/* parse the URI in the form "coaps://[host]:port" */
if (!strncmp(uri, SCHEME_COAPS, sizeof(SCHEME_COAPS) - 1)) {
host = uri + sizeof(SCHEME_COAPS) - 1;
}
else if (!strncmp(uri, SCHEME_COAP, sizeof(SCHEME_COAP) - 1)) {
host = uri + sizeof(SCHEME_COAP) - 1;
}
*port = (IS_ACTIVE(CONFIG_LWM2M_BOOTSTRAP) && !instance_id) ?
CONFIG_LWM2M_BSSERVER_PORT : CONFIG_LWM2M_STANDARD_PORT;
out:
return host;
}
static void _parse_host_and_port(char **host, char **port, char *default_port)
{
char *_port = NULL;
char *pos = *host;
if (pos[0] == '[') {
(*host)++;
pos = strrchr(pos, ']');
}
_port = strrchr(pos, ':');
if (!_port) {
*pos = '\0';
DEBUG("[_parse_port] No port specified, using default\n");
_port = default_port;
}
else {
*(_port - 1) = '\0';
_port++;
}
*port = _port;
}
static netif_t *_get_interface(char *host) static netif_t *_get_interface(char *host)
{ {
netif_t *netif = NULL; netif_t *netif = NULL;
@ -338,41 +246,60 @@ static netif_t *_get_interface(char *host)
return netif; return netif;
} }
static lwm2m_client_connection_t *_connection_create(int instance_id, static lwm2m_client_connection_t *_connection_create(uint16_t sec_obj_inst_id,
lwm2m_client_data_t *client_data) lwm2m_client_data_t *client_data)
{ {
lwm2m_client_connection_t *conn = NULL; lwm2m_client_connection_t *conn = NULL;
char *default_port; char uri[MAX_URI_LENGTH];
char *host;
char *port; char *port;
char *uri; bool is_bootstrap;
char uri_buf[URI_LENGTH + 1];
memset(uri_buf, 0, sizeof(uri_buf));
DEBUG("Creating connection\n"); DEBUG("Creating connection\n");
/* get the list of security objects */ /* prepare Server URI query */
lwm2m_object_t *security_objects = (lwm2m_object_t *)LWM2M_LIST_FIND( lwm2m_uri_t resource_uri = {
client_data->lwm2m_ctx->objectList, .objectId = LWM2M_SECURITY_URI_ID,
LWM2M_SECURITY_OBJECT_ID); .instanceId = sec_obj_inst_id,
if (!security_objects) { .resourceId = LWM2M_SECURITY_URI_ID,
DEBUG("[_connection_create] Could not find any security object\n"); .flag = LWM2M_URI_FLAG_OBJECT_ID | LWM2M_URI_FLAG_INSTANCE_ID | LWM2M_URI_FLAG_RESOURCE_ID
return NULL; };
int res = lwm2m_get_string(client_data, &resource_uri, uri, ARRAY_SIZE(uri));
if (res < 0) {
DEBUG("[_connection_create] Could not get security instance URI\n");
goto out;
} }
/* get the URI from the security object instance */ uri_parser_result_t parsed_uri;
uri = _get_uri_from_security_obj(security_objects, instance_id, res = uri_parser_process_string(&parsed_uri, uri);
uri_buf, sizeof(uri_buf) - 1);
host = _parse_schema(uri, &default_port, instance_id); if (0 != res || !parsed_uri.host) {
if (!host) {
DEBUG("[_connection_create] Could not parse URI schema\n"); DEBUG("[_connection_create] Could not parse URI schema\n");
goto free_out; goto out;
} }
_parse_host_and_port(&host, &port, default_port); resource_uri.resourceId = LWM2M_SECURITY_BOOTSTRAP_ID;
DEBUG("[_connection_create] Creating connection to Host: %s, Port: %s\n", res = lwm2m_get_bool(client_data, &resource_uri, &is_bootstrap);
host, port); if (res < 0) {
DEBUG("[_connection_create] Could verify if the server is bootstrap\n");
goto out;
}
/* if no port specified, use the default server or BS-server ports */
if (!parsed_uri.port) {
if (is_bootstrap) {
port = CONFIG_LWM2M_BSSERVER_PORT;
}
else {
port = CONFIG_LWM2M_STANDARD_PORT;
}
}
else {
port = parsed_uri.port;
}
DEBUG("[_connection_create] Creating connection to Host: %.*s, Port: %s\n",
parsed_uri.ipv6addr_len, parsed_uri.ipv6addr, port);
/* allocate new connection */ /* allocate new connection */
conn = lwm2m_malloc(sizeof(lwm2m_client_connection_t)); conn = lwm2m_malloc(sizeof(lwm2m_client_connection_t));
@ -387,7 +314,8 @@ static lwm2m_client_connection_t *_connection_create(int instance_id,
conn->remote.netif = SOCK_ADDR_ANY_NETIF; conn->remote.netif = SOCK_ADDR_ANY_NETIF;
conn->remote.port = atoi(port); conn->remote.port = atoi(port);
if (!ipv6_addr_from_str((ipv6_addr_t *)&conn->remote.addr.ipv6, host)) { if (!ipv6_addr_from_buf((ipv6_addr_t *)&conn->remote.addr.ipv6, parsed_uri.ipv6addr,
parsed_uri.ipv6addr_len)) {
DEBUG("[_connection_create] IPv6 address malformed\n"); DEBUG("[_connection_create] IPv6 address malformed\n");
goto free_out; goto free_out;
} }
@ -401,7 +329,7 @@ static lwm2m_client_connection_t *_connection_create(int instance_id,
* if not, check the number of interfaces and default to the first if there * if not, check the number of interfaces and default to the first if there
* is only one defined. */ * is only one defined. */
if (ipv6_addr_is_link_local((ipv6_addr_t *)&conn->remote.addr.ipv6)) { if (ipv6_addr_is_link_local((ipv6_addr_t *)&conn->remote.addr.ipv6)) {
netif_t *netif = _get_interface(host); netif_t *netif = _get_interface(parsed_uri.host);
if (netif == NULL) { if (netif == NULL) {
goto free_out; goto free_out;
} }
@ -423,29 +351,3 @@ free_out:
out: out:
return conn; return conn;
} }
static char *_get_uri_from_security_obj(lwm2m_object_t *obj, int instance_id,
char *uri_buffer, int buffer_size)
{
int size = 1;
char *res = NULL;
/* allocate a data instance */
lwm2m_data_t *data = lwm2m_data_new(size);
/* get the uri from the security object */
data->id = 0;
obj->readFunc(instance_id, &size, &data, obj);
if (data != NULL && data->type == LWM2M_TYPE_STRING &&
data->value.asBuffer.length > 0) {
if ((size_t)buffer_size > data->value.asBuffer.length) {
strncpy(uri_buffer, (char *)data->value.asBuffer.buffer,
data->value.asBuffer.length);
res = uri_buffer;
}
}
lwm2m_data_free(size, data);
return res;
}

View File

@ -23,7 +23,6 @@
* @author Leandro Lanzieri <leandro.lanzieri@haw-hamburg.de> * @author Leandro Lanzieri <leandro.lanzieri@haw-hamburg.de>
*/ */
#ifndef LWM2M_CLIENT_CONFIG_H #ifndef LWM2M_CLIENT_CONFIG_H
#define LWM2M_CLIENT_CONFIG_H #define LWM2M_CLIENT_CONFIG_H