更安全的C gets()和str* 以及fgets和strcspn的用法

#include <stdio.h>int main()
{char *str;gets(str);puts(str);return(0);
}

可以说全是错误
首先char *str没有指向一个分配好的地址,就直接读入,危险

ps:
怎么理解char *str = "Hello World"
是将一个存储在一个只读的数据段中字符串常量"Hello World"的首地址赋值给了str

gets(str); 尝试从标准输入读取一个字符串并存储在 str 指向的位置。但是,由于 str 没有被初始化为指向有效的内存,gets 函数可能会尝试写入一个随机的内存地址,这会导致程序崩溃或更糟糕的后果。
puts(str); 试图打印从 gets 读取的字符串。但是,由于 gets 可能导致未定义行为,str 指向的内容可能是不确定的,所以 puts 的行为也是不确定的。

更糟糕的是,gets 函数已被认为是不安全的,并且在 C11 标准中已被移除,因为它不提供任何方式来防止缓冲区溢出。如果输入的数据超过了 str 实际指向的缓冲区的大小,就会发生缓冲区溢出,这可能导致程序崩溃、数据损坏或更严重的安全漏洞(如栈溢出攻击)。

为了避免这种危害,你应该:

使用 malloc 或其他动态内存分配函数为字符串分配内存,并确保 str 指向这块内存。
使用 fgets 替代 gets,因为 fgets 允许你指定一个缓冲区大小,从而防止缓冲区溢出。

关于fgets

char *fgets(char *str, int n, FILE *stream);

str:指向一个字符数组的指针,用于存储读取的数据。
n:要读取的最大字符数(包括结尾的空字符 \0)。
stream:指向 FILE 对象的指针,指定要从中读取数据的输入流。

fgets 函数返回一个指向 str 的指针,如果发生错误或达到文件末尾,则返回 NULL。读取的数据包括任何结尾的换行符(如果存在的话),并且字符串总是以空字符 \0 结尾。

#include <stdio.h>  #define MAX_INPUT 100 // 定义输入的最大长度  int main() {  char str[MAX_INPUT];  // 从标准输入读取一行,最多读取 MAX_INPUT - 1 个字符,保留一个位置给空字符  if (fgets(str, MAX_INPUT, stdin) != NULL) {  // 移除可能的换行符  str[strcspn(str, "\n")] = 0;  puts(str);  } else {  printf("Failed to read input.\n");  }  return 0;  
}

strcspn 代表 “string character span”(字符串字符跨度)

在这里插入图片描述

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

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

相关文章

(六)Android布局类型(表格布局TableLayout)

表格布局&#xff08;TableLayout&#xff09;&#xff0c;呈现行列方式&#xff0c;无法设置列&#xff0c;可以设置行&#xff0c;行数由TableRow对象个数决定。下图中有两个TableRow元素&#xff0c;所以&#xff0c;说明表格布局中有两行。 将内容填充到行中 第一行中&…

NFTScan 正式上线 Blast NFTScan 浏览器和 NFT API 数据服务

2024 年 3 月 15 号&#xff0c;NFTScan 团队正式对外发布了 Blast NFTScan 浏览器&#xff0c;将为 Blast 生态的 NFT 开发者和用户提供简洁高效的 NFT 数据搜索查询服务。NFTScan 作为全球领先的 NFT 数据基础设施服务商&#xff0c;Blast 是继 Bitcoin、Ethereum、BNBChain、…

EtherCAT 开源主站 IGH 在 linux 开发板的移植和伺服通信测试

手边有一套正点原子linux开发板imax6ul&#xff0c;一直在吃灰&#xff0c;周末业余时间无聊&#xff0c;把EtherCAT的开源IGH主站移植到开发板上玩玩儿&#xff0c;搞点事情做。顺便学习研究下EtherCAT总线协议及其对伺服驱动器的运动控制过程。实验很有意思&#xff0c;这里总…

vite打包时发布时,放在服务器的二级目录中

方式一 hash模式 如果我们的站点根目录为 public , 我们访问的时候使用的是 http://www.abc.com/ 访问到了站点的根目当&#xff0c;现在我们要访问 http://www.abc.com/mysite/#/ 配置如下 修改 vite.config.js base:“/mysite/” 修改 router中的配置 上面的步骤完成&…

RocketMQ学习笔记四(黑马)项目

课程地址&#xff1a; 1.Rocket第二章内容介绍_哔哩哔哩_bilibili &#xff08;视频35~88&#xff0c;搭建了一个电商项目&#xff09; 待学&#xff0c;待完善。

Microsoft Visio 编辑属性值

Microsoft Visio 编辑属性值 1. 编辑属性值References 1. 编辑属性值 单击长度或高度位置&#xff0c;弹出形状的各属性值&#xff0c;点击编辑对应的属性值。 ​ References [1] Yongqiang Cheng, https://yongqiang.blog.csdn.net/

创业板指399006行情数据API接口

# 测试&#xff1a;返回不超过10条数据&#xff08;2年历史&#xff09; https://tsanghi.com/api/fin/index/CHN/daily?tokendemo&ticker399006&order2Python示例 import requestsurl f"https://tsanghi.com/api/fin/index/CHN/daily?tokendemo&ticker399…

win10 + cpu + pycharm + mindspore

MindSpore是华为公司自研的最佳匹配昇腾AI处理器算力的全场景深度学习框架。 1、打开官网&#xff1a; MindSpore官网 2、选择以下选项&#xff1a; 3、创建conda 环境&#xff0c;这里python 选择3.9.0&#xff0c;也可以选择其他版本&#xff1a; conda create -c conda-…

flink1.18.0 自定义函数 接收row类型的参数

比如sql中某字段类型 array<row<f1 string,f2 string,f3 string,f4 bigint>> 现在需要编写 tableFunction 需要接受的参数如上 解决方案 用户定义函数|阿帕奇弗林克 --- User-defined Functions | Apache Flink

【List集合】List接口源码解读一(ArrayList)

目录 前言 1. List接口的基本信息 2. ArrayList 2.1.ArrayList 的基本信息 2.2. ArrayList 的构造方法 2.2.1 ArrayList 的构造方法一 2.2.2 ArrayList 的构造方法二 2.2.3 ArrayList 的构造方法三 2.3 ArrayList 的扩容方式 总结 前言 Java 语言由于其跨平台、社区良…

代码学习记录21--回溯算法第二天

随想录日记part21 t i m e &#xff1a; time&#xff1a; time&#xff1a; 2024.03.16 主要内容&#xff1a;今天主要是结合类型的题目加深对回溯算法的理解&#xff1a;1&#xff1a;组合总和&#xff1b;2&#xff1a;电话号码的字母组合 216.组合总和III17.电话号码的字母…

Docker----Dockerfile构建微服务镜像

目录 一、关键步骤 二、具体步骤 1、准备后端jar包(这里以java后端演示) 2、编写Dockerfile 3、构建镜像 4、运行镜像容器 5、测试是否成功 一、关键步骤 1、准备后端jar包(这里以java后端演示) 2、编写Dockerfile 3、构建镜像 4、运行镜像容器 5、测试是否成功 二…