statfs函数

来源:互联网 发布:伦敦金数据 编辑:程序博客网 时间:2024/06/02 23:47

因为要读取SD卡的大小和使用情况,所以用到statfs这个函数,功能类似于df命令。

需要的头文件:#include <sys/vfs.h> 

int statfs(const char *path, struct statfs *buf);

struct statfs {long f_type; /* 文件系统类型 */long f_bsize; /* 经过优化的传输块大小 */long f_blocks; /* 文件系统数据块总数 */long f_bfree; /* 可用块数 */long f_bavail; /* 非超级用户可获取的块数 */long f_files; /* 文件结点总数 */long f_ffree; /* 可用文件结点数 */fsid_t f_fsid; /* 文件系统标识 */long f_namelen; /* 文件名的最大长度 */};
返回值:
成功执行时,返回0。失败返回-1,errno被设为以下的某个值  
 
EACCES: (statfs())文件或路径名中包含的目录不可访问EBADF : (fstatfs()) 文件描述词无效EFAULT: 内存地址无效EINTR : 操作由信号中断EIO    : 读写出错ELOOP : (statfs())解释路径名过程中存在太多的符号连接ENAMETOOLONG:(statfs()) 路径名太长ENOENT:(statfs()) 文件不存在ENOMEM: 核心内存不足ENOSYS: 文件系统不支持调用ENOTDIR:(statfs())路径名中当作目录的组件并非目录EOVERFLOW:信息溢出

上代码例子:

#include <sys/vfs.h>#include <stdio.h>int main(){    struct statfs diskInfo;    //statfs("/media/card",&diskInfo);statfs("/dev",&diskInfo);    unsigned long long blocksize = diskInfo.f_bsize;// 每个block里面包含的字节数    unsigned long long totalsize = blocksize*diskInfo.f_blocks;//总的字节数char totalsize_GB[10]={0};    printf("TOTAL_SIZE == %llu KB  %llu MB  %llu GB\n",totalsize>>10,totalsize>>20,totalsize>>30); // 分别换成KB,MB,GB为单位sprintf(totalsize_GB,"%.2f",(float)(totalsize>>20)/1024);printf("totalsize_GB=%s\n",totalsize_GB);    unsigned long long freesize = blocksize*diskInfo.f_bfree; //再计算下剩余的空间大小    printf("DISK_FREE == %llu KB  %llu MB  %llu GB\n",freesize>>10,freesize>>20,freesize>>30);unsigned long long usedsize = blocksize*(diskInfo.f_blocks - diskInfo.f_bfree);char usedsize_GB[10]={0};sprintf(usedsize_GB,"%.2f",(float)(usedsize>>20)/1024);printf("usedsize_GB=%s\n",usedsize_GB); return 0;}

打印结果:

TOTAL_SIZE == 4079928 KB  3984 MB  3 GBtotalsize_GB=3.89DISK_FREE == 4079924 KB  3984 MB  3 GBusedsize_GB=0.00
df命令:

udev                   4079928         4   4079924   1% /dev
可见结果是一致的。

代码里有几点有意思,换算成MB、GB是通过移位完成的。

但如果用GB为单位,需要保留两位小数呢?当 %.f2  格式即可,如果要传递这个数据,最好是用sprintf把小数格式成字符串更好吧。

已用的空间=总大小—剩余大小。




0 0