首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >是同步-与edegs编译器重新排序障碍在两个方向?

是同步-与edegs编译器重新排序障碍在两个方向?
EN

Stack Overflow用户
提问于 2014-11-03 22:27:27
回答 1查看 234关注 0票数 10

我有一个关于Java内存模型的问题。给出了以下示例:

代码语言:javascript
复制
action 1
action 2
synchronized(monitorObject) { //acquire
    action 3
} //release
action 4

acquirerelease可以是任何同步-与边缘(锁定,解锁,启动线程,连接线程,检测线程中断,易失性写入,易失性读取等)

它是否保证在获得之前不能移动action 3,在发布后不能移动?

它是否保证action 2不能在获得之后被移动(无论是在发布之前还是之后),以及不能在发布之前(无论是在获得之前还是之后)移动action 4

那么,对于编译器的重排序操作来说,具有边“双向屏障”的同步是否是同步的呢?

编辑1我很担心这一点,因为如果同步-与边不是双向的重新排序障碍,编译器可以简单地创建一个死锁通过移动获得的锁到其他。

或者双向重排障碍甚至没有必要来阻止这一点,因为锁获得的锁不能被推到其他锁中,因为这会改变同步顺序吗?

编辑2操作1、2、3和4是JMM定义的“线程间操作”。

编辑3这里的一个例子展示了重新排序可能如何导致死锁:

X和y是共享变量,任何其他线程都可以获得syncA和syncB。但是有了下面的代码,就不可能出现死锁。

代码语言:javascript
复制
/* 1 */  synchronized(syncA) {
/* 2 */      x = 1;
/* 3 */  }
/* 4 */  y = 0;
/* 5 */  synchronized(syncB) {
/* 6 */      y = 1;
/* 7 */  }

但是,如果syncA的获取被重新排序到syncB块中,这可能会导致死锁:

代码语言:javascript
复制
y = 0;
synchronized(syncB) {
    y = 1;
    synchronized(syncA) {
        x = 1;
    }
}

我认为这不是一个合法的编译器转换,因为它会改变同步顺序。这个假设我说得对吗?Java内存模型(JMM)的哪个部分允许/不允许这样做?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2014-11-06 18:26:30

感谢水连翘链接到这个问题,它包含了来自JSR-133烹饪本的图像的答案

根据这个映像,编辑3的编译器转换是非法的,因为它重新排序了两个MonitorEnters。

另外,本表还显示了哪些同步-边是哪些类型的“重新排序-障碍”的其他操作。

(谢谢你的帮助:)

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/26724443

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档