From: Junichi Uekawa Date: Thu, 6 Jul 2023 08:40:38 +0000 (+0900) Subject: Support device files. X-Git-Tag: v2.40-rc1~324^2~1 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=ab0a751700ff6f3e31366d62d996ec49b53ab9dd;p=thirdparty%2Futil-linux.git Support device files. Device files do not give file size with st.st_size field, they return 0. Instead use blkdev_get_size to call the ioctls for block devices. --- diff --git a/misc-utils/fincore.c b/misc-utils/fincore.c index e5e25e5c77..e8dfef2353 100644 --- a/misc-utils/fincore.c +++ b/misc-utils/fincore.c @@ -31,6 +31,7 @@ #include "closestream.h" #include "xalloc.h" #include "strutils.h" +#include "blkdev.h" #include "libsmartcols.h" @@ -227,28 +228,33 @@ static int fincore_fd (struct fincore_control *ctl, */ static int fincore_name(struct fincore_control *ctl, const char *name, - struct stat *sb, + unsigned long long *size, off_t *count_incore) { int fd; int rc = 0; + struct stat sb; if ((fd = open (name, O_RDONLY)) < 0) { warn(_("failed to open: %s"), name); return -errno; } - if (fstat (fd, sb) < 0) { + if (fstat (fd, &sb) < 0) { warn(_("failed to do fstat: %s"), name); close (fd); return -errno; } - if (S_ISDIR(sb->st_mode)) - rc = 1; /* ignore */ - - else if (sb->st_size) - rc = fincore_fd(ctl, fd, name, sb->st_size, count_incore); + if (S_ISBLK(sb.st_mode) || S_ISREG(sb.st_mode)) { + if (blkdev_get_size(fd, size) == 0) + rc = fincore_fd(ctl, fd, name, *size, count_incore); + else + warn(_("failed ioctl to get size: %s"), name); + } else { + rc = 1; /* ignore things like symlinks + * and directories*/ + } close (fd); return rc; @@ -391,12 +397,12 @@ int main(int argc, char ** argv) for(; optind < argc; optind++) { char *name = argv[optind]; - struct stat sb; off_t count_incore = 0; + unsigned long long size = 0; - switch (fincore_name(&ctl, name, &sb, &count_incore)) { + switch (fincore_name(&ctl, name, &size, &count_incore)) { case 0: - add_output_data(&ctl, name, sb.st_size, count_incore); + add_output_data(&ctl, name, size, count_incore); break; case 1: break; /* ignore */