dispatcher: look for the scripts in /usr/lib as well
This makes it possible for packages that ship dispatcher scripts to use the correct location.
This commit is contained in:
@@ -466,12 +466,6 @@ check_permissions (struct stat *s, const char **out_error_msg)
|
|||||||
g_return_val_if_fail (out_error_msg != NULL, FALSE);
|
g_return_val_if_fail (out_error_msg != NULL, FALSE);
|
||||||
g_return_val_if_fail (*out_error_msg == NULL, FALSE);
|
g_return_val_if_fail (*out_error_msg == NULL, FALSE);
|
||||||
|
|
||||||
/* Only accept regular files */
|
|
||||||
if (!S_ISREG (s->st_mode)) {
|
|
||||||
*out_error_msg = "not a regular file.";
|
|
||||||
return FALSE;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Only accept files owned by root */
|
/* Only accept files owned by root */
|
||||||
if (s->st_uid != 0) {
|
if (s->st_uid != 0) {
|
||||||
*out_error_msg = "not owned by root.";
|
*out_error_msg = "not owned by root.";
|
||||||
@@ -573,59 +567,104 @@ dispatch_one_script (Request *request)
|
|||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
static GSList *
|
static int
|
||||||
find_scripts (const char *str_action)
|
_compare_basenames (gconstpointer a, gconstpointer b)
|
||||||
{
|
{
|
||||||
GDir *dir;
|
const char *basename_a = strrchr (a, '/');
|
||||||
const char *filename;
|
const char *basename_b = strrchr (b, '/');
|
||||||
GSList *sorted = NULL;
|
int ret;
|
||||||
GError *error = NULL;
|
|
||||||
const char *dirname;
|
|
||||||
|
|
||||||
if ( strcmp (str_action, NMD_ACTION_PRE_UP) == 0
|
nm_assert (basename_a);
|
||||||
|| strcmp (str_action, NMD_ACTION_VPN_PRE_UP) == 0)
|
nm_assert (basename_b);
|
||||||
dirname = NMD_SCRIPT_DIR_PRE_UP;
|
|
||||||
else if ( strcmp (str_action, NMD_ACTION_PRE_DOWN) == 0
|
ret = strcmp (++basename_a, ++basename_b);
|
||||||
|| strcmp (str_action, NMD_ACTION_VPN_PRE_DOWN) == 0)
|
if (ret)
|
||||||
dirname = NMD_SCRIPT_DIR_PRE_DOWN;
|
return ret;
|
||||||
else
|
|
||||||
dirname = NMD_SCRIPT_DIR_DEFAULT;
|
nm_assert_not_reached ();
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
_find_scripts (GHashTable *scripts, const char *base, const char *subdir)
|
||||||
|
{
|
||||||
|
const char *filename;
|
||||||
|
gs_free char *dirname = NULL;
|
||||||
|
GError *error = NULL;
|
||||||
|
GDir *dir;
|
||||||
|
|
||||||
|
dirname = g_build_filename (base, "dispatcher.d", subdir, NULL);
|
||||||
|
|
||||||
if (!(dir = g_dir_open (dirname, 0, &error))) {
|
if (!(dir = g_dir_open (dirname, 0, &error))) {
|
||||||
g_message ("find-scripts: Failed to open dispatcher directory '%s': %s",
|
g_message ("find-scripts: Failed to open dispatcher directory '%s': %s",
|
||||||
dirname, error->message);
|
dirname, error->message);
|
||||||
g_error_free (error);
|
g_error_free (error);
|
||||||
return NULL;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
while ((filename = g_dir_read_name (dir))) {
|
while ((filename = g_dir_read_name (dir))) {
|
||||||
char *path;
|
|
||||||
struct stat st;
|
|
||||||
int err;
|
|
||||||
const char *err_msg = NULL;
|
|
||||||
|
|
||||||
if (!check_filename (filename))
|
if (!check_filename (filename))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
path = g_build_filename (dirname, filename, NULL);
|
g_hash_table_insert (scripts,
|
||||||
|
g_strdup (filename),
|
||||||
|
g_build_filename (dirname, filename, NULL));
|
||||||
|
}
|
||||||
|
|
||||||
|
g_dir_close (dir);
|
||||||
|
}
|
||||||
|
|
||||||
|
static GSList *
|
||||||
|
find_scripts (const char *str_action)
|
||||||
|
{
|
||||||
|
gs_unref_hashtable GHashTable *scripts = NULL;
|
||||||
|
GSList *script_list = NULL;
|
||||||
|
GHashTableIter iter;
|
||||||
|
const char *subdir = NULL;
|
||||||
|
char *path;
|
||||||
|
char *filename;
|
||||||
|
|
||||||
|
if ( strcmp (str_action, NMD_ACTION_PRE_UP) == 0
|
||||||
|
|| strcmp (str_action, NMD_ACTION_VPN_PRE_UP) == 0)
|
||||||
|
subdir = "pre-up.d";
|
||||||
|
else if ( strcmp (str_action, NMD_ACTION_PRE_DOWN) == 0
|
||||||
|
|| strcmp (str_action, NMD_ACTION_VPN_PRE_DOWN) == 0)
|
||||||
|
subdir = "pre-down.d";
|
||||||
|
|
||||||
|
scripts = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, g_free);
|
||||||
|
|
||||||
|
_find_scripts (scripts, NMLIBDIR, subdir);
|
||||||
|
_find_scripts (scripts, NMCONFDIR, subdir);
|
||||||
|
|
||||||
|
g_hash_table_iter_init (&iter, scripts);
|
||||||
|
while (g_hash_table_iter_next (&iter, (gpointer *) &filename, (gpointer *) &path)) {
|
||||||
|
struct stat st;
|
||||||
|
char *link_target;
|
||||||
|
int err;
|
||||||
|
const char *err_msg = NULL;
|
||||||
|
|
||||||
|
link_target = g_file_read_link (path, NULL);
|
||||||
|
if (g_strcmp0 (link_target, "/dev/null") == 0) {
|
||||||
|
g_free (link_target);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
g_free (link_target);
|
||||||
|
|
||||||
err = stat (path, &st);
|
err = stat (path, &st);
|
||||||
if (err)
|
if (err)
|
||||||
g_warning ("find-scripts: Failed to stat '%s': %d", path, err);
|
g_warning ("find-scripts: Failed to stat '%s': %d", path, err);
|
||||||
else if (S_ISDIR (st.st_mode))
|
else if (!S_ISREG (st.st_mode))
|
||||||
; /* silently skip. */
|
; /* silently skip. */
|
||||||
else if (!check_permissions (&st, &err_msg))
|
else if (!check_permissions (&st, &err_msg))
|
||||||
g_warning ("find-scripts: Cannot execute '%s': %s", path, err_msg);
|
g_warning ("find-scripts: Cannot execute '%s': %s", path, err_msg);
|
||||||
else {
|
else {
|
||||||
/* success */
|
/* success */
|
||||||
sorted = g_slist_insert_sorted (sorted, path, (GCompareFunc) g_strcmp0);
|
script_list = g_slist_prepend (script_list, g_strdup (path));
|
||||||
path = NULL;
|
continue;
|
||||||
}
|
}
|
||||||
g_free (path);
|
|
||||||
}
|
}
|
||||||
g_dir_close (dir);
|
|
||||||
|
|
||||||
return sorted;
|
return g_slist_sort (script_list, _compare_basenames);
|
||||||
}
|
}
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
@@ -636,6 +675,7 @@ script_must_wait (const char *path)
|
|||||||
gs_free char *real = NULL;
|
gs_free char *real = NULL;
|
||||||
char *tmp;
|
char *tmp;
|
||||||
|
|
||||||
|
|
||||||
link = g_file_read_link (path, NULL);
|
link = g_file_read_link (path, NULL);
|
||||||
if (link) {
|
if (link) {
|
||||||
if (!g_path_is_absolute (link)) {
|
if (!g_path_is_absolute (link)) {
|
||||||
@@ -648,8 +688,7 @@ script_must_wait (const char *path)
|
|||||||
|
|
||||||
dir = g_path_get_dirname (link);
|
dir = g_path_get_dirname (link);
|
||||||
real = realpath (dir, NULL);
|
real = realpath (dir, NULL);
|
||||||
|
if (real && !g_str_has_suffix (real, "/no-wait.d"))
|
||||||
if (real && !strcmp (real, NMD_SCRIPT_DIR_NO_WAIT))
|
|
||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -21,11 +21,6 @@
|
|||||||
#ifndef __NM_DISPACHER_API_H__
|
#ifndef __NM_DISPACHER_API_H__
|
||||||
#define __NM_DISPACHER_API_H__
|
#define __NM_DISPACHER_API_H__
|
||||||
|
|
||||||
#define NMD_SCRIPT_DIR_DEFAULT NMCONFDIR "/dispatcher.d"
|
|
||||||
#define NMD_SCRIPT_DIR_PRE_UP NMD_SCRIPT_DIR_DEFAULT "/pre-up.d"
|
|
||||||
#define NMD_SCRIPT_DIR_PRE_DOWN NMD_SCRIPT_DIR_DEFAULT "/pre-down.d"
|
|
||||||
#define NMD_SCRIPT_DIR_NO_WAIT NMD_SCRIPT_DIR_DEFAULT "/no-wait.d"
|
|
||||||
|
|
||||||
#define NM_DISPATCHER_DBUS_SERVICE "org.freedesktop.nm_dispatcher"
|
#define NM_DISPATCHER_DBUS_SERVICE "org.freedesktop.nm_dispatcher"
|
||||||
#define NM_DISPATCHER_DBUS_INTERFACE "org.freedesktop.nm_dispatcher"
|
#define NM_DISPATCHER_DBUS_INTERFACE "org.freedesktop.nm_dispatcher"
|
||||||
#define NM_DISPATCHER_DBUS_PATH "/org/freedesktop/nm_dispatcher"
|
#define NM_DISPATCHER_DBUS_PATH "/org/freedesktop/nm_dispatcher"
|
||||||
|
Reference in New Issue
Block a user