Linux文件IO(四)-返回错误处理与errno详解

news2024/9/21 18:36:05

1.前言

在上一文章中,给大家编写了很多的示例代码,大家会发现这些示例代码会有一个共同的特点,那就是当判断函数执行失败后,会调用 return 退出程序,但是对于我们来说,我们并不知道为什么会出错,什么原因导致此函数执行失败,因为执行出错之后它们的返回值都是-1。

难道我们真的就不知道错误原因了吗?其实不然,在 Linux 系统下对常见的错误做了一个编号,每一个编号都代表着每一种不同的错误类型,当函数执行发生错误的时候,操作系统会将这个错误所对应的编号赋值给 errno 变量,每一个进程(程序)都维护了自己的 errno 变量,它是程序中的全局变量,该变量用于存储就近发生的函数执行错误编号,也就意味着下一次的错误码会覆盖上一次的错误码。所以由此可知道,程序中调用函数发生错误的时候,操作系统内部会通过设置程序的 errno 变量来告知调用者究竟发生了什么错误!

errno 本质上是一个 int 类型的变量,用于存储错误编号,但是需要注意的是,并不是执行所有的系统调用或 C 库函数出错时,操作系统都会设置 errno,那我们如何确定一个函数出错时系统是否会设置 errno 呢?

其实这个通过 man 手册便可以查到,譬如以 open 函数为例,执行"man 2 open"打开 open 函数的帮助信息,找到函数返回值描述段,如下所示:

从图中红框部分描述文字可知,当函数返回错误时会设置 errno,当然这里是以 open 函数为例,其它的系统调用也可以这样查找,大家可以自己试试!

在我们的程序当中如何去获取系统所维护的这个errno变量呢?只需要在我们程序当中包含<errno.h>头文件即可,你可以直接认为此变量就是在<errno.h>头文件中的申明的,好,我们来测试下:

#include <stdio.h>
#include <stdio.h>
#include <errno.h>

int main(void)
{
	printf("%d\\n", errno);
	return 0;
}

以上的这段代码是不会报错的,大家可以自己试试!

2.strerror 函数

前面给大家说到了 errno 变量,但是 errno 仅仅只是一个错误编号,对于开发者来说,即使拿到了 errno也不知道错误为何?还需要对比源码中对此编号的错误定义,可以说非常不友好,这里介绍一个 C 库函数strerror(),该函数可以将对应的 errno 转换成适合我们查看的字符串信息,其函数原型如下所示(可通过"man 3 strerror"命令查看,注意此函数是 C 库函数,并不是系统调用):

#include <string.h>
char *strerror(int errnum);

首先调用此函数需要包含头文件<string.h>。

函数参数和返回值如下:

errnum:错误编号 errno。

返回值:对应错误编号的字符串描述信息。

测试

接下来我们测试下,测试代码如下:

//示例代码 3.2.1 strerror 测试代码

#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <stdio.h>
#include <errno.h>
#include <string.h>

int main(void)
{
		int fd;

		/* 打开文件 */
		fd = open("./test_file", O_RDONLY);
		if (-1 == fd) {
				printf("Error: %s\\n", strerror(errno));
				return -1;
		}
		close(fd);
		return 0;
}

编译源代码,在 Ubuntu 系统下运行测试下,在当前目录下并不存在 test_file 文件,测试打印结果如下:

从打印信息可以知道,strerror 返回的字符串是"No such file or directory",所以从打印信息可知,我们就可以很直观的知道 open 函数执行的错误原因是文件不存在!

3.perror 函数

除了 strerror 函数之外,我们还可以使用 perror 函数来查看错误信息,一般用的最多的还是这个函数,用此函数不需要传入 errno,函数内部会自己去获取 errno 变量的值,调用此函数会直接将错误提示字符串打印出来,而不是返回字符串,除此之外还可以在输出的错误提示字符串之前加入自己的打印信息,函数原型如下所示(可通过"man 3 perror"命令查看):

#include <stdio.h>

void perror(const char *s);

需要包含<stdio.h>头文件。

函数参数和返回值含义如下:

s:在错误提示字符串信息之前,可加入自己的打印信息,也可不加,不加则传入空字符串即可。

返回值:void 无返回值。

测试

接下来我们进行测试,测试代码如下所示:

//示例代码 3.2.2 perror 测试代码
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <stdio.h>
int main(void)
{
		int fd;
		
		/* 打开文件 */
		fd = open("./test_file", O_RDONLY);
		if (-1 == fd) {
			perror("open error");
			return -1;
		
		
		close(fd);
		return 0;
}

编译源代码,在 Ubuntu 系统下运行测试下,在当前目录下并不存在 test_file 文件,测试打印结果如下:

从打印信息可以知道,perror 函数打印出来的错误提示字符串是"No such file or directory",跟 strerror 函数返回的字符串信息一样,"open error"便是我们附加的打印信息,而且从打印信息可知,perror 函数会在附加信息后面自动加入冒号和空格以区分。

以上给大家介绍了 strerror、perror 两个 C 库函数,都是用于查看函数执行错误时对应的提示信息,大家用哪个函数都可以,这里推荐大家使用 perror,在实际的编程中这个函数用的还是比较多的。

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

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

相关文章

C++进阶|多态知识点详解及经典面试题总结

&#x1f36c; mooridy-CSDN博客 &#x1f9c1;C专栏&#xff08;更新中&#xff01;&#xff09; 目录 1. 多态的概念 2. 多态的定义及实现 2.1 多态的构成条件 2.2 虚函数的重写/覆盖 2.3 虚函数重写的⼀些其他问题 2.4 override 和 final关键字 2.5 重载/重写/隐藏的…

(笔记自用)位运算总结+LeetCode例题:颠倒二进制位+位1的个数

一.位运算总结: 在解题之前理解一下为什么需要位运算&#xff1f;它的本质是什么&#xff1f; 力扣上不少位运算相关的题&#xff0c;并且很多题也会用到位运算的技巧。这又是为什么&#xff1f; 位运算的由来 在计算机里面&#xff0c;任何数据最终都是用数字来表示的&…

mysqldump使用cmd窗口和powersell窗口导出sql中文乱码的问题

项目场景 我在使用Mariadb数据库更新数据的时候&#xff0c;由于数据库的表格中含有中文&#xff0c;在使用mysqldump导出sql语句的时候&#xff0c;中文显示乱码&#xff0c;如下图所示&#xff1a; 环境描述 系统&#xff1a;windows10数据库&#xff1a; Mariadb -10.6.16…

Vue2中路由的介绍和使用

一.路由的基本概念 一说路由&#xff0c;大家首先想到的可能是路由器&#xff0c;路由器的原理就是给连接的设备一个IP地址&#xff0c;通过IP地址来映射到设备&#xff0c;实现连接&#xff0c;本质上是一种映射关系。 在vue2中就是路径与组件间的映射。 路由是使用vue2制作…

Python爬虫使用实例-umei

优美图库 www.umei.cc BV1Ag41137re 1/获取资源 查看网站资源结构 多页&#xff0c;每个item只有一张图 多页&#xff0c;每个item都是一个图集 最大页码 内外层图集均有若干page。 通过尾页按钮确定pageNum&#xff1a; 2/发送请求 response requests.get(urlurl, header…

快速将Mongo Compass的shell语句转成java代码

步骤一、从MongoCompass中获取java代码 将java代码复制出来&#xff0c;从MongoCompass中复制的java代码基本格式如下&#xff1a;&#xff08;是Bson原生格式&#xff09; List<Document> list Arrays.asList(new Document("$match",new Document("name…

探索视频美颜SDK与直播美颜工具的开发实践方案

直播平台的不断发展&#xff0c;让开发出性能优异、效果自然的美颜技术&#xff0c;成为了技术团队必须面对的重要挑战。本篇文章&#xff0c;小编将深入讲解视频美颜SDK与直播美颜工具的开发实践方案。 一、视频美颜SDK的核心功能 视频美颜SDK是视频处理中的核心组件&#xf…

Cocos Creator3.x设置动态加载背景图并且循环移动

效果图 项目结构 项目层级结构&#xff1a; 预制&#xff1a; 代码 import { _decorator, CCFloat, Component, Node, Sprite, instantiate, Prefab, assert } from cc; const { ccclass, property } _decorator;/*** 背景脚本*/ ccclass(Background) export class Backg…

2024年华为杯研赛(D题)数学建模竞赛解题思路|完整代码论文集合

我是Tina表姐&#xff0c;毕业于中国人民大学&#xff0c;对数学建模的热爱让我在这一领域深耕多年。我的建模思路已经帮助了百余位学习者和参赛者在数学建模的道路上取得了显著的进步和成就。现在&#xff0c;我将这份宝贵的经验和知识凝练成一份全面的解题思路与代码论文集合…

反激电路中TL431光耦反馈参数的计算,环路设计思路

反馈的过程 当副边的输出电压升高时&#xff0c;TL431参考端电压&#xff08;R端&#xff09;电压也会升高&#xff0c;使得TL431的导通量增加&#xff0c;同时光耦内部的发光二极管流过的电流也会增大&#xff0c;进而使得光耦三极管导通量增加&#xff0c;相连的电源IC电压反…

《粮油与饲料科技》是什么级别的期刊?是正规期刊吗?能评职称吗?

问题解答 问&#xff1a;《粮油与饲料科技》是不是核心期刊&#xff1f; 答&#xff1a;不是&#xff0c;是知网收录的第一批认定 学术期刊。 问&#xff1a;《粮油与饲料科技》级别&#xff1f; 答&#xff1a;省级。主管单位&#xff1a;中文天地出版传媒集团股份有限公司…

缺陷及缺陷管理(复习)

​ 大家好&#xff0c;我是程序员小羊&#xff01; 前言&#xff1a; 今日目标 能够说出缺陷的判定标准 能够说出描述缺陷的6大核心内容 能够描述缺陷状态、严重程度、优先级的作用 能够按照提供的缺陷模版完成一个缺陷的提交 能够说出缺陷的跟踪流程 能够在禅道中提交测…

黑神话:悟空配置推荐,升级显卡还是ToDesk云电脑

虽然距离《黑神话&#xff1a;悟空》上线已有一个月的时间&#xff0c;但该游戏在国内外市场仍然火热&#xff0c;想要玩好、玩顺它着实是需要花费一些心力的。除了操作上的经验、技巧&#xff0c;用高配置电脑设备来实现无疑是最为关键的要素之一。那么如若现有机型性能不足&a…

2024年华为杯数学建模研赛(C题) 建模解析| 磁芯损耗建模 | 小鹿学长带队指引全代码文章与思路

我是鹿鹿学长&#xff0c;就读于上海交通大学&#xff0c;截至目前已经帮2000人完成了建模与思路的构建的处理了&#xff5e; 本篇文章是鹿鹿学长经过深度思考&#xff0c;独辟蹊径&#xff0c;实现综合建模。独创复杂系统视角&#xff0c;帮助你解决研赛的难关呀。 完整内容可…

(学习总结18)C++多态

C多态 一、多态的概念二、多态的定义及实现多态的构成条件1. 实现多态的两个必须条件&#xff1a;2. 虚函数3. 虚函数的重写/覆盖4. 多态场景的一个选择题5. 虚函数重写的一些其他问题协变析构函数的重写 6. override 和 final 关键字7. 重载/重写/隐藏的对比 三、纯虚函数和抽…

【堆栈操作基本规则】假设SS的初值为2000H,SP初值为0200H,在执行了5次入栈操作和2次出栈操作后SP的内容为多少?写出计算过程。

欢迎来到我的技术博客&#xff01; &#x1f389; 这里不仅有满满的编程干货和学习资源&#xff0c;我的某站账号也为你准备了更多实用的技术视频和知识分享。 &#x1f449; 点击关注我的小破站账号&#xff0c;获取更多编程技巧和学习资源&#xff01; 小破站主页 我们来逐…

新手入门:小程序架构快速上手

目录 新建项目和配置 项目基本结构 新建小程序页面 修改项目首页 全局配置 窗口 tabBar 页面配置 小程序基本语法 wxml 数据绑定 条件渲染 列表渲染 wxss wxss 对比 css rpx import 全局样式和局部样式 js wxs 数据请求 get和post请求 小程序和跨域 小程…

C++进阶 set和map讲解

set 和 map set 和 multiset set set 类的介绍 set 是基于红黑树实现的有序容器。它的插入、删除、查找操作的时间复杂度均为 O(log n)。遍历时&#xff0c;set 的迭代器按照中序遍历&#xff0c;因此它总是以升序排列元素。 set 的声明如下&#xff0c;T 表示 set 的关键字类…

The First项目报告:变革全链身份,Layer3的未来价值解读

2024年7月5日&#xff0c;代币分发协议 Layer3 基金会公布代币 L3 经济模型&#xff0c;以任务平台为市场切入点的 Layer3 聚合了市场上花样繁多的项目&#xff0c;帮助用户实现通过一个平台交互全链项目的操作。乘着牛市的浪潮&#xff0c;各链生态重新火热&#xff0c;Layer3…

微服务_入门1

文章目录 一、 认识微服务二、 微服务演变2.1、 单体架构2.2、 分布式架构2.3、 微服务2.4、 微服务方案对比 三、 注册中心3.1、 Eureka3.2、 Nacos3.2.1、服务分级存储模型3.2.2、权重配置3.2.3、环境隔离 一、 认识微服务 二、 微服务演变 随着互联网行业的发展&#xff0c;…