同时更新结构的不同字段 - 是否安全?

时间:2011-01-03 18:09:17

标签: c concurrency

考虑我有一个结构:

struct SimpleStruct {
    int x;
    int y;
    int z;
}

现在,如果我有3个单独的线程,每个线程只分别更新结构的x,y,z字段之一,是否可以安全地让它们同时更新,或者我应该使用互斥锁或某些东西来阻止它发生?

6 个答案:

答案 0 :(得分:8)

这是安全的(结构是对齐的)。

但是,您应该注意虚假共享(请参阅Herb Sutter's article):如果字段位于同一个缓存行中,则写入将被有效序列化。

答案 1 :(得分:3)

您可以安全地从一个线程更新x而在另一个线程上更新y,但是如果没有某种同步,则无法安全地从2个单独的线程更新x

答案 2 :(得分:2)

正如很多人所说,如果每个线程只更新其中一个(没有冲突),那么它是安全的 - 如果你有一个连贯的缓存。如果你在一个没有缓存一致性的多处理器上,事情变得棘手(并且根据你是否需要写入一致性或读取一致性而不同)。某些体系结构可能需要处理器A在处理器B可以看到它之前进行高速缓存写回。根据体系结构的不同,如果A和B写入相同的高速缓存行,则A的写入在极少数情况下会被“丢失”并被B的写入的高速缓存行刷新覆盖。

请参阅DaVinci处理器中的DSP与ARM一致性问题。

在大多数情况下(连贯的缓存,同一进程中的线程等),这不是问题。

答案 3 :(得分:1)

只要它们只是改变结构的内容而不是指向结构的指针或类似的奇怪的东西,我就不会想到这有任何问题。

答案 4 :(得分:1)

使用不同的线程更新不同的字段绝对是安全的。 但是如果线程使用相同的指针(到结构)来更新字段,请确保没有线程更改该指针。

答案 5 :(得分:1)

x,y,z是不同的变量,驻留在不同的内存块中。它们被分组到一个结构中的事实并没有改变任何东西。只要多个线程没有更新相同的变量并且更新线程不尝试从其他两个变量读取,就可以安全地从多个线程更新x,y,z。另外,请注意虚假分享。如果在紧密循环内执行更新,则错误共享可能会使多线程实现比单线程实现更慢。