【问题标题】:Why do C++11 CAS operations take two pointer parameters?为什么 C++11 CAS 操作需要两个指针参数?
【发布时间】:2013-04-09 06:03:15
【问题描述】:

许多 C++11 CAS 操作(例如,atomic_compare_exchange_weakatomic_compare_exchange_strong)采用两个指针和一个值,例如:

bool atomic_compare_exchange(T* pointer, T* expected,       // pseudodeclaration!
                             T desired);

相比之下,微软、gcc 和 Intel 的 CAS 操作都采用一个指针和两个值:

long InterlockedCompareExchange(long* pointer, long desired,       // Microsoft
                                long expected);

int __sync_bool_compare_and_swap (T* pointer, T expected,          // gcc and
                                  T desired);                      // Intel

为什么 C++11 CAS 函数采用两个指针和一个值,而不是看起来更传统的一个指针和两个值?

【问题讨论】:

  • __sync_bool_... 返回一个 bool
  • @KerrekSB:我展示的签名是从英特尔手册中复制而来的。我假设 gcc 使用相同的签名。我现在发现它没有。

标签: c++ c++11 compare-and-swap


【解决方案1】:

C++11 的方式更有用:如果交换失败,那么*expected更新 为新的当前值。这使得在循环中使用函数变得容易:

T value = x.load();
T newvalue = frob(value);

while (!atomic_compare_exchange(&x, &value, newvalue))
{
    newvalue = frob(value);
}

使用微软签名,测试操作是否成功比较麻烦,GCC的__sync_type版本也是如此。使用 GCC 的 __sync_bool,您甚至需要在每次交换失败时执行另一个加载。

【讨论】:

    【解决方案2】:

    我不明白为什么你不会同时拥有这两者。在我的用例中,C++ 版本不太有用。我想等到一个变量有某个值,然后我想将它设置为一个新值。

    使用 GCC 内在函数:

    while (!__sync_bool_compare_and_swap(&value, expected, desired)) { }
    

    使用 C++11:

    auto tmp = expected;
    while (!value.compare_exchange_weak(tmp,desired)) 
    {
      tmp = expected;
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2010-12-11
      • 2014-10-31
      • 2014-01-26
      • 1970-01-01
      • 2015-02-25
      • 1970-01-01
      • 2013-06-06
      相关资源
      最近更新 更多