46
47
GIsiClient *client;
49
static int decode_read_response(const unsigned char *msg, size_t len,
50
struct ofono_phonebook *pb)
56
static gboolean parse_adn(GIsiSubBlockIter *iter, uint16_t *location,
57
char **name, char **number)
62
if (!g_isi_sb_iter_get_word(iter, location, 4) ||
63
!g_isi_sb_iter_get_byte(iter, &namelen, 6) ||
64
!g_isi_sb_iter_get_byte(iter, &numlen, 7))
67
if (!g_isi_sb_iter_get_alpha_tag(iter, name, namelen * 2, 8))
70
if (!g_isi_sb_iter_get_alpha_tag(iter, number, numlen * 2,
78
static gboolean parse_sne(GIsiSubBlockIter *iter, char **sne)
82
if (!g_isi_sb_iter_get_byte(iter, &len, 6))
85
if (!g_isi_sb_iter_get_alpha_tag(iter, sne, len * 2, 8))
91
static gboolean parse_anr(GIsiSubBlockIter *iter, char **anr)
95
if (!g_isi_sb_iter_get_byte(iter, &len, 6))
98
if (!g_isi_sb_iter_get_alpha_tag(iter, anr, len * 2, 8))
104
static gboolean parse_email(GIsiSubBlockIter *iter, char **email)
108
if (!g_isi_sb_iter_get_byte(iter, &len, 6))
111
if (!g_isi_sb_iter_get_alpha_tag(iter, email, len * 2, 8))
117
static gboolean decode_response(const GIsiMessage *msg, uint16_t *location,
120
struct ofono_phonebook *pb = data;
121
const struct read_resp *resp = g_isi_msg_data(msg);
122
size_t len = g_isi_msg_data_len(msg);
52
124
GIsiSubBlockIter iter;
54
126
char *name = NULL;
58
130
char *email = NULL;
63
if (len < 3 || msg[0] != SIM_PB_RESP_SIM_PB_READ)
66
if (msg[1] != SIM_PB_READ)
69
for (g_isi_sb_iter_init_full(&iter, msg, len, 3, TRUE, msg[2]);
70
g_isi_sb_iter_is_valid(&iter);
71
g_isi_sb_iter_next(&iter)) {
133
gboolean success = FALSE;
135
if (g_isi_msg_id(msg) != SIM_PB_RESP_SIM_PB_READ ||
136
resp == NULL || len < sizeof(struct read_resp) ||
137
resp->service_type != SIM_PB_READ)
140
for (g_isi_sb_iter_init_full(&iter, msg, 2, TRUE, resp->sb_count);
141
g_isi_sb_iter_is_valid(&iter);
142
g_isi_sb_iter_next(&iter)) {
73
144
switch (g_isi_sb_iter_get_id(&iter)) {
80
if (!g_isi_sb_iter_get_word(&iter, &loc, 4) ||
81
!g_isi_sb_iter_get_byte(&iter, &namelen, 6) ||
82
!g_isi_sb_iter_get_byte(&iter, &numberlen, 7))
85
if (!g_isi_sb_iter_get_alpha_tag(&iter, &name,
89
if (!g_isi_sb_iter_get_alpha_tag(&iter, &number,
90
numberlen * 2, 8 + namelen * 2))
100
if (!g_isi_sb_iter_get_byte(&iter, &snelen, 6))
103
if (!g_isi_sb_iter_get_alpha_tag(&iter, &sne,
112
if (!g_isi_sb_iter_get_byte(&iter, &anrlen, 6))
115
if (!g_isi_sb_iter_get_alpha_tag(&iter, &anr,
124
if (!g_isi_sb_iter_get_byte(&iter, &emaillen, 6))
127
if (!g_isi_sb_iter_get_alpha_tag(&iter, &email,
147
if (!parse_adn(&iter, location, &name, &number))
154
if (!parse_sne(&iter, &sne))
160
if (!parse_anr(&iter, &anr))
166
if (!parse_email(&iter, &email))
133
170
case SIM_PB_STATUS:
135
172
if (!g_isi_sb_iter_get_byte(&iter, &status, 4))
148
if (status != SIM_SERV_OK) {
149
DBG("Request failed: %s (0x%02X)",
150
sim_isi_cause_name(status), status);
154
ofono_phonebook_entry(pb, -1, number, -1, name, -1, NULL,
155
anr, -1, sne, email, NULL, NULL);
184
if (status == SIM_SERV_OK)
185
ofono_phonebook_entry(pb, -1, number, -1, name, -1, NULL,
186
anr, -1, sne, email, NULL, NULL);
167
static void read_next_entry(GIsiClient *client, int location,
168
GIsiResponseFunc read_cb,
169
struct isi_cb_data *cbd)
197
static void read_next_entry(GIsiClient *client, uint16_t location,
198
GIsiNotifyFunc notify, void *data)
200
struct isi_cb_data *cbd = data;
171
201
ofono_phonebook_cb_t cb = cbd->cb;
172
const unsigned char msg[] = {
202
const uint8_t msg[] = {
173
203
SIM_PB_REQ_SIM_PB_READ,
175
205
2, /* number of subblocks */
207
static gboolean read_resp_cb(GIsiClient *client,
208
const void *restrict data, size_t len,
209
uint16_t object, void *opaque)
233
static void read_resp_cb(const GIsiMessage *msg, void *data)
211
const unsigned char *msg = data;
212
struct isi_cb_data *cbd = opaque;
235
struct isi_cb_data *cbd = data;
236
struct ofono_phonebook *pb = cbd->user;
237
struct pb_data *pbd = ofono_phonebook_get_data(pb);
213
239
ofono_phonebook_cb_t cb = cbd->cb;
217
DBG("ISI client error: %d", g_isi_client_error(client));
242
if (g_isi_msg_error(msg) < 0) {
243
CALLBACK_WITH_FAILURE(cb, cbd->data);
221
location = decode_read_response(data, len, cbd->user);
222
if (location != -1) {
223
read_next_entry(client, location, read_resp_cb, cbd);
248
if (decode_response(msg, &location, cbd->user)) {
249
read_next_entry(pbd->client, location, read_resp_cb, cbd);
227
253
CALLBACK_WITH_SUCCESS(cb, cbd->data);
231
CALLBACK_WITH_FAILURE(cb, cbd->data);
238
257
static void isi_export_entries(struct ofono_phonebook *pb, const char *storage,
259
278
0, 0 /* filler */
265
if (strcmp(storage, "SM"))
268
if (g_isi_request_make(pbd->client, msg, sizeof(msg), SIM_TIMEOUT,
280
size_t len = sizeof(msg);
282
if (cbd == NULL || pbd == NULL || strcmp(storage, "SM") != 0)
285
if (g_isi_client_send(pbd->client, msg, len, read_resp_cb, cbd, NULL))
276
289
CALLBACK_WITH_FAILURE(cb, data);
279
static gboolean isi_phonebook_register(gpointer user)
293
static void reachable_cb(const GIsiMessage *msg, void *data)
281
struct ofono_phonebook *pb = user;
295
struct ofono_phonebook *pb = data;
297
if (g_isi_msg_error(msg) < 0)
300
ISI_VERSION_DBG(msg);
283
302
ofono_phonebook_register(pb);
288
static void reachable_cb(GIsiClient *client, gboolean alive, uint16_t object,
291
struct ofono_phonebook *pb = opaque;
292
const char *debug = NULL;
295
DBG("Unable to bootstrap phonebook driver");
299
DBG("%s (v%03d.%03d) reachable",
300
pn_resource_name(g_isi_client_resource(client)),
301
g_isi_version_major(client),
302
g_isi_version_minor(client));
304
debug = getenv("OFONO_ISI_DEBUG");
305
if (debug && (strcmp(debug, "all") == 0 || strcmp(debug, "sim") == 0))
306
g_isi_client_set_debug(client, sim_debug, NULL);
308
g_idle_add(isi_phonebook_register, pb);
311
305
static int isi_phonebook_probe(struct ofono_phonebook *pb, unsigned int vendor,
314
GIsiModem *idx = user;
315
struct pb_data *data = g_try_new0(struct pb_data, 1);
308
GIsiModem *modem = user;
309
struct pb_data *data;
311
data = g_try_new0(struct pb_data, 1);
320
data->client = g_isi_client_create(idx, PN_SIM);
315
data->client = g_isi_client_create(modem, PN_SIM);
316
if (data->client == NULL) {
326
321
ofono_phonebook_set_data(pb, data);
328
if (!g_isi_verify(data->client, reachable_cb, pb))
329
DBG("Unable to verify reachability");
323
g_isi_client_verify(data->client, reachable_cb, pb, NULL);
350
345
.export_entries = isi_export_entries
353
void isi_phonebook_init()
348
void isi_phonebook_init(void)
355
350
ofono_phonebook_driver_register(&driver);
358
void isi_phonebook_exit()
353
void isi_phonebook_exit(void)
360
355
ofono_phonebook_driver_unregister(&driver);