summaryrefslogtreecommitdiff
path: root/udev_lib.c
diff options
context:
space:
mode:
authorkay.sievers@vrfy.org <kay.sievers@vrfy.org>2004-03-27 01:21:46 -0800
committerGreg KH <gregkh@suse.de>2005-04-26 21:35:12 -0700
commit4a539daf1e5daa17b52239478d97f8dc7a6506b6 (patch)
tree0c0554e55bba3ec47ca9844da0135ee8c68c3622 /udev_lib.c
parent949e32f2249da55890a6a49208023df30b6b5227 (diff)
[PATCH] dev_d.c file sorting and cleanup
On Thu, Mar 25, 2004 at 02:52:13AM +0100, Kay Sievers wrote: > Please have look if it still works for you, I only did a very quick > test. Here is a unified version, with all the functions moved to udev_lib.c. We have a generic function now, to call a given fnct(char *) for every file ending with a specific suffix, sorted in lexical order. We use it to execute the dev.d/ files and read our rules.d/ files. The binary should be a bit smaller now. I've also changed it, to not do the dev.d/ exec for net devices.
Diffstat (limited to 'udev_lib.c')
-rw-r--r--udev_lib.c86
1 files changed, 86 insertions, 0 deletions
diff --git a/udev_lib.c b/udev_lib.c
index 4a9eea506c..e9c16c863a 100644
--- a/udev_lib.c
+++ b/udev_lib.c
@@ -21,14 +21,19 @@
#include <stdlib.h>
#include <stdio.h>
+#include <stddef.h>
#include <unistd.h>
#include <fcntl.h>
+#include <errno.h>
+#include <dirent.h>
#include <sys/stat.h>
#include <sys/mman.h>
#include "libsysfs/sysfs/libsysfs.h"
#include "udev.h"
+#include "logging.h"
#include "udev_lib.h"
+#include "list.h"
char *get_action(void)
@@ -136,3 +141,84 @@ size_t buf_get_line(char *buf, size_t buflen, size_t cur)
return count - cur;
}
+struct files {
+ struct list_head list;
+ char name[NAME_SIZE];
+};
+
+/* sort files in lexical order */
+static int file_list_insert(char *filename, struct list_head *file_list)
+{
+ struct files *loop_file;
+ struct files *new_file;
+
+ list_for_each_entry(loop_file, file_list, list) {
+ if (strcmp(loop_file->name, filename) > 0) {
+ break;
+ }
+ }
+
+ new_file = malloc(sizeof(struct files));
+ if (new_file == NULL) {
+ dbg("error malloc");
+ return -ENOMEM;
+ }
+
+ strfieldcpy(new_file->name, filename);
+ list_add_tail(&new_file->list, &loop_file->list);
+ return 0;
+}
+
+/* calls function for file or every file found in directory */
+int call_foreach_file(int fnct(char *f) , char *dirname, char *suffix)
+{
+ struct dirent *ent;
+ DIR *dir;
+ char *ext;
+ char file[NAME_SIZE];
+ struct files *loop_file;
+ struct files *tmp_file;
+ LIST_HEAD(file_list);
+
+ dbg("open directory '%s'", dirname);
+ dir = opendir(dirname);
+ if (dir == NULL) {
+ dbg("unable to open '%s'", dirname);
+ return -1;
+ }
+
+ while (1) {
+ ent = readdir(dir);
+ if (ent == NULL || ent->d_name[0] == '\0')
+ break;
+
+ if ((ent->d_name[0] == '.') || (ent->d_name[0] == COMMENT_CHARACTER))
+ continue;
+
+ /* look for file with specified suffix */
+ ext = strrchr(ent->d_name, '.');
+ if (ext == NULL)
+ continue;
+
+ if (strcmp(ext, suffix) != 0)
+ continue;
+
+ dbg("put file '%s/%s' in list", dirname, ent->d_name);
+ file_list_insert(ent->d_name, &file_list);
+ }
+
+ /* call function for every file in the list */
+ list_for_each_entry_safe(loop_file, tmp_file, &file_list, list) {
+ strfieldcpy(file, dirname);
+ strfieldcat(file, "/");
+ strfieldcat(file, loop_file->name);
+
+ fnct(file);
+
+ list_del(&loop_file->list);
+ free(loop_file);
+ }
+
+ closedir(dir);
+ return 0;
+}