Ejemplo n.º 1
0
static DBusMessage *set_property_request(struct ofono_call_forwarding *cf,
						DBusMessage *msg,
						int type, int cls,
						struct ofono_phone_number *ph,
						int timeout)
{
	if (ph->number[0] != '\0' && cf->driver->registration == NULL)
		return __ofono_error_not_implemented(msg);

	if (ph->number[0] == '\0' && cf->driver->erasure == NULL)
		return __ofono_error_not_implemented(msg);

	cf->pending = dbus_message_ref(msg);
	cf->query_next = type;
	cf->query_end = type;

	DBG("Farming off request, will be erasure: %d", ph->number[0] == '\0');

	if (ph->number[0] != '\0')
		cf->driver->registration(cf, type, cls, ph, timeout,
					set_property_callback, cf);
	else
		cf->driver->erasure(cf, type, cls, set_property_callback, cf);

	return NULL;
}
Ejemplo n.º 2
0
static DBusMessage *handsfree_set_property(DBusConnection *conn,
						DBusMessage *msg, void *data)
{
	struct ofono_handsfree *hf = data;
	DBusMessageIter iter, var;
	ofono_bool_t enabled;
	const char *name;

	if (hf->pending)
		return __ofono_error_busy(msg);

	if (dbus_message_iter_init(msg, &iter) == FALSE)
		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_get_arg_type(&var) != DBUS_TYPE_BOOLEAN)
		return __ofono_error_invalid_args(msg);

	dbus_message_iter_get_basic(&var, &enabled);

	if (g_str_equal(name, "VoiceRecognition") == TRUE) {

		if (!hf->driver->voice_recognition)
			return __ofono_error_not_implemented(msg);

		if (hf->voice_recognition == enabled)
			return dbus_message_new_method_return(msg);

		hf->voice_recognition_pending = enabled;
		hf->pending = dbus_message_ref(msg);
		hf->driver->voice_recognition(hf, enabled, voicerec_set_cb, hf);
	} else if (g_str_equal(name, "EchoCancelingNoiseReduction") == TRUE) {

		if (!(hf->ag_features & HFP_AG_FEATURE_ECNR))
			return __ofono_error_not_supported(msg);

		if (!hf->driver->disable_nrec || enabled == TRUE)
			return __ofono_error_not_implemented(msg);

		if (hf->nrec == FALSE)
			return dbus_message_new_method_return(msg);

		hf->pending = dbus_message_ref(msg);
		hf->driver->disable_nrec(hf, nrec_set_cb, hf);
	} else
		return __ofono_error_invalid_args(msg);

	return NULL;
}
Ejemplo n.º 3
0
static DBusMessage *set_property_online(struct ofono_modem *modem,
					DBusMessage *msg,
					DBusMessageIter *var)
{
	ofono_bool_t online;
	const struct ofono_modem_driver *driver = modem->driver;

	if (modem->powered == FALSE)
		return __ofono_error_not_available(msg);

	if (dbus_message_iter_get_arg_type(var) != DBUS_TYPE_BOOLEAN)
		return __ofono_error_invalid_args(msg);

	dbus_message_iter_get_basic(var, &online);

	if (modem->pending != NULL)
		return __ofono_error_busy(msg);

	if (modem->online == online)
		return dbus_message_new_method_return(msg);

	if (ofono_modem_get_emergency_mode(modem) == TRUE)
		return __ofono_error_emergency_active(msg);

	if (modem_is_always_online(modem) == TRUE)
		return __ofono_error_not_implemented(msg);

	modem->pending = dbus_message_ref(msg);

	driver->set_online(modem, online,
				online ? online_cb : offline_cb, modem);

	return NULL;
}
Ejemplo n.º 4
0
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;
}
Ejemplo n.º 5
0
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;
}
Ejemplo n.º 6
0
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;
}
Ejemplo n.º 7
0
static DBusMessage *oem_raw_make_request(DBusConnection *conn,
					 DBusMessage *msg, void *data)
{
	char *array; /* Byte array containing client request*/
	int array_len; /* Length of request byte array */
	DBusMessageIter iter;
	DBusMessageIter subiter;
	struct ofono_oem_raw_request *req;
	struct ofono_oem_raw *raw;
	raw = data;
	req = 0;

	if (raw && raw->driver->request == NULL)
		return __ofono_error_not_implemented(msg);

	dbus_message_iter_init(msg, &iter);

	if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_ARRAY)
		goto error_arg;

	if (dbus_message_iter_get_element_type(&iter) != DBUS_TYPE_BYTE) {
		DBG("Ignoring request because dbus request element type=%c",
		    dbus_message_iter_get_element_type(&iter));
		goto error_arg;
	}

	dbus_message_iter_recurse(&iter, &subiter);

	dbus_message_iter_get_fixed_array(&subiter, &array, &array_len);

	req = g_new0(struct ofono_oem_raw_request, 1);
	req->data = array;
	req->length = array_len;
	/* Store msg to request struct to allow multiple parallel requests */
	req->pending = dbus_message_ref(msg);
	raw->driver->request(raw, req, ofono_oem_raw_query_cb, req);

	return NULL;

error_arg:
	DBG("DBus arg type=%c, msg signature: %s",
		dbus_message_iter_get_arg_type(&iter),
		dbus_message_get_signature(msg));
	return __ofono_error_invalid_args(msg);
}
Ejemplo n.º 8
0
static DBusMessage *prop_set_acm_max(DBusMessage *msg,
					struct ofono_call_meter *cm,
					DBusMessageIter *dbus_value,
					const char *pin2)
{
	dbus_uint32_t value;

	if (cm->driver->acm_max_set == NULL)
		return __ofono_error_not_implemented(msg);

	dbus_message_iter_get_basic(dbus_value, &value);

	cm->pending = dbus_message_ref(msg);

	cm->driver->acm_max_set(cm, value, pin2, set_acm_max_callback, cm);

	return NULL;
}
Ejemplo n.º 9
0
static DBusMessage *radio_get_properties(DBusConnection *conn,
						DBusMessage *msg, void *data)
{
	struct ofono_radio_settings *rs = data;

	if (rs->flags & RADIO_SETTINGS_FLAG_CACHED)
		return radio_get_properties_reply(msg, rs);

	if (rs->driver->query_rat_mode == NULL)
		return __ofono_error_not_implemented(msg);

	if (rs->pending)
		return __ofono_error_busy(msg);

	rs->pending = dbus_message_ref(msg);
	rs->driver->query_rat_mode(rs, radio_rat_mode_query_callback, rs);

	return NULL;
}
Ejemplo n.º 10
0
Archivo: sms.c Proyecto: AndriusA/ofono
static DBusMessage *sms_get_properties(DBusConnection *conn,
					DBusMessage *msg, void *data)
{
	struct ofono_sms *sms = data;

	if (sms->flags & MESSAGE_MANAGER_FLAG_CACHED)
		return generate_get_properties_reply(sms, msg);

	if (sms->pending)
		return __ofono_error_busy(msg);

	if (sms->driver->sca_query == NULL)
		return __ofono_error_not_implemented(msg);

	sms->pending = dbus_message_ref(msg);

	sms->driver->sca_query(sms, sms_sca_query_cb, sms);

	return NULL;
}
Ejemplo n.º 11
0
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;
}
Ejemplo n.º 12
0
static DBusMessage *cf_get_properties(DBusConnection *conn, DBusMessage *msg,
					void *data)
{
	struct ofono_call_forwarding *cf = data;
	struct ofono_modem *modem = __ofono_atom_get_modem(cf->atom);

	if ((cf->flags & CALL_FORWARDING_FLAG_CACHED) ||
			ofono_modem_get_online(modem) == FALSE)
		return cf_get_properties_reply(msg, cf);

	if (cf->driver->query == 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);

	cf->pending = dbus_message_ref(msg);
	cf->query_next = 0;

	get_query_next_cf_cond(cf);

	return NULL;
}
Ejemplo n.º 13
0
static DBusMessage *ussd_cancel(DBusConnection *conn, DBusMessage *msg,
					void *data)
{
	struct ofono_ussd *ussd = data;

	if (ussd->state == USSD_STATE_IDLE)
		return __ofono_error_not_active(msg);

	/* We have called Respond() but not returned from its callback yet */
	if (ussd->state == USSD_STATE_USER_ACTION && ussd->pending)
		return __ofono_error_busy(msg);

	if (ussd->cancel)
		return __ofono_error_busy(msg);

	if (ussd->driver->cancel == NULL)
		return __ofono_error_not_implemented(msg);

	ussd->cancel = dbus_message_ref(msg);

	ussd->driver->cancel(ussd, ussd_cancel_callback, ussd);

	return NULL;
}
Ejemplo n.º 14
0
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;
}
Ejemplo n.º 15
0
Archivo: sms.c Proyecto: AndriusA/ofono
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);
}
Ejemplo n.º 16
0
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;
}
Ejemplo n.º 17
0
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;
}
Ejemplo n.º 18
0
static DBusMessage *radio_set_property(DBusConnection *conn, DBusMessage *msg,
					void *data)
{
	struct ofono_radio_settings *rs = data;
	DBusMessageIter iter;
	DBusMessageIter var;
	const char *property;

	if (rs->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_strcmp0(property, "TechnologyPreference") == 0) {
		const char *value;
		enum ofono_radio_access_mode mode;

		if (rs->driver->set_rat_mode == NULL)
			return __ofono_error_not_implemented(msg);

		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 (radio_access_mode_from_string(value, &mode) == FALSE)
			return __ofono_error_invalid_args(msg);

		if (rs->mode == mode)
			return dbus_message_new_method_return(msg);

		rs->pending = dbus_message_ref(msg);
		rs->pending_mode = mode;

		rs->driver->set_rat_mode(rs, mode, radio_mode_set_callback, rs);

		return NULL;
	} else if (g_strcmp0(property, "GsmBand") == 0) {
		const char *value;
		enum ofono_radio_band_gsm band;

		if (rs->driver->set_band == NULL)
			return __ofono_error_not_implemented(msg);

		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 (radio_band_gsm_from_string(value, &band) == FALSE)
			return __ofono_error_invalid_args(msg);

		if (rs->band_gsm == band)
			return dbus_message_new_method_return(msg);

		rs->pending = dbus_message_ref(msg);
		rs->pending_band_gsm = band;

		rs->driver->set_band(rs, band, rs->band_umts,
					radio_band_set_callback, rs);

		return NULL;
	} else if (g_strcmp0(property, "UmtsBand") == 0) {
		const char *value;
		enum ofono_radio_band_umts band;

		if (rs->driver->set_band == NULL)
			return __ofono_error_not_implemented(msg);

		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 (radio_band_umts_from_string(value, &band) == FALSE)
			return __ofono_error_invalid_args(msg);

		if (rs->band_umts == band)
			return dbus_message_new_method_return(msg);

		rs->pending = dbus_message_ref(msg);
		rs->pending_band_umts = band;

		rs->driver->set_band(rs, rs->band_gsm, band,
					radio_band_set_callback, rs);

		return NULL;
	} else if (g_strcmp0(property, "FastDormancy") == 0) {
		dbus_bool_t value;
		int target;

		if (rs->driver->set_fast_dormancy == 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, &value);
		target = value;

		if (rs->fast_dormancy_pending == target)
			return dbus_message_new_method_return(msg);

		rs->pending = dbus_message_ref(msg);
		rs->fast_dormancy_pending = target;

		rs->driver->set_fast_dormancy(rs, target,
					radio_fast_dormancy_set_callback, rs);
		return NULL;
	}

	return __ofono_error_invalid_args(msg);
}
Ejemplo n.º 19
0
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);
}