当前位置: 首页 > news >正文

深入了解fcntl函数:Linux系统编程中的文件控制

文章目录

  • 概述
  • 介绍
    • 函数原型与参数
  • 拓展:fcntl改文件属性
  • 总结

概述

摘要: fcntl函数是Linux系统编程中一个重要的函数,用于对文件描述符进行各种控制操作。本文将详细介绍fcntl函数的原型、各个参数的用法,以及阻塞和非阻塞模式切换的方法,并提供相应的代码示例,帮助读者更好地理解和应用fcntl函数。

介绍

fcntl函数是Linux系统编程中的一个文件控制函数,用于对文件描述符进行各种操作,如文件锁定、文件描述符状态设置等。它的原型如下:

函数原型与参数

#include <fcntl.h>
int fcntl(int fd, int cmd, ...);

fcntl函数接受三个参数:文件描述符fd、控制命令cmd和可选的第三个参数arg。

参数用法

文件描述符fd:需要进行控制的文件描述符。

控制命令cmd:决定了具体的操作。常见的命令有:

F_GETFL:获取文件描述符的状态标志。
F_SETFL:设置文件描述符的状态标志。
F_GETFD:获取文件描述符的文件执行标志。
F_SETFD:设置文件描述符的文件执行标志。
F_SETLK:设置文件锁。
F_GETLK:获取文件锁状态。
可选的第三个参数arg:用于某些控制命令的附加参数,具体取决于cmd的值。

拓展:fcntl改文件属性

fcntl用来改变一个【已经打开】的文件的 访问控制属性
重点掌握两个参数的使用, F_GETFL,F_SETFL

int fcntl(int fd, int cmd, ...)

fd 文件描述符
cmd 命令,决定了后续参数个数

int flgs = fcntl(fd,  F_GETFL);flgs |= O_NONBLOCKfcntl(fd,  F_SETFL, flgs);获取文件状态: F_GETFL设置文件状态: F_SETFL

终端文件默认是阻塞读的,这里用fcntl将其更改为非阻塞读

1.#include <unistd.h>  
2.#include <fcntl.h>  
3.#include <errno.h>  
4.#include <stdio.h>  
5.#include <stdlib.h>  
6.#include <string.h>  
7.  
8.#define MSG_TRY "try again\n"  
9.  
10.int main(void)  
11.{  
12.    char buf[10];  
13.    int flags, n;  
14.  
15.    flags = fcntl(STDIN_FILENO, F_GETFL); //获取stdin属性信息  
16.    if(flags == -1){  
17.        perror("fcntl error");  
18.        exit(1);  
19.    }  
20.    flags |= O_NONBLOCK;  
21.    int ret = fcntl(STDIN_FILENO, F_SETFL, flags);  
22.    if(ret == -1){  
23.        perror("fcntl error");  
24.        exit(1);  
25.    }  
26.  
27.tryagain:  
28.    n = read(STDIN_FILENO, buf, 10);  
29.    if(n < 0){  
30.        if(errno != EAGAIN){          
31.            perror("read /dev/tty");  
32.            exit(1);  
33.        }  
34.        sleep(3);  
35.        write(STDOUT_FILENO, MSG_TRY, strlen(MSG_TRY));  
36.        goto tryagain;  
37.    }  
38.    write(STDOUT_FILENO, buf, n);  
39.  
40.    return 0;  
41.}  

编译运行,结果如下:
在这里插入图片描述

可以看到,是非阻塞读取。

总结

通过详细介绍fcntl函数的原型、参数用法以及阻塞和非阻塞模式切换的方法,我们希望读者能够更好地理解和应用fcntl函数

http://www.lryc.cn/news/145143.html

相关文章:

  • 汇川技术内推码
  • nacos服务器启动报错集合
  • C语言_分支和循环语句(2)
  • JMeter 接口自动化测试:从入门到精通的完全指南
  • 【Java】集合List的toArray()方法及其重载
  • Python学习笔记:Requests库安装、通过url下载文件
  • git pull --rebase 用法
  • react antd框架中的徽标获取数据对应状态的数量
  • 【多线程】Thread类的用法
  • 第八章 贪心算法 part03 1005.K次取反后最大化的数组和 134. 加油站 135. 分发糖果 (day34补)
  • Android Activity启动过程一:从Intent到Activity创建
  • 第9章:聚类
  • 程序员为什么要写bug,不能一次性写好吗?
  • Nginx反向代理其他服务
  • MQ 简介-RabbitMQ
  • 强化学习(2)
  • Visual Studio 2022的MFC框架——theApp全局对象
  • SpringBoot Cache
  • vue 简单实验 自定义组件 component
  • C++ 改善程序的具体做法 学习笔记
  • Unity 之 GameObject.Find()在场景中查找指定名称的游戏对象
  • flink on yarn with kerberos 边缘提交
  • NodeJS的简介以及下载和安装
  • 量化面试-概率题
  • 【spark】java类在spark中的传递,scala object在spark中的传递
  • php 文字生成图片保存到本地
  • 面试手撕—二叉搜索树及其后序遍历
  • Java数据结构面试题以及答案
  • Java——它要求用户输入一个整数(实际上是一个字符串),然后计算该整数的平方值,并将结果输出。
  • 【科研论文配图绘制】task6直方图绘制