Tag: 内存 障碍

受欢迎的“挥发性民意调查旗帜”模式是否破裂?

假设我想在线程之间使用布尔状态标志来进行协作取消。 (我意识到最好使用CancellationTokenSource ;这不是这个问题的重点。) private volatile bool _stopping; public void Start() { var thread = new Thread(() => { while (!_stopping) { // Do computation lasting around 10 seconds. } }); thread.Start(); } public void Stop() { _stopping = true; } 问 :如果我在0s调用Start()而在另一个线程调用3s的Stop() ,那么循环是否保证在当前迭代结束时在10s左右退出? 我见过的绝大多数消息来源表明上述内容应该按预期工作; 见: MSDN ; Jon Skeet ; 布赖恩吉迪恩 ; 马克格拉维尔 ; Remus […]

加入线程时是否需要内存屏障?

如果一个线程A生成另一个线程B,其唯一目的是写入变量V然后等待它终止,那么是否需要内存屏障以确保后续读取线程A上的V是新鲜的? 我不确定终止/加入操作中是否有任何隐含的障碍使它们变得多余。 这是一个例子: public static T ExecuteWithCustomStackSize (Func func, int stackSize) { T result = default(T); var thread = new Thread( () => { result = func(); Thread.MemoryBarrier(); // Required? } , stackSize); thread.Start(); thread.Join(); Thread.MemoryBarrier(); // Required? return result; } 是否需要上述代码段中的两个(或更多)障碍?

.NET中的可变新鲜度保证(易失性与易失性读取)

我读过很多关于volatile和VoletileRead(ReadAcquireFence)的矛盾信息(msdn,SO等)。 我理解那些内存访问重新排序的限制含义 – 我仍然完全混淆的是新鲜度保证 – 这对我来说非常重要。 msdn doc for volatile提及: (…)这可确保始终在字段中显示最新值。 用于volatile字段的msdn doc提及: 读取volatile字段称为volatile读取。 易失性读取具有“获取语义”; 也就是说,保证在指令序列之后的任何内存引用之前发生。 VolatileRead的.NET代码是: public static int VolatileRead(ref int address) { int ret = address; MemoryBarrier(); // Call MemoryBarrier to ensure the proper semantic in a portable way. return ret; } 根据msdn MemoryBarrier doc内存屏障阻止重新排序。 然而,这似乎对新鲜度没有任何影响 – 对吗? 那怎样才能获得保鲜? 标记字段volatile与使用VolatileRead和VolatileWrite语义访问它有区别吗? 我目前正在执行我的性能关键代码,需要保证新鲜度,但读者有时会得到陈旧的价值。 我想知道如果标记状态不稳定会使情况不同。 EDIT1: […]