chiark / gitweb /
e6c6173ecab6a3a5fdc0678ba8d807d4be9b4e0e
[elogind.git] / extras / run_directory / run_directory.c
1 /*
2  * udev_run_directory.c - directory multiplexer
3  *
4  * Copyright (C) 2005 Kay Sievers <kay@vrfy.org>
5  *
6  *      This program is free software; you can redistribute it and/or modify it
7  *      under the terms of the GNU General Public License as published by the
8  *      Free Software Foundation version 2 of the License.
9  *
10  */
11
12 #include <stdio.h>
13 #include <stdlib.h>
14 #include <string.h>
15 #include <stddef.h>
16 #include <dirent.h>
17 #include <errno.h>
18 #include <unistd.h>
19 #include <fcntl.h>
20 #include <limits.h>
21 #include <sys/types.h>
22 #include <sys/wait.h>
23 #include <sys/stat.h>
24
25 #include "../../udev_utils.h"
26 #include "../../list.h"
27 #include "../../logging.h"
28
29 int run_directory(const char *dir, const char *suffix, const char *subsystem);
30
31 static int run_program(const char *filename, const char *subsystem)
32 {
33         pid_t pid;
34
35         dbg("running %s", filename);
36         pid = fork();
37         switch (pid) {
38         case 0:
39                 /* child */
40                 execl(filename, filename, subsystem, NULL);
41                 dbg("exec of child failed");
42                 _exit(1);
43         case -1:
44                 dbg("fork of child failed");
45                 break;
46                 return -1;
47         default:
48                 waitpid(pid, NULL, 0);
49         }
50
51         return 0;
52 }
53
54 int run_directory(const char *dir, const char *suffix, const char *subsystem)
55 {
56         char dirname[NAME_SIZE];
57         struct name_entry *name_loop, *name_tmp;
58         LIST_HEAD(name_list);
59
60         if (subsystem) {
61                 snprintf(dirname, sizeof(dirname), "%s/%s", dir, subsystem);
62                 dirname[sizeof(dirname)-1] = '\0';
63                 dbg("looking at '%s'", dirname);
64                 add_matching_files(&name_list, dirname, suffix);
65         }
66
67         snprintf(dirname, sizeof(dirname), "%s/default", dir);
68         dirname[sizeof(dirname)-1] = '\0';
69         dbg("looking at '%s'", dirname);
70         add_matching_files(&name_list, dirname, suffix);
71
72         list_for_each_entry_safe(name_loop, name_tmp, &name_list, node) {
73                 run_program(name_loop->name, subsystem);
74                 list_del(&name_loop->node);
75         }
76
77         logging_close();
78         return 0;
79 }