Add command to get IMEI from the device
[project/uqmi.git] / commands-dms.c
1 #include "qmi-message.h"
2
3 static struct {
4 QmiDmsUimPinId pin_id;
5 char* pin;
6 char* new_pin;
7 char* puk;
8 } dms_req_data;
9
10 static void cmd_dms_get_capabilities_cb(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg)
11 {
12 void *t, *networks;
13 int i;
14 struct qmi_dms_get_capabilities_response res;
15 const char *radio_cap[] = {
16 [QMI_DMS_RADIO_INTERFACE_CDMA20001X] = "cdma1x",
17 [QMI_DMS_RADIO_INTERFACE_EVDO] = "cdma1xevdo",
18 [QMI_DMS_RADIO_INTERFACE_GSM] = "gsm",
19 [QMI_DMS_RADIO_INTERFACE_UMTS] = "umts",
20 [QMI_DMS_RADIO_INTERFACE_LTE] = "lte",
21 };
22 const char *service_cap[] = {
23 [QMI_DMS_DATA_SERVICE_CAPABILITY_NONE] = "none",
24 [QMI_DMS_DATA_SERVICE_CAPABILITY_CS] = "cs",
25 [QMI_DMS_DATA_SERVICE_CAPABILITY_PS] = "ps",
26 [QMI_DMS_DATA_SERVICE_CAPABILITY_SIMULTANEOUS_CS_PS] = "simultaneous_cs_ps",
27 [QMI_DMS_DATA_SERVICE_CAPABILITY_NON_SIMULTANEOUS_CS_PS] = "non_simultaneous_cs_ps",
28 };
29
30 qmi_parse_dms_get_capabilities_response(msg, &res);
31
32 t = blobmsg_open_table(&status, NULL);
33
34 blobmsg_add_u32(&status, "max_tx_channel_rate", (int32_t) res.data.info.max_tx_channel_rate);
35 blobmsg_add_u32(&status, "max_rx_channel_rate", (int32_t) res.data.info.max_rx_channel_rate);
36 if ((int)res.data.info.data_service_capability >= 0 && res.data.info.data_service_capability < ARRAY_SIZE(service_cap))
37 blobmsg_add_string(&status, "data_service", service_cap[res.data.info.data_service_capability]);
38
39 if(res.data.info.sim_capability == QMI_DMS_SIM_CAPABILITY_NOT_SUPPORTED)
40 blobmsg_add_string(&status, "sim", "not supported");
41 else if(res.data.info.sim_capability == QMI_DMS_SIM_CAPABILITY_SUPPORTED)
42 blobmsg_add_string(&status, "sim", "supported");
43
44 networks = blobmsg_open_array(&status, "networks");
45 for (i = 0; i < res.data.info.radio_interface_list_n; i++) {
46 if ((int)res.data.info.radio_interface_list[i] >= 0 && res.data.info.radio_interface_list[i] < ARRAY_SIZE(radio_cap))
47 blobmsg_add_string(&status, NULL, radio_cap[res.data.info.radio_interface_list[i]]);
48 else
49 blobmsg_add_string(&status, NULL, "unknown");
50 }
51 blobmsg_close_array(&status, networks);
52
53 blobmsg_close_table(&status, t);
54 }
55
56 static enum qmi_cmd_result
57 cmd_dms_get_capabilities_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
58 {
59 qmi_set_dms_get_capabilities_request(msg);
60 return QMI_CMD_REQUEST;
61 }
62
63 static const char *get_pin_status(int status)
64 {
65 static const char *pin_status[] = {
66 [QMI_DMS_UIM_PIN_STATUS_NOT_INITIALIZED] = "not_initialized",
67 [QMI_DMS_UIM_PIN_STATUS_ENABLED_NOT_VERIFIED] = "not_verified",
68 [QMI_DMS_UIM_PIN_STATUS_ENABLED_VERIFIED] = "verified",
69 [QMI_DMS_UIM_PIN_STATUS_DISABLED] = "disabled",
70 [QMI_DMS_UIM_PIN_STATUS_BLOCKED] = "blocked",
71 [QMI_DMS_UIM_PIN_STATUS_PERMANENTLY_BLOCKED] = "permanently_blocked",
72 [QMI_DMS_UIM_PIN_STATUS_UNBLOCKED] = "unblocked",
73 [QMI_DMS_UIM_PIN_STATUS_CHANGED] = "changed",
74 };
75 const char *res = "Unknown";
76
77 if (status < ARRAY_SIZE(pin_status) && pin_status[status])
78 res = pin_status[status];
79
80 return res;
81 }
82
83 static void cmd_dms_get_pin_status_cb(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg)
84 {
85 struct qmi_dms_uim_get_pin_status_response res;
86 void *c;
87
88 qmi_parse_dms_uim_get_pin_status_response(msg, &res);
89 c = blobmsg_open_table(&status, NULL);
90 if (res.set.pin1_status) {
91 blobmsg_add_string(&status, "pin1_status", get_pin_status(res.data.pin1_status.current_status));
92 blobmsg_add_u32(&status, "pin1_verify_tries", (int32_t) res.data.pin1_status.verify_retries_left);
93 blobmsg_add_u32(&status, "pin1_unblock_tries", (int32_t) res.data.pin1_status.unblock_retries_left);
94 }
95 if (res.set.pin2_status) {
96 blobmsg_add_string(&status, "pin2_status", get_pin_status(res.data.pin2_status.current_status));
97 blobmsg_add_u32(&status, "pin2_verify_tries", (int32_t) res.data.pin2_status.verify_retries_left);
98 blobmsg_add_u32(&status, "pin2_unblock_tries", (int32_t) res.data.pin2_status.unblock_retries_left);
99 }
100 blobmsg_close_table(&status, c);
101 }
102
103 static enum qmi_cmd_result
104 cmd_dms_get_pin_status_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
105 {
106 qmi_set_dms_uim_get_pin_status_request(msg);
107 return QMI_CMD_REQUEST;
108 }
109
110 #define cmd_dms_verify_pin1_cb no_cb
111 static enum qmi_cmd_result
112 cmd_dms_verify_pin1_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
113 {
114 struct qmi_dms_uim_verify_pin_request data = {
115 QMI_INIT_SEQUENCE(info,
116 .pin_id = QMI_DMS_UIM_PIN_ID_PIN,
117 .pin = arg
118 )
119 };
120 qmi_set_dms_uim_verify_pin_request(msg, &data);
121 return QMI_CMD_REQUEST;
122 }
123
124 #define cmd_dms_verify_pin2_cb no_cb
125 static enum qmi_cmd_result
126 cmd_dms_verify_pin2_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
127 {
128 struct qmi_dms_uim_verify_pin_request data = {
129 QMI_INIT_SEQUENCE(info,
130 .pin_id = QMI_DMS_UIM_PIN_ID_PIN2,
131 .pin = arg
132 )
133 };
134 qmi_set_dms_uim_verify_pin_request(msg, &data);
135 return QMI_CMD_REQUEST;
136 }
137
138 #define cmd_dms_set_pin_cb no_cb
139 static enum qmi_cmd_result
140 cmd_dms_set_pin_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
141 {
142 dms_req_data.pin = arg;
143 return QMI_CMD_DONE;
144 }
145
146 static enum qmi_cmd_result
147 cmd_dms_set_pin_protection_prepare(struct qmi_msg *msg, char *arg)
148 {
149 if (!dms_req_data.pin) {
150 uqmi_add_error("Missing argument");
151 return QMI_CMD_EXIT;
152 }
153
154 int is_enabled;
155 if (strcasecmp(arg, "disabled") == 0)
156 is_enabled = false;
157 else if (strcasecmp(arg, "enabled") == 0)
158 is_enabled = true;
159 else {
160 uqmi_add_error("Invalid value (valid: disabled, enabled)");
161 return QMI_CMD_EXIT;
162 }
163
164 struct qmi_dms_uim_set_pin_protection_request dms_pin_protection_req = {
165 QMI_INIT_SEQUENCE(info,
166 .pin_id = dms_req_data.pin_id
167 ),
168 QMI_INIT_PTR(info.pin, dms_req_data.pin),
169 QMI_INIT_PTR(info.protection_enabled, is_enabled)
170 };
171
172 qmi_set_dms_uim_set_pin_protection_request(msg, &dms_pin_protection_req);
173 return QMI_CMD_REQUEST;
174 }
175
176 #define cmd_dms_set_pin1_protection_cb no_cb
177 static enum qmi_cmd_result
178 cmd_dms_set_pin1_protection_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
179 {
180 dms_req_data.pin_id = QMI_DMS_UIM_PIN_ID_PIN;
181 return cmd_dms_set_pin_protection_prepare(msg, arg);
182 }
183
184 #define cmd_dms_set_pin2_protection_cb no_cb
185 static enum qmi_cmd_result
186 cmd_dms_set_pin2_protection_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
187 {
188 dms_req_data.pin_id = QMI_DMS_UIM_PIN_ID_PIN2;
189 return cmd_dms_set_pin_protection_prepare(msg, arg);
190 }
191
192 static enum qmi_cmd_result
193 cmd_dms_change_pin_prepare(struct qmi_msg *msg, char *arg)
194 {
195 if (!dms_req_data.pin || !dms_req_data.new_pin) {
196 uqmi_add_error("Missing argument");
197 return QMI_CMD_EXIT;
198 }
199
200 struct qmi_dms_uim_change_pin_request dms_change_pin_req = {
201 QMI_INIT_SEQUENCE(info,
202 .pin_id = dms_req_data.pin_id
203 ),
204 QMI_INIT_PTR(info.old_pin, dms_req_data.pin),
205 QMI_INIT_PTR(info.new_pin, dms_req_data.new_pin)
206 };
207
208 qmi_set_dms_uim_change_pin_request(msg, &dms_change_pin_req);
209 return QMI_CMD_REQUEST;
210 }
211
212 #define cmd_dms_change_pin1_cb no_cb
213 static enum qmi_cmd_result
214 cmd_dms_change_pin1_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
215 {
216 dms_req_data.pin_id = QMI_DMS_UIM_PIN_ID_PIN;
217 return cmd_dms_change_pin_prepare(msg, arg);
218 }
219
220 #define cmd_dms_change_pin2_cb no_cb
221 static enum qmi_cmd_result
222 cmd_dms_change_pin2_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
223 {
224 dms_req_data.pin_id = QMI_DMS_UIM_PIN_ID_PIN2;
225 return cmd_dms_change_pin_prepare(msg, arg);
226 }
227
228 #define cmd_dms_set_new_pin_cb no_cb
229 static enum qmi_cmd_result
230 cmd_dms_set_new_pin_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
231 {
232 dms_req_data.new_pin = arg;
233 return QMI_CMD_DONE;
234 }
235
236 #define cmd_dms_set_puk_cb no_cb
237 static enum qmi_cmd_result
238 cmd_dms_set_puk_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
239 {
240 dms_req_data.puk = arg;
241 return QMI_CMD_DONE;
242 }
243
244 #define cmd_dms_unblock_pin1_cb no_cb
245 static enum qmi_cmd_result
246 cmd_dms_unblock_pin1_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
247 {
248 if (!dms_req_data.puk || !dms_req_data.new_pin) {
249 uqmi_add_error("Missing argument");
250 return QMI_CMD_EXIT;
251 }
252
253 struct qmi_dms_uim_unblock_pin_request dms_unlock_pin_req = {
254 QMI_INIT_SEQUENCE(info,
255 .pin_id = QMI_DMS_UIM_PIN_ID_PIN
256 ),
257 QMI_INIT_PTR(info.puk, dms_req_data.puk),
258 QMI_INIT_PTR(info.new_pin, dms_req_data.new_pin)
259 };
260
261 qmi_set_dms_uim_unblock_pin_request(msg, &dms_unlock_pin_req);
262 return QMI_CMD_REQUEST;
263 }
264
265 #define cmd_dms_unblock_pin2_cb no_cb
266 static enum qmi_cmd_result
267 cmd_dms_unblock_pin2_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
268 {
269 if (!dms_req_data.puk || !dms_req_data.new_pin) {
270 uqmi_add_error("Missing argument");
271 return QMI_CMD_EXIT;
272 }
273
274 struct qmi_dms_uim_unblock_pin_request dms_unlock_pin_req = {
275 QMI_INIT_SEQUENCE(info,
276 .pin_id = QMI_DMS_UIM_PIN_ID_PIN2
277 ),
278 QMI_INIT_PTR(info.puk, dms_req_data.puk),
279 QMI_INIT_PTR(info.new_pin, dms_req_data.new_pin)
280 };
281
282 qmi_set_dms_uim_unblock_pin_request(msg, &dms_unlock_pin_req);
283 return QMI_CMD_REQUEST;
284 }
285
286 static void cmd_dms_get_iccid_cb(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg)
287 {
288 struct qmi_dms_uim_get_iccid_response res;
289
290 qmi_parse_dms_uim_get_iccid_response(msg, &res);
291 if (res.data.iccid)
292 blobmsg_add_string(&status, NULL, res.data.iccid);
293 }
294
295 static enum qmi_cmd_result
296 cmd_dms_get_iccid_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
297 {
298 qmi_set_dms_uim_get_iccid_request(msg);
299 return QMI_CMD_REQUEST;
300 }
301
302 static void cmd_dms_get_imsi_cb(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg)
303 {
304 struct qmi_dms_uim_get_imsi_response res;
305
306 qmi_parse_dms_uim_get_imsi_response(msg, &res);
307 if (res.data.imsi)
308 blobmsg_add_string(&status, NULL, res.data.imsi);
309 }
310
311 static enum qmi_cmd_result
312 cmd_dms_get_imsi_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
313 {
314 qmi_set_dms_uim_get_imsi_request(msg);
315 return QMI_CMD_REQUEST;
316 }
317
318 static void cmd_dms_get_msisdn_cb(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg)
319 {
320 struct qmi_dms_get_msisdn_response res;
321
322 qmi_parse_dms_get_msisdn_response(msg, &res);
323 if (res.data.msisdn)
324 blobmsg_add_string(&status, NULL, res.data.msisdn);
325 }
326
327 static enum qmi_cmd_result
328 cmd_dms_get_msisdn_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
329 {
330 qmi_set_dms_get_msisdn_request(msg);
331 return QMI_CMD_REQUEST;
332 }
333
334 static void cmd_dms_get_imei_cb(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg)
335 {
336 struct qmi_dms_get_ids_response res;
337
338 qmi_parse_dms_get_ids_response(msg, &res);
339 if (res.data.imei)
340 blobmsg_add_string(&status, NULL, res.data.imei);
341 }
342
343 static enum qmi_cmd_result
344 cmd_dms_get_imei_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
345 {
346 qmi_set_dms_get_ids_request(msg);
347 return QMI_CMD_REQUEST;
348 }
349
350 #define cmd_dms_reset_cb no_cb
351 static enum qmi_cmd_result
352 cmd_dms_reset_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
353 {
354 qmi_set_dms_reset_request(msg);
355 return QMI_CMD_REQUEST;
356 }
357
358 #define cmd_dms_set_operating_mode_cb no_cb
359 static enum qmi_cmd_result
360 cmd_dms_set_operating_mode_prepare(struct qmi_dev *qmi, struct qmi_request *req, struct qmi_msg *msg, char *arg)
361 {
362 static const char *modes[] = {
363 [QMI_DMS_OPERATING_MODE_ONLINE] = "online",
364 [QMI_DMS_OPERATING_MODE_LOW_POWER] = "low_power",
365 [QMI_DMS_OPERATING_MODE_FACTORY_TEST] = "factory_test",
366 [QMI_DMS_OPERATING_MODE_OFFLINE] = "offline",
367 [QMI_DMS_OPERATING_MODE_RESET] = "reset",
368 [QMI_DMS_OPERATING_MODE_SHUTTING_DOWN] = "shutting_down",
369 [QMI_DMS_OPERATING_MODE_PERSISTENT_LOW_POWER] = "persistent_low_power",
370 [QMI_DMS_OPERATING_MODE_MODE_ONLY_LOW_POWER] = "mode_only_low_power",
371 };
372 static struct qmi_dms_set_operating_mode_request sreq = {
373 QMI_INIT(mode, QMI_DMS_OPERATING_MODE_ONLINE),
374 };
375 int i;
376
377 for (i = 0; i < ARRAY_SIZE(modes); i++) {
378 if (!modes[i])
379 continue;
380
381 if (strcmp(arg, modes[i]) != 0)
382 continue;
383
384 sreq.data.mode = i;
385 qmi_set_dms_set_operating_mode_request(msg, &sreq);
386 return QMI_CMD_REQUEST;
387 }
388
389 return uqmi_add_error("Invalid argument");
390 }