strcpy/strncpy/strcpy_s比较
转载自:http://blog.csdn.net/caomiao2006/article/details/4766416
strcpy()是依据源串的/0作为结束判断的,不检查copy先的Buffer的Size,如果目标空间不够,就有BufferOverflow问题。请务必使用按照strncpy_s()、strcpy_s()、strncpy()等不同环境而准备的安全度很高的函数。
strcpy函数,就象gets函数一样,它没有方法来保证有效的缓冲区尺寸,所以它只能假定缓冲足够大来容纳要拷贝的字符串。在程序运行时,这将导致不可预料的行为。
另外、即使是使用安全度很高的函数,由于用法方面的原因,也可能发生Buffer Overflow,请注意如下几点。不要在strcpy_s()、strncpy_s()进行Buffer Size的誤指定。
strcpy_s()两个参数和三个参数的不同用法区别如下代码所示:
- char *str1=NULL;
- str1=new char[20];
- char str[7];
- strcpy_s(str1,20,"hello world");//三个参数
- strcpy_s(str,"hello");//两个参数但如果:char *str=new char[7];会出错:提示不支持两个参数
第二个参数表示目标缓冲区大小,大于或等于源串的长度+1(存放结束符/0),strcpy_s必须完全拷贝源串,若只想拷贝一部分源串则应该用strncpy_s函数。
- char * dst = (char *)malloc(10);
- //strcpy_s(dst, 10, "Hello world!");
- strncpy(dst, "Hello world!", 10);
若使用strncpy不会出错,观察内存可以发现,目标指针所指的缓冲区中完全是从源字符串拷贝过来的字符,没有/0结束符,但是若使用strcpy_s则在运行是出现断言出错,所以strncpy仍然不是安全的,因为有可能出现目标指针的字节数不足存放源指针所指向的内容。另外,若使用语句strncpy(dst, "Hello", 10);则会把剩下的空间都填充为空字符/0,带来效率问题,strcpy_s则不会。
所以从VS2005开始已经推出相应的安全版本——strcpy_s(末尾的s可能代表safe)。
接口的定义改变如下:
char* strcpy(char* dest, const char* src) --> errno_t strcpy_s(char* dest, size_t numElems, const char* src)
char* strcpy(char* dest, const char* src, size_t count) --> errno_t strcpy_s(char* dest, size_t numElems, const char* src, size_t count)
后者之所以比前者安全,是因为他们在接口增加了一个参数numElems来表明dest中的字节数,防止目标指针dest中的空间不够而导致出现Bug,同时返回值改成返回错误代码,而不是为了一些所谓的方便而返回char*。这样接口的定义就比原来安全很多。
更多关于CRT安全性修改的函数参见另一篇文章(转):VS 2005 CRT函数的安全性增强版本
strcpy/strncpy/strcpy_s比较的更多相关文章
- C语言中函数strcpy ,strncpy ,strlcpy的用法【转】
转自:http://blog.chinaunix.net/uid-20797562-id-99311.html strcpy ,strncpy ,strlcpy的用法好多人已经知道利用strncpy替 ...
- C语言中函数strcpy ,strncpy ,strlcpy的用法
strcpy ,strncpy ,strlcpy的用法 好多人已经知道利用strncpy替代strcpy来防止缓冲区越界. 但是如果还要考虑运行效率的话,也许strlcpy是一个更好的方式. 1. s ...
- C语言strcpy,strncpy和strlcpy讲解
前言 C风格的字符串处理函数有很多,如strcpy().strcat()等等. strcpy与strcat char* strcpy (char* dest, const char* src); ch ...
- C语言——常用标准输入输出函数 scanf(), printf(), gets(), puts(), getchar(), putchar(); 字符串拷贝函数 strcpy(), strncpy(), strchr(), strstr()函数用法特点
1 首先介绍几个常用到的转义符 (1) 换行符“\n”, ASCII值为10: (2) 回车符“\r”, ASCII值为13: (3) 水平制表符“\t”, ASCII值为 9 ...
- (C)strcpy ,strncpy与strlcpy
1. 背景 好多人已经知道利用strncpy替代strcpy来防止缓冲区越界. 但是如果还要考虑运行效率的话,也许strlcpy是一个更好的方式. 2. strcpy strcpy 是依据 /0 作为 ...
- (C)strcpy ,strncpy和strlcpy的基本用法
好多人已经知道利用strncpy替代strcpy来防止缓冲区越界. 但是如果还要考虑运行效率的话,也许strlcpy是一个更好的方式. 1. strcpy strcpy 是依据 /0 作为结束判断的, ...
- C++ strcpy strcpy_s strncpy strlcpy
strncpy的用法:它与strcpy的不同之处就在于复制n个字符,而不是把所有字符拷贝(包括结尾'\0'). 函数原型:char * strncpy(char *dst,const char * s ...
- strcpy函数和strncpy函数的区别
strcpy函数和strncpy函数的原型介绍在我的另一篇文章中介绍了,见strcpy,strncpy,strlen等函数原型 strcpy:字串复制 原型:char *strcpy(char *de ...
- Linux C中strcpy , strncpy , strlcpy 的区别
strcpy ,strncpy ,strlcpy的用法 好多人已经知道利用strncpy替代strcpy来防止缓冲区越界. 但是如果还要考虑运行效率的话,也许strlcpy是一个更好的方式. 1. s ...
随机推荐
- springboot整合mybatis时无法读取xml文件解决方法(必读)
转 http://baijiahao.baidu.com/s?id=1588136004120071836&wfr=spider&for=pc 在springboot整合myba ...
- Linux/UNIX编程:使用C语言实现简单的 ls 命令
刚好把 Linux/UNIX 编程中的文件和IO部分学完了,就想编写个 ls 命令练习一下,本以为很简单,调用个 stat 就完事了,没想到前前后后弄了七八个小时,90%的时间都用在格式化(像 ls ...
- jQuery 小测试
1.在div元素中,包含了一个<span>元素,通过has选择器获取<div>元素中的<span>元素的语法是? 提示使用has() 答案: $(div:has(s ...
- 有关vs2010将c++生成exe文件时出现LINK : fatal error LNK1123: 转换到 COFF 期间失败和环境变量问题
不知怎么本来编译好好的VS2010环境,忽然出现“转换到 COFF 期间失败: 文件无效或损坏”的链接错误.花了好多天,试了好多方法,最终解决了这个问题.现在罗列一下这几种解决方案:方案1:点击“项目 ...
- 从三个语言(C++,Java,.Net)的几个性能测试案例来看性能优化
随着时间的发展,现在的虚拟机技术越来越成熟了,在有些情况下,Java,.Net等虚拟机密集计算的性能已经和C++相仿,在个别情况下,甚至还要更加优秀.本文详细分析几个性能测试案例,探讨现象背后的原因. ...
- codeforces 347A - Difference Row
给你一个序列,让你求(x1 - x2) + (x2 - x3) + ... + (xn - 1 - xn).值最大的一个序列,我们化简一下公式就会发现(x1 - x2) + (x2 - x3) + . ...
- 实时同步lsyncd
实时同步lsyncd 1 lsyncd 1.1 lsyncd 简介 Lsyncd使用文件系统事件接口(inotify或fsevents)来监视对本地文件和目录的更改.Lsyncd将这些事件整理几秒钟, ...
- 10分钟了解一致性hash算法
应用场景 当我们的数据表超过500万条或更多时,我们就会考虑到采用分库分表:当我们的系统使用了一台缓存服务器还是不能满足的时候,我们会使用多台缓存服务器,那我们如何去访问背后的库表或缓存服务器呢,我们 ...
- 自定义ItemToggleView
极力推荐文章:欢迎收藏 Android 干货分享 阅读五分钟,每日十点,和您一起终身学习,这里是程序员Android 本篇文章主要介绍 Android 开发中的部分知识点,通过阅读本篇文章,您将收获以 ...
- 十分钟带你看一遍ES6新特性
let , const关键字 var 看习惯了java, 看js真的是忍不住想笑,比如说这个var,它太自由了,自由到{}根本限制不住它的生命周期 js的var关键字,无论在何处声明,都会被视为声明在 ...