From: Keith Busch Date: Tue, 30 Aug 2016 20:33:54 +0000 (-0600) Subject: Simplify list command X-Git-Tag: v0.9~2 X-Git-Url: https://www.infradead.org/git/?a=commitdiff_plain;h=74de779fc0e426815a989e909b5ada07361c2261;p=users%2Fsagi%2Fnvme-cli.git Simplify list command Use scandir with an appropriate filter to find all our nvme namespaces and handle allocating all the dirent's. Makes the implementation a little simpler. Signed-off-by: Keith Busch --- diff --git a/nvme.c b/nvme.c index 1bd74fd6..636053d9 100644 --- a/nvme.c +++ b/nvme.c @@ -772,70 +772,55 @@ static int get_nvme_info(int fd, struct list_item *item, const char *node) } static const char *dev = "/dev/"; -static int list(int argc, char **argv, struct command *cmd, struct plugin *plugin) + +/* Assume every block device starting with /dev/nvme is an nvme namespace */ +static int scan_dev_filter(const struct dirent *d) { - DIR *d; - struct dirent *entry; - char path[256] = { 0 }; - struct list_item list_items[MAX_LIST_ITEMS]; + char path[256]; struct stat bd; - unsigned int count = 0; - int ret; - d = opendir(dev); - if (!d) { - fprintf(stderr, - "Failed to open directory %s with error %s\n", - dev, strerror(errno)); - return errno; + if (d->d_name[0] == '.') + return 0; + + if (strstr(d->d_name, "nvme")) { + snprintf(path, sizeof(path), "%s%s", dev, d->d_name); + if (stat(path, &bd)) + return 0; + if (S_ISBLK(bd.st_mode)) + return 1; } + return 0; +} - while (1) { - errno = 0; - entry = readdir(d); - if (NULL == entry) { - /* Error while reading directory */ - if (errno) { - fprintf(stderr, - "Failed to read contents of %s with error %s\n", - dev, strerror(errno)); - closedir(d); - return errno; - } - else { - /* done reading the directory stream */ - break; - } - } - /* lets not walk the entire fs */ - if (!strcmp(entry->d_name, "..")) - continue; - if (strstr(entry->d_name, "nvme") != NULL) { - snprintf(path, sizeof(path), "%s%s", dev, entry->d_name); - if (stat(path, &bd)) { - fprintf(stderr, - "Failed to stat %s with error %s\n", - path, strerror(errno)); - closedir(d); - return errno; - } - if (S_ISBLK(bd.st_mode)) { - open_dev(path); - ret = get_nvme_info(fd, &list_items[count], path); - if (ret > 0) { - closedir(d); - return ret; - } - count++; - } - } +static int list(int argc, char **argv, struct command *cmd, struct plugin *plugin) +{ + char path[256]; + struct dirent **devices; + struct list_item *list_items; + unsigned int i, n, fd, ret; + + n = scandir(dev, &devices, scan_dev_filter, alphasort); + if (n <= 0) + return n; + + list_items = calloc(n, sizeof(*list_items)); + if (!list_items) + return ENOMEM; + + for (i = 0; i < n; i++) { + snprintf(path, sizeof(path), "%s%s", dev, devices[i]->d_name); + fd = open(path, O_RDONLY); + ret = get_nvme_info(fd, &list_items[i], path); + if (ret) + return ret; } - closedir(d); + print_list_items(list_items, n); + + for (i = 0; i < n; i++) + free(devices[i]); + free(devices); + free(list_items); - if (count) - print_list_items(list_items, count); - else - printf("No NVMe devices detected.\n"); return 0; }