AT: Better failure handling and removed wrong unlock
[hayes-ril.git] / at.h
1 /*
2  * This file is part of hayes-ril.
3  *
4  * Copyright (C) 2012 Paul Kocialkowski <contact@paulk.fr>
5  *
6  * Parts of this code are based on htcgeneric-ril, reference-ril:
7  * Copyright 2006-2011, htcgeneric-ril contributors
8  * Copyright 2006, The Android Open Source Project
9  *
10  * Licensed under the Apache License, Version 2.0 (the "License");
11  * you may not use this file except in compliance with the License.
12  * You may obtain a copy of the License at
13  *
14  *     http://www.apache.org/licenses/LICENSE-2.0
15  *
16  * Unless required by applicable law or agreed to in writing, software
17  * distributed under the License is distributed on an "AS IS" BASIS,
18  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
19  * See the License for the specific language governing permissions and
20  * limitations under the License.
21  */
22
23 #include <telephony/ril.h>
24
25 #ifndef _HAYES_RIL_AT_H_
26 #define _HAYES_RIL_AT_H_
27
28 /*
29  * Defines
30  */
31
32 #define AT_RESPONSES_QUEUE_LOCK() pthread_mutex_lock(&(at_handling.responses_queue.queue_mutex));
33 #define AT_RESPONSES_QUEUE_UNLOCK() pthread_mutex_unlock(&(at_handling.responses_queue.queue_mutex));
34 #define AT_RESPONSES_LOCK() pthread_mutex_lock(&(at_handling.responses_queue.mutex));
35 #define AT_RESPONSES_UNLOCK() pthread_mutex_unlock(&(at_handling.responses_queue.mutex));
36 #define AT_REQUESTS_LOCK() pthread_mutex_lock(&(at_handling.requests_queue.mutex));
37 #define AT_REQUESTS_UNLOCK() pthread_mutex_unlock(&(at_handling.requests_queue.mutex));
38 #define AT_SYNC_QUEUE_LOCK() pthread_mutex_lock(&(at_handling.sync_requests_queue.queue_mutex));
39 #define AT_SYNC_QUEUE_UNLOCK() pthread_mutex_unlock(&(at_handling.sync_requests_queue.queue_mutex));
40 #define AT_SYNC_LOCK() pthread_mutex_lock(&(at_handling.sync_requests_queue.mutex));
41 #define AT_SYNC_UNLOCK() pthread_mutex_unlock(&(at_handling.sync_requests_queue.mutex));
42 #define AT_ASYNC_LOCK() pthread_mutex_lock(&(at_handling.async_requests_queue.mutex));
43 #define AT_ASYNC_UNLOCK() pthread_mutex_unlock(&(at_handling.async_requests_queue.mutex));
44
45 #define AT_PARSE_SINGLE_QUOTE   (1 << 0)
46 #define AT_PARSE_DOUBLE_QUOTE   (1 << 1)
47
48 /*
49  * Variables structures
50  */
51
52 struct at_response {
53         char *command;
54
55         char **data;
56         int data_count;
57
58         int status;
59         char *error;
60 };
61
62 struct at_request {
63         char *command;
64         char *data;
65
66         int status;
67         char *error;
68 };
69
70 enum {
71         AT_STATUS_UNDEF,
72         AT_STATUS_OK,
73         AT_STATUS_CONNECT,
74         AT_STATUS_ERROR,
75         AT_STATUS_CME_ERROR,
76         AT_STATUS_INTERNAL_ERROR,
77 };
78
79 enum {
80         AT_CME_ERROR_PHONE_FAILURE = 0,
81         AT_CME_ERROR_PHONE_NO_CONNECTION,
82         AT_CME_ERROR_PHONE_LINK_RESERVED,
83         AT_CME_ERROR_OPERATION_NOT_ALLOWED,
84         AT_CME_ERROR_OPERATION_NOT_SUPPORTED,
85         AT_CME_ERROR_PH_SIM_PIN_REQD,
86         AT_CME_ERROR_PH_FSIM_PIN_REQD,
87         AT_CME_ERROR_PH_FSIM_PUK_REQD,
88         AT_CME_ERROR_SIM_NOT_INSERTED=10,
89         AT_CME_ERROR_SIM_PIN_REQD,
90         AT_CME_ERROR_SIM_PUK_REQD,
91         AT_CME_ERROR_SIM_FAILURE,
92         AT_CME_ERROR_SIM_BUSY,
93         AT_CME_ERROR_SIM_WRONG,
94         AT_CME_ERROR_INCORRECT_PASSWORD,
95         AT_CME_ERROR_SIM_PIN2_REQD,
96         AT_CME_ERROR_SIM_PUK2_REQD,
97         AT_CME_ERROR_MEMORY_FULL=20,
98         AT_CME_ERROR_INVALID_INDEX,
99         AT_CME_ERROR_NOT_FOUND,
100         AT_CME_ERROR_MEMORY_FAILURE,
101         AT_CME_ERROR_TEXT_STRING_TOO_LONG,
102         AT_CME_ERROR_INVALID_CHARS_IN_TEXT,
103         AT_CME_ERROR_DIAL_STRING_TOO_LONG,
104         AT_CME_ERROR_INVALID_CHARS_IN_DIAL,
105         AT_CME_ERROR_NO_NETWORK_SERVICE=30,
106         AT_CME_ERROR_NETWORK_TIMEOUT,
107         AT_CME_ERROR_NETWORK_NOT_ALLOWED,
108         AT_CME_ERROR_NETWORK_PERS_PIN_REQD=40,
109         AT_CME_ERROR_NETWORK_PERS_PUK_REQD,
110         AT_CME_ERROR_NETWORK_SUBSET_PERS_PIN_REQD,
111         AT_CME_ERROR_NETWORK_SUBSET_PERS_PUK_REQD,
112         AT_CME_ERROR_PROVIDER_PERS_PIN_REQD,
113         AT_CME_ERROR_PROVIDER_PERS_PUK_REQD,
114         AT_CME_ERROR_CORP_PERS_PIN_REQD,
115         AT_CME_ERROR_CORP_PERS_PUK_REQD,
116         AT_CME_ERROR_PH_SIM_PUK_REQD,
117         AT_CME_ERROR_UNKNOWN_ERROR=100,
118         AT_CME_ERROR_ILLEGAL_MS=103,
119         AT_CME_ERROR_ILLEGAL_ME=106,
120         AT_CME_ERROR_GPRS_NOT_ALLOWED,
121         AT_CME_ERROR_PLMN_NOT_ALLOWED=111,
122         AT_CME_ERROR_LOCATION_NOT_ALLOWED,
123         AT_CME_ERROR_ROAMING_NOT_ALLOWED,
124         AT_CME_ERROR_TEMPORARY_NOT_ALLOWED=126,
125         AT_CME_ERROR_SERVICE_OPTION_NOT_SUPPORTED=132,
126         AT_CME_ERROR_SERVICE_OPTION_NOT_SUBSCRIBED,
127         AT_CME_ERROR_SERVICE_OPTION_OUT_OF_ORDER,
128         AT_CME_ERROR_UNSPECIFIED_GPRS_ERROR=148,
129         AT_CME_ERROR_PDP_AUTHENTICATION_FAILED,
130         AT_CME_ERROR_INVALID_MOBILE_CLASS,
131         AT_CME_ERROR_OPERATION_TEMP_NOT_ALLOWED=256,
132         AT_CME_ERROR_CALL_BARRED,
133         AT_CME_ERROR_PHONE_BUSY,
134         AT_CME_ERROR_USER_ABORT,
135         AT_CME_ERROR_INVALID_DIAL_STRING,
136         AT_CME_ERROR_SS_NOT_EXECUTED,
137         AT_CME_ERROR_SIM_BLOCKED,
138         AT_CME_ERROR_INVALID_BLOCK,
139         AT_CME_ERROR_SIM_POWERED_DOWN=772
140 };
141
142 enum {
143         AT_RESPONSE_WAITING,
144         AT_RESPONSE_SENT,
145         AT_RESPONSE_UNHANDELD_REASON_DATA,
146         AT_RESPONSE_UNHANDELD_REASON_STATUS,
147         AT_RESPONSE_HANDLED_OK,
148         AT_RESPONSE_HANDLED_ERROR,
149         AT_RESPONSE_SENT_FREEZED,
150         AT_RESPONSE_UNFREEZE,
151         AT_RESPONSE_GARBAGE,
152 };
153
154 enum {
155         AT_FREEZE_OFF,
156         AT_FREEZE_ON,
157         AT_FREEZE_SEND,
158         AT_FREEZE_RESPAWN,
159 };
160
161 typedef int (*at_async_request_cb)(struct at_response *response, void *data, RIL_Token t);
162
163 struct at_sync_request {
164         int handled;
165
166         struct at_request *request;
167         struct at_response *response;
168
169         char *command;
170 };
171
172 struct at_async_request {
173         int handled;
174
175         struct at_request *request;
176         struct at_response *response;
177
178         char *command;
179         void *data;
180         RIL_Token token;
181         at_async_request_cb func;
182 };
183
184 struct at_responses_queue {
185         struct at_response **responses;
186         int responses_count;
187
188         pthread_mutex_t queue_mutex;
189         pthread_mutex_t mutex;
190 };
191
192 struct at_requests_queue {
193         struct at_request **requests;
194         int requests_count;
195
196         pthread_mutex_t mutex;
197 };
198
199 struct at_sync_requests_queue {
200         struct at_sync_request **sync_requests;
201         int sync_requests_count;
202
203         pthread_mutex_t queue_mutex;
204         pthread_mutex_t mutex;
205 };
206
207 struct at_async_requests_queue {
208         struct at_async_request **async_requests;
209         int async_requests_count;
210
211         pthread_mutex_t mutex;
212 };
213
214 struct at_handling {
215         int freeze;
216
217         struct at_responses_queue responses_queue;
218         struct at_requests_queue requests_queue;
219
220         struct at_sync_requests_queue sync_requests_queue;
221         struct at_async_requests_queue async_requests_queue;
222 };
223
224 enum {
225         AT_RESPONSE_DATA_NUMERIC,
226         AT_RESPONSE_DATA_STRING,
227 };
228
229 union at_response_data_value {
230         int n;
231         char *s;
232 };
233
234 struct at_response_data {
235         union at_response_data_value value;
236         int type;
237 };
238
239 /*
240  * Functions
241  */
242
243 // Utilities
244 int at_strings_compare(char *major, char *minor);
245 int at_commands_compare(char *major, char *minor);
246 void at_string_clean(char *string, int length);
247 int at_status_error(int status);
248
249 // Responses structures processing
250 int at_responses_process(struct at_response ***responses_p, char *data, int length);
251 void at_response_free(struct at_response *response);
252
253 // Handling
254 void at_handling_init(void);
255
256 // Responses queue
257 void at_responses_queue_unlock(void);
258 int at_response_queue(struct at_response *response);
259 struct at_response *at_response_dequeue(void);
260
261 // Async
262 int at_async_response_dequeue(struct at_response *response);
263
264 // Sync
265 int at_sync_response_dequeue(struct at_response *response);
266
267 // Request
268 int at_request_send(struct at_request *request);
269 struct at_request *at_request_create(char *command, char *data);
270 void at_request_free(struct at_request *request);
271 int at_request_send_async(struct at_request *request, void *data, RIL_Token token, at_async_request_cb func);
272 struct at_response *at_request_send_sync(struct at_request *request);
273
274 // Freeze
275 void at_freeze_set(int freeze);
276 int at_freeze_get(void);
277 int at_freeze_start(void);
278 int at_freeze_stop(void);
279 int at_freeze_send(void);
280 int at_freeze_respawn(void);
281
282 // Send
283 int at_send_next_request(void);
284 struct at_response *at_send_sync(char *command, char *data);
285 int at_send_expect_to_func(char *command, char *data, void *async_data, RIL_Token token, at_async_request_cb func);
286 int at_send_expect_status(char *command, char *data);
287 int at_send_noresp(char *command, char *data);
288 struct at_response *at_send_command(char *command);
289 struct at_response *at_send(char *command, char *data);
290
291 #endif