Linux——文件标识符

目录

一、文件基础

二、常见的C语言文件接口

三、系统文件接口 

四、理解语言与系统文件操作的关系

五、如何理解一切皆文件

六、文件标识符再理解


一、文件基础

一个空文件,也会占用磁盘空间,这是因为文件不仅仅有存放在里面的内容,还有属性,比如文件名。创建时间,文件权限等。

文件 = 内容 + 属性。我们对文件的操作,无非是对内容或者对属性的操作。我们知道,=文件是存储在磁盘中的,如果我们打开文件,需要将文件加载到内存中,这样CPU才可以对文件进行处理。打开文件的本质,就是将文件加载到内存

操作系统在运行过程中,可能会打开很多文件,因此操作系统要对打开的文件进行管理。管理的本质操作就是先描述在组织。因此在内核中一定存在已打开文件的结构体,他们依次用链表存储起来,操作系统对文件的管理转为对链表的增删查改。

今天我们着重学系的就是进程与被打开文件的关系。

二、常见的C语言文件接口

  • fopen() —— 打开文件;
    • FILE * fopen ( const char * filename, const char * mode );
  • fclose() —— 关闭文件;
    • int fclose ( FILE * stream );

C语言写入函数

C语言读取函数 

使用fputs写入函数测试下。 

其中“w”权限是写入,没有文件就先创建文件,在写入前会先清空文件内容。在linux中还有一个方法可以进行w写入,就是输出重定向。> 

还有“a”,追加方式,他不会在写入前清空文件内容,而是在文件内容末尾继续追加新内容。linux中的追加重定向为  >> 

重定向这里先了解一下,后续会继续讲解。

三、系统文件接口 

我们知道,打开文件是要将文件加载到内存中,我们之前的操作是使用进程打开文件,进程是没有这么大的权利的,他肯定是调用了操作系统给我们的系统接口。虽然刚刚我们没有调用系统接口,用的是C语言给我们的接口,但其实,C语言打开文件的接口,底层是封装了系统调用接口的!!

系统接口open,第一个参数为路径+文件名,第二个参数是以什么样的方式打开,第三个参数对已创建的文件可以不填,对未创建的文件表示对文件设置什么权限。创建成功返回值为文件描述符file descriptor(简称fd),创建失败返回值为-1。

主要方式如下

  • O_RDONLY:只读模式
  • O_WRONLY:只写模式
  • O_RDWR:可读可写
  • O_APPEND 表示追加,如果原来文件里面有内容,则这次写入会写在文件的最末尾。
  • O_CREAT 表示如果指定文件不存在,则创建这个文件
  • O_EXCL 表示如果要创建的文件已存在,则出错,同时返回 -1,并且修改 errno 的值。
  • O_TRUNC 表示截断,如果文件存在,并且以只写、读写方式打开,则将其长度截断为0。

这些方式是通过位图来实现的,比如O_RDONLY为00000001,O_WRONLY为00000010,O_RDWR为00000100,如此类推,需要使用指定的方式,我们直接进行或运算就好。

运行结果如下,我们创建了log.txt文件,但权限为664,而不是我们代码中的0666,这是因为我们系统权限掩码为0002的原因,0666 &(~0002)= 0664。

写数据的系统接口为write,第一个参数代表往那个文件中写入(是open打开文件获取的文件描述符fd),第二个参数需要写入的字符串,第三个参数为写入的字节数。返回值为实际写入了多少字节的数据。

写入代码

成功写入

我们使用的为O_WRONLY | O_CREAT,只写的方式,没有文件就创建。因此如果再进行写入,并不会将文件内容清空,而是进行覆盖。

如下将str进行修改,再执行命令,查看log.txt的内容,发现good覆盖上了hell 。

 如果我们打开方式  | O_TRUNC,就会在打开前先清空文件。

 如果我们打开方式  | O_APPEND,会从文件结尾处开始写入,这是追加(不清空文件)。

四、理解语言与系统文件操作的关系

经过前面的学习,我们知道C语言文件的处理底层是封装了系统调用接口的,但是C语言fopen返回的是FILE* 指针,而系统open返回的是int类型整数fd,后续也是通过fd来对指定文件做处理的。

那么fd存放的内容是什么呢?我们通过如下代码打印出来看。

发现fd从 3 开始,是连续的小整数。 为什么不从0开始呢,0 1 2这三个去哪里了。如下

进程在运行的时候,默认是把这三小只打开的。但是这三小只不是硬件嘛,怎么跟文件扯上关系了,因为Linux下,一切皆文件。(后面会讲)

我们是通过进程对文件进行处理,那么进程的task_struct里面存在一个files_struct指针指向文件描述符表,里面有很多数据,其中有一个struct file* fd_array[]的数组指针,他指向被打开的文件结构体,这个索引就是文件描述符。如下图所示

但我们查看C标准库,发现这三个变量类型为FILE* 。  

File是C语言提供的结构体类型,fopen的底层是open,那么File结构体里面必定封装了文件描述符。我们通过如下代码也能印证一番

操作系统默认将stdin  stdout  stderr 打开,就是为了让程序员方便进行输入输出代码。就可以直接scanf 和 printf进行输入和显示。我们C语言第一个头文件基本都是stdio.h,stdio就是标准输入输出,C++第一个头文件 iostream,输入输出流。

五、如何理解一切皆文件

操作系统要管理硬件,也是先描述在组织,会将各种硬件使用结构体组织起来,不同的硬件,读写的方法肯定是不一样的,但是struct file里的接口read和write函数指针会指向对应硬件的读写。这样从统一的视角去看待不同硬件。我们也就理解了为何文件先会打开0  1  2这三小只。

六、文件标识符再理解

我们知道了0  1  2号文件标识符分别为stdin,stdout,stderr,也知道了linux一切皆文件,那么我们尝试下使用  read与write + 文件标识符  进行读写来代替(scanf和printf)。

read函数第一个参数fd为文件标识符,第二个参数为读取的数据保存到buf缓冲区中,第三个参数为读取的字节数,返回值为带符号整数(实际读取字节数,失败返回-1)

write函数第一个参数fd也为文件标识符,第二个参数为从buf缓冲区中写入数据到文件,第三个参数为写入的字节数,返回值为带符号整数(实际写入字节数,失败返回-1)

代码如下,从0(stdin)中读取输入到buffer,从buffer写入数据到1(stdout)中。 

成功输出我王慕霸没有开挂!!!! 

我们知道,打开文件fd是从3开始,按顺序依次累加。如果我们先关闭某一个或几个fd文件,那么新打开的文件还是从3开始吗?

使用下面代码测试下

发现是从索引0开始,往后依次查找空位进行放入,比如fd1找到0不存在,就放入到0位置,fd2发现0  1   2都存在,3不存在,就放入3位置。

 如果你关掉了1,虽然fd也会放入1位置,但是不会打印,因为1号为标准输出,关闭还打印个啥

 

 

 

 

 

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/728633.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Chapter20-Ideal gases-CIE课本要点摘录、总结(编辑中)

20.1 Particles of a gas Brownian motion Fast modules 速率的数值大概了解下: average speed of the molecules:400m/s speed of sound:approximately 330m/s at STP(standard temperature and pressure) Standard Temperature and Pres…

ROS 2基础概念#5:执行器(Executor)| ROS 2学习笔记

在ROS 2中,Executor是一个核心概念,负责管理节点(Node)中的回调函数,如订阅消息的回调、服务请求的回调、定时器回调等。Executor决定了何时以及如何执行这些回调,从而在ROS 2系统中实现异步编程。 ROS 2 …

七彩虹八渐变 外贸建站公司wordpress模板

进出口水果wordpress外贸模板 漂亮水果wordpress外贸模板,做水果进出品生意的外贸公司自建站官网模板。 https://www.jianzhanpress.com/?p3516 玩具wordpress外贸模板 简洁玩具wordpress外贸模板,适合做跨境电商外贸公司使用的wordpres外贸s网站主题…

FPGA 按键控制串口发送

按键消抖 消抖时间一般为10ms,我使用的板子是ACX720,晶振为50MHZ,20ns为一周期。 状态机 模块设计 设计文件 timescale 1ns / 1ps // // Company: // Engineer: // // Create Date: 2023/01/11 12:18:36 // Design Name: // Module Name…

(学习总结)如何使用ChatGPT API训练自定义知识库

第一步: 安装OpenAI、GPT Index、PyPDF2和Gradio库 pip install openai pip install gpt_index pip install PyPDF2 pip install gradio 第二步:用VScode代码编辑器写app.py代码 记得替换api密钥 from llama_index import SimpleDirectoryReader, …

纯css实现太极八卦图

感觉最近好像闯鬼了&#xff0c;赶紧写个八卦图避避邪&#xff0c;开玩笑了&#xff0c;不废话&#xff0c;上菜&#xff0c;看效果上代码。 效果 代码&#xff0c;你们都是大佬&#xff0c;这里就不解释代码了 &#xff08;hover会转动喔&#xff09;。 <!DOCTYPE html&g…

LabVIEW智能Modbus监控系统

LabVIEW智能Modbus监控系统 在自动化和信息化迅速发展下&#xff0c;传统的监控系统已无法满足现代工业对于数据通讯和处理的高效率和高可靠性要求。为了解决这一问题&#xff0c;设计了一套基于LabVIEW的智能Modbus监控系统。该系统利用LabVIEW的图形化编程环境和Modbus协议的…

数字孪生10个技术栈:数据处理的六步骤,以获得可靠数据。

一、什么是数据处理 在数字孪生中&#xff0c;数据处理是指对采集到的实时或历史数据进行整理、清洗、分析和转化的过程。数据处理是数字孪生的基础&#xff0c;它将原始数据转化为有意义的信息&#xff0c;用于模型构建、仿真和决策支持。 数据处理是为了提高数据质量、整合数…

深入理解Servlet

目录&#xff1a; ServletWeb开发历史Servlet简介Servlet技术特点Servlet在应用程序中的位置Tomcat运行过程Servlet继承结构Servlet生命周期Servlet处理请求的原理Servlet的作用HttpServletRequest对象HttpServletResponse对象ServletContext对象ServletConfig对象Cookie对象与…

SpringBoot快速入门(介绍,创建的3种方式,Web分析)

目录 一、SpringBoot介绍 二、SpringBootWeb快速入门 创建 定义请求处理类 运行测试 三、Web分析 一、SpringBoot介绍 我们可以打开Spring的官网(Spring | Home)&#xff0c;去看一下Spring的简介&#xff1a;Spring makes Java simple。 Spring发展到今天已经形成了一种…

Android 多桌面图标启动, 爬坑点击打开不同页面

备注 &#xff1a; MainActivity 正常带界面的UI MainActivityBt 和 MainActivityUsb 是透明的&#xff0c;即 android:theme"style/TranslucentTheme" ###场景1:只有MainActivity 设置成&#xff1a;android:launchMode"singleTask" 点击顺序&#xff1…

ThreadLocal :在 Java中隱匿的魔法之力

优质博文&#xff1a;IT-BLOG-CN ThreadLocal 并不是一个Thread&#xff0c;而是 ThreadLocalVariable(线程局部变量)。也许把它命名为 ThreadLocalVar更加合适。线程局部变量就是为每一个使用该变量的线程都提供一个变量值的副本&#xff0c;是 Java中一种较为特殊的线程绑定机…

MySQL--优化(索引--聚簇和非聚簇索引)

MySQL–优化&#xff08;索引–聚簇和非聚簇索引&#xff09; 定位慢查询SQL执行计划索引 存储引擎索引底层数据结构聚簇和非聚簇索引索引创建原则索引失效场景 SQL优化经验 一、聚簇索引 聚簇索引&#xff1a;将数据存储与索引放到了一块&#xff0c;索引结构的叶子节点保存…

01-环境搭建、SpringCloud微服务-黑马头条

环境搭建、SpringCloud微服务(注册发现、服务调用、网关) 1)课程对比 2)项目概述 2.1)能让你收获什么 2.2)项目课程大纲 2.3)项目概述 随着智能手机的普及&#xff0c;人们更加习惯于通过手机来看新闻。由于生活节奏的加快&#xff0c;很多人只能利用碎片时间来获取信息&…

数据开发 - 面经(已OC) - 北京中海通

投递流程&#xff1a; 2023.12.28 Boss 打招呼 2024.1.3 约面 2024.1.4 上午面试 &#xff08;手机端腾讯会议&#xff09; 2024.1.5 上午 通知面试通过 腾讯会议手机端无法和录影机同时运行&#xff0c;录音无效&#xff0c;之后注意使用电脑面试 面试流程&#xff1a;首…

搜维尔科技:3D Systems Geomagic Design X 逆向工程软件

产品概述 3D Systems Geomagic Design X 是全面的逆向工程软件 GeomagicoDesign XTM是全面的逆向工程软件&#xff0c;它结合了基于特征的CAD数模与三维扫描数据处理&#xff0c;使您能创建出可编辑、基于特征的CAD数模&#xff0c;并与您现有的CAD软件兼容。 拓展您的设计能…

两两交换链表中的节点+力扣

题目 题目链接 . - 力扣&#xff08;LeetCode&#xff09; 题目描述 代码实现 class Solution { public:ListNode* swapPairs(ListNode* head) {if(head nullptr || head->next nullptr) return head;ListNode *tmpHead swapPairs(head->next->next);ListNode …

Spring Boot异常处理和单元测试

1.SpringBoot异常处理 1.1.自定义错误页面 SpringBoot默认的处理异常的机制&#xff1a;SpringBoot 默认的已经提供了一套处理异常的机制。一旦程序中出现了异常 SpringBoot 会向/error 的 url 发送请求。在 springBoot 中提供了一个叫 BasicErrorController 来处理/error 请…

Qt/C++音视频开发68-检查是否含有B帧/转码推流/拉流显示/监控拉流推流/海康大华宇视监控

一、前言 为什么需要判断视频文件是否含有B帧&#xff0c;这个在推流的时候很容易遇到这个问题&#xff0c;一般来说&#xff0c;没有B帧的视频文件&#xff0c;解码后的数据帧pts和dts都是顺序递增的&#xff0c;而有B帧的则未必&#xff0c;可能有些需要先解码后面显示&…

让娃学习效率更高的“可视化”时间管理器

如果要问&#xff0c;老母亲在娃开学后&#xff0c;蕞着急孩子哪一种坏习惯&#xff0c;那时间管理肯定榜上有名&#xff01; 做作业的时候&#xff0c;才写了5分钟&#xff0c;已经没有耐心了&#xff0c;东摸摸西看看&#xff0c;一会说肚子疼想上厕所&#xff0c;一会又拿出…