【问题标题】:What is my best approach to determining compiler behaviour for empty infinite loops?确定空无限循环的编译器行为的最佳方法是什么?
【发布时间】:2015-07-27 13:44:53
【问题描述】:

An infinite loop with an empty body has undefined behaviour in C++11。我不知道它在 C 中是否也可以,所以假设我正在用 C++11 编写嵌入式固件(我知道,不太可能,但请耐心等待)。

如果我的main 只是一个:

while (true) {}

并且设备的其余功能由中断处理,我可以采取哪些方法来发现我的实现是否使这个循环安全且有意义?请记住,根据标准,在这种情况下,实现可以随意做任何事情,包括完全删除循环。

假设它没有在实现文档中明确说明,因为我从未见过。

或者这是一个失败的原因,我应该破解一个解决方法?

volatile unsigned int dummy = 0;

while (true) {
   // Make the loop well-defined...
   dummy++;

   // ...with a trivial operation that'll hardly ever even happen
   sleep(42*86400);
}

我认识到嵌入式开发人员历来并没有过多考虑这类事情,而是从他们的编译器中假设一种更“脚踏实地”、“常识”的方法。但我更喜欢按照标准严格编码,尽可能避免意外。

【问题讨论】:

  • 奇怪你也应该有问题:)
  • 如果这不仅仅是一个理论问题,那么您的嵌入式 CPU 几乎可以肯定有一条指令可以暂停操作,直到出现中断。这将节省一些电池电量(并且,据我所知,使您的循环明确定义)。
  • @zneak:这听起来像是一个好的答案的开始...... :)
  • 我自己有一些 MCU 经验,我同意 @zneak 的观点,即进入睡眠/低功耗状态可能是实践中的最佳方法。至于标题中的问题,听起来显而易见的方法是查看生成的程序集?在大多数情况下,我希望只看到一条跳转指令(或类似指令)循环回自身。
  • 旁注:while(true){} 在 C11 中不是 UB;它的“可能假定终止”子句不包括控制表达式为常量表达式的循环。

标签: c++ c++11


【解决方案1】:

看看你的编译器的汇编语言输出怎么样?

g++ -std=c++0x x.cpp -S

输出:

.L2:
        jmp     .L2

clang++-3.5 -S -std=c++11 x.cpp

输出:

.LBB0_1:                                # =>This Inner Loop Header: Depth=1
        jmp     .LBB0_1

【讨论】:

  • 在给定的构建运行中查看生成的程序集并不能真正为您提供所需的信息。好吧,除非你只打算发送那个精确的二进制文件。 :)
  • 有些人可能会认为“嵌入式固件”意味着一个精确的二进制映像。
  • 足够好了。而且,坦率地说,可能是正确的答案。 :)
猜你喜欢
  • 1970-01-01
  • 2011-02-25
  • 2017-04-21
  • 1970-01-01
  • 2021-08-24
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多