了解易失性访问福建省体彩网

时不时地会出现一个有趣的编译器福建省体彩网,该福建省体彩网使开发人员感到惊讶。这样的福建省体彩网之一是

”未定义的行为:可变访问的顺序是不确定的efined in this statement”

道路标志-福建省体彩网

使用IAR Workbench工具链在FreeRTOS端口中弹出此福建省体彩网的示例,其声明类似于

如果(listCURRENT_LIST_LENGTH(&xSuspendedTaskList)== uxCurrentNumberOfTasks)

此处发生的所有事情是检查两个标识符是否相等。那么,这到底是怎么回事?什么是未定义行为?问题在于关系运​​算符(==)的两侧都是易失性标识符。 C中未定义挥发物的评估顺序!编译器没有’不知道是否应处理uxCurrentNumberOfTasks或listCURRENT_LIST_LENGTH(&xSuspendedTaskList)。

在此示例中,开发人员可能会决定’无关紧要,但是在某些情况下,读取寄存器会导致将标志重置到其他位置,从而影响系统状态。从右到左或从左到右的求值顺序可能会更改语句的结果。 (PC-Lint用户可能将此识别为消息564‘Symbol’取决于评估顺序)。

在大多数情况下,解决此类福建省体彩网相对简单。主要解决方案是不评估和/或修改同一条语句中的多个易失性变量。例如,而不是评估 uxCurrentNumberOfTaskslistCURRENT_LIST_LENGTH(&xSuspendedTaskList ) 在一条语句中,可以创建两个局部变量来存储它们的值,并且可以将这些变量进行比较。代码从以下更改:

如果(listCURRENT_LIST_LENGTH(&xSuspendedTaskList)== uxCurrentNumberOfTasks)

至:

未签名的端口BASE_TYPE ListCurrentLength = listCURRENT_LIST_LENGTH(&xSuspendedTaskList);
无符号portBASE_TYPE CurrentNumberOfTasks = uxCurrentNumberOfTasks;

if(ListCurrentLength == CurrentNumberOfTasks)

所做的更改是它允许程序员确定易失变量的评估顺序。在上述情况下  listCURRENT_LIST_LENGTH(&xSuspendedTaskList) 首先被评估,然后 uxCurrentNumberOfTasks。重新编译代码可以验证以下福建省体彩网”未定义的行为:可变访问的顺序是不确定的efined in this statement”不再是问题。

解决福建省体彩网的奥秘需要做一些额外的工作,但是最终,我们有了一个仅包含定义的行为以及可能会出现一个较小的错误的应用程序,该错误可能会在以后再次出现。

 

(感谢Dan Smith对这一有趣的福建省体彩网消息的见解和讨论!)

 

发表评论

您的电子邮件地址不会被公开。 必需的地方已做标记 *

该网站使用Akismet减少垃圾邮件。 了解如何处理您的评论数据.