mirror of
https://gitlab.freedesktop.org/NetworkManager/NetworkManager.git
synced 2025-12-25 03:40:07 +01:00
config: merge branch 'th/nm-config-intern-bgo750558'
Add write support to NMConfig. Also, add a new configuration directory /usr/lib/NetworkManager/conf.d/ which allows us to install configuration snippets under /usr, instead of /etc. https://bugzilla.gnome.org/show_bug.cgi?id=738853 https://bugzilla.gnome.org/show_bug.cgi?id=750558
This commit is contained in:
commit
05db3ee08a
14 changed files with 1503 additions and 188 deletions
|
|
@ -78,6 +78,7 @@ AC_SUBST(runstatedir)
|
|||
# NetworkManager paths
|
||||
AC_SUBST(nmbinary, "$sbindir/$PACKAGE", [NetworkManager binary executable])
|
||||
AC_SUBST(nmconfdir, "$sysconfdir/$PACKAGE", [NetworkManager configuration directory])
|
||||
AC_SUBST(nmlibdir, "$libdir/$PACKAGE", [NetworkManager library directory])
|
||||
AC_SUBST(nmdatadir, "$datadir/$PACKAGE", [NetworkManager shared data directory])
|
||||
AC_SUBST(nmstatedir, "$localstatedir/lib/$PACKAGE", [NetworkManager persistent state directory])
|
||||
AC_SUBST(nmrundir, "$runstatedir/$PACKAGE", [NetworkManager runtime state directory])
|
||||
|
|
@ -125,6 +126,11 @@ test "$enable_ifnet" = "yes" && distro_plugins="$distro_plugins,ifn
|
|||
distro_plugins="${distro_plugins#,}"
|
||||
|
||||
AC_DEFINE_UNQUOTED(CONFIG_PLUGINS_DEFAULT, "$config_plugins_default", [Default configuration option for main.plugins setting])
|
||||
if test "${enable_config_plugin_ibft}" = yes; then
|
||||
AC_DEFINE(WITH_SETTINGS_PLUGIN_IBFT, 1, [Whether compilation of ibft setting plugin is enabled])
|
||||
else
|
||||
AC_DEFINE(WITH_SETTINGS_PLUGIN_IBFT, 0, [Whether compilation of ibft setting plugin is enabled])
|
||||
fi
|
||||
|
||||
if test "$enable_ifcfg_rh" = "yes"; then
|
||||
DISTRO_NETWORK_SERVICE=network.service
|
||||
|
|
@ -1065,6 +1071,7 @@ echo " exec_prefix: $exec_prefix"
|
|||
echo " systemdunitdir: $with_systemdsystemunitdir"
|
||||
echo " nmbinary: $nmbinary"
|
||||
echo " nmconfdir: $nmconfdir"
|
||||
echo " nmlibdir: $nmlibdir"
|
||||
echo " nmdatadir: $nmdatadir"
|
||||
echo " nmstatedir: $nmstatedir"
|
||||
echo " nmrundir: $nmrundir"
|
||||
|
|
|
|||
|
|
@ -2,14 +2,24 @@
|
|||
#
|
||||
# See "man 5 NetworkManager.conf" for details.
|
||||
#
|
||||
# The directory /usr/lib/NetworkManager/conf.d/ can contain additional configuration
|
||||
# snippets installed by packages. These files are read before NetworkManager.conf
|
||||
# and have thus lowest priority.
|
||||
# The directory /etc/NetworkManager/conf.d/ can contain additional configuration
|
||||
# snippets that are installed by some packages. Those snippets override the
|
||||
# settings from this main file.
|
||||
# To override a configuration from a conf.d/ snippet, add another configuration
|
||||
# with a name sorted lastly (such as 99-my.conf).
|
||||
# snippets. Those snippets override the settings from this main file.
|
||||
#
|
||||
# The files within one conf.d/ directory are read in asciibetical order.
|
||||
#
|
||||
# If /etc/NetworkManager/conf.d/ contains a file with the same name as
|
||||
# /usr/lib/NetworkManager/conf.d/, the latter file is shadowed and thus ignored.
|
||||
# Hence, to disable loading a file from /usr/lib/NetworkManager/conf.d/ you can
|
||||
# put an empty file with the same name.
|
||||
#
|
||||
# If two files define the same key, the one that is read afterwards will overwrite
|
||||
# the previous one.
|
||||
|
||||
[main]
|
||||
plugins=ifcfg-rh,ibft
|
||||
#plugins=ifcfg-rh,ibft
|
||||
|
||||
[logging]
|
||||
#level=DEBUG
|
||||
|
|
|
|||
|
|
@ -34,6 +34,7 @@
|
|||
|
||||
%define systemd_dir %{_prefix}/lib/systemd/system
|
||||
%define udev_dir %{_prefix}/lib/udev
|
||||
%define nmlibdir %{_prefix}/lib/%{name}
|
||||
|
||||
%global with_adsl 1
|
||||
%global with_bluetooth 1
|
||||
|
|
@ -83,8 +84,7 @@ URL: http://www.gnome.org/projects/NetworkManager/
|
|||
Source: __SOURCE1__
|
||||
Source1: NetworkManager.conf
|
||||
Source2: 00-server.conf
|
||||
Source3: 10-ibft-plugin.conf
|
||||
Source4: 20-connectivity-fedora.conf
|
||||
Source3: 20-connectivity-fedora.conf
|
||||
|
||||
#Patch1: 0001-some.patch
|
||||
|
||||
|
|
@ -443,9 +443,9 @@ make install DESTDIR=$RPM_BUILD_ROOT
|
|||
%{__cp} %{SOURCE1} $RPM_BUILD_ROOT%{_sysconfdir}/%{name}/
|
||||
|
||||
mkdir -p $RPM_BUILD_ROOT%{_sysconfdir}/%{name}/conf.d
|
||||
%{__cp} %{SOURCE2} $RPM_BUILD_ROOT%{_sysconfdir}/%{name}/conf.d
|
||||
%{__cp} %{SOURCE3} $RPM_BUILD_ROOT%{_sysconfdir}/%{name}/conf.d
|
||||
%{__cp} %{SOURCE4} $RPM_BUILD_ROOT%{_sysconfdir}/%{name}/conf.d
|
||||
mkdir -p $RPM_BUILD_ROOT%{nmlibdir}/conf.d
|
||||
%{__cp} %{SOURCE2} $RPM_BUILD_ROOT%{nmlibdir}/conf.d/
|
||||
%{__cp} %{SOURCE3} $RPM_BUILD_ROOT%{nmlibdir}/conf.d/
|
||||
|
||||
# create a VPN directory
|
||||
%{__mkdir_p} $RPM_BUILD_ROOT%{_sysconfdir}/NetworkManager/VPN
|
||||
|
|
@ -543,7 +543,8 @@ fi
|
|||
%endif
|
||||
%dir %{_sysconfdir}/%{name}
|
||||
%dir %{_sysconfdir}/%{name}/conf.d
|
||||
%config %{_sysconfdir}/%{name}/conf.d/10-ibft-plugin.conf
|
||||
%dir %{nmlibdir}
|
||||
%dir %{nmlibdir}/conf.d
|
||||
%{_mandir}/man1/*
|
||||
%{_mandir}/man5/*
|
||||
%{_mandir}/man8/*
|
||||
|
|
@ -660,15 +661,15 @@ fi
|
|||
|
||||
%files config-connectivity-fedora
|
||||
%defattr(-,root,root,0755)
|
||||
%dir %{_sysconfdir}/%{name}
|
||||
%dir %{_sysconfdir}/%{name}/conf.d
|
||||
%config(noreplace) %{_sysconfdir}/%{name}/conf.d/20-connectivity-fedora.conf
|
||||
%dir %{nmlibdir}
|
||||
%dir %{nmlibdir}/conf.d
|
||||
%{nmlibdir}/conf.d/20-connectivity-fedora.conf
|
||||
|
||||
%files config-server
|
||||
%defattr(-,root,root,0755)
|
||||
%dir %{_sysconfdir}/%{name}
|
||||
%dir %{_sysconfdir}/%{name}/conf.d
|
||||
%config(noreplace) %{_sysconfdir}/%{name}/conf.d/00-server.conf
|
||||
%dir %{nmlibdir}
|
||||
%dir %{nmlibdir}/conf.d
|
||||
%{nmlibdir}/conf.d/00-server.conf
|
||||
|
||||
%if 0%{?with_nmtui}
|
||||
%files tui
|
||||
|
|
|
|||
|
|
@ -73,7 +73,6 @@ SOURCE="$(abs_path "$SOURCE" "$(ls -1 "$GITDIR/NetworkManager-$VERSION"*.tar* 2>
|
|||
[[ -f "$SOURCE" ]] || die "could not find source ${_SOURCE:-$GITDIR/NetworkManager-$VERSION*.tar*} . Did you execute \`make dist\`? Otherwise set \$SOURCE variable"
|
||||
SOURCE_NETWORKMANAGER_CONF="$(abs_path "$SOURCE_NETWORKMANAGER_CONF" "$SCRIPTDIR/NetworkManager.conf")"
|
||||
SOURCE_CONFIG_SERVER="$(abs_path "$SOURCE_CONFIG_SERVER" "$SCRIPTDIR/00-server.conf")"
|
||||
SOURCE_CONFIG_IBFT_PLUGIN="$(abs_path "$SOURCE_CONFIG_IBFT_PLUGIN" "$SCRIPTDIR/10-ibft-plugin.conf")"
|
||||
SOURCE_CONFIG_CONNECTIVITY_FEDORA="$(abs_path "$SOURCE_CONFIG_CONNECTIVITY_FEDORA" "$SCRIPTDIR/20-connectivity-fedora.conf")"
|
||||
|
||||
TEMP="$(mktemp -d "$SCRIPTDIR/NetworkManager.$DATE.XXXXXX")"
|
||||
|
|
@ -88,7 +87,6 @@ LOG "SPECFILE=$SPECFILE"
|
|||
LOG "SOURCE=$SOURCE"
|
||||
LOG "SOURCE_NETWORKMANAGER_CONF=$SOURCE_NETWORKMANAGER_CONF"
|
||||
LOG "SOURCE_CONFIG_SERVER=$SOURCE_CONFIG_SERVER"
|
||||
LOG "SOURCE_CONFIG_IBFT_PLUGIN=$SOURCE_CONFIG_IBFT_PLUGIN"
|
||||
LOG "SOURCE_CONFIG_CONNECTIVITY_FEDORA=$SOURCE_CONFIG_CONNECTIVITY_FEDORA"
|
||||
LOG "BASEDIR=$TEMP"
|
||||
|
||||
|
|
@ -102,7 +100,6 @@ mkdir -p "$TEMP/SOURCES/" "$TEMP/SPECS/" || die "error creating SPECS directoy"
|
|||
cp "$SOURCE" "$TEMP/SOURCES/" || die "Could not copy source $SOURCE to $TEMP/SOURCES"
|
||||
cp "$SOURCE_NETWORKMANAGER_CONF" "$TEMP/SOURCES/NetworkManager.conf" || die "Could not copy source $SOURCE_NETWORKMANAGER_CONF to $TEMP/SOURCES"
|
||||
cp "$SOURCE_CONFIG_SERVER" "$TEMP/SOURCES/00-server.conf" || die "Could not copy source $SOURCE_CONFIG_SERVER to $TEMP/SOURCES"
|
||||
cp "$SOURCE_CONFIG_IBFT_PLUGIN" "$TEMP/SOURCES/10-ibft-plugin.conf" || die "Could not copy source $SOURCE_CONFIG_IBFT_PLUGIN to $TEMP/SOURCES"
|
||||
cp "$SOURCE_CONFIG_CONNECTIVITY_FEDORA" "$TEMP/SOURCES/20-connectivity-fedora.conf" || die "Could not copy source $SOURCE_CONFIG_CONNECTIVITY_FEDORA to $TEMP/SOURCES"
|
||||
|
||||
write_changelog
|
||||
|
|
|
|||
|
|
@ -27,23 +27,39 @@ Copyright 2010 - 2014 Red Hat, Inc.
|
|||
|
||||
<refsynopsisdiv>
|
||||
<para><filename>/etc/NetworkManager/NetworkManager.conf</filename>,
|
||||
<filename>/etc/NetworkManager/conf.d/<replaceable>name</replaceable>.conf</filename>
|
||||
<filename>/etc/NetworkManager/conf.d/<replaceable>name</replaceable>.conf</filename>,
|
||||
<filename>/usr/lib/NetworkManager/conf.d/<replaceable>name</replaceable>.conf</filename>,
|
||||
<filename>/var/lib/NetworkManager/NetworkManager-intern.conf</filename>
|
||||
</para>
|
||||
</refsynopsisdiv>
|
||||
|
||||
<refsect1>
|
||||
<title>Description</title>
|
||||
<para>This is a configuration file for NetworkManager. It is used
|
||||
<para><literal>NetworkManager.conf</literal> is the configuration file for NetworkManager. It is used
|
||||
to set up various aspects of NetworkManager's behavior. The
|
||||
location of the file may be changed through use of the
|
||||
<option>--config</option> argument for NetworkManager.
|
||||
location of the main file and configuration directories may be changed
|
||||
through use of the <option>--config</option>, <option>--config-dir</option>,
|
||||
<option>--system-config-dir</option>, and <option>--intern-config</option>
|
||||
argument for NetworkManager, respectively.
|
||||
</para>
|
||||
<para>If a default <literal>NetworkManager.conf</literal> is
|
||||
provided by your distribution's packages, you should not modify
|
||||
it, since your changes may get overwritten by package
|
||||
updates. Instead, you can add additional <literal>.conf</literal>
|
||||
files to the <literal>conf.d</literal> directory. These will be read in order,
|
||||
with later files overriding earlier ones.
|
||||
files to the <literal>/etc/NetworkManager/conf.d</literal> directory.
|
||||
These will be read in order, with later files overriding earlier ones.
|
||||
Packages might install further configuration snippets to <literal>/usr/lib/NetworkManager/conf.d</literal>.
|
||||
This directory is parsed first, even before <literal>NetworkManager.conf</literal>.
|
||||
The loading of a file <literal>/usr/lib/NetworkManager/conf.d/<replaceable>name</replaceable>.conf</literal>
|
||||
can be prevented by adding a file <literal>/etc/NetworkManager/conf.d/<replaceable>name</replaceable>.conf</literal>.
|
||||
In this case, the file from the etc configuration shadows the file from the
|
||||
system configuration directory.
|
||||
</para>
|
||||
<para>
|
||||
NetworkManager can overwrite certain user configuration options via D-Bus or other internal
|
||||
operations. In this case it writes those changes to <literal>/var/lib/NetworkManager/NetworkManager-intern.conf</literal>.
|
||||
This file is not intended to be modified by the user, but it is read last and can shadow
|
||||
user configuration from <literal>NetworkManager.conf</literal>.
|
||||
</para>
|
||||
|
||||
</refsect1>
|
||||
|
|
@ -625,6 +641,9 @@ ipv6.ip6-privacy=1
|
|||
<filename>/etc/sysconfig/network-scripts/ifcfg-*</filename>
|
||||
files. It currently supports reading Ethernet, Wi-Fi,
|
||||
InfiniBand, VLAN, Bond, Bridge, and Team connections.
|
||||
Enabling <literal>ifcfg-rh</literal> implicitly enables
|
||||
<literal>ibft</literal> plugin, if it is available.
|
||||
This can be disabled by adding <literal>no-ibft</literal>.
|
||||
</para>
|
||||
</listitem>
|
||||
</varlistentry>
|
||||
|
|
@ -658,12 +677,16 @@ ipv6.ip6-privacy=1
|
|||
</varlistentry>
|
||||
|
||||
<varlistentry>
|
||||
<term><varname>ibft</varname></term>
|
||||
<term><varname>ibft</varname>, <varname>no-ibft</varname></term>
|
||||
<listitem>
|
||||
<para>
|
||||
This plugin allows to read iBFT configuration (iSCSI Boot Firmware Table).
|
||||
The configuration is read using /sbin/iscsiadm. Users are expected to
|
||||
configure iBFT connections via the firmware interfaces.
|
||||
If ibft support is available, it is automatically enabled after
|
||||
<literal>ifcfg-rh</literal>. This can be disabled by <literal>no-ibft</literal>.
|
||||
You can also explicitly specify <literal>ibft</literal> to load the
|
||||
plugin without <literal>ifcfg-rh</literal> or to change the plugin order.
|
||||
</para>
|
||||
</listitem>
|
||||
</varlistentry>
|
||||
|
|
|
|||
|
|
@ -428,6 +428,7 @@ AM_CPPFLAGS += \
|
|||
-DNMPLUGINDIR=\"$(pkglibdir)\" \
|
||||
-DNMRUNDIR=\"$(nmrundir)\" \
|
||||
-DNMSTATEDIR=\"$(nmstatedir)\" \
|
||||
-DNMLIBDIR=\"$(nmlibdir)\" \
|
||||
\
|
||||
-DDHCLIENT_PATH=\"$(DHCLIENT_PATH)\" \
|
||||
-DDHCPCD_PATH=\"$(DHCPCD_PATH)\" \
|
||||
|
|
|
|||
|
|
@ -3323,7 +3323,7 @@ ip4_config_merge_and_apply (NMDevice *self,
|
|||
if ( !priv->default_route.v4_configure_first_time
|
||||
&& !nm_device_uses_assumed_connection (self)
|
||||
&& connection_is_never_default) {
|
||||
/* If the connection is explicitly configured as never-default, we enforce the (absense of the)
|
||||
/* If the connection is explicitly configured as never-default, we enforce the (absence of the)
|
||||
* default-route only once. That allows the user to configure a connection as never-default,
|
||||
* but he can add default routes externally (via a dispatcher script) and NM will not interfere. */
|
||||
goto END_ADD_DEFAULT_ROUTE;
|
||||
|
|
|
|||
|
|
@ -343,7 +343,7 @@ main (int argc, char *argv[])
|
|||
}
|
||||
|
||||
/* Read the config file and CLI overrides */
|
||||
config = nm_config_setup (config_cli, &error);
|
||||
config = nm_config_setup (config_cli, NULL, &error);
|
||||
nm_config_cmd_line_options_free (config_cli);
|
||||
config_cli = NULL;
|
||||
if (config == NULL) {
|
||||
|
|
|
|||
|
|
@ -48,6 +48,8 @@ typedef struct {
|
|||
char *config_description;
|
||||
|
||||
GKeyFile *keyfile;
|
||||
GKeyFile *keyfile_user;
|
||||
GKeyFile *keyfile_intern;
|
||||
|
||||
/* A zero-terminated list of pre-processed information from the
|
||||
* [connection] sections. This is to speed up lookup. */
|
||||
|
|
@ -77,7 +79,8 @@ enum {
|
|||
PROP_0,
|
||||
PROP_CONFIG_MAIN_FILE,
|
||||
PROP_CONFIG_DESCRIPTION,
|
||||
PROP_KEYFILE,
|
||||
PROP_KEYFILE_USER,
|
||||
PROP_KEYFILE_INTERN,
|
||||
PROP_CONNECTIVITY_URI,
|
||||
PROP_CONNECTIVITY_INTERVAL,
|
||||
PROP_CONNECTIVITY_RESPONSE,
|
||||
|
|
@ -92,6 +95,14 @@ G_DEFINE_TYPE (NMConfigData, nm_config_data, G_TYPE_OBJECT)
|
|||
|
||||
/************************************************************************/
|
||||
|
||||
#define _HAS_PREFIX(str, prefix) \
|
||||
({ \
|
||||
const char *_str = (str); \
|
||||
g_str_has_prefix ( _str, ""prefix"") && _str[STRLEN(prefix)] != '\0'; \
|
||||
})
|
||||
|
||||
/************************************************************************/
|
||||
|
||||
const char *
|
||||
nm_config_data_get_config_main_file (const NMConfigData *self)
|
||||
{
|
||||
|
|
@ -238,6 +249,40 @@ nm_config_data_get_assume_ipv6ll_only (const NMConfigData *self, NMDevice *devic
|
|||
return nm_device_spec_match_list (device, NM_CONFIG_DATA_GET_PRIVATE (self)->assume_ipv6ll_only);
|
||||
}
|
||||
|
||||
GKeyFile *
|
||||
nm_config_data_clone_keyfile_intern (const NMConfigData *self)
|
||||
{
|
||||
NMConfigDataPrivate *priv;
|
||||
GKeyFile *keyfile;
|
||||
|
||||
g_return_val_if_fail (NM_IS_CONFIG_DATA (self), FALSE);
|
||||
|
||||
priv = NM_CONFIG_DATA_GET_PRIVATE (self);
|
||||
|
||||
keyfile = nm_config_create_keyfile ();
|
||||
if (priv->keyfile_intern)
|
||||
_nm_keyfile_copy (keyfile, priv->keyfile_intern);
|
||||
return keyfile;
|
||||
}
|
||||
|
||||
GKeyFile *
|
||||
_nm_config_data_get_keyfile (const NMConfigData *self)
|
||||
{
|
||||
return NM_CONFIG_DATA_GET_PRIVATE (self)->keyfile;
|
||||
}
|
||||
|
||||
GKeyFile *
|
||||
_nm_config_data_get_keyfile_intern (const NMConfigData *self)
|
||||
{
|
||||
return NM_CONFIG_DATA_GET_PRIVATE (self)->keyfile_intern;
|
||||
}
|
||||
|
||||
GKeyFile *
|
||||
_nm_config_data_get_keyfile_user (const NMConfigData *self)
|
||||
{
|
||||
return NM_CONFIG_DATA_GET_PRIVATE (self)->keyfile_user;
|
||||
}
|
||||
|
||||
/************************************************************************/
|
||||
|
||||
/**
|
||||
|
|
@ -265,15 +310,128 @@ nm_config_data_get_keys (const NMConfigData *self, const char *group)
|
|||
return g_key_file_get_keys (NM_CONFIG_DATA_GET_PRIVATE (self)->keyfile, group, NULL, NULL);
|
||||
}
|
||||
|
||||
/**
|
||||
* nm_config_data_is_intern_atomic_group:
|
||||
* @self:
|
||||
* @group: name of the group to check.
|
||||
*
|
||||
* whether a configuration group @group exists and is entirely overwritten
|
||||
* by internal configuration, i.e. whether it is an atomic group that is
|
||||
* overwritten.
|
||||
*
|
||||
* It doesn't say, that there actually is a user setting that was overwritten. That
|
||||
* means there could be no corresponding section defined in user configuration
|
||||
* that required overwriting.
|
||||
*
|
||||
* Returns: %TRUE if @group exists and is an atomic group set via internal configuration.
|
||||
*/
|
||||
gboolean
|
||||
nm_config_data_is_intern_atomic_group (const NMConfigData *self, const char *group)
|
||||
{
|
||||
NMConfigDataPrivate *priv;
|
||||
|
||||
g_return_val_if_fail (NM_IS_CONFIG_DATA (self), FALSE);
|
||||
g_return_val_if_fail (group && *group, FALSE);
|
||||
|
||||
priv = NM_CONFIG_DATA_GET_PRIVATE (self);
|
||||
|
||||
if ( !priv->keyfile_intern
|
||||
|| !g_key_file_has_key (priv->keyfile_intern, group, NM_CONFIG_KEYFILE_KEY_ATOMIC_SECTION_WAS, NULL))
|
||||
return FALSE;
|
||||
|
||||
/* we have a .was entry for the section. That means that the section would be overwritten
|
||||
* from user configuration. But it doesn't mean that the merged configuration contains this
|
||||
* groups, because the internal setting could hide the user section.
|
||||
* Only return TRUE, if we actually have such a group in the merged configuration.*/
|
||||
return g_key_file_has_group (priv->keyfile, group);
|
||||
}
|
||||
|
||||
/************************************************************************/
|
||||
|
||||
static GKeyFile *
|
||||
_merge_keyfiles (GKeyFile *keyfile_user, GKeyFile *keyfile_intern)
|
||||
{
|
||||
gs_strfreev char **groups = NULL;
|
||||
guint g, k;
|
||||
GKeyFile *keyfile;
|
||||
gsize ngroups;
|
||||
|
||||
keyfile = nm_config_create_keyfile ();
|
||||
if (keyfile_user)
|
||||
_nm_keyfile_copy (keyfile, keyfile_user);
|
||||
if (!keyfile_intern)
|
||||
return keyfile;
|
||||
|
||||
groups = g_key_file_get_groups (keyfile_intern, &ngroups);
|
||||
if (!groups)
|
||||
return keyfile;
|
||||
|
||||
/* we must reverse the order of the connection settings so that we
|
||||
* have lowest priority last. */
|
||||
_nm_config_sort_groups (groups, ngroups);
|
||||
for (g = 0; groups[g]; g++) {
|
||||
const char *group = groups[g];
|
||||
gs_strfreev char **keys = NULL;
|
||||
gboolean is_intern, is_atomic = FALSE;
|
||||
|
||||
keys = g_key_file_get_keys (keyfile_intern, group, NULL, NULL);
|
||||
if (!keys)
|
||||
continue;
|
||||
|
||||
is_intern = g_str_has_prefix (group, NM_CONFIG_KEYFILE_GROUPPREFIX_INTERN);
|
||||
if ( !is_intern
|
||||
&& g_key_file_has_key (keyfile_intern, group, NM_CONFIG_KEYFILE_KEY_ATOMIC_SECTION_WAS, NULL)) {
|
||||
/* the entire section is atomically overwritten by @keyfile_intern. */
|
||||
g_key_file_remove_group (keyfile, group, NULL);
|
||||
is_atomic = TRUE;
|
||||
}
|
||||
|
||||
for (k = 0; keys[k]; k++) {
|
||||
const char *key = keys[k];
|
||||
gs_free char *value = NULL;
|
||||
|
||||
if (is_atomic && strcmp (key, NM_CONFIG_KEYFILE_KEY_ATOMIC_SECTION_WAS) == 0)
|
||||
continue;
|
||||
|
||||
if ( !is_intern && !is_atomic
|
||||
&& _HAS_PREFIX (key, NM_CONFIG_KEYFILE_KEYPREFIX_WAS)) {
|
||||
const char *key_base = &key[STRLEN (NM_CONFIG_KEYFILE_KEYPREFIX_WAS)];
|
||||
|
||||
if (!g_key_file_has_key (keyfile_intern, group, key_base, NULL))
|
||||
g_key_file_remove_key (keyfile, group, key_base, NULL);
|
||||
continue;
|
||||
}
|
||||
if (!is_intern && !is_atomic && _HAS_PREFIX (key, NM_CONFIG_KEYFILE_KEYPREFIX_SET))
|
||||
continue;
|
||||
|
||||
value = g_key_file_get_value (keyfile_intern, group, key, NULL);
|
||||
g_key_file_set_value (keyfile, group, key, value);
|
||||
}
|
||||
}
|
||||
return keyfile;
|
||||
}
|
||||
|
||||
/************************************************************************/
|
||||
|
||||
static int
|
||||
_nm_config_data_log_sort (const char **pa, const char **pb, gpointer dummy)
|
||||
{
|
||||
gboolean a_is_connection, b_is_connection;
|
||||
gboolean a_is_intern, b_is_intern;
|
||||
const char *a = *pa;
|
||||
const char *b = *pb;
|
||||
|
||||
/* we sort intern groups to the end. */
|
||||
a_is_intern = g_str_has_prefix (a, NM_CONFIG_KEYFILE_GROUPPREFIX_INTERN);
|
||||
b_is_intern = g_str_has_prefix (b, NM_CONFIG_KEYFILE_GROUPPREFIX_INTERN);
|
||||
|
||||
if (a_is_intern && b_is_intern)
|
||||
return 0;
|
||||
if (a_is_intern)
|
||||
return 1;
|
||||
if (b_is_intern)
|
||||
return -1;
|
||||
|
||||
/* we sort connection groups before intern groups (to the end). */
|
||||
a_is_connection = a && g_str_has_prefix (a, NM_CONFIG_KEYFILE_GROUPPREFIX_CONNECTION);
|
||||
b_is_connection = b && g_str_has_prefix (b, NM_CONFIG_KEYFILE_GROUPPREFIX_CONNECTION);
|
||||
|
|
@ -336,9 +494,12 @@ nm_config_data_log (const NMConfigData *self, const char *prefix)
|
|||
for (g = 0; g < ngroups; g++) {
|
||||
const char *group = groups[g];
|
||||
gs_strfreev char **keys = NULL;
|
||||
gboolean is_atomic;
|
||||
|
||||
is_atomic = nm_config_data_is_intern_atomic_group (self, group);
|
||||
|
||||
_LOG ("");
|
||||
_LOG ("[%s]", group);
|
||||
_LOG ("[%s]%s", group, is_atomic ? "*" : "");
|
||||
|
||||
keys = g_key_file_get_keys (priv->keyfile, group, NULL, NULL);
|
||||
for (k = 0; keys && keys[k]; k++) {
|
||||
|
|
@ -479,8 +640,11 @@ nm_config_data_diff (NMConfigData *old_data, NMConfigData *new_data)
|
|||
priv_old = NM_CONFIG_DATA_GET_PRIVATE (old_data);
|
||||
priv_new = NM_CONFIG_DATA_GET_PRIVATE (new_data);
|
||||
|
||||
if (!_nm_keyfile_equals (priv_old->keyfile, priv_new->keyfile, TRUE))
|
||||
changes |= NM_CONFIG_CHANGE_VALUES;
|
||||
if (!_nm_keyfile_equals (priv_old->keyfile_user, priv_new->keyfile_user, TRUE))
|
||||
changes |= NM_CONFIG_CHANGE_VALUES | NM_CONFIG_CHANGE_VALUES_USER;
|
||||
|
||||
if (!_nm_keyfile_equals (priv_old->keyfile_intern, priv_new->keyfile_intern, TRUE))
|
||||
changes |= NM_CONFIG_CHANGE_VALUES | NM_CONFIG_CHANGE_VALUES_INTERN;
|
||||
|
||||
if ( g_strcmp0 (nm_config_data_get_config_main_file (old_data), nm_config_data_get_config_main_file (new_data)) != 0
|
||||
|| g_strcmp0 (nm_config_data_get_config_description (old_data), nm_config_data_get_config_description (new_data)) != 0)
|
||||
|
|
@ -553,10 +717,21 @@ set_property (GObject *object,
|
|||
case PROP_CONFIG_DESCRIPTION:
|
||||
priv->config_description = g_value_dup_string (value);
|
||||
break;
|
||||
case PROP_KEYFILE:
|
||||
priv->keyfile = g_value_dup_boxed (value);
|
||||
if (!priv->keyfile)
|
||||
priv->keyfile = nm_config_create_keyfile ();
|
||||
case PROP_KEYFILE_USER:
|
||||
priv->keyfile_user = g_value_dup_boxed (value);
|
||||
if ( priv->keyfile_user
|
||||
&& !_nm_keyfile_has_values (priv->keyfile_user)) {
|
||||
g_key_file_unref (priv->keyfile_user);
|
||||
priv->keyfile_user = NULL;
|
||||
}
|
||||
break;
|
||||
case PROP_KEYFILE_INTERN:
|
||||
priv->keyfile_intern = g_value_dup_boxed (value);
|
||||
if ( priv->keyfile_intern
|
||||
&& !_nm_keyfile_has_values (priv->keyfile_intern)) {
|
||||
g_key_file_unref (priv->keyfile_intern);
|
||||
priv->keyfile_intern = NULL;
|
||||
}
|
||||
break;
|
||||
case PROP_NO_AUTO_DEFAULT:
|
||||
{
|
||||
|
|
@ -620,6 +795,10 @@ finalize (GObject *gobject)
|
|||
}
|
||||
|
||||
g_key_file_unref (priv->keyfile);
|
||||
if (priv->keyfile_user)
|
||||
g_key_file_unref (priv->keyfile_user);
|
||||
if (priv->keyfile_intern)
|
||||
g_key_file_unref (priv->keyfile_intern);
|
||||
|
||||
G_OBJECT_CLASS (nm_config_data_parent_class)->finalize (gobject);
|
||||
}
|
||||
|
|
@ -636,6 +815,8 @@ constructed (GObject *object)
|
|||
NMConfigDataPrivate *priv = NM_CONFIG_DATA_GET_PRIVATE (self);
|
||||
char *interval;
|
||||
|
||||
priv->keyfile = _merge_keyfiles (priv->keyfile_user, priv->keyfile_intern);
|
||||
|
||||
priv->connection_infos = _get_connection_infos (priv->keyfile);
|
||||
|
||||
priv->connectivity.uri = nm_strstrip (g_key_file_get_string (priv->keyfile, NM_CONFIG_KEYFILE_GROUP_CONNECTIVITY, "uri", NULL));
|
||||
|
|
@ -664,16 +845,32 @@ NMConfigData *
|
|||
nm_config_data_new (const char *config_main_file,
|
||||
const char *config_description,
|
||||
const char *const*no_auto_default,
|
||||
GKeyFile *keyfile)
|
||||
GKeyFile *keyfile_user,
|
||||
GKeyFile *keyfile_intern)
|
||||
{
|
||||
return g_object_new (NM_TYPE_CONFIG_DATA,
|
||||
NM_CONFIG_DATA_CONFIG_MAIN_FILE, config_main_file,
|
||||
NM_CONFIG_DATA_CONFIG_DESCRIPTION, config_description,
|
||||
NM_CONFIG_DATA_KEYFILE, keyfile,
|
||||
NM_CONFIG_DATA_KEYFILE_USER, keyfile_user,
|
||||
NM_CONFIG_DATA_KEYFILE_INTERN, keyfile_intern,
|
||||
NM_CONFIG_DATA_NO_AUTO_DEFAULT, no_auto_default,
|
||||
NULL);
|
||||
}
|
||||
|
||||
NMConfigData *
|
||||
nm_config_data_new_update_keyfile_intern (const NMConfigData *base, GKeyFile *keyfile_intern)
|
||||
{
|
||||
NMConfigDataPrivate *priv = NM_CONFIG_DATA_GET_PRIVATE (base);
|
||||
|
||||
return g_object_new (NM_TYPE_CONFIG_DATA,
|
||||
NM_CONFIG_DATA_CONFIG_MAIN_FILE, priv->config_main_file,
|
||||
NM_CONFIG_DATA_CONFIG_DESCRIPTION, priv->config_description,
|
||||
NM_CONFIG_DATA_KEYFILE_USER, priv->keyfile_user, /* the keyfile is unchanged. It's safe to share it. */
|
||||
NM_CONFIG_DATA_KEYFILE_INTERN, keyfile_intern,
|
||||
NM_CONFIG_DATA_NO_AUTO_DEFAULT, priv->no_auto_default.arr,
|
||||
NULL);
|
||||
}
|
||||
|
||||
NMConfigData *
|
||||
nm_config_data_new_update_no_auto_default (const NMConfigData *base,
|
||||
const char *const*no_auto_default)
|
||||
|
|
@ -683,7 +880,8 @@ nm_config_data_new_update_no_auto_default (const NMConfigData *base,
|
|||
return g_object_new (NM_TYPE_CONFIG_DATA,
|
||||
NM_CONFIG_DATA_CONFIG_MAIN_FILE, priv->config_main_file,
|
||||
NM_CONFIG_DATA_CONFIG_DESCRIPTION, priv->config_description,
|
||||
NM_CONFIG_DATA_KEYFILE, priv->keyfile, /* the keyfile is unchanged. It's safe to share it. */
|
||||
NM_CONFIG_DATA_KEYFILE_USER, priv->keyfile_user, /* the keyfile is unchanged. It's safe to share it. */
|
||||
NM_CONFIG_DATA_KEYFILE_INTERN, priv->keyfile_intern,
|
||||
NM_CONFIG_DATA_NO_AUTO_DEFAULT, no_auto_default,
|
||||
NULL);
|
||||
}
|
||||
|
|
@ -718,8 +916,16 @@ nm_config_data_class_init (NMConfigDataClass *config_class)
|
|||
G_PARAM_STATIC_STRINGS));
|
||||
|
||||
g_object_class_install_property
|
||||
(object_class, PROP_KEYFILE,
|
||||
g_param_spec_boxed (NM_CONFIG_DATA_KEYFILE, "", "",
|
||||
(object_class, PROP_KEYFILE_USER,
|
||||
g_param_spec_boxed (NM_CONFIG_DATA_KEYFILE_USER, "", "",
|
||||
G_TYPE_KEY_FILE,
|
||||
G_PARAM_WRITABLE |
|
||||
G_PARAM_CONSTRUCT_ONLY |
|
||||
G_PARAM_STATIC_STRINGS));
|
||||
|
||||
g_object_class_install_property
|
||||
(object_class, PROP_KEYFILE_INTERN,
|
||||
g_param_spec_boxed (NM_CONFIG_DATA_KEYFILE_INTERN, "", "",
|
||||
G_TYPE_KEY_FILE,
|
||||
G_PARAM_WRITABLE |
|
||||
G_PARAM_CONSTRUCT_ONLY |
|
||||
|
|
|
|||
|
|
@ -38,7 +38,8 @@ G_BEGIN_DECLS
|
|||
|
||||
#define NM_CONFIG_DATA_CONFIG_MAIN_FILE "config-main-file"
|
||||
#define NM_CONFIG_DATA_CONFIG_DESCRIPTION "config-description"
|
||||
#define NM_CONFIG_DATA_KEYFILE "keyfile"
|
||||
#define NM_CONFIG_DATA_KEYFILE_USER "keyfile-user"
|
||||
#define NM_CONFIG_DATA_KEYFILE_INTERN "keyfile-intern"
|
||||
#define NM_CONFIG_DATA_CONNECTIVITY_URI "connectivity-uri"
|
||||
#define NM_CONFIG_DATA_CONNECTIVITY_INTERVAL "connectivity-interval"
|
||||
#define NM_CONFIG_DATA_CONNECTIVITY_RESPONSE "connectivity-response"
|
||||
|
|
@ -71,10 +72,12 @@ typedef enum { /*< flags >*/
|
|||
|
||||
NM_CONFIG_CHANGE_CONFIG_FILES = (1L << 3),
|
||||
NM_CONFIG_CHANGE_VALUES = (1L << 4),
|
||||
NM_CONFIG_CHANGE_CONNECTIVITY = (1L << 5),
|
||||
NM_CONFIG_CHANGE_NO_AUTO_DEFAULT = (1L << 6),
|
||||
NM_CONFIG_CHANGE_DNS_MODE = (1L << 7),
|
||||
NM_CONFIG_CHANGE_RC_MANAGER = (1L << 8),
|
||||
NM_CONFIG_CHANGE_VALUES_USER = (1L << 5),
|
||||
NM_CONFIG_CHANGE_VALUES_INTERN = (1L << 6),
|
||||
NM_CONFIG_CHANGE_CONNECTIVITY = (1L << 7),
|
||||
NM_CONFIG_CHANGE_NO_AUTO_DEFAULT = (1L << 8),
|
||||
NM_CONFIG_CHANGE_DNS_MODE = (1L << 9),
|
||||
NM_CONFIG_CHANGE_RC_MANAGER = (1L << 10),
|
||||
|
||||
_NM_CONFIG_CHANGE_LAST,
|
||||
NM_CONFIG_CHANGE_ALL = ((_NM_CONFIG_CHANGE_LAST - 1) << 1) - 1,
|
||||
|
|
@ -93,7 +96,9 @@ GType nm_config_data_get_type (void);
|
|||
NMConfigData *nm_config_data_new (const char *config_main_file,
|
||||
const char *config_description,
|
||||
const char *const*no_auto_default,
|
||||
GKeyFile *keyfile);
|
||||
GKeyFile *keyfile_user,
|
||||
GKeyFile *keyfile_intern);
|
||||
NMConfigData *nm_config_data_new_update_keyfile_intern (const NMConfigData *base, GKeyFile *keyfile_intern);
|
||||
NMConfigData *nm_config_data_new_update_no_auto_default (const NMConfigData *base, const char *const*no_auto_default);
|
||||
|
||||
NMConfigChangeFlags nm_config_data_diff (NMConfigData *old_data, NMConfigData *new_data);
|
||||
|
|
@ -127,6 +132,14 @@ char *nm_config_data_get_connection_default (const NMConfigData *self,
|
|||
|
||||
char **nm_config_data_get_groups (const NMConfigData *self);
|
||||
char **nm_config_data_get_keys (const NMConfigData *self, const char *group);
|
||||
gboolean nm_config_data_is_intern_atomic_group (const NMConfigData *self, const char *group);
|
||||
|
||||
GKeyFile *nm_config_data_clone_keyfile_intern (const NMConfigData *self);
|
||||
|
||||
/* private accessors */
|
||||
GKeyFile *_nm_config_data_get_keyfile (const NMConfigData *self);
|
||||
GKeyFile *_nm_config_data_get_keyfile_user (const NMConfigData *self);
|
||||
GKeyFile *_nm_config_data_get_keyfile_intern (const NMConfigData *self);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
|
|
|
|||
799
src/nm-config.c
799
src/nm-config.c
File diff suppressed because it is too large
Load diff
|
|
@ -39,6 +39,7 @@ G_BEGIN_DECLS
|
|||
|
||||
/* Properties */
|
||||
#define NM_CONFIG_CMD_LINE_OPTIONS "cmd-line-options"
|
||||
#define NM_CONFIG_ATOMIC_SECTION_PREFIXES "atomic-section-prefixes"
|
||||
|
||||
/* Signals */
|
||||
#define NM_CONFIG_SIGNAL_CONFIG_CHANGED "config-changed"
|
||||
|
|
@ -48,6 +49,7 @@ G_BEGIN_DECLS
|
|||
|
||||
#define NM_CONFIG_KEYFILE_LIST_SEPARATOR ','
|
||||
|
||||
#define NM_CONFIG_KEYFILE_GROUPPREFIX_INTERN ".intern."
|
||||
#define NM_CONFIG_KEYFILE_GROUPPREFIX_CONNECTION "connection"
|
||||
#define NM_CONFIG_KEYFILE_GROUPPREFIX_TEST_APPEND_STRINGLIST ".test-append-stringlist"
|
||||
|
||||
|
|
@ -59,10 +61,14 @@ G_BEGIN_DECLS
|
|||
#define NM_CONFIG_KEYFILE_GROUP_IFUPDOWN "ifupdown"
|
||||
#define NM_CONFIG_KEYFILE_GROUP_IFNET "ifnet"
|
||||
|
||||
#define NM_CONFIG_KEYFILE_KEY_ATOMIC_SECTION_WAS ".was"
|
||||
#define NM_CONFIG_KEYFILE_KEY_IFNET_AUTO_REFRESH "auto_refresh"
|
||||
#define NM_CONFIG_KEYFILE_KEY_IFNET_MANAGED "managed"
|
||||
#define NM_CONFIG_KEYFILE_KEY_IFUPDOWN_MANAGED "managed"
|
||||
|
||||
#define NM_CONFIG_KEYFILE_KEYPREFIX_WAS ".was."
|
||||
#define NM_CONFIG_KEYFILE_KEYPREFIX_SET ".set."
|
||||
|
||||
typedef struct NMConfigCmdLineOptions NMConfigCmdLineOptions;
|
||||
|
||||
struct _NMConfig {
|
||||
|
|
@ -97,6 +103,11 @@ const char *nm_config_get_log_domains (NMConfig *config);
|
|||
const char *nm_config_get_debug (NMConfig *config);
|
||||
gboolean nm_config_get_configure_and_quit (NMConfig *config);
|
||||
|
||||
void nm_config_set_values (NMConfig *self,
|
||||
GKeyFile *keyfile_intern_new,
|
||||
gboolean allow_write,
|
||||
gboolean force_rewrite);
|
||||
|
||||
/* for main.c only */
|
||||
NMConfigCmdLineOptions *nm_config_cmd_line_options_new (void);
|
||||
void nm_config_cmd_line_options_free (NMConfigCmdLineOptions *cli);
|
||||
|
|
@ -106,8 +117,8 @@ void nm_config_cmd_line_options_add_to_entries (NMConfigCmdLi
|
|||
gboolean nm_config_get_no_auto_default_for_device (NMConfig *config, NMDevice *device);
|
||||
void nm_config_set_no_auto_default_for_device (NMConfig *config, NMDevice *device);
|
||||
|
||||
NMConfig *nm_config_new (const NMConfigCmdLineOptions *cli, GError **error);
|
||||
NMConfig *nm_config_setup (const NMConfigCmdLineOptions *cli, GError **error);
|
||||
NMConfig *nm_config_new (const NMConfigCmdLineOptions *cli, char **atomic_section_prefixes, GError **error);
|
||||
NMConfig *nm_config_setup (const NMConfigCmdLineOptions *cli, char **atomic_section_prefixes, GError **error);
|
||||
void nm_config_reload (NMConfig *config, int signal);
|
||||
|
||||
gint nm_config_parse_boolean (const char *str, gint default_value);
|
||||
|
|
@ -128,6 +139,8 @@ void nm_config_keyfile_set_string_list (GKeyFile *keyfile,
|
|||
gssize len);
|
||||
GSList *nm_config_get_device_match_spec (const GKeyFile *keyfile, const char *group, const char *key, gboolean *out_has_key);
|
||||
|
||||
void _nm_config_sort_groups (char **groups, gsize ngroups);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
#endif /* __NETWORKMANAGER_CONFIG_H__ */
|
||||
|
|
|
|||
|
|
@ -764,18 +764,20 @@ load_plugins (NMSettings *self, const char **plugins, GError **error)
|
|||
const char **iter;
|
||||
gboolean keyfile_added = FALSE;
|
||||
gboolean success = TRUE;
|
||||
gboolean add_ibft = FALSE;
|
||||
gboolean has_no_ibft;
|
||||
gssize idx_no_ibft, idx_ibft;
|
||||
|
||||
idx_ibft = _nm_utils_strv_find_first ((char **) plugins, -1, "ibft");
|
||||
idx_no_ibft = _nm_utils_strv_find_first ((char **) plugins, -1, "no-ibft");
|
||||
has_no_ibft = idx_no_ibft >= 0 && idx_no_ibft > idx_ibft;
|
||||
#if WITH_SETTINGS_PLUGIN_IBFT
|
||||
add_ibft = idx_no_ibft < 0 && idx_ibft < 0;
|
||||
#endif
|
||||
|
||||
for (iter = plugins; iter && *iter; iter++) {
|
||||
GModule *plugin;
|
||||
gs_free char *full_name = NULL;
|
||||
gs_free char *path = NULL;
|
||||
const char *pname;
|
||||
const char *pname = *iter;
|
||||
GObject *obj;
|
||||
GObject * (*factory_func) (void);
|
||||
struct stat st;
|
||||
int errsv;
|
||||
|
||||
pname = *iter;
|
||||
|
||||
if (!*pname || strchr (pname, '/')) {
|
||||
LOG (LOGL_WARN, "ignore invalid plugin \"%s\"", pname);
|
||||
|
|
@ -787,6 +789,11 @@ load_plugins (NMSettings *self, const char **plugins, GError **error)
|
|||
continue;
|
||||
}
|
||||
|
||||
if (!strcmp (pname, "no-ibft"))
|
||||
continue;
|
||||
if (has_no_ibft && !strcmp (pname, "ibft"))
|
||||
continue;
|
||||
|
||||
obj = find_plugin (list, pname);
|
||||
if (obj)
|
||||
continue;
|
||||
|
|
@ -800,61 +807,79 @@ load_plugins (NMSettings *self, const char **plugins, GError **error)
|
|||
continue;
|
||||
}
|
||||
|
||||
full_name = g_strdup_printf ("nm-settings-plugin-%s", pname);
|
||||
path = g_module_build_path (NMPLUGINDIR, full_name);
|
||||
load_plugin:
|
||||
{
|
||||
GModule *plugin;
|
||||
gs_free char *full_name = NULL;
|
||||
gs_free char *path = NULL;
|
||||
GObject * (*factory_func) (void);
|
||||
struct stat st;
|
||||
int errsv;
|
||||
|
||||
if (stat (path, &st) != 0) {
|
||||
errsv = errno;
|
||||
LOG (LOGL_WARN, "Could not load plugin '%s' from file '%s': %s", pname, path, strerror (errsv));
|
||||
continue;
|
||||
}
|
||||
if (!S_ISREG (st.st_mode)) {
|
||||
LOG (LOGL_WARN, "Could not load plugin '%s' from file '%s': not a file", pname, path);
|
||||
continue;
|
||||
}
|
||||
if (st.st_uid != 0) {
|
||||
LOG (LOGL_WARN, "Could not load plugin '%s' from file '%s': file must be owned by root", pname, path);
|
||||
continue;
|
||||
}
|
||||
if (st.st_mode & (S_IWGRP | S_IWOTH | S_ISUID)) {
|
||||
LOG (LOGL_WARN, "Could not load plugin '%s' from file '%s': invalid file permissions", pname, path);
|
||||
continue;
|
||||
}
|
||||
full_name = g_strdup_printf ("nm-settings-plugin-%s", pname);
|
||||
path = g_module_build_path (NMPLUGINDIR, full_name);
|
||||
|
||||
plugin = g_module_open (path, G_MODULE_BIND_LOCAL);
|
||||
if (!plugin) {
|
||||
LOG (LOGL_WARN, "Could not load plugin '%s' from file '%s': %s",
|
||||
pname, path, g_module_error ());
|
||||
continue;
|
||||
if (stat (path, &st) != 0) {
|
||||
errsv = errno;
|
||||
LOG (LOGL_WARN, "Could not load plugin '%s' from file '%s': %s", pname, path, strerror (errsv));
|
||||
goto next;
|
||||
}
|
||||
if (!S_ISREG (st.st_mode)) {
|
||||
LOG (LOGL_WARN, "Could not load plugin '%s' from file '%s': not a file", pname, path);
|
||||
goto next;
|
||||
}
|
||||
if (st.st_uid != 0) {
|
||||
LOG (LOGL_WARN, "Could not load plugin '%s' from file '%s': file must be owned by root", pname, path);
|
||||
goto next;
|
||||
}
|
||||
if (st.st_mode & (S_IWGRP | S_IWOTH | S_ISUID)) {
|
||||
LOG (LOGL_WARN, "Could not load plugin '%s' from file '%s': invalid file permissions", pname, path);
|
||||
goto next;
|
||||
}
|
||||
|
||||
plugin = g_module_open (path, G_MODULE_BIND_LOCAL);
|
||||
if (!plugin) {
|
||||
LOG (LOGL_WARN, "Could not load plugin '%s' from file '%s': %s",
|
||||
pname, path, g_module_error ());
|
||||
goto next;
|
||||
}
|
||||
|
||||
/* errors after this point are fatal, because we loaded the shared library already. */
|
||||
|
||||
if (!g_module_symbol (plugin, "nm_system_config_factory", (gpointer) (&factory_func))) {
|
||||
g_set_error (error, NM_SETTINGS_ERROR, NM_SETTINGS_ERROR_FAILED,
|
||||
"Could not find plugin '%s' factory function.",
|
||||
pname);
|
||||
success = FALSE;
|
||||
g_module_close (plugin);
|
||||
break;
|
||||
}
|
||||
|
||||
obj = (*factory_func) ();
|
||||
if (!obj || !NM_IS_SYSTEM_CONFIG_INTERFACE (obj)) {
|
||||
g_set_error (error, NM_SETTINGS_ERROR, NM_SETTINGS_ERROR_FAILED,
|
||||
"Plugin '%s' returned invalid system config object.",
|
||||
pname);
|
||||
success = FALSE;
|
||||
g_module_close (plugin);
|
||||
break;
|
||||
}
|
||||
|
||||
g_module_make_resident (plugin);
|
||||
g_object_weak_ref (obj, (GWeakNotify) g_module_close, plugin);
|
||||
g_object_set_data_full (obj, PLUGIN_MODULE_PATH, path, g_free);
|
||||
path = NULL;
|
||||
add_plugin (self, NM_SYSTEM_CONFIG_INTERFACE (obj));
|
||||
list = g_slist_append (list, obj);
|
||||
}
|
||||
|
||||
/* errors after this point are fatal, because we loaded the shared library already. */
|
||||
|
||||
if (!g_module_symbol (plugin, "nm_system_config_factory", (gpointer) (&factory_func))) {
|
||||
g_set_error (error, NM_SETTINGS_ERROR, NM_SETTINGS_ERROR_FAILED,
|
||||
"Could not find plugin '%s' factory function.",
|
||||
pname);
|
||||
success = FALSE;
|
||||
g_module_close (plugin);
|
||||
break;
|
||||
next:
|
||||
if (add_ibft && !strcmp (pname, "ifcfg-rh")) {
|
||||
/* The plugin ibft is not explicitly mentioned but we just enabled "ifcfg-rh".
|
||||
* Enable "ibft" by default after "ifcfg-rh". */
|
||||
pname = "ibft";
|
||||
add_ibft = FALSE;
|
||||
goto load_plugin;
|
||||
}
|
||||
|
||||
obj = (*factory_func) ();
|
||||
if (!obj || !NM_IS_SYSTEM_CONFIG_INTERFACE (obj)) {
|
||||
g_set_error (error, NM_SETTINGS_ERROR, NM_SETTINGS_ERROR_FAILED,
|
||||
"Plugin '%s' returned invalid system config object.",
|
||||
pname);
|
||||
success = FALSE;
|
||||
g_module_close (plugin);
|
||||
break;
|
||||
}
|
||||
|
||||
g_module_make_resident (plugin);
|
||||
g_object_weak_ref (obj, (GWeakNotify) g_module_close, plugin);
|
||||
g_object_set_data_full (obj, PLUGIN_MODULE_PATH, path, g_free);
|
||||
path = NULL;
|
||||
add_plugin (self, NM_SYSTEM_CONFIG_INTERFACE (obj));
|
||||
list = g_slist_append (list, obj);
|
||||
}
|
||||
|
||||
/* If keyfile plugin was not among configured plugins, add it as the last one */
|
||||
|
|
|
|||
|
|
@ -32,8 +32,27 @@
|
|||
|
||||
#include "nm-test-utils.h"
|
||||
|
||||
/********************************************************************************/
|
||||
|
||||
static void
|
||||
_assert_config_value (const NMConfigData *config_data, const char *group, const char *key, const char *expected_value, const char *file, int line)
|
||||
{
|
||||
gs_free char *value = NULL;
|
||||
|
||||
value = nm_config_data_get_value (config_data, group, key, NM_CONFIG_GET_VALUE_NONE);
|
||||
if (g_strcmp0 (value, expected_value)) {
|
||||
g_error ("(%s:%d) invalid value in config-data %s.%s = %s%s%s (instead of %s%s%s)",
|
||||
file, line, group, key,
|
||||
NM_PRINT_FMT_QUOTED (value, "\"", value, "\"", "(null)"),
|
||||
NM_PRINT_FMT_QUOTED (expected_value, "\"", expected_value, "\"", "(null)"));
|
||||
}
|
||||
}
|
||||
#define assert_config_value(config_data, group, key, expected_value) _assert_config_value (config_data, group, key, expected_value, __FILE__, __LINE__)
|
||||
|
||||
/********************************************************************************/
|
||||
|
||||
static NMConfig *
|
||||
setup_config (GError **error, const char *config_file, const char *config_dir, ...)
|
||||
setup_config (GError **error, const char *config_file, const char *intern_config, const char *const* atomic_section_prefixes, const char *config_dir, const char *system_config_dir, ...)
|
||||
{
|
||||
va_list ap;
|
||||
GPtrArray *args;
|
||||
|
|
@ -51,10 +70,18 @@ setup_config (GError **error, const char *config_file, const char *config_dir, .
|
|||
g_ptr_array_add (args, "test-config");
|
||||
g_ptr_array_add (args, "--config");
|
||||
g_ptr_array_add (args, (char *)config_file);
|
||||
if (intern_config) {
|
||||
g_ptr_array_add (args, "--intern-config");
|
||||
g_ptr_array_add (args, (char *)intern_config);
|
||||
}
|
||||
g_ptr_array_add (args, "--config-dir");
|
||||
g_ptr_array_add (args, (char *)config_dir);
|
||||
if (system_config_dir) {
|
||||
g_ptr_array_add (args, "--system-config-dir");
|
||||
g_ptr_array_add (args, (char *) system_config_dir);
|
||||
}
|
||||
|
||||
va_start (ap, config_dir);
|
||||
va_start (ap, system_config_dir);
|
||||
while ((arg = va_arg (ap, char *)))
|
||||
g_ptr_array_add (args, arg);
|
||||
va_end (ap);
|
||||
|
|
@ -74,7 +101,7 @@ setup_config (GError **error, const char *config_file, const char *config_dir, .
|
|||
|
||||
g_ptr_array_free (args, TRUE);
|
||||
|
||||
config = nm_config_setup (cli, &local_error);
|
||||
config = nm_config_setup (cli, (char **) atomic_section_prefixes, &local_error);
|
||||
if (error) {
|
||||
g_assert (!config);
|
||||
g_assert (local_error);
|
||||
|
|
@ -97,7 +124,7 @@ test_config_simple (void)
|
|||
gs_unref_object NMDevice *dev51 = nm_test_device_new ("00:00:00:00:00:51");
|
||||
gs_unref_object NMDevice *dev52 = nm_test_device_new ("00:00:00:00:00:52");
|
||||
|
||||
config = setup_config (NULL, SRCDIR "/NetworkManager.conf", "/no/such/dir", NULL);
|
||||
config = setup_config (NULL, SRCDIR "/NetworkManager.conf", "", NULL, "/no/such/dir", "", NULL);
|
||||
|
||||
g_assert_cmpstr (nm_config_data_get_config_main_file (nm_config_get_data_orig (config)), ==, SRCDIR "/NetworkManager.conf");
|
||||
g_assert_cmpstr (nm_config_get_dhcp_client (config), ==, "dhclient");
|
||||
|
|
@ -176,7 +203,7 @@ test_config_non_existent (void)
|
|||
{
|
||||
GError *error = NULL;
|
||||
|
||||
setup_config (&error, SRCDIR "/no-such-file", "/no/such/dir", NULL);
|
||||
setup_config (&error, SRCDIR "/no-such-file", "", NULL, "/no/such/dir", "", NULL);
|
||||
g_assert_error (error, G_KEY_FILE_ERROR, G_KEY_FILE_ERROR_NOT_FOUND);
|
||||
g_clear_error (&error);
|
||||
}
|
||||
|
|
@ -186,7 +213,7 @@ test_config_parse_error (void)
|
|||
{
|
||||
GError *error = NULL;
|
||||
|
||||
setup_config (&error, SRCDIR "/bad.conf", "/no/such/dir", NULL);
|
||||
setup_config (&error, SRCDIR "/bad.conf", "", NULL, "/no/such/dir", "", NULL);
|
||||
g_assert_error (error, G_KEY_FILE_ERROR, G_KEY_FILE_ERROR_PARSE);
|
||||
g_clear_error (&error);
|
||||
}
|
||||
|
|
@ -197,7 +224,7 @@ test_config_override (void)
|
|||
NMConfig *config;
|
||||
const char **plugins;
|
||||
|
||||
config = setup_config (NULL, SRCDIR "/NetworkManager.conf", "/no/such/dir",
|
||||
config = setup_config (NULL, SRCDIR "/NetworkManager.conf", "", NULL, "/no/such/dir", "",
|
||||
"--plugins", "alpha,beta,gamma,delta",
|
||||
"--connectivity-interval", "12",
|
||||
NULL);
|
||||
|
|
@ -235,7 +262,7 @@ test_config_no_auto_default (void)
|
|||
g_assert_cmpint (nwrote, ==, 18);
|
||||
close (fd);
|
||||
|
||||
config = setup_config (NULL, SRCDIR "/NetworkManager.conf", "/no/such/dir",
|
||||
config = setup_config (NULL, SRCDIR "/NetworkManager.conf", "", NULL, "/no/such/dir", "",
|
||||
"--no-auto-default", state_file,
|
||||
NULL);
|
||||
|
||||
|
|
@ -257,7 +284,7 @@ test_config_no_auto_default (void)
|
|||
|
||||
g_object_unref (config);
|
||||
|
||||
config = setup_config (NULL, SRCDIR "/NetworkManager.conf", "/no/such/dir",
|
||||
config = setup_config (NULL, SRCDIR "/NetworkManager.conf", "", NULL, "/no/such/dir", "",
|
||||
"--no-auto-default", state_file,
|
||||
NULL);
|
||||
|
||||
|
|
@ -285,7 +312,7 @@ test_config_confdir (void)
|
|||
char *value;
|
||||
GSList *specs;
|
||||
|
||||
config = setup_config (NULL, SRCDIR "/NetworkManager.conf", SRCDIR "/conf.d", NULL);
|
||||
config = setup_config (NULL, SRCDIR "/NetworkManager.conf", "", NULL, SRCDIR "/conf.d", "", NULL);
|
||||
|
||||
g_assert_cmpstr (nm_config_data_get_config_main_file (nm_config_get_data_orig (config)), ==, SRCDIR "/NetworkManager.conf");
|
||||
g_assert_cmpstr (nm_config_get_dhcp_client (config), ==, "dhcpcd");
|
||||
|
|
@ -391,11 +418,336 @@ test_config_confdir_parse_error (void)
|
|||
GError *error = NULL;
|
||||
|
||||
/* Using SRCDIR as the conf dir will pick up bad.conf */
|
||||
setup_config (&error, SRCDIR "/NetworkManager.conf", SRCDIR, NULL);
|
||||
setup_config (&error, SRCDIR "/NetworkManager.conf", "", NULL, SRCDIR, "", NULL);
|
||||
g_assert_error (error, G_KEY_FILE_ERROR, G_KEY_FILE_ERROR_PARSE);
|
||||
g_clear_error (&error);
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
||||
typedef void (*TestSetValuesUserSetFcn) (NMConfig *config, gboolean is_user, GKeyFile *keyfile_user, NMConfigChangeFlags *out_expected_changes);
|
||||
typedef void (*TestSetValuesCheckStateFcn) (NMConfig *config, NMConfigData *config_data, gboolean is_change_event, NMConfigChangeFlags changes, NMConfigData *old_data);
|
||||
|
||||
typedef struct {
|
||||
NMConfigChangeFlags changes;
|
||||
TestSetValuesCheckStateFcn check_state_fcn;
|
||||
} TestSetValuesConfigChangedData;
|
||||
|
||||
static void
|
||||
_set_values_config_changed_cb (NMConfig *config,
|
||||
NMConfigData *config_data,
|
||||
NMConfigChangeFlags changes,
|
||||
NMConfigData *old_data,
|
||||
TestSetValuesConfigChangedData *config_changed_data)
|
||||
{
|
||||
g_assert (changes != NM_CONFIG_CHANGE_NONE);
|
||||
g_assert (config_changed_data);
|
||||
g_assert (config_changed_data->changes == NM_CONFIG_CHANGE_NONE);
|
||||
|
||||
if (changes == NM_CONFIG_CHANGE_SIGHUP)
|
||||
return;
|
||||
changes &= ~NM_CONFIG_CHANGE_SIGHUP;
|
||||
|
||||
config_changed_data->changes = changes;
|
||||
|
||||
if (config_changed_data->check_state_fcn)
|
||||
config_changed_data->check_state_fcn (config, config_data, TRUE, changes, old_data);
|
||||
}
|
||||
|
||||
static void
|
||||
_set_values_user (NMConfig *config,
|
||||
const char *CONFIG_USER,
|
||||
TestSetValuesUserSetFcn set_fcn,
|
||||
TestSetValuesCheckStateFcn check_state_fcn)
|
||||
{
|
||||
GKeyFile *keyfile_user;
|
||||
gboolean success;
|
||||
gs_free_error GError *error = NULL;
|
||||
TestSetValuesConfigChangedData config_changed_data = {
|
||||
.changes = NM_CONFIG_CHANGE_NONE,
|
||||
.check_state_fcn = check_state_fcn,
|
||||
};
|
||||
NMConfigChangeFlags expected_changes = NM_CONFIG_CHANGE_NONE;
|
||||
gs_unref_object NMConfigData *config_data_before = NULL;
|
||||
|
||||
keyfile_user = nm_config_create_keyfile ();
|
||||
|
||||
success = g_key_file_load_from_file (keyfile_user, CONFIG_USER, G_KEY_FILE_NONE, &error);
|
||||
nmtst_assert_success (success, error);
|
||||
|
||||
if (set_fcn)
|
||||
set_fcn (config, TRUE, keyfile_user, &expected_changes);
|
||||
|
||||
success = g_key_file_save_to_file (keyfile_user, CONFIG_USER, &error);
|
||||
nmtst_assert_success (success, error);
|
||||
|
||||
g_signal_connect (G_OBJECT (config),
|
||||
NM_CONFIG_SIGNAL_CONFIG_CHANGED,
|
||||
G_CALLBACK (_set_values_config_changed_cb),
|
||||
&config_changed_data);
|
||||
|
||||
config_data_before = g_object_ref (nm_config_get_data (config));
|
||||
|
||||
if (expected_changes != NM_CONFIG_CHANGE_NONE)
|
||||
g_test_expect_message ("NetworkManager", G_LOG_LEVEL_MESSAGE, "*config: update *");
|
||||
else
|
||||
g_test_expect_message ("NetworkManager", G_LOG_LEVEL_MESSAGE, "*config: signal SIGHUP (no changes from disk)*");
|
||||
|
||||
nm_config_reload (config, SIGHUP);
|
||||
|
||||
g_test_assert_expected_messages ();
|
||||
|
||||
g_assert (expected_changes == config_changed_data.changes);
|
||||
|
||||
if (check_state_fcn)
|
||||
check_state_fcn (config, nm_config_get_data (config), FALSE, NM_CONFIG_CHANGE_NONE, config_data_before);
|
||||
|
||||
g_signal_handlers_disconnect_by_func (config, _set_values_config_changed_cb, &config_changed_data);
|
||||
|
||||
g_key_file_unref (keyfile_user);
|
||||
}
|
||||
|
||||
static void
|
||||
_set_values_intern (NMConfig *config,
|
||||
TestSetValuesUserSetFcn set_fcn,
|
||||
TestSetValuesCheckStateFcn check_state_fcn)
|
||||
{
|
||||
GKeyFile *keyfile_intern;
|
||||
TestSetValuesConfigChangedData config_changed_data = {
|
||||
.changes = NM_CONFIG_CHANGE_NONE,
|
||||
.check_state_fcn = check_state_fcn,
|
||||
};
|
||||
NMConfigChangeFlags expected_changes = NM_CONFIG_CHANGE_NONE;
|
||||
gs_unref_object NMConfigData *config_data_before = NULL;
|
||||
|
||||
config_data_before = g_object_ref (nm_config_get_data (config));
|
||||
|
||||
keyfile_intern = nm_config_data_clone_keyfile_intern (config_data_before);
|
||||
|
||||
if (set_fcn)
|
||||
set_fcn (config, FALSE, keyfile_intern, &expected_changes);
|
||||
|
||||
g_signal_connect (G_OBJECT (config),
|
||||
NM_CONFIG_SIGNAL_CONFIG_CHANGED,
|
||||
G_CALLBACK (_set_values_config_changed_cb),
|
||||
&config_changed_data);
|
||||
|
||||
if (expected_changes != NM_CONFIG_CHANGE_NONE)
|
||||
g_test_expect_message ("NetworkManager", G_LOG_LEVEL_MESSAGE, "*config: update *");
|
||||
|
||||
nm_config_set_values (config, keyfile_intern, TRUE, FALSE);
|
||||
|
||||
g_test_assert_expected_messages ();
|
||||
|
||||
g_assert (expected_changes == config_changed_data.changes);
|
||||
|
||||
if (check_state_fcn)
|
||||
check_state_fcn (config, nm_config_get_data (config), FALSE, NM_CONFIG_CHANGE_NONE, config_data_before);
|
||||
|
||||
g_signal_handlers_disconnect_by_func (config, _set_values_config_changed_cb, &config_changed_data);
|
||||
|
||||
g_key_file_unref (keyfile_intern);
|
||||
}
|
||||
|
||||
static void
|
||||
_set_values_user_intern_section_set (NMConfig *config, gboolean set_user, GKeyFile *keyfile, NMConfigChangeFlags *out_expected_changes)
|
||||
{
|
||||
g_key_file_set_string (keyfile, NM_CONFIG_KEYFILE_GROUPPREFIX_INTERN"section1", "key", "this-should-be-ignored");
|
||||
}
|
||||
|
||||
static void
|
||||
_set_values_user_intern_section_check (NMConfig *config, NMConfigData *config_data, gboolean is_change_event, NMConfigChangeFlags changes, NMConfigData *old_data)
|
||||
{
|
||||
g_assert (changes == NM_CONFIG_CHANGE_NONE);
|
||||
g_assert (!nm_config_data_has_group (config_data, NM_CONFIG_KEYFILE_GROUPPREFIX_INTERN"section1"));
|
||||
}
|
||||
|
||||
static void
|
||||
_set_values_user_initial_values_set (NMConfig *config, gboolean set_user, GKeyFile *keyfile, NMConfigChangeFlags *out_expected_changes)
|
||||
{
|
||||
g_key_file_remove_group (keyfile, NM_CONFIG_KEYFILE_GROUPPREFIX_INTERN"section1", NULL);
|
||||
g_key_file_set_string (keyfile, "section1", "key1", "value1");
|
||||
*out_expected_changes = NM_CONFIG_CHANGE_VALUES | NM_CONFIG_CHANGE_VALUES_USER;
|
||||
}
|
||||
|
||||
static void
|
||||
_set_values_user_initial_values_check (NMConfig *config, NMConfigData *config_data, gboolean is_change_event, NMConfigChangeFlags changes, NMConfigData *old_data)
|
||||
{
|
||||
if (is_change_event)
|
||||
g_assert (changes == (NM_CONFIG_CHANGE_VALUES | NM_CONFIG_CHANGE_VALUES_USER));
|
||||
assert_config_value (config_data, "section1", "key1", "value1");
|
||||
}
|
||||
|
||||
static void
|
||||
_set_values_intern_internal_set (NMConfig *config, gboolean set_user, GKeyFile *keyfile, NMConfigChangeFlags *out_expected_changes)
|
||||
{
|
||||
g_key_file_set_string (keyfile, NM_CONFIG_KEYFILE_GROUPPREFIX_INTERN"section1", "key", "internal-section");
|
||||
*out_expected_changes = NM_CONFIG_CHANGE_VALUES | NM_CONFIG_CHANGE_VALUES_INTERN;
|
||||
}
|
||||
|
||||
static void
|
||||
_set_values_intern_internal_check (NMConfig *config, NMConfigData *config_data, gboolean is_change_event, NMConfigChangeFlags changes, NMConfigData *old_data)
|
||||
{
|
||||
if (is_change_event)
|
||||
g_assert (changes == (NM_CONFIG_CHANGE_VALUES | NM_CONFIG_CHANGE_VALUES_INTERN));
|
||||
assert_config_value (config_data, NM_CONFIG_KEYFILE_GROUPPREFIX_INTERN"section1", "key", "internal-section");
|
||||
}
|
||||
|
||||
static void
|
||||
_set_values_user_atomic_section_1_set (NMConfig *config, gboolean set_user, GKeyFile *keyfile, NMConfigChangeFlags *out_expected_changes)
|
||||
{
|
||||
g_key_file_set_string (keyfile, "atomic-prefix-1.section-a", "key1", "user-value1");
|
||||
g_key_file_set_string (keyfile, "atomic-prefix-1.section-a", "key2", "user-value2");
|
||||
g_key_file_set_string (keyfile, "atomic-prefix-1.section-b", "key1", "user-value1");
|
||||
g_key_file_set_string (keyfile, "non-atomic-prefix-1.section-a", "nap1-key1", "user-value1");
|
||||
g_key_file_set_string (keyfile, "non-atomic-prefix-1.section-a", "nap1-key2", "user-value2");
|
||||
*out_expected_changes = NM_CONFIG_CHANGE_VALUES | NM_CONFIG_CHANGE_VALUES_USER;
|
||||
}
|
||||
|
||||
static void
|
||||
_set_values_user_atomic_section_1_check (NMConfig *config, NMConfigData *config_data, gboolean is_change_event, NMConfigChangeFlags changes, NMConfigData *old_data)
|
||||
{
|
||||
if (is_change_event)
|
||||
g_assert (changes == (NM_CONFIG_CHANGE_VALUES | NM_CONFIG_CHANGE_VALUES_USER));
|
||||
assert_config_value (config_data, "atomic-prefix-1.section-a", "key1", "user-value1");
|
||||
assert_config_value (config_data, "atomic-prefix-1.section-a", "key2", "user-value2");
|
||||
assert_config_value (config_data, "atomic-prefix-1.section-b", "key1", "user-value1");
|
||||
assert_config_value (config_data, "non-atomic-prefix-1.section-a", "nap1-key1", "user-value1");
|
||||
assert_config_value (config_data, "non-atomic-prefix-1.section-a", "nap1-key2", "user-value2");
|
||||
}
|
||||
|
||||
static void
|
||||
_set_values_intern_atomic_section_1_set (NMConfig *config, gboolean set_user, GKeyFile *keyfile, NMConfigChangeFlags *out_expected_changes)
|
||||
{
|
||||
g_key_file_set_string (keyfile, "atomic-prefix-1.section-a", "key1", "intern-value1");
|
||||
g_key_file_set_string (keyfile, "atomic-prefix-1.section-a", "key3", "intern-value3");
|
||||
g_key_file_set_string (keyfile, "non-atomic-prefix-1.section-a", "nap1-key1", "intern-value1");
|
||||
g_key_file_set_string (keyfile, "non-atomic-prefix-1.section-a", "nap1-key3", "intern-value3");
|
||||
*out_expected_changes = NM_CONFIG_CHANGE_VALUES | NM_CONFIG_CHANGE_VALUES_INTERN;
|
||||
}
|
||||
|
||||
static void
|
||||
_set_values_intern_atomic_section_1_check (NMConfig *config, NMConfigData *config_data, gboolean is_change_event, NMConfigChangeFlags changes, NMConfigData *old_data)
|
||||
{
|
||||
if (is_change_event)
|
||||
g_assert (changes == (NM_CONFIG_CHANGE_VALUES | NM_CONFIG_CHANGE_VALUES_INTERN));
|
||||
assert_config_value (config_data, "atomic-prefix-1.section-a", "key1", "intern-value1");
|
||||
assert_config_value (config_data, "atomic-prefix-1.section-a", "key2", NULL);
|
||||
assert_config_value (config_data, "atomic-prefix-1.section-a", "key3", "intern-value3");
|
||||
assert_config_value (config_data, "atomic-prefix-1.section-b", "key1", "user-value1");
|
||||
assert_config_value (config_data, "non-atomic-prefix-1.section-a", "nap1-key1", "intern-value1");
|
||||
assert_config_value (config_data, "non-atomic-prefix-1.section-a", "nap1-key2", "user-value2");
|
||||
assert_config_value (config_data, "non-atomic-prefix-1.section-a", "nap1-key3", "intern-value3");
|
||||
g_assert ( nm_config_data_is_intern_atomic_group (config_data, "atomic-prefix-1.section-a"));
|
||||
g_assert (!nm_config_data_is_intern_atomic_group (config_data, "atomic-prefix-1.section-b"));
|
||||
g_assert (!nm_config_data_is_intern_atomic_group (config_data, "non-atomic-prefix-1.section-a"));
|
||||
}
|
||||
|
||||
static void
|
||||
_set_values_user_atomic_section_2_set (NMConfig *config, gboolean set_user, GKeyFile *keyfile, NMConfigChangeFlags *out_expected_changes)
|
||||
{
|
||||
g_key_file_set_string (keyfile, "atomic-prefix-1.section-a", "key1", "user-value1-x");
|
||||
g_key_file_set_string (keyfile, "atomic-prefix-1.section-a", "key2", "user-value2");
|
||||
g_key_file_set_string (keyfile, "non-atomic-prefix-1.section-a", "nap1-key1", "user-value1-x");
|
||||
g_key_file_set_string (keyfile, "non-atomic-prefix-1.section-a", "nap1-key2", "user-value2-x");
|
||||
*out_expected_changes = NM_CONFIG_CHANGE_VALUES | NM_CONFIG_CHANGE_VALUES_USER | NM_CONFIG_CHANGE_VALUES_INTERN;
|
||||
}
|
||||
|
||||
static void
|
||||
_set_values_user_atomic_section_2_check (NMConfig *config, NMConfigData *config_data, gboolean is_change_event, NMConfigChangeFlags changes, NMConfigData *old_data)
|
||||
{
|
||||
if (is_change_event)
|
||||
g_assert (changes == (NM_CONFIG_CHANGE_VALUES | NM_CONFIG_CHANGE_VALUES_USER | NM_CONFIG_CHANGE_VALUES_INTERN));
|
||||
assert_config_value (config_data, "atomic-prefix-1.section-a", "key1", "user-value1-x");
|
||||
assert_config_value (config_data, "atomic-prefix-1.section-a", "key2", "user-value2");
|
||||
assert_config_value (config_data, "non-atomic-prefix-1.section-a", "nap1-key1", "user-value1-x");
|
||||
assert_config_value (config_data, "non-atomic-prefix-1.section-a", "nap1-key2", "user-value2-x");
|
||||
assert_config_value (config_data, "non-atomic-prefix-1.section-a", "nap1-key3", "intern-value3");
|
||||
g_assert (!nm_config_data_is_intern_atomic_group (config_data, "atomic-prefix-1.section-a"));
|
||||
g_assert (!nm_config_data_is_intern_atomic_group (config_data, "atomic-prefix-1.section-b"));
|
||||
g_assert (!nm_config_data_is_intern_atomic_group (config_data, "non-atomic-prefix-1.section-a"));
|
||||
}
|
||||
|
||||
static void
|
||||
_set_values_intern_atomic_section_2_set (NMConfig *config, gboolean set_user, GKeyFile *keyfile, NMConfigChangeFlags *out_expected_changes)
|
||||
{
|
||||
/* let's hide an atomic section and one key. */
|
||||
g_key_file_set_string (keyfile, "atomic-prefix-1.section-a", NM_CONFIG_KEYFILE_KEY_ATOMIC_SECTION_WAS, "any-value");
|
||||
g_key_file_set_string (keyfile, "non-atomic-prefix-1.section-a", NM_CONFIG_KEYFILE_KEYPREFIX_WAS"nap1-key1", "any-value");
|
||||
g_key_file_set_string (keyfile, "non-atomic-prefix-1.section-a", "nap1-key3", "intern-value3");
|
||||
g_key_file_set_string (keyfile, NM_CONFIG_KEYFILE_GROUPPREFIX_INTERN"with-whitespace", "key1", " b c\\, d ");
|
||||
g_key_file_set_value (keyfile, NM_CONFIG_KEYFILE_GROUPPREFIX_INTERN"with-whitespace", "key2", " b c\\, d ");
|
||||
*out_expected_changes = NM_CONFIG_CHANGE_VALUES | NM_CONFIG_CHANGE_VALUES_INTERN;
|
||||
}
|
||||
|
||||
static void
|
||||
_set_values_intern_atomic_section_2_check (NMConfig *config, NMConfigData *config_data, gboolean is_change_event, NMConfigChangeFlags changes, NMConfigData *old_data)
|
||||
{
|
||||
if (is_change_event)
|
||||
g_assert (changes == (NM_CONFIG_CHANGE_VALUES | NM_CONFIG_CHANGE_VALUES_INTERN));
|
||||
g_assert (!nm_config_data_has_group (config_data, "atomic-prefix-1.section-a"));
|
||||
assert_config_value (config_data, "atomic-prefix-1.section-b", "key1", "user-value1");
|
||||
assert_config_value (config_data, "non-atomic-prefix-1.section-a", "nap1-key1", NULL);
|
||||
assert_config_value (config_data, "non-atomic-prefix-1.section-a", "nap1-key2", "user-value2-x");
|
||||
assert_config_value (config_data, "non-atomic-prefix-1.section-a", "nap1-key3", "intern-value3");
|
||||
g_assert (!nm_config_data_is_intern_atomic_group (config_data, "atomic-prefix-1.section-a"));
|
||||
g_assert (!nm_config_data_is_intern_atomic_group (config_data, "atomic-prefix-1.section-b"));
|
||||
g_assert (!nm_config_data_is_intern_atomic_group (config_data, "non-atomic-prefix-1.section-a"));
|
||||
assert_config_value (config_data, NM_CONFIG_KEYFILE_GROUPPREFIX_INTERN"with-whitespace", "key1", " b c\\, d ");
|
||||
assert_config_value (config_data, NM_CONFIG_KEYFILE_GROUPPREFIX_INTERN"with-whitespace", "key2", " b c\\, d ");
|
||||
}
|
||||
|
||||
static void
|
||||
test_config_set_values (void)
|
||||
{
|
||||
gs_unref_object NMConfig *config = NULL;
|
||||
const char *CONFIG_USER = SRCDIR"/test-set-values-user.conf";
|
||||
const char *CONFIG_INTERN = SRCDIR"/test-set-values-intern.conf";
|
||||
const char *atomic_section_prefixes[] = {
|
||||
"atomic-prefix-1.",
|
||||
"atomic-prefix-2.",
|
||||
NULL,
|
||||
};
|
||||
|
||||
g_assert (g_file_set_contents (CONFIG_USER, "", 0, NULL));
|
||||
g_assert (g_file_set_contents (CONFIG_INTERN, "", 0, NULL));
|
||||
|
||||
config = setup_config (NULL, CONFIG_USER, CONFIG_INTERN, atomic_section_prefixes, "", "", NULL);
|
||||
|
||||
_set_values_user (config, CONFIG_USER,
|
||||
_set_values_user_intern_section_set,
|
||||
_set_values_user_intern_section_check);
|
||||
|
||||
_set_values_user (config, CONFIG_USER,
|
||||
_set_values_user_initial_values_set,
|
||||
_set_values_user_initial_values_check);
|
||||
|
||||
_set_values_intern (config,
|
||||
_set_values_intern_internal_set,
|
||||
_set_values_intern_internal_check);
|
||||
|
||||
_set_values_user (config, CONFIG_USER,
|
||||
_set_values_user_atomic_section_1_set,
|
||||
_set_values_user_atomic_section_1_check);
|
||||
|
||||
_set_values_intern (config,
|
||||
_set_values_intern_atomic_section_1_set,
|
||||
_set_values_intern_atomic_section_1_check);
|
||||
|
||||
_set_values_user (config, CONFIG_USER,
|
||||
_set_values_user_atomic_section_2_set,
|
||||
_set_values_user_atomic_section_2_check);
|
||||
|
||||
_set_values_intern (config,
|
||||
_set_values_intern_atomic_section_2_set,
|
||||
_set_values_intern_atomic_section_2_check);
|
||||
|
||||
g_assert (remove (CONFIG_USER) == 0);
|
||||
g_assert (remove (CONFIG_INTERN) == 0);
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
||||
NMTST_DEFINE ();
|
||||
|
||||
int
|
||||
|
|
@ -419,6 +771,8 @@ main (int argc, char **argv)
|
|||
g_test_add_func ("/config/confdir", test_config_confdir);
|
||||
g_test_add_func ("/config/confdir-parse-error", test_config_confdir_parse_error);
|
||||
|
||||
g_test_add_func ("/config/set-values", test_config_set_values);
|
||||
|
||||
/* This one has to come last, because it leaves its values in
|
||||
* nm-config.c's global variables, and there's no way to reset
|
||||
* those to NULL.
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue