笔记二 习题2.26有符号和无符号引出的问题

这几天没有看书。以后记得坚持。

看到讲位移和符号的关系。
其中对于嵌入式开发人员,关注的是逻辑右移和算术右移(高位如果为1,就依次填充1)的差异性,一般的编译器默认的是算术右移。
我们在操作硬件时,必须使用无符号的类型。上面是概念性的理解。

但是关于有符号和无符号类型,在现实中的确会造成困扰。
分析代码在此

我用的是64位的机器编译的,所以size_t类型是unsigned long int类型。这点与书中讲的有些区别。因为书中估计是32位的机器。
例子中的returen值是一个逻辑真,与逻辑假, 感觉是一个strcmp的实现(随手查了strcmp的讨论,得到一个有用的链接,可以认真读一下,里面有很有用的编程技巧)。但是最后的结果,只能判断两个字符串长度是否一致。并不知道谁的长度长。所以我写了一个例子。然后比较了两种方法的异同。
一种是return的逻辑判断结果,一种是直接显示最后的结果。
当然,书中有明显的提示,也就是返回值是size_t的问题。如果返回值为无符号,那么就很难判断了。在printf中,分别打印出了有符号和无符号,可以明显看到结果。

看到了符号数造成的差异性的问题,我们更加关注的应该是利用有符号类型造成的安全性的问题。就和书中的注解中提到了FreeBSD中的getpeername的早期实现一样。是由于利用了符号数,恶意传值引发的安全问题。这种问题叫做缓冲区溢出漏洞。是我们在编程时,要时刻注意的。代码如下:

void* memcpy(void* dest, void* src, size_t s);

#define KSIZE 1024
char kbuf[KSIZE];

int copy_from_kernel(void *user_dset, int maxlen){
    int len=KSIZE < maxlen ? KSIZE : maxlen;
    memcpy(user_dest, kbuf, len);
    return len;
}

可以看出,参数maxlen如果为有符号的整型,传入一个负数后,len的值经过无符号转换之后,会变得异常大。后面的数据完全暴露了。。。修正挺简单,maxlen为size_t即可。

一个有经验的程序员,应该是在写代码时,就会有意识的规避各种潜在问题的程序员。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值