5 * Copyright (C) 2012 Intel Corporation. All rights reserved.
6 * Copyright (C) 2019 Jolla Ltd. All rights reserved.
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 as
10 * published by the Free Software Foundation.
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
32 #include <connman/log.h>
33 #include <connman/agent.h>
34 #include <connman/vpn-dbus.h>
35 #include <connman/task.h>
36 #include <vpn/vpn-provider.h>
38 #include "vpn-agent.h"
41 bool vpn_agent_check_reply_has_dict(DBusMessage *reply)
43 const char *signature = DBUS_TYPE_ARRAY_AS_STRING
44 DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING
45 DBUS_TYPE_STRING_AS_STRING
46 DBUS_TYPE_VARIANT_AS_STRING
47 DBUS_DICT_ENTRY_END_CHAR_AS_STRING;
49 if (dbus_message_has_signature(reply, signature))
52 connman_warn("Reply %s to %s from %s has wrong signature %s",
54 dbus_message_get_interface(reply),
55 dbus_message_get_sender(reply),
56 dbus_message_get_signature(reply));
61 static void request_input_append_name(DBusMessageIter *iter, void *user_data)
63 struct vpn_provider *provider = user_data;
64 const char *str = "string";
66 connman_dbus_dict_append_basic(iter, "Type",
67 DBUS_TYPE_STRING, &str);
68 str = "informational";
69 connman_dbus_dict_append_basic(iter, "Requirement",
70 DBUS_TYPE_STRING, &str);
72 str = vpn_provider_get_name(provider);
73 connman_dbus_dict_append_basic(iter, "Value",
74 DBUS_TYPE_STRING, &str);
77 static void request_input_append_host(DBusMessageIter *iter, void *user_data)
79 struct vpn_provider *provider = user_data;
80 const char *str = "string";
82 connman_dbus_dict_append_basic(iter, "Type",
83 DBUS_TYPE_STRING, &str);
84 str = "informational";
85 connman_dbus_dict_append_basic(iter, "Requirement",
86 DBUS_TYPE_STRING, &str);
88 str = vpn_provider_get_host(provider);
89 connman_dbus_dict_append_basic(iter, "Value",
90 DBUS_TYPE_STRING, &str);
93 void vpn_agent_append_host_and_name(DBusMessageIter *iter,
94 struct vpn_provider *provider)
96 connman_dbus_dict_append_dict(iter, "Host",
97 request_input_append_host,
100 connman_dbus_dict_append_dict(iter, "Name",
101 request_input_append_name,
105 struct user_info_data {
106 struct vpn_provider *provider;
107 const char *username_str;
108 const char *type_str;
111 static void request_input_append_user_info(DBusMessageIter *iter,
114 struct user_info_data *data = user_data;
115 struct vpn_provider *provider = data->provider;
116 const char *str = NULL;
118 connman_dbus_dict_append_basic(iter, "Type",
119 DBUS_TYPE_STRING, &data->type_str);
121 connman_dbus_dict_append_basic(iter, "Requirement",
122 DBUS_TYPE_STRING, &str);
124 if (data->username_str) {
125 str = vpn_provider_get_string(provider, data->username_str);
127 connman_dbus_dict_append_basic(iter, "Value",
128 DBUS_TYPE_STRING, &str);
132 void vpn_agent_append_user_info(DBusMessageIter *iter,
133 struct vpn_provider *provider,
134 const char *username_str)
136 struct user_info_data data = {
137 .provider = provider,
138 .username_str = username_str
141 data.type_str = "string";
142 connman_dbus_dict_append_dict(iter, "Username",
143 request_input_append_user_info,
146 data.username_str = NULL;
147 data.type_str = "password";
148 connman_dbus_dict_append_dict(iter, "Password",
149 request_input_append_user_info,
153 static void request_input_append_flag(DBusMessageIter *iter,
156 dbus_bool_t data = (dbus_bool_t)GPOINTER_TO_INT(user_data);
157 const char *str = NULL;
160 connman_dbus_dict_append_basic(iter, "Type",
161 DBUS_TYPE_STRING, &str);
164 connman_dbus_dict_append_basic(iter, "Requirement",
165 DBUS_TYPE_STRING, &str);
167 connman_dbus_dict_append_basic(iter, "Value",
168 DBUS_TYPE_BOOLEAN, &data);
171 void vpn_agent_append_allow_credential_storage(DBusMessageIter *iter,
174 connman_dbus_dict_append_dict(iter, "AllowStoreCredentials",
175 request_input_append_flag,
176 GINT_TO_POINTER(allow));
179 void vpn_agent_append_allow_credential_retrieval(DBusMessageIter *iter,
182 connman_dbus_dict_append_dict(iter, "AllowRetrieveCredentials",
183 request_input_append_flag,
184 GINT_TO_POINTER(allow));
187 void vpn_agent_append_keep_credentials(DBusMessageIter *iter, bool allow)
189 connman_dbus_dict_append_dict(iter, "KeepCredentials",
190 request_input_append_flag,
191 GINT_TO_POINTER(allow));
194 struct failure_data {
195 struct vpn_provider *provider;
196 const char* type_str;
201 static void request_input_append_failure(DBusMessageIter *iter,
204 struct failure_data *data;
209 connman_dbus_dict_append_basic(iter, "Type",
210 DBUS_TYPE_STRING, &data->type_str);
211 str = "informational";
212 connman_dbus_dict_append_basic(iter, "Requirement",
213 DBUS_TYPE_STRING, &str);
217 /* Try to get information from provider about error */
219 str = vpn_provider_get_string(data->provider, data->key);
222 connman_dbus_dict_append_basic(iter, "Value",
223 DBUS_TYPE_STRING, &str);
226 void vpn_agent_append_auth_failure(DBusMessageIter *iter,
227 struct vpn_provider *provider,
228 const char* information)
230 struct failure_data data;
233 /* Skip if there are no auth errors */
234 value = vpn_provider_get_authentication_errors(provider);
238 data.provider = provider;
239 data.type_str = "string";
240 data.key = "VpnAgent.AuthFailure";
241 data.str = information;
243 connman_dbus_dict_append_dict(iter, data.key,
244 request_input_append_failure, &data);
247 int vpn_agent_check_and_process_reply_error(DBusMessage *reply,
248 struct vpn_provider *provider,
249 struct connman_task *task,
250 vpn_provider_connect_cb_t cb, void *user_data)
255 if (!reply || !provider)
258 dbus_error_init(&error);
260 if (!dbus_set_error_from_message(&error, reply))
263 if (!g_strcmp0(error.name, VPN_AGENT_INTERFACE ".Error.Canceled"))
265 else if (!g_strcmp0(error.name, "org.freedesktop.DBus.Error.Timeout"))
267 else if (!g_strcmp0(error.name, "org.freedesktop.DBus.Error.NoReply"))
272 dbus_error_free(&error);
275 cb(provider, user_data, err);
278 connman_task_stop(task);
281 * VPN agent dialog cancel, timeout, broken connection should set the
282 * VPN back to idle state
284 vpn_provider_set_state(provider, VPN_PROVIDER_STATE_IDLE);