mirror of
git://sourceware.org/git/lvm2.git
synced 2024-12-21 13:34:40 +03:00
o Quick and dirty *UGLY* hack of a /proc/devices cache using a linked list
o I don't like it, but I'm committing it so I can go back and laugh at myself later o I have a (hopefully) better idea that i'll try to commit yet today.
This commit is contained in:
parent
7af02225cc
commit
83b2c0d30a
@ -73,12 +73,21 @@ struct dev_i {
|
|||||||
struct dev_i *next;
|
struct dev_i *next;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/* temporary structure - will replace with something smarter later */
|
||||||
|
struct dev_n {
|
||||||
|
int major;
|
||||||
|
struct dev_n *next;
|
||||||
|
};
|
||||||
|
|
||||||
struct dev_mgr {
|
struct dev_mgr {
|
||||||
/* everything is allocated from this pool */
|
/* everything is allocated from this pool */
|
||||||
struct pool *pool;
|
struct pool *pool;
|
||||||
|
|
||||||
int has_scanned;
|
int has_scanned;
|
||||||
|
|
||||||
|
/* linked list of valid major numbers */
|
||||||
|
struct dev_n *dev_list;
|
||||||
|
|
||||||
/* hash table */
|
/* hash table */
|
||||||
int num_slots;
|
int num_slots;
|
||||||
int mask;
|
int mask;
|
||||||
@ -110,7 +119,8 @@ static void _name_insert(struct dev_mgr *dm, struct dev_i *device);
|
|||||||
static void _dev_insert(struct dev_mgr *dm, struct dev_i *device);
|
static void _dev_insert(struct dev_mgr *dm, struct dev_i *device);
|
||||||
static void _list_insert(struct dev_mgr *dm, struct dev_i *device);
|
static void _list_insert(struct dev_mgr *dm, struct dev_i *device);
|
||||||
static unsigned int _hash_dev(dev_t d);
|
static unsigned int _hash_dev(dev_t d);
|
||||||
static int _check_dev(struct stat *stat_b);
|
static int _check_dev(struct dev_mgr *dm, struct stat *stat_b);
|
||||||
|
static int _scan_proc_dev(struct dev_mgr *dm);
|
||||||
|
|
||||||
static inline struct device *_get_dev(struct dev_i *di)
|
static inline struct device *_get_dev(struct dev_i *di)
|
||||||
{
|
{
|
||||||
@ -151,6 +161,8 @@ struct dev_mgr *init_dev_manager(struct config_node *cn)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
_scan_proc_dev(dm);
|
||||||
|
|
||||||
return dm;
|
return dm;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -262,7 +274,7 @@ static struct dev_i *_add_named_device(struct dev_mgr *dm, const char *devpath)
|
|||||||
struct stat stat_b;
|
struct stat stat_b;
|
||||||
|
|
||||||
/* FIXME: move lvm_check_dev into this file */
|
/* FIXME: move lvm_check_dev into this file */
|
||||||
if ((stat(devpath, &stat_b) == -1) || _check_dev(&stat_b))
|
if ((stat(devpath, &stat_b) == -1) || _check_dev(dm, &stat_b))
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
/* Check for directories and scan them if they aren't this directory
|
/* Check for directories and scan them if they aren't this directory
|
||||||
@ -425,23 +437,37 @@ static unsigned int _hash_dev(dev_t d)
|
|||||||
return (unsigned int) d;
|
return (unsigned int) d;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int _check_dev(struct stat *stat_b)
|
static int _check_dev(struct dev_mgr *dm, struct stat *stat_b)
|
||||||
{
|
{
|
||||||
char line[80];
|
|
||||||
int ret = 1;
|
int ret = 1;
|
||||||
int seek_major = MAJOR(stat_b->st_rdev);
|
int seek_major = MAJOR(stat_b->st_rdev);
|
||||||
|
struct dev_n *node;
|
||||||
|
|
||||||
if (stat_b == NULL)
|
if (stat_b == NULL)
|
||||||
ret = -LOCAL_EPARAM;
|
ret = -LOCAL_EPARAM;
|
||||||
else if ( ! S_ISBLK(stat_b->st_mode))
|
else if ( ! S_ISBLK(stat_b->st_mode))
|
||||||
ret = -LOCAL_CHECK_NAME;
|
ret = -LOCAL_CHECK_NAME;
|
||||||
else {
|
else {
|
||||||
|
for(node = dm->dev_list; node != NULL; node = node->next)
|
||||||
|
if (node->major == seek_major)
|
||||||
|
ret = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Caches /proc/device info and
|
||||||
|
returns the number of block devices found in /proc/devices */
|
||||||
|
static int _scan_proc_dev(struct dev_mgr *dm)
|
||||||
|
{
|
||||||
|
char line[80];
|
||||||
FILE *procdevices = NULL;
|
FILE *procdevices = NULL;
|
||||||
|
int ret = 0;
|
||||||
int i, j = 0;
|
int i, j = 0;
|
||||||
int line_major = 0;
|
int line_major = 0;
|
||||||
int blocksection = 0;
|
int blocksection = 0;
|
||||||
|
struct dev_n * dev_node= NULL;
|
||||||
|
|
||||||
/* FIXME Ought to cache this first time */
|
|
||||||
if ((procdevices = fopen("/proc/devices", "r")) != NULL) {
|
if ((procdevices = fopen("/proc/devices", "r")) != NULL) {
|
||||||
while (fgets(line, 80, procdevices) != NULL) {
|
while (fgets(line, 80, procdevices) != NULL) {
|
||||||
i = 0;
|
i = 0;
|
||||||
@ -458,34 +484,34 @@ static int _check_dev(struct stat *stat_b)
|
|||||||
if (!blocksection)
|
if (!blocksection)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
if (line_major == seek_major) {
|
/* Find the start of the device major name */
|
||||||
while (line[i] != ' ' && line[i] != '\0')
|
while (line[i] != ' ' && line[i] != '\0')
|
||||||
i++;
|
i++;
|
||||||
while (line[i] == ' ' && line[i] != '\0')
|
while (line[i] == ' ' && line[i] != '\0')
|
||||||
i++;
|
i++;
|
||||||
|
|
||||||
for (j = 0; device_names[j] != NULL; j++) {
|
for (j = 0; device_names[j] != NULL; j++) {
|
||||||
if (strlen(device_names[j])
|
if (strlen(device_names[j])
|
||||||
<= strlen(line + i)) {
|
<= strlen(line + i)) {
|
||||||
if (strncmp (device_names[j],
|
if (strncmp (device_names[j],
|
||||||
line + i,
|
line + i,
|
||||||
strlen(device_names[j])) == 0) {
|
strlen(device_names[j])) == 0) {
|
||||||
ret = j;
|
dev_node = pool_alloc(dm->pool,
|
||||||
|
sizeof(*dev_node));
|
||||||
|
dev_node->major = line_major;
|
||||||
|
dev_node->next=dm->dev_list;
|
||||||
|
dm->dev_list = dev_node;
|
||||||
|
ret++;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
fclose(procdevices);
|
fclose(procdevices);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Local variables:
|
* Local variables:
|
||||||
* c-file-style: "linux"
|
* c-file-style: "linux"
|
||||||
|
Loading…
Reference in New Issue
Block a user