之前在开发板上实现了个u盘挂载及设备信息(主要是存储空间使用情况)显示功能。
显示u盘存储空间使用情况是利用busybox中的df -h命令来得到的。这个时候问题来了,发现通过这个busybox df命令得到的数据是有问题的。
下图中 /dev/sdb1的信息明显是错的。
我的解决办法是,找了一个轻量级df命令源码,做了一些适当的修改,发现解决了这个问题。下面是源码:
#include <stdio.h>
#include <mntent.h>
#include <string.h>
#include <sys/vfs.h>
static const unsigned long long G = 1024*1024*1024ull;
static const unsigned long long M = 1024*1024;
static const unsigned long long K = 1024;
static char str[20];
char* kscale(unsigned long b, unsigned long bs)
{
unsigned long long size = b * (unsigned long long)bs;
if (size > G){
sprintf(str, "%0.1fG", size/(G*1.0));
return str;
} else if (size > M){
sprintf(str, "%0.1fM", size/(1.0*M));
return str;
} else if (size > K){
sprintf(str, "%0.1fK", size/(1.0*K));
return str;
} else {
sprintf(str, "%0.1fB", size*1.0);
return str;
}
}
void usage(void)
{
printf("Usage: litedf [-d MOUNTDIRECTION ]\n");
}
int main(int argc, char *argv[])
{
int flag = 0; /*附加选项标志*/
if (argc > 3 || 2 == argc){
usage();
return -1;
}
if (3 == argc){
if ( 0 != strcmp(argv[1],"-d")){
usage();
return -1;
}
flag = 1;
}
char mount_on[50] = {0};
strcpy(mount_on, argv[2]);
FILE* mount_table;
struct mntent *mount_entry;
struct statfs s;
unsigned long blocks_used;
unsigned blocks_percent_used;
const char *disp_units_hdr = NULL;
mount_table = NULL;
mount_table = setmntent("/proc/mounts", "r");
if (!mount_table){
fprintf(stderr, "set mount entry error\n");
return -1;
}
disp_units_hdr = " Size";
printf("Filesystem %-15sUsed Available %s Mounted on\n",
disp_units_hdr, "Use%");
while (1) {
const char *device;
const char *mount_point;
if (mount_table) {
mount_entry = getmntent(mount_table);
if (!mount_entry) {
endmntent(mount_table);
break;
}
}
else
continue;
device = mount_entry->mnt_fsname;
mount_point = mount_entry->mnt_dir;
if ( 0 != strcmp(mount_on, mount_point) && flag == 1)
continue;
//fprintf(stderr, "mount info: device=%s mountpoint=%s/n", device, mount_point);
if (statfs(mount_point, &s) != 0){
fprintf(stderr, "statfs failed!\n");
continue;
}
if ((s.f_blocks > 0) || !mount_table ){
blocks_used = s.f_blocks - s.f_bfree;
blocks_percent_used = 0;
if (blocks_used + s.f_bavail){
blocks_percent_used = (blocks_used * 100ULL
+ (blocks_used + s.f_bavail)/2
) / (blocks_used + s.f_bavail);
}
/* GNU coreutils 6.10 skips certain mounts, try to be compatible. */
if (strcmp(device, "rootfs") == 0)
continue;
printf("%-20s", device);
char s1[20];
char s2[20];
char s3[20];
strcpy(s1, kscale(s.f_blocks, s.f_bsize));
strcpy(s2, kscale(s.f_blocks - s.f_bfree, s.f_bsize));
strcpy(s3, kscale(s.f_bavail, s.f_bsize));
printf(" %9s %9s %9s %3u%% %s\n",
s1,
s2,
s3,
blocks_percent_used, mount_point);
}
}
return 0;
}
参考文章:http://blog.csdn.net/fjb2080/article/details/5990355#