C++11 内存模型是否可以防止内存撕裂和冲突?
Does the C++11 memory model prevent memory tearing and conflicts?
阅读 C++11 的草稿 我对条款 1.7.3 很感兴趣:
内存位置要么是标量类型的对象,要么是具有非零宽度的相邻位字段的最大序列。两个执行线程 (1.10) 可以更新和访问单独的内存位置,而不会相互干扰。
此子句是否保护与硬件相关的争用条件,例如:
- 在两个总线事务中更新内存(内存撕裂)的未对齐数据访问?
- 在系统内存单元中具有不同的对象时,例如 32 位字中的两个 16 位有符号整数,并且单独对象的每次独立更新都需要写入整个内存单元(内存冲突)?
关于第二点,标准保证那里不会有比赛。话虽如此,我被告知此保证未在当前编译器中实现,甚至可能无法在某些体系结构中实现。
关于第一点,如果第二点是保证的,并且如果您的程序不包含任何竞争条件,那么自然的结果是这也不会是竞争条件。也就是说,假设标准保证写入不同的子字位置是安全的,那么唯一可以有争用条件的情况是多个线程访问同一个变量(跨字拆分,或者更有可能是有问题的,跨缓存行)。
同样,这可能很难甚至不可能实现。如果未对齐的基准面穿过缓存行,则几乎不可能保证代码的正确性,而不会给性能带来巨大的成本。出于此原因和其他原因(包括原始性能,写入接触两个缓存行的对象涉及将多达 32 个字节写入内存,如果任何其他线程接触任何缓存行,则还涉及缓存同步的成本......
它不能防止内存撕裂,只有当两个线程访问相同的内存位置时,内存撕裂才可见(但该子句仅适用于单独的内存位置)。
根据您的示例,它似乎可以防止内存冲突。 最可能的方法是,一个不能一次写入少于32位的系统将具有32位char
,然后两个独立的对象永远不会共享一个"系统内存单元"。 (在具有 32 位char
的系统上,两个 16 位整数相邻的唯一方法是作为位域。
相关文章:
- 将字符串存储在c++中的稳定内存中
- C++ 指针的内存地址和指向数组的内存地址如何相同?
- Win32编译器选项和内存分配
- 当vector是tje全局变量时,c++中vector的内存管理
- 带内存和隔离功能的SQLite
- 是否可以通过C++扩展强制多个python进程共享同一内存
- 迭代时从向量和内存中删除对象
- 在C++中打印指向不同基元数据类型的指针的内存地址
- 这个指针和内存代码打印是什么?我不知道是打印垃圾还是如何打印我需要的值
- 多个文件的内存分配错误"在抛出 'std :: bad_alloc' what (): std :: bad_alloc 的实例后终止调用" [C++]
- 为什么示例代码访问IUnknown中已删除的内存
- 如何在C++类内存结构中创建"spacer"?
- 从构造函数抛出异常时如何克服内存泄漏
- malloc() 可能出现内存泄漏
- 如何理解将半精度指针转换为无符号长指针和相关的内存对齐
- 在调用FreeLibrary后,释放动态链接到具有相同版本的CRT堆的DLL的内存
- 如何针对特定情况调试和修复此双自由内存损坏问题
- 类型总是使用其大小存储在内存中吗
- 有没有一种方法可以测量c++程序的运行时内存使用情况
- C++11 内存模型是否可以防止内存撕裂和冲突?