X-Git-Url: http://www.chiark.greenend.org.uk/ucgi/~ianmdlvl/git?p=elogind.git;a=blobdiff_plain;f=udevdb.c;h=c4e064fc115d4414ef21cbbbc44403ed4570e7bc;hp=5be3c2515126efb327d2276bbaddfbdb98963597;hb=bb513a064ce00e8efca1c697955d4a34b6782c29;hpb=d546791d3ab1cbf8cb08b27eab1fc09e1c5d04dc diff --git a/udevdb.c b/udevdb.c index 5be3c2515..c4e064fc1 100644 --- a/udevdb.c +++ b/udevdb.c @@ -35,6 +35,7 @@ #include "udev_version.h" #include "udev.h" +#include "logging.h" #include "namedev.h" #include "udevdb.h" #include "tdb/tdb.h" @@ -62,29 +63,22 @@ int udevdb_add_dev(const char *path, const struct udevice *dev) return tdb_store(udevdb, key, data, TDB_REPLACE); } -struct udevice *udevdb_get_dev(const char *path) +int udevdb_get_dev(const char *path, struct udevice *dev) { TDB_DATA key, data; - struct udevice *dev; if (path == NULL) - return NULL; + return -ENODEV; key.dptr = (void *)path; key.dsize = strlen(path) + 1; data = tdb_fetch(udevdb, key); if (data.dptr == NULL || data.dsize == 0) - return NULL; - - dev = malloc(sizeof(*dev)); - if (dev == NULL) - goto exit; + return -ENODEV; memcpy(dev, data.dptr, sizeof(*dev)); -exit: - free(data.dptr); - return dev; + return 0; } int udevdb_delete_dev(const char *path) @@ -131,7 +125,80 @@ int udevdb_init(int init_flag) dbg("unable to initialize in-memory database"); else dbg("unable to initialize database at '%s'", udev_db_filename); + return -EACCES; + } + return 0; +} + +/** + * udevdb_open_ro: open database for reading + */ +int udevdb_open_ro(void) +{ + udevdb = tdb_open(udev_db_filename, 0, 0, O_RDONLY, 0); + if (udevdb == NULL) { + dbg("unable to open database at '%s'", udev_db_filename); + return -EACCES; + } + return 0; +} + +static int (*user_record_callback) (char *path, struct udevice *dev); + +static int traverse_callback(TDB_CONTEXT *tdb, TDB_DATA key, TDB_DATA dbuf, void *state) +{ + return user_record_callback((char*) key.dptr, (struct udevice*) dbuf.dptr); +} + +/** + * udevdb_call_foreach: dumps whole database by passing record data to user function + * @user_record_handler: user function called for every record in the database + */ +int udevdb_call_foreach(int (*user_record_handler) (char *path, struct udevice *dev)) +{ + int retval = 0; + + if (user_record_handler == NULL) { + dbg("invalid user record handling function"); return -EINVAL; } + user_record_callback = user_record_handler; + retval = tdb_traverse(udevdb, traverse_callback, NULL); + if (retval < 0) + return -ENODEV; + else + return 0; +} + +static struct udevice *find_dev; +static char *find_path; +static const char *find_name; +static int find_found; + +static int find_device_by_name(char *path, struct udevice *dev) +{ + if (strncmp(dev->name, find_name, sizeof(dev->name)) == 0) { + memcpy(find_dev, dev, sizeof(*find_dev)); + strncpy(find_path, path, NAME_SIZE); + find_found = 1; + /* stop search */ + return 1; + } return 0; } + +/** + * udevdb_get_dev_byname: search device with given name by traversing the whole database + */ +int udevdb_get_dev_byname(const char *name, char *path, struct udevice *dev) +{ + find_found = 0; + find_path = path; + find_dev = dev; + find_name = name; + udevdb_call_foreach(find_device_by_name); + if (find_found == 1) + return 0; + else + return -1; +}