MyMSDN

MyMSDN记录开发新知道

Expert C Programming notes

1、const其实并不是真正的常量(P32)

const_is_not_constant

2、早期的gets()中的Bug导致了Internet蠕虫(P42)

gets()函数并不检查缓冲区的空间,事实上它也无法检查缓冲区的空间。如果函数的调用者提供了一个指向堆栈的指针,并且gets()函数读入的字符数量超过缓冲区的空间,gets()函数将会愉快地将多出来的字符继续写入到堆栈中,这就覆盖了堆栈原先的内容。——这就是病毒利用它来写入额外空间,并引发蠕虫病毒的前提。

推荐的方式是将

gets(line)

替换为

if(fgets(line, sizeof(line), stdin) == NULL)

exit(1);

3、相邻字符串常量自动连接(P45)

这个其实已经应用很普遍了,但是我个人用的比较少,特此记录一下。

ansi-c_connect_string

4、返回一个指针?(P48)

这个话题围绕一个程序的BUG来展开,这个程序返回了局部变量的值的指针,这么说当然你一眼就能看得出来问题所在,但是在很多时候,这个错误却总是在你的眼皮子底下溜走。

作者提供了五种方式,只能说可以用,但唯一推荐的只有一个,详见作者的分析(P48)(不是什么高深的理论,你自己也能分析地出来)。

a.返回一个字符串常量的指针。因为常量存在静态数据存储区,所以指针没问题。

b.使用全局声明的数组。提到全局两个字,就知道这个方法有很大的局限性。

c.使用静态数组。下一次调用将覆盖这个数组内容。

char * func() {

static char buffer[20];

return buffer;

}

d.显式分配一些内存,保存返回的值。

char  * func() {

char * s = malloc(120);

return s;

}

既然用到了malloc,就必然伴随着free,因此带来了内存管理的问题,增加了开发者负担。

e.(推荐)在调用前后,由函数调用者分配内存,并由其释放,在同一地方释放对于内存管理来说代价相对最小。

void func( char * result, int size) {

strncpy(result, “That’d be in the data segment, Bob”, size);

}

buffer = malloc(size);

func(buffer, size);

free(buffer);

posted on 2009-04-01 00:31 volnet 阅读(301) 评论(0)  编辑 收藏 引用 所属分类: C/C++


只有注册用户登录后才能发表评论。
网站导航: 博客园   IT新闻   BlogJava   博问   Chat2DB   管理


特殊功能