【问题标题】:Are memory visibility problems per thread also there if there is just one CPU core?如果只有一个 CPU 内核,每个线程是否也存在内存可见性问题?
【发布时间】:2013-12-24 13:05:42
【问题描述】:

标题可能看起来很奇怪,所以让我解释一下。 经常有关于竞争条件的人说线程 1 可以看到 x == 0 而线程 2 已经看到了 x=1;

我的问题是关于在同一个内核上调度的线程(并非不切实际,仍然有 1 个内核嵌入式系统,而且您至少可以在理论上将线程绑定到内核):
即使线程 1 和线程 2 在同一个核心(X86、ARM)上按顺序运行(一个在另一个之前/之后(与 c 的其他线程)),是否会出现通常的竞争可见性问题...

【问题讨论】:

  • 对于读取/写入非原子的变量以及对相关变量集的任何更新,仍将存在竞争。
  • 请注意,这远非唯一可能的比赛。即使这不会发生在单个 CPU 上,其他 CPU 无疑会发生。
  • 可见性问题只是通用问题的扩展,缺乏原子性。使用 x++ 在单核上同样不安全。在多核上进行测试的最大优势是您可以更快地检测到错误:)

标签: c++ c multithreading race-condition memory-visibility


【解决方案1】:

这仍然是一个问题。在单核上运行的线程一点也不现实。通常,您将运行数百个线程,但很可能您没有数百个内核。根据鸽子洞定理,这些线程中至少有两个共享一个内核。

竞争条件的出现是因为线程实际上不是连续的。确实它们轮流运行,但是它们会被中断,并且 CPU 会意外地转移到另一个线程。想象一下这两个(假想的)汇编程序

       Thread 1                    Thread 2

A:  Read  R1, 0x0100        E:  Read  R2, 0x0100
B:  Inc   R1                F:  Dec   R2
C:  Store R1, 0x0100        G:  Store R2, 0x0100

如果您按顺序运行此代码,则没有问题。然而,如果你被允许打断他们,那么可能会发生这样的事情:

  • A 正在运行
  • B 正在运行
  • 线程 1 中断
  • E 运行
  • F 正在运行
  • G 正在运行
  • 线程 2 完成
  • C 正在运行

如果您跟踪寄存器和地址0x0100 处的值发生了什么,那么您将意识到最终值与顺序执行两段代码不同。

因此,您的问题的答案是,竞争发生在同一 CPU 内核上的可抢占线程中,就像线程在不同的内核上运行一样。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2016-09-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-02-11
    • 2020-04-13
    • 1970-01-01
    相关资源
    最近更新 更多