0

我正在尝试使用 MS VC++ Intrinsic InterlockedCompareExchange128 函数。

作为一个 hello-world,我试图将一个 16 字节的地址与其自身进行比较,并将其替换为其他内容。这编译,但它不工作 - 地址不与新值交换。const_cast 用于使其编译(否则它会因为无法转换 volatile 而哭泣)。

typedef struct t_node
{
    volatile __int64 arr[2];
}node;

int main()
{   

    node *a = new node();

    a->arr[0] = 100;
    a->arr[1] = 1;

    __int64 i = 200;
    __int64 j = 500;

    char r = _InterlockedCompareExchange128(a->arr, i,j, const_cast<__int64*>(&a->arr[0]));

    cout<<endl<<"Interlocked Compare Res: "<<r;

    cin.get();
    return 0;
}
4

1 回答 1

4

文档中:

unsigned char _InterlockedCompareExchange128(
   __int64 volatile * Destination,
   __int64 ExchangeHigh,
   __int64 ExchangeLow,
   __int64 * ComparandResult
);

[in, out] ComparandResult
指向两个 64 位整数数组(被视为 128 位字段)的指针,用于与目标进行比较。在输出时,这将被目标的原始值覆盖

因此,发生的事情是在伪代码中:

if(ComparandResult != Destination)
{
    temp = Destination
    Destination = ExchangeHigh:ExchangeLow
    ComparandResult = temp
}

Destination == ComparandResult(您的情况)是:

if(ComparandResult != Destination)
{
    temp = Destination
    Destination = ExchangeHigh:ExchangeLow
    Destination = temp
}

这是一个nop。
此外,在同一页面中还有一个注释:

注意
ComparandResult 的值总是被覆盖。在锁定指令之后,此内在函数立即将 Destination 的初始值复制到 ComparandResult。因此,ComparandResult 和 Destination 应该指向不同的内存位置以避免意外行为。

于 2012-07-18T17:52:23.157 回答