1 /*
2  * Copyright (c) 2023 Bjarki Arge Andreasen
3  * Copyright (c) 2023 Lucas Denefle
4  *
5  * SPDX-License-Identifier: Apache-2.0
6  */
7 
8 /**
9  * @file drivers/cellular.h
10  * @brief Public cellular network API
11  */
12 
13 #ifndef ZEPHYR_INCLUDE_DRIVERS_CELLULAR_H_
14 #define ZEPHYR_INCLUDE_DRIVERS_CELLULAR_H_
15 
16 /**
17  * @brief Cellular interface
18  * @defgroup cellular_interface Cellular Interface
19  * @ingroup io_interfaces
20  * @{
21  */
22 
23 #include <zephyr/types.h>
24 #include <zephyr/device.h>
25 #include <errno.h>
26 
27 #ifdef __cplusplus
28 extern "C" {
29 #endif
30 
31 /** Cellular access technologies */
32 enum cellular_access_technology {
33 	CELLULAR_ACCESS_TECHNOLOGY_GSM = 0,
34 	CELLULAR_ACCESS_TECHNOLOGY_GPRS,
35 	CELLULAR_ACCESS_TECHNOLOGY_UMTS,
36 	CELLULAR_ACCESS_TECHNOLOGY_EDGE,
37 	CELLULAR_ACCESS_TECHNOLOGY_LTE,
38 	CELLULAR_ACCESS_TECHNOLOGY_LTE_CAT_M1,
39 	CELLULAR_ACCESS_TECHNOLOGY_LTE_CAT_M2,
40 	CELLULAR_ACCESS_TECHNOLOGY_NB_IOT,
41 };
42 
43 /** Cellular network structure */
44 struct cellular_network {
45 	/** Cellular access technology */
46 	enum cellular_access_technology technology;
47 	/**
48 	 * List of bands, as defined by the specified cellular access technology,
49 	 * to enables. All supported bands are enabled if none are provided.
50 	 */
51 	uint16_t *bands;
52 	/** Size of bands */
53 	uint16_t size;
54 };
55 
56 /** Cellular signal type */
57 enum cellular_signal_type {
58 	CELLULAR_SIGNAL_RSSI,
59 	CELLULAR_SIGNAL_RSRP,
60 	CELLULAR_SIGNAL_RSRQ,
61 };
62 
63 /** Cellular modem info type */
64 enum cellular_modem_info_type {
65 	/** International Mobile Equipment Identity */
66 	CELLULAR_MODEM_INFO_IMEI,
67 	/** Modem model ID */
68 	CELLULAR_MODEM_INFO_MODEL_ID,
69 	/** Modem manufacturer */
70 	CELLULAR_MODEM_INFO_MANUFACTURER,
71 	/** Modem fw version */
72 	CELLULAR_MODEM_INFO_FW_VERSION,
73 	/** International Mobile Subscriber Identity */
74 	CELLULAR_MODEM_INFO_SIM_IMSI,
75 	/** Integrated Circuit Card Identification Number (SIM) */
76 	CELLULAR_MODEM_INFO_SIM_ICCID,
77 };
78 
79 /** API for configuring networks */
80 typedef int (*cellular_api_configure_networks)(const struct device *dev,
81 					       const struct cellular_network *networks,
82 					       uint8_t size);
83 
84 /** API for getting supported networks */
85 typedef int (*cellular_api_get_supported_networks)(const struct device *dev,
86 						   const struct cellular_network **networks,
87 						   uint8_t *size);
88 
89 /** API for getting network signal strength */
90 typedef int (*cellular_api_get_signal)(const struct device *dev,
91 				       const enum cellular_signal_type type, int16_t *value);
92 
93 /** API for getting modem information */
94 typedef int (*cellular_api_get_modem_info)(const struct device *dev,
95 					   const enum cellular_modem_info_type type,
96 					   char *info, size_t size);
97 
98 /** Cellular driver API */
99 __subsystem struct cellular_driver_api {
100 	cellular_api_configure_networks configure_networks;
101 	cellular_api_get_supported_networks get_supported_networks;
102 	cellular_api_get_signal get_signal;
103 	cellular_api_get_modem_info get_modem_info;
104 };
105 
106 /**
107  * @brief Configure cellular networks for the device
108  *
109  * @details Cellular network devices support at least one cellular access technology.
110  * Each cellular access technology defines a set of bands, of which the cellular device
111  * will support all or a subset of.
112  *
113  * The cellular device can only use one cellular network technology at a time. It must
114  * exclusively use the cellular network configurations provided, and will prioritize
115  * the cellular network configurations in the order they are provided in case there are
116  * multiple (the first cellular network configuration has the highest priority).
117  *
118  * @param dev Cellular network device instance.
119  * @param networks List of cellular network configurations to apply.
120  * @param size Size of list of cellular network configurations.
121  *
122  * @retval 0 if successful.
123  * @retval -EINVAL if any provided cellular network configuration is invalid or unsupported.
124  * @retval -ENOTSUP if API is not supported by cellular network device.
125  * @retval Negative errno-code otherwise.
126  */
cellular_configure_networks(const struct device * dev,const struct cellular_network * networks,uint8_t size)127 static inline int cellular_configure_networks(const struct device *dev,
128 					      const struct cellular_network *networks, uint8_t size)
129 {
130 	const struct cellular_driver_api *api = (const struct cellular_driver_api *)dev->api;
131 
132 	if (api->configure_networks == NULL) {
133 		return -ENOSYS;
134 	}
135 
136 	return api->configure_networks(dev, networks, size);
137 }
138 
139 /**
140  * @brief Get supported cellular networks for the device
141  *
142  * @param dev Cellular network device instance
143  * @param networks Pointer to list of supported cellular network configurations.
144  * @param size Size of list of cellular network configurations.
145  *
146  * @retval 0 if successful.
147  * @retval -ENOTSUP if API is not supported by cellular network device.
148  * @retval Negative errno-code otherwise.
149  */
cellular_get_supported_networks(const struct device * dev,const struct cellular_network ** networks,uint8_t * size)150 static inline int cellular_get_supported_networks(const struct device *dev,
151 						  const struct cellular_network **networks,
152 						  uint8_t *size)
153 {
154 	const struct cellular_driver_api *api = (const struct cellular_driver_api *)dev->api;
155 
156 	if (api->get_supported_networks == NULL) {
157 		return -ENOSYS;
158 	}
159 
160 	return api->get_supported_networks(dev, networks, size);
161 }
162 
163 /**
164  * @brief Get signal for the device
165  *
166  * @param dev Cellular network device instance
167  * @param type Type of the signal information requested
168  * @param value Signal strength destination (one of RSSI, RSRP, RSRQ)
169  *
170  * @retval 0 if successful.
171  * @retval -ENOTSUP if API is not supported by cellular network device.
172  * @retval -ENODATA if device is not in a state where signal can be polled
173  * @retval Negative errno-code otherwise.
174  */
cellular_get_signal(const struct device * dev,const enum cellular_signal_type type,int16_t * value)175 static inline int cellular_get_signal(const struct device *dev,
176 				      const enum cellular_signal_type type, int16_t *value)
177 {
178 	const struct cellular_driver_api *api = (const struct cellular_driver_api *)dev->api;
179 
180 	if (api->get_signal == NULL) {
181 		return -ENOSYS;
182 	}
183 
184 	return api->get_signal(dev, type, value);
185 }
186 
187 /**
188  * @brief Get modem info for the device
189  *
190  * @param dev Cellular network device instance
191  * @param type Type of the modem info requested
192  * @param info Info string destination
193  * @param size Info string size
194  *
195  * @retval 0 if successful.
196  * @retval -ENOTSUP if API is not supported by cellular network device.
197  * @retval -ENODATA if modem does not provide info requested
198  * @retval Negative errno-code from chat module otherwise.
199  */
cellular_get_modem_info(const struct device * dev,const enum cellular_modem_info_type type,char * info,size_t size)200 static inline int cellular_get_modem_info(const struct device *dev,
201 					  const enum cellular_modem_info_type type, char *info,
202 					  size_t size)
203 {
204 	const struct cellular_driver_api *api = (const struct cellular_driver_api *)dev->api;
205 
206 	if (api->get_modem_info == NULL) {
207 		return -ENOSYS;
208 	}
209 
210 	return api->get_modem_info(dev, type, info, size);
211 }
212 
213 #ifdef __cplusplus
214 }
215 #endif
216 
217 /**
218  * @}
219  */
220 
221 #endif /* ZEPHYR_INCLUDE_DRIVERS_CELLULAR_H_ */
222