杂项:编译器优化导致代码异常

先上代码

static int arr[4] = {1, 2, 3, 4};

void func2(int v, int nv) {
    int n = 0;
    while (n < 4 && arr[n] != v)
        n++;
	if(n < 4)
	    arr[n] = nv;
}

void func3(int v, int nv) {
    int n = 0;
    while (arr[n] != v && n < 4)
        n++;
    if(n < 4)
	    arr[n] = nv;
}

测试结果

  无论是在linux 下编译还是在windows 下使用gcc 在-O2/-Os 级别下编译都会出现:
  func2 不会 出现n >= 4 的情况
  func3 会出现 n >= 4 的情况

问题分析

  通过分析汇编 func3 函数 在 -O2/-Os 级别的中编译会将 && n < 4 和 if(n < 4) 这两个判断给优化掉(没有cmp R0, 4 这句汇编)

导致问题

  由于有 if(n < 4)这个判断,我们会认为,怎么的这n 也不会超过 4 ,从而进行读写操作,进而可能引发灾难的后果!!!

推测原因

  编译器认为:既然会第一个判断arr[n] != v,那么就有可能会越界访问(arr数组长度就是4),如果是正确的代码,那么就是写代码时就会控制不会溢出访问,那么就没有第一个 n < 4 判断就没有必要,既然n 不会超过或者等于4,那么if(n < 4) 也没有必要存在。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值