| static void helper_function(my_struct_t *e,int *outArr)
{
  unsigned char event_type = e->header.type;
  if (event_type == event_A || event_type == event_B) {
    outArr[0] = action_one;
  } else if (event_type == event_C) {
    outArr[0] = action_one;
    outArr[1] = action_two;
  } else if (...) { ... }
}
static void buggy_invoker(my_struct_t *e,predicate_t pred)
{
  // MAX_ACTIONS is #defined to 5
  int action_array[MAX_ACTIONS] = {0};
  helper_function(e,action_array);
  ...
}
static int has_any_actions(my_struct_t *e)
{
  int actions[MAX_ACTIONS] = {0};
  helper_function(e,actions);
  return actions[0] != 0;
}
// *** ENTRY POINT to this code is this function (note not static).
void perfectly_fine_invoker(my_struct_t e,predicate_t pred)
{
  memfence();
  if (has_any_actions(&e)) {
    buggy_invoker(&e,pred);
  }
  ...
}
 如果您认为我已经过度混淆或消除了太多,请告诉我.用户这段代码叫’perfect_fine_invoker’.通过优化,g优化了
 ‘has_any_actions’函数可直接调用’helper_function’,即
 你可以在装配中看到.
 问题 所以,我的问题是,对任何人来说,它看起来像一个错误的优化吗? 如果它有用,我可以发布原始C代码的消毒版本. 这是我第一次发布Stack Overflow,所以如果我能做的话请告诉我任何使问题更清晰或提供任何其他信息的事情.
 答案 编辑(事后几天): 我在下面接受了我的问题的答案 – 这不是g中的优化错误,我只是看错了汇编代码. 但是,对于将来可能会看到这个问题的人,我找到了答案.我在C(http://blog.regehr.org/archives/213和http://blog.llvm.org/2011/05/what-every-c-programmer-should-know.html)中对未定义的行为进行了一些阅读,并且编译器的一些描述使用未定义的行为优化掉函数似乎非常熟悉. 我在函数’helper_function’中添加了一些NULL指针检查,并且看到…… bug消失了.我应该开始使用NULL指针检查,但显然没有让它们允许g做任何想做的事情(在我的情况下,优化掉调用). 希望这些信息有助于未来的人.最佳答案
我觉得你在看错了.我想编译器注意到你的函数很短并且没有触及%rdi寄存器所以它只是不管它(你有与第一个参数相同的变量,我想这是放在%rdi中的内容.参见第21页这里http://www.x86-64.org/documentation/abi.pdf) 如果查看未优化的版本,它会在此行保存%rdi寄存器 9498:       48 89 bd 38 fe ff ff    mov    %rdi,-0x1c8(%rbp)
 …然后在调用helper_function之前,它将保存的值移动到移动到%rdi的%rax中. 94c1:       48 8b 85 38 fe ff ff    mov    -0x1c8(%rbp),%rax
94c8:       48 89 d6                mov    %rdx,%rsi
94cb:       48 89 c7                mov    %rax,%rdi
 在优化它时,编译器就可以摆脱所有来回移动.
 (编辑:南平站长网) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |