static DBusMessage *ussd_respond(DBusConnection *conn, DBusMessage *msg, void *data) { struct ofono_ussd *ussd = data; const char *str; int dcs = 0x0f; unsigned char buf[160]; long num_packed; if (ussd->pending) return __ofono_error_busy(msg); if (ussd->state != USSD_STATE_USER_ACTION) return __ofono_error_not_active(msg); if (dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &str, DBUS_TYPE_INVALID) == FALSE) return __ofono_error_invalid_args(msg); if (strlen(str) == 0) return __ofono_error_invalid_format(msg); if (!ussd_encode(str, &num_packed, buf)) return __ofono_error_invalid_format(msg); if (ussd->driver->request == NULL) return __ofono_error_not_implemented(msg); ussd->pending = dbus_message_ref(msg); ussd->driver->request(ussd, dcs, buf, num_packed, ussd_response_callback, ussd); return NULL; }
static DBusMessage *ussd_initiate(DBusConnection *conn, DBusMessage *msg, void *data) { struct ofono_ussd *ussd = data; struct ofono_modem *modem = __ofono_atom_get_modem(ussd->atom); struct ofono_voicecall *vc; gboolean call_in_progress; const char *str; int dcs = 0x0f; unsigned char buf[160]; long num_packed; if (__ofono_ussd_is_busy(ussd)) return __ofono_error_busy(msg); if (dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &str, DBUS_TYPE_INVALID) == FALSE) return __ofono_error_invalid_args(msg); if (strlen(str) == 0) return __ofono_error_invalid_format(msg); DBG("checking if this is a recognized control string"); if (recognized_control_string(ussd, str, msg)) return NULL; vc = __ofono_atom_find(OFONO_ATOM_TYPE_VOICECALL, modem); if (vc) call_in_progress = __ofono_voicecall_is_busy(vc, OFONO_VOICECALL_INTERACTION_NONE); else call_in_progress = FALSE; DBG("No.., checking if this is a USSD string"); if (!valid_ussd_string(str, call_in_progress)) return __ofono_error_not_recognized(msg); if (!ussd_encode(str, &num_packed, buf)) return __ofono_error_invalid_format(msg); if (ussd->driver->request == NULL) return __ofono_error_not_implemented(msg); DBG("OK, running USSD request"); ussd->pending = dbus_message_ref(msg); ussd->driver->request(ussd, dcs, buf, num_packed, ussd_callback, ussd); return NULL; }
/* * Pre-process a SMS text message and deliver it [D-Bus SendMessage()] * * @conn: D-Bus connection * @msg: message data (telephone number and text) * @data: SMS object to use for transmision * * An alphabet is chosen for the text and it (might be) segmented in * fragments by sms_text_prepare() into @msg_list. A queue list @entry * is created by tx_queue_entry_new() and g_queue_push_tail() * appends that entry to the SMS transmit queue. Then the tx_next() * function is scheduled to run to process the queue. */ static DBusMessage *sms_send_message(DBusConnection *conn, DBusMessage *msg, void *data) { struct ofono_sms *sms = data; const char *to; const char *text; GSList *msg_list; struct ofono_modem *modem; unsigned int flags; gboolean use_16bit_ref = FALSE; int err; struct ofono_uuid uuid; if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &to, DBUS_TYPE_STRING, &text, DBUS_TYPE_INVALID)) return __ofono_error_invalid_args(msg); if (valid_phone_number_format(to) == FALSE) return __ofono_error_invalid_format(msg); msg_list = sms_text_prepare_with_alphabet(to, text, sms->ref, use_16bit_ref, sms->use_delivery_reports, sms->alphabet); if (msg_list == NULL) return __ofono_error_invalid_format(msg); flags = OFONO_SMS_SUBMIT_FLAG_RECORD_HISTORY; flags |= OFONO_SMS_SUBMIT_FLAG_RETRY; flags |= OFONO_SMS_SUBMIT_FLAG_EXPOSE_DBUS; if (sms->use_delivery_reports) flags |= OFONO_SMS_SUBMIT_FLAG_REQUEST_SR; err = __ofono_sms_txq_submit(sms, msg_list, flags, &uuid, message_queued, msg); g_slist_foreach(msg_list, (GFunc) g_free, NULL); g_slist_free(msg_list); if (err < 0) return __ofono_error_failed(msg); modem = __ofono_atom_get_modem(sms->atom); __ofono_history_sms_send_pending(modem, &uuid, to, time(NULL), text); return NULL; }
static DBusMessage *stk_register_agent(DBusConnection *conn, DBusMessage *msg, void *data) { struct ofono_stk *stk = data; const char *agent_path; if (stk->default_agent) return __ofono_error_busy(msg); if (dbus_message_get_args(msg, NULL, DBUS_TYPE_OBJECT_PATH, &agent_path, DBUS_TYPE_INVALID) == FALSE) return __ofono_error_invalid_args(msg); if (!__ofono_dbus_valid_object_path(agent_path)) return __ofono_error_invalid_format(msg); stk->default_agent = stk_agent_new(agent_path, dbus_message_get_sender(msg), FALSE); if (!stk->default_agent) return __ofono_error_failed(msg); stk_agent_set_removed_notify(stk->default_agent, default_agent_notify, stk); if (!stk->session_agent) stk->current_agent = stk->default_agent; return dbus_message_new_method_return(msg); }
static DBusMessage *cm_acm_reset(DBusConnection *conn, DBusMessage *msg, void *data) { struct ofono_call_meter *cm = data; const char *pin2; if (cm->driver->acm_reset == NULL) return __ofono_error_not_implemented(msg); if (cm->pending) return __ofono_error_busy(msg); if (dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &pin2, DBUS_TYPE_INVALID) == FALSE) return __ofono_error_invalid_args(msg); if (!__ofono_is_valid_sim_pin(pin2, OFONO_SIM_PASSWORD_SIM_PIN2)) return __ofono_error_invalid_format(msg); cm->pending = dbus_message_ref(msg); cm->driver->acm_reset(cm, pin2, acm_reset_callback, cm); return NULL; }
static DBusMessage *gnss_register_agent(DBusConnection *conn, DBusMessage *msg, void *data) { struct ofono_gnss *gnss = data; const char *agent_path; if (gnss->pending) return __ofono_error_busy(msg); if (gnss->posr_agent) return __ofono_error_busy(msg); if (dbus_message_get_args(msg, NULL, DBUS_TYPE_OBJECT_PATH, &agent_path, DBUS_TYPE_INVALID) == FALSE) return __ofono_error_invalid_args(msg); if (!__ofono_dbus_valid_object_path(agent_path)) return __ofono_error_invalid_format(msg); gnss->posr_agent = gnss_agent_new(agent_path, dbus_message_get_sender(msg)); if (gnss->posr_agent == NULL) return __ofono_error_failed(msg); gnss_agent_set_removed_notify(gnss->posr_agent, gnss_agent_notify, gnss); gnss->driver->set_position_reporting(gnss, TRUE, gnss_register_agent_cb, gnss); gnss->pending = dbus_message_ref(msg); return NULL; }
static DBusMessage *stk_select_item(DBusConnection *conn, DBusMessage *msg, void *data) { struct ofono_stk *stk = data; const char *agent_path; unsigned char selection, i; struct stk_envelope e; struct stk_menu *menu = stk->main_menu; if (stk->pending) return __ofono_error_busy(msg); if (stk->session_agent || !menu) return __ofono_error_busy(msg); if (dbus_message_get_args(msg, NULL, DBUS_TYPE_BYTE, &selection, DBUS_TYPE_OBJECT_PATH, &agent_path, DBUS_TYPE_INVALID) == FALSE) return __ofono_error_invalid_args(msg); if (!__ofono_dbus_valid_object_path(agent_path)) return __ofono_error_invalid_format(msg); for (i = 0; i < selection && menu->items[i].text; i++); if (i != selection) return __ofono_error_invalid_format(msg); memset(&e, 0, sizeof(e)); e.type = STK_ENVELOPE_TYPE_MENU_SELECTION; e.src = STK_DEVICE_IDENTITY_TYPE_KEYPAD, e.menu_selection.item_id = menu->items[selection].item_id; e.menu_selection.help_request = FALSE; if (stk_send_envelope(stk, &e, menu_selection_envelope_cb, 0)) return __ofono_error_failed(msg); stk->pending = dbus_message_ref(msg); return NULL; }
static DBusMessage *cm_set_property(DBusConnection *conn, DBusMessage *msg, void *data) { struct ofono_call_meter *cm = data; DBusMessageIter iter; DBusMessageIter var; const char *name, *passwd = ""; struct call_meter_property *property; if (cm->pending) return __ofono_error_busy(msg); if (!dbus_message_iter_init(msg, &iter)) return __ofono_error_invalid_args(msg); if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_STRING) return __ofono_error_invalid_args(msg); dbus_message_iter_get_basic(&iter, &name); dbus_message_iter_next(&iter); if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_VARIANT) return __ofono_error_invalid_args(msg); dbus_message_iter_recurse(&iter, &var); if (!dbus_message_iter_next(&iter)) return __ofono_error_invalid_args(msg); if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_STRING) return __ofono_error_invalid_args(msg); dbus_message_iter_get_basic(&iter, &passwd); if (!__ofono_is_valid_sim_pin(passwd, OFONO_SIM_PASSWORD_SIM_PIN2)) return __ofono_error_invalid_format(msg); for (property = cm_properties; property->name; property++) { if (strcmp(name, property->name)) continue; if (dbus_message_iter_get_arg_type(&var) != property->type) return __ofono_error_invalid_args(msg); return property->set(msg, cm, &var, passwd); } return __ofono_error_invalid_args(msg); }
static gboolean recognized_passwd_change_string(struct ofono_ussd *ussd, int type, char *sc, char *sia, char *sib, char *sic, char *sid, char *dn, DBusMessage *msg) { GSList *l = ussd->ss_passwd_list; switch (type) { case SS_CONTROL_TYPE_ACTIVATION: case SS_CONTROL_TYPE_REGISTRATION: break; default: return FALSE; } if (strcmp(sc, "03") || strlen(dn)) return FALSE; /* If SIC & SID don't match, then we just bail out here */ if (strcmp(sic, sid)) { DBusConnection *conn = ofono_dbus_get_connection(); DBusMessage *reply = __ofono_error_invalid_format(msg); g_dbus_send_message(conn, reply); return TRUE; } while ((l = g_slist_find_custom(l, sia, ssc_entry_find_by_service)) != NULL) { struct ssc_entry *entry = l->data; ofono_ussd_passwd_cb_t cb = entry->cb; if (cb(sia, sib, sic, msg, entry->user)) return TRUE; l = l->next; } return FALSE; }
static DBusMessage *push_notification_register_agent(DBusConnection *conn, DBusMessage *msg, void *data) { struct push_notification *pn = data; const char *agent_path; if (pn->agent) return __ofono_error_busy(msg); if (dbus_message_get_args(msg, NULL, DBUS_TYPE_OBJECT_PATH, &agent_path, DBUS_TYPE_INVALID) == FALSE) return __ofono_error_invalid_args(msg); if (!__ofono_dbus_valid_object_path(agent_path)) return __ofono_error_invalid_format(msg); pn->agent = sms_agent_new(AGENT_INTERFACE, dbus_message_get_sender(msg), agent_path); if (pn->agent == NULL) return __ofono_error_failed(msg); sms_agent_set_removed_notify(pn->agent, agent_exited, pn); pn->push_watch[0] = __ofono_sms_datagram_watch_add(pn->sms, push_received, WAP_PUSH_DST_PORT, WAP_PUSH_SRC_PORT, pn, NULL); pn->push_watch[1] = __ofono_sms_datagram_watch_add(pn->sms, push_received, WAP_PUSH_DST_PORT, 0, pn, NULL); return dbus_message_new_method_return(msg); }
static DBusMessage *prop_set_cur(DBusMessage *msg, struct ofono_call_meter *cm, DBusMessageIter *var, const char *pin2) { const char *value; if (cm->driver->puct_set == NULL || cm->driver->puct_query == NULL) return __ofono_error_not_implemented(msg); dbus_message_iter_get_basic(var, &value); if (strlen(value) > 3) return __ofono_error_invalid_format(msg); cm->pending = dbus_message_ref(msg); if (cm->flags & CALL_METER_FLAG_HAVE_PUCT) cm->driver->puct_set(cm, value, cm->ppu, pin2, set_puct_callback, cm); else cm->driver->puct_query(cm, set_puct_initial_query_callback, cm); return NULL; }
static DBusMessage *cf_disable_all(DBusConnection *conn, DBusMessage *msg, void *data) { struct ofono_call_forwarding *cf = data; const char *strtype; int type; if (cf->driver->erasure == NULL) return __ofono_error_not_implemented(msg); if (__ofono_call_forwarding_is_busy(cf) || __ofono_ussd_is_busy(cf->ussd)) return __ofono_error_busy(msg); if (dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &strtype, DBUS_TYPE_INVALID) == FALSE) return __ofono_error_invalid_args(msg); if (!strcmp(strtype, "all") || !strcmp(strtype, "")) type = CALL_FORWARDING_TYPE_ALL; else if (!strcmp(strtype, "conditional")) type = CALL_FORWARDING_TYPE_ALL_CONDITIONAL; else return __ofono_error_invalid_format(msg); cf->pending = dbus_message_ref(msg); if (type == CALL_FORWARDING_TYPE_ALL) cf->driver->erasure(cf, type, BEARER_CLASS_DEFAULT, disable_all_callback, cf); else cf->driver->erasure(cf, type, BEARER_CLASS_DEFAULT, disable_conditional_callback, cf); return NULL; }
static DBusMessage *sms_set_property(DBusConnection *conn, DBusMessage *msg, void *data) { struct ofono_sms *sms = data; DBusMessageIter iter; DBusMessageIter var; const char *property; if (sms->pending) return __ofono_error_busy(msg); if (!dbus_message_iter_init(msg, &iter)) return __ofono_error_invalid_args(msg); if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_STRING) return __ofono_error_invalid_args(msg); dbus_message_iter_get_basic(&iter, &property); dbus_message_iter_next(&iter); if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_VARIANT) return __ofono_error_invalid_args(msg); dbus_message_iter_recurse(&iter, &var); if (!strcmp(property, "ServiceCenterAddress")) { const char *value; struct ofono_phone_number sca; if (dbus_message_iter_get_arg_type(&var) != DBUS_TYPE_STRING) return __ofono_error_invalid_args(msg); dbus_message_iter_get_basic(&var, &value); if (strlen(value) == 0 || !valid_phone_number_format(value)) return __ofono_error_invalid_format(msg); if (sms->driver->sca_set == NULL || sms->driver->sca_query == NULL) return __ofono_error_not_implemented(msg); string_to_phone_number(value, &sca); sms->pending = dbus_message_ref(msg); sms->driver->sca_set(sms, &sca, sca_set_callback, sms); return NULL; } if (!strcmp(property, "Bearer")) { const char *value; int bearer; if (dbus_message_iter_get_arg_type(&var) != DBUS_TYPE_STRING) return __ofono_error_invalid_args(msg); dbus_message_iter_get_basic(&var, &value); if (sms_bearer_from_string(value, &bearer) != TRUE) return __ofono_error_invalid_format(msg); if (sms->driver->bearer_set == NULL || sms->driver->bearer_query == NULL) return __ofono_error_not_implemented(msg); sms->pending = dbus_message_ref(msg); sms->driver->bearer_set(sms, bearer, bearer_set_callback, sms); return NULL; } if (!strcmp(property, "UseDeliveryReports")) { const char *path = __ofono_atom_get_path(sms->atom); dbus_bool_t value; if (dbus_message_iter_get_arg_type(&var) != DBUS_TYPE_BOOLEAN) return __ofono_error_invalid_args(msg); dbus_message_iter_get_basic(&var, &value); g_dbus_send_reply(conn, msg, DBUS_TYPE_INVALID); if (sms->use_delivery_reports != (ofono_bool_t) value) { sms->use_delivery_reports = value; ofono_dbus_signal_property_changed(conn, path, OFONO_MESSAGE_MANAGER_INTERFACE, "UseDeliveryReports", DBUS_TYPE_BOOLEAN, &value); } return NULL; } if (!strcmp(property, "Alphabet")) { const char *value; enum sms_alphabet alphabet; if (dbus_message_iter_get_arg_type(&var) != DBUS_TYPE_STRING) return __ofono_error_invalid_args(msg); dbus_message_iter_get_basic(&var, &value); if (!sms_alphabet_from_string(value, &alphabet)) return __ofono_error_invalid_format(msg); set_alphabet(sms, alphabet); g_dbus_send_reply(conn, msg, DBUS_TYPE_INVALID); return NULL; } return __ofono_error_invalid_args(msg); }
static gboolean cf_ss_control(int type, const char *sc, const char *sia, const char *sib, const char *sic, const char *dn, DBusMessage *msg, void *data) { struct ofono_call_forwarding *cf = data; DBusConnection *conn = ofono_dbus_get_connection(); int cls = BEARER_CLASS_SS_DEFAULT; int timeout = DEFAULT_NO_REPLY_TIMEOUT; int cf_type; DBusMessage *reply; struct ofono_phone_number ph; void *operation = NULL; /* Before we do anything, make sure we're actually initialized */ if (cf == NULL) return FALSE; if (__ofono_call_forwarding_is_busy(cf)) { reply = __ofono_error_busy(msg); g_dbus_send_message(conn, reply); return TRUE; } DBG("Received call forwarding ss control request"); DBG("type: %d, sc: %s, sia: %s, sib: %s, sic: %s, dn: %s", type, sc, sia, sib, sic, dn); if (!strcmp(sc, "21")) cf_type = CALL_FORWARDING_TYPE_UNCONDITIONAL; else if (!strcmp(sc, "67")) cf_type = CALL_FORWARDING_TYPE_BUSY; else if (!strcmp(sc, "61")) cf_type = CALL_FORWARDING_TYPE_NO_REPLY; else if (!strcmp(sc, "62")) cf_type = CALL_FORWARDING_TYPE_NOT_REACHABLE; else if (!strcmp(sc, "002")) cf_type = CALL_FORWARDING_TYPE_ALL; else if (!strcmp(sc, "004")) cf_type = CALL_FORWARDING_TYPE_ALL_CONDITIONAL; else return FALSE; if (strlen(sia) && (type == SS_CONTROL_TYPE_QUERY || type == SS_CONTROL_TYPE_ERASURE || type == SS_CONTROL_TYPE_DEACTIVATION)) goto error; /* * Activation / Registration is figured context specific according to * 22.030 Section 6.5.2 "The UE shall determine from the context * whether, an entry of a single *, activation or registration * was intended." */ if (type == SS_CONTROL_TYPE_ACTIVATION && strlen(sia) > 0) type = SS_CONTROL_TYPE_REGISTRATION; if (type == SS_CONTROL_TYPE_REGISTRATION && !valid_phone_number_format(sia)) goto error; if (strlen(sib) > 0) { long service_code; char *end; service_code = strtoul(sib, &end, 10); if (end == sib || *end != '\0') goto error; cls = mmi_service_code_to_bearer_class(service_code); if (cls == 0) goto error; } if (strlen(sic) > 0) { char *end; if (type != SS_CONTROL_TYPE_REGISTRATION) goto error; if (cf_type != CALL_FORWARDING_TYPE_ALL && cf_type != CALL_FORWARDING_TYPE_ALL_CONDITIONAL && cf_type != CALL_FORWARDING_TYPE_NO_REPLY) goto error; timeout = strtoul(sic, &end, 10); if (end == sic || *end != '\0') goto error; if (timeout < 1 || timeout > 30) goto error; } switch (type) { case SS_CONTROL_TYPE_REGISTRATION: operation = cf->driver->registration; break; case SS_CONTROL_TYPE_ACTIVATION: operation = cf->driver->activation; break; case SS_CONTROL_TYPE_DEACTIVATION: operation = cf->driver->deactivation; break; case SS_CONTROL_TYPE_ERASURE: operation = cf->driver->erasure; break; case SS_CONTROL_TYPE_QUERY: operation = cf->driver->query; break; } if (operation == NULL) { reply = __ofono_error_not_implemented(msg); g_dbus_send_message(conn, reply); return TRUE; } cf->ss_req = g_try_new0(struct cf_ss_request, 1); if (cf->ss_req == NULL) { reply = __ofono_error_failed(msg); g_dbus_send_message(conn, reply); return TRUE; } cf->ss_req->ss_type = type; cf->ss_req->cf_type = cf_type; cf->ss_req->cls = cls; cf->pending = dbus_message_ref(msg); switch (cf->ss_req->cf_type) { case CALL_FORWARDING_TYPE_ALL: cf->query_next = CALL_FORWARDING_TYPE_UNCONDITIONAL; cf->query_end = CALL_FORWARDING_TYPE_NOT_REACHABLE; break; case CALL_FORWARDING_TYPE_ALL_CONDITIONAL: cf->query_next = CALL_FORWARDING_TYPE_BUSY; cf->query_end = CALL_FORWARDING_TYPE_NOT_REACHABLE; break; default: cf->query_next = cf->ss_req->cf_type; cf->query_end = cf->ss_req->cf_type; break; } /* * Some modems don't understand all classes very well, particularly * the older models. So if the bearer class is the default, we * just use the more commonly understood value of 7 since BEARER_SMS * is not applicable to CallForwarding conditions according to 22.004 * Annex A */ if (cls == BEARER_CLASS_SS_DEFAULT) cls = BEARER_CLASS_DEFAULT; switch (cf->ss_req->ss_type) { case SS_CONTROL_TYPE_REGISTRATION: string_to_phone_number(sia, &ph); cf->driver->registration(cf, cf_type, cls, &ph, timeout, cf_ss_control_callback, cf); break; case SS_CONTROL_TYPE_ACTIVATION: cf->driver->activation(cf, cf_type, cls, cf_ss_control_callback, cf); break; case SS_CONTROL_TYPE_DEACTIVATION: cf->driver->deactivation(cf, cf_type, cls, cf_ss_control_callback, cf); break; case SS_CONTROL_TYPE_ERASURE: cf->driver->erasure(cf, cf_type, cls, cf_ss_control_callback, cf); break; case SS_CONTROL_TYPE_QUERY: ss_set_query_next_cf_cond(cf); break; } return TRUE; error: reply = __ofono_error_invalid_format(msg); g_dbus_send_message(conn, reply); return TRUE; }
static gboolean cb_ss_control(int type, const char *sc, const char *sia, const char *sib, const char *sic, const char *dn, DBusMessage *msg, void *data) { struct ofono_call_barring *cb = data; DBusConnection *conn = ofono_dbus_get_connection(); int cls = BEARER_CLASS_DEFAULT; const char *fac; DBusMessage *reply; void *operation = NULL; int i; if (cb->pending) { reply = __ofono_error_busy(msg); g_dbus_send_message(conn, reply); return TRUE; } DBG("Received call barring ss control request"); DBG("type: %d, sc: %s, sia: %s, sib: %s, sic: %s, dn: %s", type, sc, sia, sib, sic, dn); fac = cb_ss_service_to_fac(sc); if (!fac) return FALSE; cb_set_query_bounds(cb, fac, type == SS_CONTROL_TYPE_QUERY); i = 0; while (cb_locks[i].name && strcmp(cb_locks[i].fac, fac)) i++; cb->ss_req_lock = i; if (strlen(sic) > 0) goto bad_format; if (strlen(dn) > 0) goto bad_format; if (type != SS_CONTROL_TYPE_QUERY && !is_valid_pin(sia, PIN_TYPE_NET)) goto bad_format; switch (type) { case SS_CONTROL_TYPE_ACTIVATION: case SS_CONTROL_TYPE_DEACTIVATION: case SS_CONTROL_TYPE_REGISTRATION: case SS_CONTROL_TYPE_ERASURE: operation = cb->driver->set; break; case SS_CONTROL_TYPE_QUERY: operation = cb->driver->query; break; default: break; } if (!operation) { reply = __ofono_error_not_implemented(msg); g_dbus_send_message(conn, reply); return TRUE; } /* According to 27.007, AG, AC and AB only work with mode = 0 * We support query by querying all relevant types, since we must * do this for the deactivation case anyway */ if ((!strcmp(fac, "AG") || !strcmp(fac, "AC") || !strcmp(fac, "AB")) && (type == SS_CONTROL_TYPE_ACTIVATION || type == SS_CONTROL_TYPE_REGISTRATION)) goto bad_format; if (strlen(sib) > 0) { long service_code; char *end; service_code = strtoul(sib, &end, 10); if (end == sib || *end != '\0') goto bad_format; cls = mmi_service_code_to_bearer_class(service_code); if (cls == 0) goto bad_format; } cb->ss_req_cls = cls; cb->pending = dbus_message_ref(msg); switch (type) { case SS_CONTROL_TYPE_ACTIVATION: case SS_CONTROL_TYPE_REGISTRATION: cb->ss_req_type = SS_CONTROL_TYPE_ACTIVATION; cb->driver->set(cb, fac, 1, sia, cls, cb_ss_set_lock_callback, cb); break; case SS_CONTROL_TYPE_ERASURE: case SS_CONTROL_TYPE_DEACTIVATION: cb->ss_req_type = SS_CONTROL_TYPE_DEACTIVATION; cb->driver->set(cb, fac, 0, sia, cls, cb_ss_set_lock_callback, cb); break; case SS_CONTROL_TYPE_QUERY: cb->ss_req_type = SS_CONTROL_TYPE_QUERY; cb_ss_query_next_lock(cb); break; } return TRUE; bad_format: reply = __ofono_error_invalid_format(msg); g_dbus_send_message(conn, reply); return TRUE; }
static DBusMessage *cv_set_property(DBusConnection *conn, DBusMessage *msg, void *data) { struct ofono_call_volume *cv = data; DBusMessageIter iter; DBusMessageIter var; const char *property; if (cv->pending) return __ofono_error_busy(msg); if (!dbus_message_iter_init(msg, &iter)) return __ofono_error_invalid_args(msg); if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_STRING) return __ofono_error_invalid_args(msg); dbus_message_iter_get_basic(&iter, &property); dbus_message_iter_next(&iter); if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_VARIANT) return __ofono_error_invalid_args(msg); dbus_message_iter_recurse(&iter, &var); if (g_str_equal(property, "SpeakerVolume") == TRUE) { unsigned char percent; if (cv->driver->speaker_volume == NULL) return __ofono_error_not_implemented(msg); if (dbus_message_iter_get_arg_type(&var) != DBUS_TYPE_BYTE) return __ofono_error_invalid_args(msg); dbus_message_iter_get_basic(&var, &percent); if (percent > 100) return __ofono_error_invalid_format(msg); if (percent == cv->speaker_volume) return dbus_message_new_method_return(msg); cv->pending_volume = percent; cv->pending = dbus_message_ref(msg); cv->driver->speaker_volume(cv, percent, sv_set_callback, cv); return NULL; } else if (g_str_equal(property, "MicrophoneVolume") == TRUE) { unsigned char percent; if (cv->driver->microphone_volume == NULL) return __ofono_error_not_implemented(msg); if (dbus_message_iter_get_arg_type(&var) != DBUS_TYPE_BYTE) return __ofono_error_invalid_args(msg); dbus_message_iter_get_basic(&var, &percent); if (percent > 100) return __ofono_error_invalid_format(msg); if (percent == cv->microphone_volume) return dbus_message_new_method_return(msg); cv->pending_volume = percent; cv->pending = dbus_message_ref(msg); cv->driver->microphone_volume(cv, percent, mv_set_callback, cv); return NULL; } else if (g_str_equal(property, "Muted") == TRUE) { dbus_bool_t muted; if (cv->driver->mute == NULL) return __ofono_error_not_implemented(msg); if (dbus_message_iter_get_arg_type(&var) != DBUS_TYPE_BOOLEAN) return __ofono_error_invalid_args(msg); dbus_message_iter_get_basic(&var, &muted); if (muted == (dbus_bool_t) cv->muted) return dbus_message_new_method_return(msg); cv->muted_pending = muted; cv->pending = dbus_message_ref(msg); cv->driver->mute(cv, muted, muted_set_callback, cv); return NULL; } return __ofono_error_invalid_args(msg); }
static DBusMessage *cf_set_property(DBusConnection *conn, DBusMessage *msg, void *data) { struct ofono_call_forwarding *cf = data; struct ofono_modem *modem = __ofono_atom_get_modem(cf->atom); DBusMessageIter iter; DBusMessageIter var; const char *property; int cls; int type; if (ofono_modem_get_online(modem) == FALSE) return __ofono_error_not_available(msg); if (__ofono_call_forwarding_is_busy(cf) || __ofono_ussd_is_busy(cf->ussd)) return __ofono_error_busy(msg); if (!dbus_message_iter_init(msg, &iter)) return __ofono_error_invalid_args(msg); if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_STRING) return __ofono_error_invalid_args(msg); dbus_message_iter_get_basic(&iter, &property); dbus_message_iter_next(&iter); if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_VARIANT) return __ofono_error_invalid_args(msg); dbus_message_iter_recurse(&iter, &var); if (cf_condition_timeout_property(property, &cls)) { dbus_uint16_t timeout; GSList *l; struct ofono_call_forwarding_condition *c; type = CALL_FORWARDING_TYPE_NO_REPLY; if (dbus_message_iter_get_arg_type(&var) != DBUS_TYPE_UINT16) return __ofono_error_invalid_args(msg); dbus_message_iter_get_basic(&var, &timeout); if (timeout < 1 || timeout > 30) return __ofono_error_invalid_format(msg); l = g_slist_find_custom(cf->cf_conditions[type], GINT_TO_POINTER(cls), cf_condition_find_with_cls); if (l == NULL) return __ofono_error_failed(msg); c = l->data; return set_property_request(cf, msg, type, cls, &c->phone_number, timeout); } else if (cf_condition_enabled_property(cf, property, &type, &cls)) { struct ofono_phone_number ph; const char *number; int timeout; ph.number[0] = '\0'; ph.type = 129; if (dbus_message_iter_get_arg_type(&var) != DBUS_TYPE_STRING) return __ofono_error_invalid_args(msg); dbus_message_iter_get_basic(&var, &number); if (strlen(number) > 0 && !valid_phone_number_format(number)) return __ofono_error_invalid_format(msg); if (number[0] != '\0') string_to_phone_number(number, &ph); timeout = cf_find_timeout(cf->cf_conditions[type], cls); return set_property_request(cf, msg, type, cls, &ph, timeout); } return __ofono_error_invalid_args(msg); }