/dev 目录
dev目录是一个特殊的目录,其内部包含许多设备文件。这些设备文件为操作系统上次应用提供了访问底层设备的接口。对这些设备文件的I/O操作都会按照如下的流程进行设备文件I/O ——》底层设备驱动--》 实际设备
为什么存在这个文件夹
“如何访问物理设备”是一个经典的问题,不是只利用文件系统就能满足我们所有的开发任务了,有的时候我们开发的程序必须要能够访问逻辑扇区(LGB)而不是简单地利用内核提供的文件系统,例如ghost备份还原系统、分区表的备份等这些操作。
注意点
- 设备文件并不代表实际物理设备
设备文件用于从逻辑上代表一个设备,其为系统和上层应用提供一个可访问的接口来操作设备文件所代表的设备。但是这些设备类似于抽象设备,而不是实际意义上的物理设备。例如sda sda1 sda2
这三个设备的意义分别是SCSI上的硬盘,硬盘的第一个分区,硬盘的第二个分区。硬盘才是实际的物理设备,分区只是其内部根据分区表做的磁盘划分策略而已。同理tty
也是抽象概念,其应该是键盘和屏幕共同组成的终端,而不是单一的某个设备。
- 设备文件提供访问接口
用户不允许直接调用硬件驱动直接操作硬件,必须通过调用操作系统才能访问底层设备。那么为了操作、获取底层设备,其提供了设备文件。通过设备文件的概念,我们可以轻松按照扇区读写硬盘。并且由于ioctl
这个垃圾桶函数的存在,设备的访问可以依据其具体实现进行动态无限扩充。通过文件的形式进行特性增加,而不是增加系统调用的数量,从一定层面上显示了万物皆文件的设计哲学,保证了接口的整洁。
- 设备文件是设备驱动的门户
数据传递顺序为应用程序将数据传递至设备文件,之后设备文件调用关联的设备驱动程序,最后驱动程序与物理设备进行交互。
利用/dev/sda 获取磁盘大小
#include <stdio.h>
#include <fcntl.h>
#include <linux/fs.h>
#include <unistd.h>
#include <sys/ioctl.h>
int main(void)
{
int fd;
unsigned long long size;
int len;
int r;
if ((fd = open("/dev/sda", O_RDONLY)) < 0)
{
printf("open error %d\n");
return -1;
}
if ((r = ioctl(fd, BLKGETSIZE64, &size)) < 0)
{
printf("ioctl error \n");
return -1;
}
len = (size>>30);
printf("size of sda = %d G\n", len);
return 0;
}