系统调用
访问设备驱动程序的底层函数主要有:
open:打开文件或者设备。
read:从打开的文件或者设备里面读取数据。
write:向文件或者设备写数据。
close:关闭文件或者设备。
open系统调用:
#include <fcntl.h>
#include <sys/types.h>
#include <sys/stat.h>
int open (const char *path, int flags);
int open (const char *path, int flags, mode_t mode);
path表示文件名,flags用来定义准备对打开的文件进行操作的动作。
如果open调用成功,则返回一个新的文件描述符(非负整型);如果失败,就返回-1。
close系统调用:
#include <unistd.h>
int close(int filedes);
成功返回0;出错返回-1;
read系统调用:
#include <unistd.h>
ssize_t read(int filedes, const void *buf, size_t nbytes);< publishblog.blogchina.com http:>
将n个字节从文件描述符对应的文件读出放入到buf中。成功则返回实际的读取字节数。
write系统调用:
#include <unistd.h>
ssize_t write(int filedes, const void *buf, size_t nbytes);
返回值是实际写入的字节数(可能会小于nbytes);如果返回值是0,表示没有写入任何数据;如果返回值是-1,表示在write调用中出错了。
将n个字节从buf中写入到文件描述符对应的文件中。
常用标准I/O库文件函数:fopen,fwrite,fread,fclose,fflush,fseek,fgets,getchar,fputs等系列的函数
他们与系统调用的一个主要的区别在于,这是带缓冲的函数,操作的对象不是int型的文件描述符,而是fopen返回的FILE型的文件指针(*fp).对应的标准输入,输出,出错为stdin,stdout,stderr文件指针。
我把这些函数的用法全都写在这里:
#include <stdio.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <errno.h>
#include <time.h>
#define SIZE 1024
// fopen
int main0()
{
FILE* fp = fopen ("abc", "ab+");
if (NULL == fp)
{
perror ("fopen");
return -1;
}
printf ("打开文件成功\n");
return 0;
}
// fread
int main1()
{
FILE* fp = fopen ("BTree.c", "ab+");
if (NULL == fp)
{
perror ("fopen");
return -1;
}
char buf[SIZE] = {0};
// feof 判断是否读到文件结尾,如果读到文件结尾,它返回一个非0 的值
int ret;
while (ret = fread (buf, sizeof(char), SIZE-1, fp))
{
buf[ret*sizeof(char)] = '\0';
printf ("%s\n", buf);
}
if (0 == ret && !feof(fp))
{
perror ("fread");
return -1;
}
printf ("文件读取结束\n");
return 0;
}
// fwrite
int main2()
{
FILE* fp = fopen ("1.ppt", "ab+");
if (NULL == fp)
{
perror ("fopen");
return -1;
}
FILE* fp1 = fopen ("2.ppt", "ab+");
if (NULL == fp1)
{
perror ("fopen");
return -1;
}
char buf[SIZE] = {0};
// feof判断是否读到文件结尾,如果读到文件结尾,它返回一个非0 的值
int ret;
while (ret = fread (buf, sizeof(char), SIZE, fp))
{
fwrite (buf, sizeof(char), ret, fp1);
}
if (0 == ret && !feof(fp))
{
perror ("fread");
return -1;
}
printf ("文件读取结束\n");
fclose (fp);
fclose (fp1);
return 0;
}
// fgetc
int main3()
{
FILE* fp = fopen ("1.ppt", "ab+");
if (NULL == fp)
{
perror ("fopen");
return -1;
}
FILE* fp1 = fopen ("2.ppt", "ab+");
if (NULL == fp1)
{
perror ("fopen");
return -1;
}
char buf[SIZE] = {0};
// feof 判断是否读到文件结尾,如果读到文件结尾,它返回一个非0 的值
int ret;
while(1)
{
int c = fgetc (fp);
if (EOF == c)
{
break;
}
fputc (c, fp1);
}
fclose (fp);
fclose (fp1);
return 0;
}
// 数据获取
/***************************************************************/
typedef struct student
{
int id;
char name[20];
}STU;
void write_data(STU* a, int len)
{
FILE* fp = fopen ("student", "ab+");
if (NULL == fp)
{
perror ("fopen");
return;
}
// 要写入个数
fwrite (&len, sizeof(int), 1, fp);
int i;
for (i = 0; i < len; i++)
{
// 写入数据长度
len = sizeof(a[i]);
fwrite (&len, sizeof(int), 1, fp);
// 写入数据
fwrite (&a[i], sizeof(STU), 1, fp);
}
fclose (fp);
}
// 读取数据
void read_data()
{
FILE* fp = fopen ("student", "ab+");
if (NULL == fp)
{
perror ("fopen");
return;
}
// 读记录的个数
int count;
fread (&count, sizeof(int), 1, fp);
printf ("记录个数是:%d\n", count);
int i;
STU tmp;
for (i = 0; i < count; i++)
{
int len;
fread (&len, sizeof(int), 1, fp);
// 读取数据
fread (&tmp, len, 1, fp);
printf ("id = %d, name = %s\n", tmp.id, tmp.name);
}
fclose (fp);
}
int main4()
{
int i;
STU a[20];
for (i = 0; i < 20; i++)
{
a[i].id = i;
sprintf (a[i].name, "zhang%d", i);
}
int len = sizeof(a)/sizeof(a[0]);
// 写数据
write_data(a, len);
// 读数据
read_data();
return 0;
}
/***************************************************************/
// open
int main5()
{
close(1);
// 打开一个文件
int fd = open ("test.txt", O_RDWR | O_CREAT, S_IRUSR | S_IWUSR | S_IXUSR);
// int fd = open("test.txt", O_RDONLY);
if (-1 == fd)
{
printf ("打开文件失败\n");
perror ("open");
printf ("%s\n", strerror(errno));
}
printf ("fd = %d\n", fd);
printf ("asdadsafsfkj\n", fd);
printf ("asdadsafsfkj\n", fd);
printf ("asdadsafsfkj\n", fd);
printf ("asdadsafsfkj\n", fd);
printf ("asdadsafsfkj\n", fd);
printf ("asdadsafsfkj\n", fd);
printf ("asdadsafsfkj\n", fd);
// fflush(stdout);
close(fd);
return 0;
}
// read
/***************************************************************/
int main6()
{
int fd = open ("BTree.c", O_RDONLY, 0777);
if (-1 == fd)
{
perror ("open");
return -1;
}
// 缓冲区
char buf[SIZE] = {0};
ssize_t ret = read (fd, buf, SIZE-1);
if (-1 == ret)
{
perror ("read");
}
// 返回值为0 代表读到文件结尾
if (0 == ret)
{
printf ("文件读取结束\n");
}
printf ("len = %d\n", strlen(buf));
printf ("读到%d字节:%s\n", ret, buf);
return 0;
}
// 缓冲区覆盖问题
int main7()
{
int fd = open ("BTree.c", O_RDONLY, 0777);
if (-1 == fd)
{
perror ("open");
return -1;
}
char buf[SIZE] = {0};
while(1)
{
ssize_t ret = read (fd, buf, SIZE-1);
if (-1 == ret)
{
perror ("read");
}
// 返回值为0 代表读到文件结尾
if (0 == ret)
{
printf ("文件读取结束\n");
break;
}
// printf ("len = %d\n", strlen(buf));
// printf ("读到%d 字节: %s\n", ret, buf);
printf ("%s", buf);
}
return 0;
}
// 读取数据之前清空缓冲区
int main8()
{
int fd = open ("BTree.c", O_RDONLY, 0777);
if (-1 == fd)
{
perror ("open");
return -1;
}
char buf[SIZE] = {0};
while(1)
{
memset (buf, 0, SIZE); // 清空缓冲区
ssize_t ret = read (fd, buf, SIZE-1);
if (-1 == ret)
{
perror ("read");
}
if (0 == ret)
{
printf ("文件读取结束\n");
break;
}
printf ("%s", buf);
}
return 0;
}
// 每次读完数据之后讲下一个字节置为'\0';
int main9()
{
int fd = open ("BTree.c", O_RDONLY, 0777);
if (-1 == fd)
{
perror ("open");
return -1;
}
char buf[SIZE] = {0};
while(1)
{
ssize_t ret = read (fd, buf, SIZE-1);
if (-1 == ret)
{
perror ("read");
}
if (0 == ret)
{
printf ("文件读取结束\n");
break;
}
buf[ret] = '\0';
printf ("%s", buf);
}
return 0;
}
// 读一个完整的大数据
int main10()
{
int fd = open ("BTree.c", O_RDONLY, 0777);
if (-1 == fd)
{
perror ("open");
return -1;
}
char buf[SIZE] = {0};
char* p = buf;
int count = SIZE - 1; // 每次要读的数据个数
ssize_t ret =0;
while (ret = read (fd, p, count))
{
// 出错
if (-1 == ret)
{
if (errno == EAGAIN || errno == EINTR)
{
continue;
}
break;
}
printf ("sfjsfsjfs\n");
// 读完
if (ret == count)
{
break;
}
count -= ret; // 下一次要读的数据
p += ret;
}
printf ("len = %d\n", strlen(buf));
// printf ("%s\n", buf);
return 0;
}
/***************************************************************/
// write
int main11()
{
int fd = open ("abc", O_WRONLY|O_CREAT, 0777);
if (-1 == fd)
{
perror ("open");
return -1;
}
char buf[SIZE] = {0};
while(1)
{
fgets (buf, SIZE, stdin);
if (0 == strncmp ("end", buf, 3))
{
break;
}
ssize_t ret = write (fd, buf, strlen(buf));
if (-1 == ret)
{
perror ("write");
}
printf ("要写的字节数:%d,实际写的字节数:%d\n", SIZE, ret);
}
close(fd);
return 0;
}
// 文件复制
int main12()
{
// 打开要读的文件
int fd1 = open ("1.ppt", O_RDONLY);
if (-1 == fd1)
{
perror ("open fd1");
return -1;
}
int fd2 = open ("2.ppt", O_WRONLY|O_CREAT, 0777);
if (-1 == fd2)
{
perror ("open fd2");
return -1;
}
int ret = 0;
char buf[SIZE] = {0};
while (ret = read (fd1, buf, SIZE))
{
if (-1 == ret)
{
perror("read");
break;
}
write (fd2, buf, ret);
}
printf ("文件复制完成\n");
close (fd1);
close (fd2);
return 0;
}
// lseek
int main13()
{
// 打开要读的文件
int fd = open ("abc2", O_RDWR|O_CREAT, 0777);
if (-1 == fd)
{
perror ("open fd1");
return -1;
}
// 设置这个文件的偏移指针
lseek (fd, 20, SEEK_SET);
char* buf = "hello";
write (fd, buf, strlen(buf));
close (fd);
return 0;
}
// 创建一个大文件
int main14()
{
// 打开要读的文件
int fd = open ("big", O_RDWR|O_CREAT, 0777);
if (-1 == fd)
{
perror ("open fd1");
return -1;
}
// 设置这个文件的偏移指针到1G处
lseek (fd, 1024*1024*1024, SEEK_SET);
char* buf = "hello";
write (fd, "a", 1);
close (fd);
return 0;
}
// printf缓冲
int main15()
{
while(1)
{
printf ("a");
usleep (2000);
}
return 0;
}
// 文件偏移指针测试1
int main16()
{
// 打开要读的文件
int fd = open ("big", O_RDWR|O_CREAT, 0777);
if (-1 == fd)
{
perror("open fd1");
return -1;
}
printf ("%d\n", fd);
// 设置这个文件的偏移指针到1G处
lseek (fd, 20, SEEK_SET);
printf ("等待2些数据\n");
getchar();
char* buf = "hello";
write (fd, "a", 1);
getchar();
close (fd);
return 0;
}
// 文件偏移指针测试2
int main17()
{
// 打开要读的文件
int fd1 = open ("abc", O_RDWR|O_CREAT, 0777);
if (-1 == fd1)
{
perror ("open fd1");
return -1;
}
printf ("abc fd = %d\n", fd1);
int fd = open ("big", O_RDWR|O_CREAT, 0777);
if (-1 == fd)
{
perror ("open fd");
return -1;
}
printf ("bif fd = %d\n", fd);
// 设置这个文件的偏移指针到 1G处
lseek (fd, 10, SEEK_SET);
char *buf = "12345";
write (fd, buf, strlen(buf));
getchar();
close (fd);
return 0;
}
/***************************************************************/
// 随机分组
// 函数功能:互换
void swap (int* a, int i, int j)
{
int tmp = a[i];
a[i] = a[j];
a[j] = tmp;
}
// 函数功能:打印
void printA (int* a, int len)
{
int i;
for (i = 0; i < len; i++)
{
if (0 == i % 4)
{
printf ("\n");
}
printf ("%4d", a[len-i-1]);
}
putchar ('\n');
}
int main18()
{
srand ((unsigned int)time(NULL));
int a[40];
int i;
int len = 40;
for (i = 0; i < 40; i++)
{
a[i] = i;
}
for (i = len-1; i > 0; i--)
{
int index = rand() % (i+1); // 获取随机数
swap (a, index, i); // 将获得的数和最后一个互换
}
printA (a, len);
return 0;
}
/***************************************************************/