1. 背景


好多人已经知道利用strncpy替代strcpy来防止缓冲区越界。
但是如果还要考虑运行效率的话,也许strlcpy是一个更好的方式。

2. strcpy


strcpy 是依据 /0 作为结束判断的,如果 to 的空间不够,则会引起 buffer overflow。
strcpy 常规的实现代码如下:

char * strcpy(char *to, const char *from)
{
char *save = to; for (; (*to = *from) != '/0'; ++from, ++to);
return(save);
}

但通常,我们的 from 都来源于用户的输入,很可能是非常大的一个字符串,因此 strcpy 不够安全。

2. strncpy


在 ANSI C 中,strcpy 的安全版本是 strncpy

char *strncpy(char *s1, const char *s2, size_t n);

但 strncpy 其行为是很诡异的(不符合我们的通常习惯)。标准规定 n 并不是 sizeof(s1),而是要复制的 char 的个数。一个最常见的问题,就是 strncpy 并不帮你保证以'/0'结束。

char buf[8];
strncpy( buf, "abcdefgh", 8 );

看这个程序,buf 将会被 “abcdefgh” 填满,但却没有 '/0' 结束符了。
另外,如果 s2 的内容比较少,而 n 又比较大的话,strncpy 将会把之间的空间都用 '/0' 填充。这又出现了一个效率上的问题,如下:

char buf[80];
strncpy( buf, "abcdefgh", 79 );

上面的 strncpy 会填写 79 个 char,而不仅仅是 “abcdefgh” 本身。
strncpy 的标准用法为:(手工写上 '/0'

strncpy(path, src, sizeof(path) - 1);
path[sizeof(path) - 1] = '/0';
len = strlen(path);

3. strlcpy


// Copy src to string dst of size siz. At most siz-1 characters
// will be copied. Always NUL terminates (unless siz == 0).
// Returns strlen(src); if retval >= siz, truncation occurred.
size_t strlcpy(char *dst, const char *src, size_t siz);

使用 strlcpy,就不需要我们去手动负责'/0' 了,仅需要把 sizeof(dst) 告之 strlcpy 即可:

strlcpy(path, src, sizeof(path));
len = strlen(path);
if ( len >= sizeof(path) )
printf("src is truncated.");

并且 strlcpy 传回的是 strlen(str),因此我们也很方便的可以判断数据是否被截断。

[* 一点点历史 *]

strlcpy 并不属于 ANSI C,至今也还不是标准。
strlcpy 来源于 OpenBSD 2.4,之后很多 unix-like 系统的 libc 中都加入了 strlcpy 函数,我个人在 FreeBSD、Linux 里面都找到了 strlcpy。(Linux使用的是 glibc,glibc里面有 strlcpy,则所有的 Linux 版本也都应该有 strlcpy)
但 Windows 下是没有 strlcpy 的,对应的是strncpy和memset函数
本篇文章来源于 Linux公社网站(www.linuxidc.com)
原文链接:http://www.linuxidc.com/Linux/2012-06/61893.htm

(C)strcpy ,strncpy与strlcpy的更多相关文章

  1. C语言strcpy,strncpy和strlcpy讲解

    前言 C风格的字符串处理函数有很多,如strcpy().strcat()等等. strcpy与strcat char* strcpy (char* dest, const char* src); ch ...

  2. (C)strcpy ,strncpy和strlcpy的基本用法

    好多人已经知道利用strncpy替代strcpy来防止缓冲区越界. 但是如果还要考虑运行效率的话,也许strlcpy是一个更好的方式. 1. strcpy strcpy 是依据 /0 作为结束判断的, ...

  3. C语言中函数strcpy ,strncpy ,strlcpy的用法【转】

    转自:http://blog.chinaunix.net/uid-20797562-id-99311.html strcpy ,strncpy ,strlcpy的用法好多人已经知道利用strncpy替 ...

  4. C语言中函数strcpy ,strncpy ,strlcpy的用法

    strcpy ,strncpy ,strlcpy的用法 好多人已经知道利用strncpy替代strcpy来防止缓冲区越界. 但是如果还要考虑运行效率的话,也许strlcpy是一个更好的方式. 1. s ...

  5. Linux C中strcpy , strncpy , strlcpy 的区别

    strcpy ,strncpy ,strlcpy的用法 好多人已经知道利用strncpy替代strcpy来防止缓冲区越界. 但是如果还要考虑运行效率的话,也许strlcpy是一个更好的方式. 1. s ...

  6. strcpy、strncpy、strlcpy的区别

  7. C语言——常用标准输入输出函数 scanf(), printf(), gets(), puts(), getchar(), putchar(); 字符串拷贝函数 strcpy(), strncpy(), strchr(), strstr()函数用法特点

    1 首先介绍几个常用到的转义符 (1)     换行符“\n”, ASCII值为10: (2)     回车符“\r”, ASCII值为13: (3)     水平制表符“\t”, ASCII值为 9 ...

  8. strcpy/strncpy/strcpy_s比较

    转载自:http://blog.csdn.net/caomiao2006/article/details/4766416 strcpy()是依据源串的/0作为结束判断的,不检查copy先的Buffer ...

  9. C++ strcpy strcpy_s strncpy strlcpy

    strncpy的用法:它与strcpy的不同之处就在于复制n个字符,而不是把所有字符拷贝(包括结尾'\0'). 函数原型:char * strncpy(char *dst,const char * s ...

随机推荐

  1. 【loj6191】「美团 CodeM 复赛」配对游戏

    题目 显然期望dp. 简单想法: f[i][j]表示前i个人中向右看并且没有被消除的人数的概率 如果第i+1个人是向右,$f[i+1][j+1]=f[i][j]/2$ 如果第i+1个人是向左,$f[i ...

  2. Spring的声明式事务管理<tx:advice/> 有关的设置

    <tx:advice/> 有关的设置 这一节里将描述通过 <tx:advice/> 标签来指定不同的事务性设置.默认的 <tx:advice/> 设置如下: 事务传 ...

  3. FOJ Problem 2271 X

    Problem 2271 X Accept: 55    Submit: 200Time Limit: 1500 mSec    Memory Limit : 32768 KB Problem Des ...

  4. ElasticSearch API 之 UPDATE

    ES本身是一个倾向于查询检索的框架,对于更新的操作,太过频繁总归不好的. 阅读本篇后,你可以使用Script对所有的文档执行更新操作,也可以使用doc对部分文档执行更新,也可以使用upsert对不存在 ...

  5. Codevs 2602 最短路径问题

     时间限制: 1 s 空间限制: 32000 KB 题目等级 : 黄金 Gold 题目描述 Description 平面上有n个点(n<=100),每个点的坐标均在-10000~10000之间. ...

  6. Mac快速查看隐藏文件

    使用终端 显示隐藏文件的最简单方法是使用终端.只要打开终端(位于应用程序--实用工具),将以下代码复制进去然后回车 defaults write com.apple.finder AppleShowA ...

  7. SGU 106 在区间范围内的线性方程解个数

    题意:求解方程ax+by+c=0,在区间x1->x2和y1->y2的解的个数. 看似简单,真心a的不容易啊! 开始跪于第8组数据,原因是没用long long !后来改了,跪于12组,超时 ...

  8. tar [options] [list of file]

    打包:zcvf 解压:zxvf -c 创建新档案文件 -x 从档案文件中解出文件(释放文件) -v (verbose)显示tar命令执行的详细过程 -f 指定目标为一个文件而不是一个设备 -z 调用g ...

  9. luogu P1032 字串变换

    题目描述 已知有两个字串 A, B 及一组字串变换的规则(至多6个规则): A1 -> B1 A2 -> B2 规则的含义为:在 A$中的子串 A1 可以变换为 B1.A2 可以变换为 B ...

  10. Material Theme

    Material Theme提供了一下功能: 1.系统widgets可以设置调色板 2.系统widgets的触摸反馈 3.Activity过渡动画 你可以根据你品牌的色彩来定义Material The ...