笔试宝典上关于字符串复制的问题
2015-07-21 18:18
375 查看
#include <iostream> #include <stdio.h> int main(void) { <span style="white-space:pre"> </span>char s[]="123456789"; <span style="white-space:pre"> </span>char d[]="123"; <span style="white-space:pre"> </span>strcpy(d,s); <span style="white-space:pre"> </span>printf("%s,\n%s",d,s); <span style="white-space:pre"> </span>return 0; }输出结果是多少,书上说是123456789,56789运行结果是,求解释
你用的VC,如果用gcc则书中的结果是正确的,因为VC编译器在编译的时候对内存布局作出的后台处理以实现优化目的,比如节省内存或者加速访问,GCC对于C++标准的实现优于VC。 仍以在gcc下编译为例: s和d是长度分别为11和4的char型数组,都是局部变量,在栈内存区域存放(不明,可以自行学习程序中变量在内存中的存储方式),向低地址增长,加入s的起始地址是20,则d的起始地址为16, 则从地址16开始依次为‘1’ ‘2’ ‘3’ ‘\0’ '1' '2' '3' ... ' 9' '\0',前4个为d的内容,后11个为s的内容,在执行完strcpy后,从地址16开始依次为'1' '2' ... '9' '\0' '5' '6' '7' '8' '9' '\0'。 VC的结果不同是因为其内存布局有调整,并未完全按照上述,你可以在VC中输出s和d的首地址二者之差一定不是4,在我这VC上是12,故而可以理解为什么VC结果与gcc不同。 因为你将d和s申请为数组,故都在堆栈区,但在字符串常量区也有'123456789'和“123”内容. 如果如下声明 char *s = "123456789"; char *d = "123";则d和s的确都指向字符串常量区域。因为字符串常量区是只读区域不能修改,执行strcpy一定会出错。
总结:在使用strcpy时一定要注意,尽量用strncpy代替。再看下面在网上找来的例子。可以帮助加深理解。问:下面是一个简单的密码保护功能,你能在不知道密码的情况下将其破解吗?[cpp] view plaincopy#include<stdio.h>int main(int argc, char *argv[]){int flag = 0;char passwd[10];memset(passwd,0,sizeof(passwd));strcpy(passwd, argv[1]);if(0 == strcmp("LinuxGeek", passwd)){flag = 1;}if(flag){printf("\n Password cracked \n");}else{printf("\n Incorrect passwd \n");}return 0;}答:破解上述加密的关键在于利用攻破strcpy()函数的漏洞。所以用户在向“passwd”缓存输入随机密码的时候并没有提前检查“passwd”的容量是否足够。所以,如果用户输入一个足够造成缓存溢出并且重写“flag”变量默认值所存在位置的内存的长“密码”,即使这个密码无法通过验证,flag验证位也变成了非零,也就可以获得被保护的数据了。例如:[cpp] view plaincopy$ ./psswd aaaaaaaaaaaaaPassword cracked虽然上面的密码并不正确,但我们仍然可以通过缓存溢出绕开密码安全保护。
相关文章推荐
- 走迷宫
- sql如何查询主键
- 3.Swift翻译教程系列——Swift基础知识
- Java关于集合(list,set,map)的遍历与增强for循环的使用
- [JSON] JSON入门指南
- qt 中文乱码 处理QByteArray类型里含中文的数据
- 常用的Http状态码
- maven 加入json-lib.jar 报错 Missing artifact net.sf.json-lib:json-lib:jar:2.4:compile
- 【iOS开发系列】scrollView中的directionalLockEnabled
- zoj3745 Salary Increasing
- mysql in 子查询 效率慢 优化(转)
- 深入分析C++引用
- juke项目
- 使用LZMA算法(转载)
- jquery获取表单类型为radio的元素
- TEQC最新版本2015年6月23日版本
- Perl的debug小技巧
- 使用基于Http的消息代替WebService的数据交互
- 【Swift】学习笔记(六)——函数
- 工作日志 7.21