void connman_dbus_property_append_dict(DBusMessageIter *iter, const char *key, connman_dbus_append_cb_t function, void *user_data) { DBusMessageIter value, dict; dbus_message_iter_append_basic(iter, DBUS_TYPE_STRING, &key); dbus_message_iter_open_container(iter, DBUS_TYPE_VARIANT, DBUS_TYPE_ARRAY_AS_STRING DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING DBUS_TYPE_STRING_AS_STRING DBUS_TYPE_VARIANT_AS_STRING DBUS_DICT_ENTRY_END_CHAR_AS_STRING, &value); connman_dbus_dict_open(&value, &dict); if (function) function(&dict, user_data); connman_dbus_dict_close(&value, &dict); dbus_message_iter_close_container(iter, &value); }
static void append_peer_service(DBusMessageIter *iter, struct _peer_service *service) { DBusMessageIter dict; connman_dbus_dict_open(iter, &dict); switch (service->type) { case CONNMAN_PEER_SERVICE_UNKNOWN: /* Should never happen */ break; case CONNMAN_PEER_SERVICE_WIFI_DISPLAY: connman_dbus_dict_append_fixed_array(&dict, "WiFiDisplayIEs", DBUS_TYPE_BYTE, &service->data, service->length); break; } connman_dbus_dict_close(iter, &dict); }
static void append_peer_services(DBusMessageIter *iter, void *user_data) { struct connman_peer *peer = user_data; DBusMessageIter container; GSList *list; dbus_message_iter_open_container(iter, DBUS_TYPE_STRUCT, NULL, &container); if (!peer->services) { DBusMessageIter dict; connman_dbus_dict_open(&container, &dict); connman_dbus_dict_close(&container, &dict); } else { for (list = peer->services; list; list = list->next) append_peer_service(&container, list->data); } dbus_message_iter_close_container(iter, &container); }
static int request_input(struct vpn_provider *provider, request_cb_t callback, const char *dbus_sender, void *user_data) { DBusMessage *message; const char *path, *agent_sender, *agent_path; DBusMessageIter iter; DBusMessageIter dict; struct request_input_reply *l2tp_reply; int err; void *agent; agent = connman_agent_get_info(dbus_sender, &agent_sender, &agent_path); if (!provider || !agent || !agent_path || !callback) return -ESRCH; message = dbus_message_new_method_call(agent_sender, agent_path, VPN_AGENT_INTERFACE, "RequestInput"); if (!message) return -ENOMEM; dbus_message_iter_init_append(message, &iter); path = vpn_provider_get_path(provider); dbus_message_iter_append_basic(&iter, DBUS_TYPE_OBJECT_PATH, &path); connman_dbus_dict_open(&iter, &dict); vpn_agent_append_user_info(&dict, provider, "L2TP.User"); vpn_agent_append_host_and_name(&dict, provider); connman_dbus_dict_close(&iter, &dict); l2tp_reply = g_try_new0(struct request_input_reply, 1); if (!l2tp_reply) { dbus_message_unref(message); return -ENOMEM; } l2tp_reply->provider = provider; l2tp_reply->callback = callback; l2tp_reply->user_data = user_data; err = connman_agent_queue_message(provider, message, connman_timeout_input_request(), request_input_reply, l2tp_reply, agent); if (err < 0 && err != -EBUSY) { DBG("error %d sending agent request", err); dbus_message_unref(message); g_free(l2tp_reply); return err; } dbus_message_unref(message); return -EINPROGRESS; }
static void setup_tun_interface(unsigned int flags, unsigned change, void *data) { struct connman_private_network *pn = data; unsigned char prefixlen; DBusMessageIter array, dict; int err; DBG("index %d flags %d change %d", pn->index, flags, change); if (flags & IFF_UP) return; prefixlen = __connman_ipconfig_netmask_prefix_len(PRIVATE_NETWORK_NETMASK); if ((__connman_inet_modify_address(RTM_NEWADDR, NLM_F_REPLACE | NLM_F_ACK, pn->index, AF_INET, pn->server_ip, pn->peer_ip, prefixlen, NULL)) < 0) { DBG("address setting failed"); return; } connman_inet_ifup(pn->index); err = enable_nat(default_interface); if (err < 0) { connman_error("failed to enable NAT on %s", default_interface); goto error; } dbus_message_iter_init_append(pn->reply, &array); dbus_message_iter_append_basic(&array, DBUS_TYPE_OBJECT_PATH, &pn->path); connman_dbus_dict_open(&array, &dict); connman_dbus_dict_append_basic(&dict, "ServerIPv4", DBUS_TYPE_STRING, &pn->server_ip); connman_dbus_dict_append_basic(&dict, "PeerIPv4", DBUS_TYPE_STRING, &pn->peer_ip); connman_dbus_dict_append_basic(&dict, "PrimaryDNS", DBUS_TYPE_STRING, &pn->primary_dns); connman_dbus_dict_append_basic(&dict, "SecondaryDNS", DBUS_TYPE_STRING, &pn->secondary_dns); connman_dbus_dict_close(&array, &dict); dbus_message_iter_append_basic(&array, DBUS_TYPE_UNIX_FD, &pn->fd); g_dbus_send_message(connection, pn->reply); return; error: pn->reply = __connman_error_failed(pn->msg, -err); g_dbus_send_message(connection, pn->reply); g_hash_table_remove(pn_hash, pn->path); }
int __connman_agent_request_passphrase_input(struct connman_service *service, authentication_cb_t callback, const char *dbus_sender, void *user_data) { DBusMessage *message; const char *path, *agent_sender, *agent_path; DBusMessageIter iter; DBusMessageIter dict; struct request_input_reply *passphrase_reply; int err; void *agent; agent = connman_agent_get_info(dbus_sender, &agent_sender, &agent_path); DBG("agent %p service %p path %s", agent, service, agent_path); if (!service || !agent || !agent_path || !callback) return -ESRCH; message = dbus_message_new_method_call(agent_sender, agent_path, CONNMAN_AGENT_INTERFACE, "RequestInput"); if (!message) return -ENOMEM; dbus_message_iter_init_append(message, &iter); path = __connman_service_get_path(service); dbus_message_iter_append_basic(&iter, DBUS_TYPE_OBJECT_PATH, &path); connman_dbus_dict_open(&iter, &dict); if (__connman_service_is_hidden(service)) { connman_dbus_dict_append_dict(&dict, "Name", request_input_append_name, NULL); connman_dbus_dict_append_dict(&dict, "SSID", request_input_append_ssid, NULL); } if (__connman_service_get_security(service) == CONNMAN_SERVICE_SECURITY_8021X) { connman_dbus_dict_append_dict(&dict, "Identity", request_input_append_identity, service); } if (__connman_service_get_security(service) != CONNMAN_SERVICE_SECURITY_NONE) { connman_dbus_dict_append_dict(&dict, "Passphrase", request_input_append_passphrase, service); previous_passphrase_handler(&dict, service); } if (__connman_service_wps_enabled(service)) connman_dbus_dict_append_dict(&dict, "WPS", request_input_append_wps, NULL); connman_dbus_dict_close(&iter, &dict); passphrase_reply = g_try_new0(struct request_input_reply, 1); if (!passphrase_reply) { dbus_message_unref(message); return -ENOMEM; } passphrase_reply->service = service; passphrase_reply->callback = callback; passphrase_reply->user_data = user_data; err = connman_agent_queue_message(service, message, connman_timeout_input_request(), request_input_passphrase_reply, passphrase_reply, agent); if (err < 0 && err != -EBUSY) { DBG("error %d sending agent message", err); dbus_message_unref(message); g_free(passphrase_reply); return err; } dbus_message_unref(message); return -EINPROGRESS; }
int __connman_agent_request_login_input(struct connman_service *service, authentication_cb_t callback, void *user_data) { DBusMessage *message; const char *path, *agent_sender, *agent_path; DBusMessageIter iter; DBusMessageIter dict; struct request_input_reply *username_password_reply; int err; void *agent; agent = connman_agent_get_info(NULL, &agent_sender, &agent_path); if (!service || !agent || !agent_path || !callback) return -ESRCH; message = dbus_message_new_method_call(agent_sender, agent_path, CONNMAN_AGENT_INTERFACE, "RequestInput"); if (!message) return -ENOMEM; dbus_message_iter_init_append(message, &iter); path = __connman_service_get_path(service); dbus_message_iter_append_basic(&iter, DBUS_TYPE_OBJECT_PATH, &path); connman_dbus_dict_open(&iter, &dict); connman_dbus_dict_append_dict(&dict, "Username", request_input_append_identity, service); connman_dbus_dict_append_dict(&dict, "Password", request_input_append_password, service); connman_dbus_dict_close(&iter, &dict); username_password_reply = g_try_new0(struct request_input_reply, 1); if (!username_password_reply) { dbus_message_unref(message); return -ENOMEM; } username_password_reply->service = service; username_password_reply->callback = callback; username_password_reply->user_data = user_data; err = connman_agent_queue_message(service, message, connman_timeout_input_request(), request_input_login_reply, username_password_reply, agent); if (err < 0 && err != -EBUSY) { DBG("error %d sending agent request", err); dbus_message_unref(message); g_free(username_password_reply); return err; } dbus_message_unref(message); return -EINPROGRESS; }
static int create_configuration(DBusMessage *msg, connection_ready_cb callback) { DBusMessage *new_msg = NULL; DBusPendingCall *call; DBusMessageIter iter, array, new_iter, new_dict; const char *type = NULL, *name = NULL; const char *host = NULL, *domain = NULL; char *ident, *me = NULL; int err = 0; dbus_bool_t result; struct connection_data *data; struct config_create_data *user_data = NULL; GSList *networks = NULL; /* * We copy the old message data into new message. We cannot * just use the old message as is because the user route * information is not in the same format in vpnd. */ new_msg = dbus_message_new(DBUS_MESSAGE_TYPE_METHOD_CALL); dbus_message_iter_init_append(new_msg, &new_iter); connman_dbus_dict_open(&new_iter, &new_dict); dbus_message_iter_init(msg, &iter); dbus_message_iter_recurse(&iter, &array); while (dbus_message_iter_get_arg_type(&array) == DBUS_TYPE_DICT_ENTRY) { DBusMessageIter entry, value; void *item_value; const char *key; int value_type; dbus_message_iter_recurse(&array, &entry); dbus_message_iter_get_basic(&entry, &key); dbus_message_iter_next(&entry); dbus_message_iter_recurse(&entry, &value); value_type = dbus_message_iter_get_arg_type(&value); item_value = NULL; switch (value_type) { case DBUS_TYPE_STRING: dbus_message_iter_get_basic(&value, &item_value); if (g_str_equal(key, "Type") == TRUE) { type = (const char *)item_value; } else if (g_str_equal(key, "Name") == TRUE) { name = (const char *)item_value; } else if (g_str_equal(key, "Host") == TRUE) { host = (const char *)item_value; } else if (g_str_equal(key, "VPN.Domain") == TRUE) { domain = (const char *)item_value; } DBG("%s %s", key, (char *)item_value); if (item_value != NULL) connman_dbus_dict_append_basic(&new_dict, key, value_type, &item_value); break; case DBUS_TYPE_ARRAY: if (g_str_equal(key, "Networks") == TRUE) { networks = get_user_networks(&value); connman_dbus_dict_append_array(&new_dict, "UserRoutes", DBUS_TYPE_DICT_ENTRY, append_routes, networks); } break; } dbus_message_iter_next(&array); } connman_dbus_dict_close(&new_iter, &new_dict); DBG("VPN type %s name %s host %s domain %s networks %p", type, name, host, domain, networks); if (host == NULL || domain == NULL) { err = -EINVAL; goto done; } if (type == NULL || name == NULL) { err = -EOPNOTSUPP; goto done; } ident = g_strdup_printf("%s_%s", host, domain); set_dbus_ident(ident); DBG("ident %s", ident); data = g_hash_table_lookup(vpn_connections, ident); if (data != NULL) { if (data->call != NULL || data->cb_data != NULL) { DBG("create configuration call already pending"); err = -EINPROGRESS; goto done; } } else { char *path = g_strdup_printf("%s/connection/%s", VPN_PATH, ident); data = create_connection_data(path); g_free(path); if (data == NULL) { err = -ENOMEM; goto done; } g_hash_table_insert(vpn_connections, g_strdup(ident), data); } /* * User called net.connman.Manager.ConnectProvider if we are here. * So use the data from original message in the new msg. */ me = g_strdup(dbus_message_get_destination(msg)); dbus_message_set_interface(new_msg, VPN_MANAGER_INTERFACE); dbus_message_set_path(new_msg, "/"); dbus_message_set_destination(new_msg, VPN_SERVICE); dbus_message_set_sender(new_msg, me); dbus_message_set_member(new_msg, "Create"); user_data = g_try_new0(struct config_create_data, 1); if (user_data == NULL) { err = -ENOMEM; goto done; } user_data->callback = callback; user_data->message = dbus_message_ref(msg); user_data->path = NULL; DBG("cb %p msg %p", user_data, msg); result = dbus_connection_send_with_reply(connection, new_msg, &call, DBUS_TIMEOUT); if (result == FALSE || call == NULL) { err = -EIO; goto done; } dbus_pending_call_set_notify(call, configuration_create_reply, user_data, NULL); data->call = call; done: if (new_msg != NULL) dbus_message_unref(new_msg); if (networks != NULL) g_slist_free_full(networks, destroy_route); g_free(me); return err; }
int __connman_agent_request_input(struct connman_service *service, authentication_cb_t callback, void *user_data) { DBusMessage *message; const char *path; DBusMessageIter iter; DBusMessageIter dict; DBusPendingCall *call; struct request_input_reply *passphrase_reply; if (service == NULL || agent_path == NULL || callback == NULL) return -ESRCH; message = dbus_message_new_method_call(agent_sender, agent_path, CONNMAN_AGENT_INTERFACE, "RequestInput"); if (message == NULL) return -ENOMEM; dbus_message_iter_init_append(message, &iter); path = __connman_service_get_path(service); dbus_message_iter_append_basic(&iter, DBUS_TYPE_OBJECT_PATH, &path); connman_dbus_dict_open(&iter, &dict); if (__connman_service_get_security(service) == CONNMAN_SERVICE_SECURITY_8021X) { connman_dbus_dict_append_dict(&dict, "Identity", request_input_append_identity, service); } connman_dbus_dict_append_dict(&dict, "Passphrase", request_input_append_passphrase, service); if (__connman_service_wps_enabled(service) == TRUE) { connman_dbus_dict_append_dict(&dict, "WPS", request_input_append_wps, NULL); } connman_dbus_dict_close(&iter, &dict); passphrase_reply = g_try_new0(struct request_input_reply, 1); if (passphrase_reply == NULL) { dbus_message_unref(message); return -ENOMEM; } if (dbus_connection_send_with_reply(connection, message, &call, -1) == FALSE) { dbus_message_unref(message); g_free(passphrase_reply); return -ESRCH; } if (call == NULL) { dbus_message_unref(message); g_free(passphrase_reply); return -ESRCH; } passphrase_reply->service = connman_service_ref(service); passphrase_reply->callback = callback; passphrase_reply->user_data = user_data; dbus_pending_call_set_notify(call, request_input_passphrase_reply, passphrase_reply, NULL); dbus_message_unref(message); return -EIO; }
static void create_proxy_configuration(void) { DBusMessage *msg; DBusMessageIter iter, dict; DBusPendingCall *call; dbus_bool_t result; char *interface; const char *method; const char *str; char **str_list; if (default_service == NULL) return; DBG(""); msg = dbus_message_new_method_call(PACRUNNER_SERVICE, PACRUNNER_PATH, PACRUNNER_INTERFACE, "CreateProxyConfiguration"); if (msg == NULL) return; dbus_message_set_auto_start(msg, FALSE); dbus_message_iter_init_append(msg, &iter); connman_dbus_dict_open(&iter, &dict); switch(connman_service_get_proxy_method(default_service)) { case CONNMAN_SERVICE_PROXY_METHOD_UNKNOWN: goto done; case CONNMAN_SERVICE_PROXY_METHOD_DIRECT: method= "direct"; break; case CONNMAN_SERVICE_PROXY_METHOD_MANUAL: method = "manual"; str_list = connman_service_get_proxy_servers(default_service); if (str_list == NULL) goto done; connman_dbus_dict_append_array(&dict, "Servers", DBUS_TYPE_STRING, append_string_list, str_list); g_strfreev(str_list); str_list = connman_service_get_proxy_excludes(default_service); if (str_list == NULL) break; connman_dbus_dict_append_array(&dict, "Excludes", DBUS_TYPE_STRING, append_string_list, str_list); g_strfreev(str_list); break; case CONNMAN_SERVICE_PROXY_METHOD_AUTO: method = "auto"; str = connman_service_get_proxy_url(default_service); if (str == NULL) { str = connman_service_get_proxy_autoconfig( default_service); if (str == NULL) goto done; } connman_dbus_dict_append_basic(&dict, "URL", DBUS_TYPE_STRING, &str); break; } connman_dbus_dict_append_basic(&dict, "Method", DBUS_TYPE_STRING, &method); interface = connman_service_get_interface(default_service); if (interface != NULL) { connman_dbus_dict_append_basic(&dict, "Interface", DBUS_TYPE_STRING, &interface); g_free(interface); } str = connman_service_get_domainname(default_service); if (str != NULL) connman_dbus_dict_append_array(&dict, "Domains", DBUS_TYPE_STRING, append_string, &str); str_list = connman_service_get_nameservers(default_service); if (str_list != NULL) connman_dbus_dict_append_array(&dict, "Nameservers", DBUS_TYPE_STRING, append_string_list, str_list); connman_dbus_dict_close(&iter, &dict); result = dbus_connection_send_with_reply(connection, msg, &call, DBUS_TIMEOUT); if (result == FALSE || call == NULL) goto done; dbus_pending_call_set_notify(call, create_config_reply, NULL, NULL); dbus_pending_call_unref(call); done: dbus_message_unref(msg); }
static int request_cookie_input(struct vpn_provider *provider, struct oc_private_data *data) { DBusMessage *message; const char *path, *agent_sender, *agent_path; DBusMessageIter iter; DBusMessageIter dict; const char *str; int err; connman_agent_get_info(&agent_sender, &agent_path); if (provider == NULL || agent_path == NULL) return -ESRCH; message = dbus_message_new_method_call(agent_sender, agent_path, VPN_AGENT_INTERFACE, "RequestInput"); if (message == NULL) return -ENOMEM; dbus_message_iter_init_append(message, &iter); path = vpn_provider_get_path(provider); dbus_message_iter_append_basic(&iter, DBUS_TYPE_OBJECT_PATH, &path); connman_dbus_dict_open(&iter, &dict); str = vpn_provider_get_string(provider, "OpenConnect.CACert"); if (str != NULL) connman_dbus_dict_append_dict(&dict, "OpenConnect.CACert", request_input_append_informational, (void *)str); str = vpn_provider_get_string(provider, "OpenConnect.ClientCert"); if (str != NULL) connman_dbus_dict_append_dict(&dict, "OpenConnect.ClientCert", request_input_append_informational, (void *)str); connman_dbus_dict_append_dict(&dict, "OpenConnect.ServerCert", request_input_append_mandatory, NULL); connman_dbus_dict_append_dict(&dict, "OpenConnect.VPNHost", request_input_append_mandatory, NULL); connman_dbus_dict_append_dict(&dict, "OpenConnect.Cookie", request_input_append_mandatory, NULL); vpn_agent_append_host_and_name(&dict, provider); connman_dbus_dict_close(&iter, &dict); err = connman_agent_queue_message(provider, message, connman_timeout_input_request(), request_input_cookie_reply, data); if (err < 0 && err != -EBUSY) { DBG("error %d sending agent request", err); dbus_message_unref(message); return err; } dbus_message_unref(message); return -EINPROGRESS; }
static void setup_tun_interface(unsigned int flags, unsigned change, void *data) { struct connman_private_network *pn = data; unsigned char prefixlen; DBusMessageIter array, dict; const char *server_ip; const char *peer_ip; const char *subnet_mask; int err; DBG("index %d flags %d change %d", pn->index, flags, change); if (flags & IFF_UP) return; subnet_mask = __connman_ippool_get_subnet_mask(pn->pool); server_ip = __connman_ippool_get_start_ip(pn->pool); peer_ip = __connman_ippool_get_end_ip(pn->pool); prefixlen = connman_ipaddress_calc_netmask_len(subnet_mask); if ((__connman_inet_modify_address(RTM_NEWADDR, NLM_F_REPLACE | NLM_F_ACK, pn->index, AF_INET, server_ip, peer_ip, prefixlen, NULL)) < 0) { DBG("address setting failed"); return; } connman_inet_ifup(pn->index); err = __connman_nat_enable(BRIDGE_NAME, server_ip, prefixlen); if (err < 0) { connman_error("failed to enable NAT"); goto error; } dbus_message_iter_init_append(pn->reply, &array); dbus_message_iter_append_basic(&array, DBUS_TYPE_OBJECT_PATH, &pn->path); connman_dbus_dict_open(&array, &dict); connman_dbus_dict_append_basic(&dict, "ServerIPv4", DBUS_TYPE_STRING, &server_ip); connman_dbus_dict_append_basic(&dict, "PeerIPv4", DBUS_TYPE_STRING, &peer_ip); if (pn->primary_dns) connman_dbus_dict_append_basic(&dict, "PrimaryDNS", DBUS_TYPE_STRING, &pn->primary_dns); if (pn->secondary_dns) connman_dbus_dict_append_basic(&dict, "SecondaryDNS", DBUS_TYPE_STRING, &pn->secondary_dns); connman_dbus_dict_close(&array, &dict); dbus_message_iter_append_basic(&array, DBUS_TYPE_UNIX_FD, &pn->fd); g_dbus_send_message(connection, pn->reply); return; error: pn->reply = __connman_error_failed(pn->msg, -err); g_dbus_send_message(connection, pn->reply); g_hash_table_remove(pn_hash, pn->path); }