firewall: cleanups and code consolidation

Consolidate the NMDevice firewall add code so that firewall
handling is done in one place.
This commit is contained in:
Dan Williams 2011-11-09 23:05:18 -06:00
parent bc628da16b
commit cf7ec0e63e
4 changed files with 137 additions and 140 deletions

View file

@ -50,60 +50,89 @@ typedef struct {
/********************************************************************/
DBusGProxyCall *
nm_firewall_manager_add_to_zone (NMFirewallManager *self,
const char *ip_iface,
const char *zone,
DBusGProxyCallNotify callback,
gpointer callback_data)
{
NMFirewallManagerPrivate *priv = NM_FIREWALL_MANAGER_GET_PRIVATE (self);
DBusGProxyCall * call = NULL;
typedef struct {
char *iface;
FwAddToZoneFunc callback;
gpointer user_data1;
gpointer user_data2;
} AddInfo;
if (nm_firewall_manager_available (self)) {
nm_log_dbg (LOGD_DEVICE, "(%s) adding to firewall zone: %s", ip_iface, zone );
call = dbus_g_proxy_begin_call_with_timeout (priv->proxy,
"AddInterface",
callback,
callback_data, /* NMDevice */
NULL, /* destroy callback_data */
10000, /* timeout */
G_TYPE_STRING, ip_iface,
G_TYPE_STRING, zone ? zone : "",
DBUS_TYPE_G_MAP_OF_VARIANT, NULL, /* a{sv}:options */
G_TYPE_INVALID);
} else {
nm_log_dbg (LOGD_DEVICE, "Firewall zone add skipped because firewall isn't running");
callback (NULL, NULL, callback_data);
static void
add_info_free (AddInfo *info)
{
g_return_if_fail (info != NULL);
g_free (info->iface);
g_free (info);
}
static void
add_cb (DBusGProxy *proxy, DBusGProxyCall *call_id, gpointer user_data)
{
AddInfo *info = user_data;
GError *error = NULL;
if (!dbus_g_proxy_end_call (proxy, call_id, &error, G_TYPE_INVALID)) {
g_assert (error);
nm_log_warn (LOGD_DEVICE, "(%s) firewall zone change failed: (%d) %s",
info->iface, error->code, error->message);
}
return call;
info->callback (error, info->user_data1, info->user_data2);
g_clear_error (&error);
}
void nm_firewall_manager_cancel_add (NMFirewallManager *self, DBusGProxyCall * fw_call)
gpointer
nm_firewall_manager_add_to_zone (NMFirewallManager *self,
const char *iface,
const char *zone,
FwAddToZoneFunc callback,
gpointer user_data1,
gpointer user_data2)
{
NMFirewallManagerPrivate *priv = NM_FIREWALL_MANAGER_GET_PRIVATE (self);
AddInfo *info;
dbus_g_proxy_cancel_call (priv->proxy, fw_call);
if (priv->running == FALSE) {
nm_log_dbg (LOGD_DEVICE, "(%s) firewall zone change skipped (not running)", iface);
callback (NULL, user_data1, user_data2);
return NULL;
}
info = g_malloc0 (sizeof (*info));
info->iface = g_strdup (iface);
info->callback = callback;
info->user_data1 = user_data1;
info->user_data2 = user_data2;
nm_log_dbg (LOGD_DEVICE, "(%s) firewall zone change -> %s", iface, zone );
return dbus_g_proxy_begin_call_with_timeout (priv->proxy,
"AddInterface",
add_cb,
info,
(GDestroyNotify) add_info_free,
10000, /* timeout */
G_TYPE_STRING, iface,
G_TYPE_STRING, zone ? zone : "",
DBUS_TYPE_G_MAP_OF_VARIANT, NULL, /* a{sv}:options */
G_TYPE_INVALID);
}
gboolean
nm_firewall_manager_available (NMFirewallManager *self)
void nm_firewall_manager_cancel_add (NMFirewallManager *self, gpointer call)
{
g_return_val_if_fail (self != NULL, FALSE);
g_return_val_if_fail (NM_IS_FIREWALL_MANAGER (self), FALSE);
return NM_FIREWALL_MANAGER_GET_PRIVATE (self)->running;
g_return_if_fail (self != NULL);
g_return_if_fail (NM_IS_FIREWALL_MANAGER (self));
dbus_g_proxy_cancel_call (NM_FIREWALL_MANAGER_GET_PRIVATE (self)->proxy,
(DBusGProxyCall *) call);
}
static void
set_running (NMFirewallManager *self, gboolean now_running)
{
NMFirewallManagerPrivate *priv = NM_FIREWALL_MANAGER_GET_PRIVATE (self);
gboolean old_available = nm_firewall_manager_available (self);
gboolean old_running = priv->running;
priv->running = now_running;
if (old_available != nm_firewall_manager_available (self))
if (old_running != priv->running)
g_object_notify (G_OBJECT (self), NM_FIREWALL_MANAGER_AVAILABLE);
}
@ -179,7 +208,7 @@ get_property (GObject *object, guint prop_id, GValue *value, GParamSpec *pspec)
{
switch (prop_id) {
case PROP_AVAILABLE:
g_value_set_boolean (value, nm_firewall_manager_available (NM_FIREWALL_MANAGER (object)));
g_value_set_boolean (value, NM_FIREWALL_MANAGER_GET_PRIVATE (object)->running);
break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);

View file

@ -55,9 +55,17 @@ GType nm_firewall_manager_get_type (void);
NMFirewallManager *nm_firewall_manager_get (void);
gboolean nm_firewall_manager_available (NMFirewallManager *mgr);
typedef void (*FwAddToZoneFunc) (GError *error,
gpointer user_data1,
gpointer user_data2);
DBusGProxyCall *nm_firewall_manager_add_to_zone(NMFirewallManager *mgr, const char *ip_iface, const char *zone, DBusGProxyCallNotify callback, gpointer callback_data);
void nm_firewall_manager_cancel_add (NMFirewallManager *mgr, DBusGProxyCall * fw_call);
gpointer nm_firewall_manager_add_to_zone (NMFirewallManager *mgr,
const char *iface,
const char *zone,
FwAddToZoneFunc callback,
gpointer user_data1,
gpointer user_data2);
void nm_firewall_manager_cancel_add (NMFirewallManager *mgr, gpointer fw_call);
#endif /* NM_FIREWALL_MANAGER_H */

View file

@ -191,6 +191,8 @@ static gboolean nm_device_set_ip6_config (NMDevice *dev,
gboolean assumed,
NMDeviceStateReason *reason);
static gboolean nm_device_activate_ip6_config_commit (gpointer user_data);
static void dhcp4_cleanup (NMDevice *self, gboolean stop, gboolean release);
static const char *reason_to_string (NMDeviceStateReason reason);
@ -2390,6 +2392,9 @@ nm_device_activate_ip4_config_commit (gpointer user_data)
if (NM_DEVICE_GET_CLASS (self)->ip4_config_pre_commit)
NM_DEVICE_GET_CLASS (self)->ip4_config_pre_commit (self, config);
/* Merge with user overrides */
nm_utils_merge_ip4_config (config, nm_connection_get_setting_ip4_config (connection));
assumed = nm_act_request_get_assumed (priv->act_request);
if (!nm_device_set_ip4_config (self, config, assumed, &reason)) {
nm_log_info (LOGD_DEVICE | LOGD_IP4,
@ -2428,38 +2433,62 @@ out:
}
static void
ip4_add_to_zone_cb (DBusGProxy *proxy, DBusGProxyCall *call_id, gpointer user_data)
fw_add_to_zone_cb (GError *error,
gpointer user_data1,
gpointer user_data2)
{
NMDevice *self = NM_DEVICE (user_data);
NMDevice *self = NM_DEVICE (user_data1);
NMDevicePrivate *priv = NM_DEVICE_GET_PRIVATE (self);
GError *error = NULL;
gboolean ip4 = GPOINTER_TO_UINT (user_data2);
priv->fw_call = NULL;
if (proxy && call_id) {
if (!dbus_g_proxy_end_call (proxy, call_id, &error, G_TYPE_INVALID)) {
nm_log_warn (LOGD_DEVICE, "adding iface to zone failed: (%d) %s",
error ? error->code : -1,
error && error->message ? error->message : "(unknown)");
g_clear_error (&error);
/* FIXME: fail the device activation? */
}
if (error) {
/* FIXME: fail the device activation? */
}
activation_source_schedule (self, nm_device_activate_ip4_config_commit, AF_INET);
if (ip4)
activation_source_schedule (self, nm_device_activate_ip4_config_commit, AF_INET);
else
activation_source_schedule (self, nm_device_activate_ip6_config_commit, AF_INET6);
nm_log_info (LOGD_DEVICE | LOGD_IP4,
"Activation (%s) Stage 5 of 5 (IPv4 Configure Commit) scheduled...",
nm_device_get_iface (self));
nm_log_info (LOGD_DEVICE | (ip4 ? LOGD_IP4 : LOGD_IP6),
"Activation (%s) Stage 5 of 5 (IPv%c Configure Commit) scheduled...",
nm_device_get_iface (self),
ip4 ? '4' : '6');
}
static void
fw_add_to_zone (NMDevice *self, gboolean ip4)
{
NMDevicePrivate *priv = NM_DEVICE_GET_PRIVATE (self);
NMConnection *connection;
NMSettingConnection *s_con = NULL;
/* Only set the interface's zone if the device isn't yet activated. If
* already activated, the zone has already been set.
*/
if (nm_device_get_state (self) == NM_DEVICE_STATE_ACTIVATED) {
fw_add_to_zone_cb (NULL, self, GUINT_TO_POINTER (ip4));
return;
}
/* Otherwise tell the firewall to add the interface to the specified zone */
connection = nm_act_request_get_connection (priv->act_request);
g_assert (connection);
s_con = nm_connection_get_setting_connection (connection);
priv->fw_call = nm_firewall_manager_add_to_zone (priv->fw_manager,
nm_device_get_ip_iface (self),
nm_setting_connection_get_zone (s_con),
fw_add_to_zone_cb,
self,
GUINT_TO_POINTER (ip4));
}
void
nm_device_activate_schedule_ip4_config_result (NMDevice *self, NMIP4Config *config)
{
NMDevicePrivate *priv;
NMConnection *connection = NULL;
NMSettingConnection *s_con = NULL;
g_return_if_fail (NM_IS_DEVICE (self));
@ -2471,29 +2500,12 @@ nm_device_activate_schedule_ip4_config_result (NMDevice *self, NMIP4Config *conf
return;
}
connection = nm_act_request_get_connection (priv->act_request);
g_assert (connection);
/* Merge with user overrides and save the pending config */
nm_utils_merge_ip4_config (config, nm_connection_get_setting_ip4_config (connection));
g_object_set_data_full (G_OBJECT (priv->act_request),
PENDING_IP4_CONFIG,
g_object_ref (config),
g_object_unref);
/* Only set the interface's zone if the device isn't yet activated. If
* already activated, the zone has already been set.
*/
if (nm_device_get_state (self) == NM_DEVICE_STATE_ACTIVATED)
ip4_add_to_zone_cb (NULL, NULL, self);
else {
s_con = nm_connection_get_setting_connection (connection);
priv->fw_call = nm_firewall_manager_add_to_zone (priv->fw_manager,
nm_device_get_ip_iface (self),
nm_setting_connection_get_zone (s_con),
ip4_add_to_zone_cb,
self);
}
fw_add_to_zone (self, AF_INET);
}
gboolean
@ -2560,40 +2572,10 @@ nm_device_activate_ip6_config_commit (gpointer user_data)
return FALSE;
}
static void
ip6_add_to_zone_cb (DBusGProxy *proxy, DBusGProxyCall *call_id, gpointer user_data)
{
NMDevice *self = NM_DEVICE (user_data);
NMDevicePrivate *priv = NM_DEVICE_GET_PRIVATE (self);
GError *error = NULL;
priv->fw_call = NULL;
if (proxy && call_id) {
if (!dbus_g_proxy_end_call (proxy, call_id, &error, G_TYPE_INVALID)) {
nm_log_warn (LOGD_DEVICE, "adding iface to zone failed: (%d) %s",
error ? error->code : -1,
error && error->message ? error->message : "(unknown)");
g_clear_error (&error);
/* FIXME: fail the device activation? */
}
}
activation_source_schedule (self, nm_device_activate_ip6_config_commit, AF_INET6);
nm_log_info (LOGD_DEVICE | LOGD_IP6,
"Activation (%s) Stage 5 of 5 (IPv6 Commit) scheduled...",
nm_device_get_iface (self));
}
void
nm_device_activate_schedule_ip6_config_result (NMDevice *self, NMIP6Config *config)
{
NMDevicePrivate *priv;
NMConnection *connection = NULL;
NMSettingConnection *s_con = NULL;
g_return_if_fail (NM_IS_DEVICE (self));
@ -2605,28 +2587,13 @@ nm_device_activate_schedule_ip6_config_result (NMDevice *self, NMIP6Config *conf
return;
}
connection = nm_act_request_get_connection (priv->act_request);
g_assert (connection);
/* Save the pending config */
g_object_set_data_full (G_OBJECT (priv->act_request),
PENDING_IP6_CONFIG,
g_object_ref (config),
g_object_unref);
/* Only set the interface's zone if the device isn't yet activated. If
* already activated, the zone has already been set.
*/
if (nm_device_get_state (self) == NM_DEVICE_STATE_ACTIVATED)
ip6_add_to_zone_cb (NULL, NULL, self);
else {
s_con = nm_connection_get_setting_connection (connection);
priv->fw_call = nm_firewall_manager_add_to_zone (priv->fw_manager,
nm_device_get_ip_iface (self),
nm_setting_connection_get_zone (s_con),
ip6_add_to_zone_cb,
self);
}
fw_add_to_zone (self, AF_INET6);
}
gboolean

View file

@ -1200,30 +1200,21 @@ connections_loaded (NMSettings *settings, gpointer user_data)
}
static void
add_to_zone_cb (DBusGProxy *proxy,
DBusGProxyCall *call_id,
void *user_data)
add_to_zone_cb (GError *error,
gpointer user_data1,
gpointer user_data2)
{
NMDevice *device = NM_DEVICE (user_data);
GError *error = NULL;
NMDevice *device = NM_DEVICE (user_data1);
if (proxy && call_id) {
if (!dbus_g_proxy_end_call (proxy, call_id, &error, G_TYPE_INVALID)) {
nm_log_warn (LOGD_DEVICE, "(%s) addition to firewall zone failed: (%d) %s",
nm_device_get_ip_iface (device),
error ? error->code : -1,
error && error->message ? error->message : "(unknown)");
g_clear_error (&error);
/* FIXME: fail connection since firewall zone add failed? */
}
if (error) {
/* FIXME: what do we do here? */
}
g_object_unref (device);
}
static void
inform_firewall_about_zone (NMPolicy * policy,
NMConnection *connection)
inform_firewall_about_zone (NMPolicy *policy, NMConnection *connection)
{
NMSettingConnection *s_con = nm_connection_get_setting_connection (connection);
GSList *iter, *devices;
@ -1232,12 +1223,14 @@ inform_firewall_about_zone (NMPolicy * policy,
for (iter = devices; iter; iter = g_slist_next (iter)) {
NMDevice *dev = NM_DEVICE (iter->data);
if (get_device_connection (dev) == connection) {
if ( (get_device_connection (dev) == connection)
&& (nm_device_get_state (dev) == NM_DEVICE_STATE_ACTIVATED)) {
nm_firewall_manager_add_to_zone (policy->fw_manager,
nm_device_get_ip_iface (dev),
nm_setting_connection_get_zone (s_con),
add_to_zone_cb,
g_object_ref (dev));
g_object_ref (dev),
NULL);
}
}
}