blob: 01cd1ced6a5cd63f6397af7a95a39dbeb3e24239 [file] [log] [blame]
Michael Scott90e778d2019-08-07 08:01:00 -07001/** @file
2 * @brief Modem context helper driver
3 *
4 * A modem context driver allowing application to handle all
5 * aspects of received protocol data.
6 */
7
8/*
9 * Copyright (c) 2019 Foundries.io
10 *
11 * SPDX-License-Identifier: Apache-2.0
12 */
13
Gerard Marull-Paretasfb60aab2022-05-06 10:25:46 +020014#include <zephyr/logging/log.h>
Michael Scott90e778d2019-08-07 08:01:00 -070015LOG_MODULE_REGISTER(modem_context, CONFIG_MODEM_LOG_LEVEL);
16
Gerard Marull-Paretasfb60aab2022-05-06 10:25:46 +020017#include <zephyr/kernel.h>
Michael Scott90e778d2019-08-07 08:01:00 -070018
19#include "modem_context.h"
20
21static struct modem_context *contexts[CONFIG_MODEM_CONTEXT_MAX_NUM];
22
Sjors Hettinga7f9b4d82021-09-14 09:57:54 +020023int modem_context_sprint_ip_addr(const struct sockaddr *addr, char *buf, size_t buf_size)
Michael Scott90e778d2019-08-07 08:01:00 -070024{
Sjors Hettinga7f9b4d82021-09-14 09:57:54 +020025 static const char unknown_str[] = "unk";
Michael Scott90e778d2019-08-07 08:01:00 -070026
27 if (addr->sa_family == AF_INET6) {
Sjors Hettinga7f9b4d82021-09-14 09:57:54 +020028 if (buf_size < NET_IPV6_ADDR_LEN) {
29 return -ENOMEM;
30 }
31
32 if (net_addr_ntop(AF_INET6, &net_sin6(addr)->sin6_addr,
33 buf, buf_size) == NULL) {
34 return -ENOMEM;
35 }
36 return 0;
Michael Scott90e778d2019-08-07 08:01:00 -070037 }
38
39 if (addr->sa_family == AF_INET) {
Sjors Hettinga7f9b4d82021-09-14 09:57:54 +020040 if (buf_size < NET_IPV4_ADDR_LEN) {
41 return -ENOMEM;
42 }
43 if (net_addr_ntop(AF_INET, &net_sin(addr)->sin_addr,
44 buf, buf_size) == NULL) {
45 return -ENOMEM;
46 }
47 return 0;
Michael Scott90e778d2019-08-07 08:01:00 -070048 }
49
50 LOG_ERR("Unknown IP address family:%d", addr->sa_family);
Sjors Hettinga7f9b4d82021-09-14 09:57:54 +020051
52 if (buf_size < sizeof(unknown_str)) {
53 return -ENOMEM;
54 }
55 strcpy(buf, unknown_str);
56 return 0;
Michael Scott90e778d2019-08-07 08:01:00 -070057}
58
Kumar Galaa1b77fd2020-05-27 11:26:57 -050059int modem_context_get_addr_port(const struct sockaddr *addr, uint16_t *port)
Michael Scott90e778d2019-08-07 08:01:00 -070060{
61 if (!addr || !port) {
62 return -EINVAL;
63 }
64
65 if (addr->sa_family == AF_INET6) {
66 *port = ntohs(net_sin6(addr)->sin6_port);
67 return 0;
68 } else if (addr->sa_family == AF_INET) {
69 *port = ntohs(net_sin(addr)->sin_port);
70 return 0;
71 }
72
73 return -EPROTONOSUPPORT;
74}
75
76/**
77 * @brief Finds modem context which owns the iface device.
78 *
Benjamin Cabédb53c3f2023-07-13 14:18:49 +020079 * @param dev: device used by the modem iface.
Michael Scott90e778d2019-08-07 08:01:00 -070080 *
81 * @retval Modem context or NULL.
82 */
Tomasz Bursztykae18fcbb2020-04-30 20:33:38 +020083struct modem_context *modem_context_from_iface_dev(const struct device *dev)
Michael Scott90e778d2019-08-07 08:01:00 -070084{
85 int i;
86
87 for (i = 0; i < ARRAY_SIZE(contexts); i++) {
88 if (contexts[i] && contexts[i]->iface.dev == dev) {
89 return contexts[i];
90 }
91 }
92
93 return NULL;
94}
95
96/**
97 * @brief Assign a modem context if there is free space.
98 *
99 * @note Amount of stored modem contexts is determined by
100 * CONFIG_MODEM_CONTEXT_MAX_NUM.
101 *
Benjamin Cabédb53c3f2023-07-13 14:18:49 +0200102 * @param ctx: modem context to persist.
Michael Scott90e778d2019-08-07 08:01:00 -0700103 *
104 * @retval 0 if ok, < 0 if error.
105 */
106static int modem_context_get(struct modem_context *ctx)
107{
108 int i;
109
110 for (i = 0; i < ARRAY_SIZE(contexts); i++) {
111 if (!contexts[i]) {
112 contexts[i] = ctx;
113 return 0;
114 }
115 }
116
117 return -ENOMEM;
118}
119
120struct modem_context *modem_context_from_id(int id)
121{
122 if (id >= 0 && id < ARRAY_SIZE(contexts)) {
123 return contexts[id];
124 } else {
125 return NULL;
126 }
127}
128
129int modem_context_register(struct modem_context *ctx)
130{
Michael Scott90e778d2019-08-07 08:01:00 -0700131 if (!ctx) {
132 return -EINVAL;
133 }
134
Marcin Niestrojec6026c2022-05-13 19:22:13 +0200135 return modem_context_get(ctx);
Michael Scott90e778d2019-08-07 08:01:00 -0700136}