AtomicLong.lazySet是如何工作的?

原文链接  译者:孙文强

Jackson Davis说:
为一个AtomicLong对象设置一个值,jvm会确保其他线程读取到最新值,原子类和voliatile变量也是一样的,这是由依赖于硬件的系统指令(如x86的xchg)实现的。lazySet却是无法保证这一点的方法,所以其他线程在之后的一小段时间里还是可以读到旧的值。

这有什么好处呢?

性能:在多核处理器下,内存以及cpu缓存的读和写常常是顺序执行的,所以在多个cpu缓存之间同步一个内存值的代价是很昂贵的。

如何实现呢?

大多数的原子类,比如AtomicLong本质上都是一个Unsafe和一个volatile Long变量的包装类。值得注意的是AtomicLong.lazySet方法实际是调用了本地方法Unsafe.putOrderedLong,本地方法Unsafe.putOrderedLong的实现可以参考http://hg.openjdk.java.net/jdk7/…。从Unsafe的代码中可以发现Unsafe_setOrderedLong是一个本地方法(c++实现),它仅调用了SET_FIELD_VOLATILE,这很是奇怪,我们期望共享的Unsafe_setLongVolatile拥有不同的语义。PS:在非增强版本中,setOrdered仅仅是调用了setVolatile方法,很是让人失望。深入查看你会发现其实他们是相同的,SET_FIELD_VOLATILE是一个OrderAccess:release_store_fence的包装。可以在Linux x86的代码http://hg.openjdk.java.net/jdk7/…中找到此方法的实现,在64bit x86系统中采用xchgq来代码,64位版本指令的问题我上面有提到过。

ps:从理论上讲lazySet能比一个标准的volatile变量的写性能更好。但是我在openJdk里没有找到相关代码。

Felix Sulima说:
sun.misc.unsafe很多方法被jvm增强了,JIT(just in time运行时编译执行的技术)直接解释而忽略原始的实现。可以在这里找到这个例子:src/share/vm/classfile/vmSymbols.hpp@3facbb14e873列表中的native方法仅仅是非JIT环境下的一个备份的内部方法。例如,如果它没有被调用(我也不知道是什么原因),因此这些方法缺乏一些必要的优化。从Talk from JAX London的幻灯片11-12可以看到AtomicLong.lazySet(…)在x86系统上会被编译成“mov”指令。这里是Google Group里关于如何获得JIT装配的一个描述。

文章转自 并发编程网-ifeve.com

时间: 2024-09-20 07:42:45

AtomicLong.lazySet是如何工作的?的相关文章

Java中的Atomic包使用指南

引言 Java从JDK1.5开始提供了java.util.concurrent.atomic包,方便程序员在多线程环境下,无锁的进行原子操作.原子变量的底层使用了处理器提供的原子指令,但是不同的CPU架构可能提供的原子指令不一样,也有可能需要某种形式的内部锁,所以该方法不能绝对保证线程不被阻塞. Atomic包介绍 在Atomic包里一共有12个类,四种原子更新方式,分别是原子更新基本类型,原子更新数组,原子更新引用和原子更新字段.Atomic包里的类基本都是使用Unsafe实现的包装类. 原子

java-Atomic包

Java从JDK1.5开始提供了java.util.concurrent.atomic包,方便程序员在多线程环境下,无锁的进行原子操作.原子变量的底层使用了处理器提供的原子指令,但是不同的CPU架构可能提供的原子指令不一样,也有可能需要某种形式的内部锁,所以该方法不能绝对保证线程不被阻塞. Atomic包里一共有12个类,四种原子更新方式,分别是原子更新基本类型,原子更新数组,原子更新引用和原子更新字段.Atomic包里的类基本都是使用Unsafe实现的包装类. 原子更新基本类型类 用于通过原子

JUC中Atomic class之lazySet的一点疑惑

JUC中Atomic class之lazySet的一点疑惑 最近再次翻netty和disrupt的源码, 发现一些地方使用AtomicXXX.lazySet()/unsafe.putOrderedXXX系列, 以前一直没有注意lazySet这个方法, 仔细研究一下发现很有意思.我们拿AtomicReferenceFieldUpdater的set()和lazySet()作比较, 其他AtomicXXX类和这个类似. public void set(T obj, V newValue) { // .

写日志的那些事儿

写日志简介 一般提到写日志,主要有下面几种不同的场景: 诊断日志:应用打印异常信息,排查问题用,一般是给人看的,输出格式会比较随意,里面可能会有异常堆栈,或者排查问题用的一些文本信息: 数据日志:一般是用来做监控和数据分析的,可以人肉临时分析,也可以给机器分析,要求格式比较固定: 交易日志:一般在日志式文件系统.NoSQL.DB 中使用,一般有 journaling,WAL(write-ahead logging),binlog.这种日志通常都不是给人看的. EagleEye 写的日志,是数据日

Java多线程:“JUC原子类”02之AtomicLong原子类

AtomicLong介绍和函数列表 AtomicLong是作用是对长整形进行原子操作. 在32位操作系统中,64位的long 和 double 变量由 于会被JVM当作两个分离的32位来进行操作,所以不具有原子性.而使用AtomicLong能让long的操作保持 原子型. AtomicLong函数列表 // 构造函数 AtomicLong() // 创建值为initialValue的AtomicLong对象 AtomicLong(long initialValue) // 以原子方式设置当前值为

路由器QOS功能原理和工作方式

设置路由器时,大多会用到路由器的安全机制,也就常说的QOS功能,QOS功能可以保护整个网络的安全,本篇带你了解其具体的原理和工作的方式. 一.QOS用来解决带宽解决网络延迟和阻塞等问题的一种技术,一般里面包含优先级别.弹性带宽管理等等,主要用来解决各种网络的攻击和病毒,保护网络的正常运行,它主要有以下几个方面的功能: 1.端口优先:可针对源端口.目的端口进行设置优先的级别,一般来说如果是玩游戏为主.那么我可以针对一些主流游戏的端口.优先这些游戏的带宽. 2.IP/网段优先:可针对源IP.目的IP

使用Putty的Telnet及SSH功能进行相关工作

说实话,我不习惯命令行的操作.但是有些工作必须要使用命令行才能完成操作.比如公司的网络设备,都是通过命令行. 唉,没有办法只能去适应了.先来说说Telnet吧.以前我认为Telnet因为是明文的方式进行传输,在实际工作中使用的比较少.但是目前看来我错了,而且错的很离谱呢. 公司很多的管理都是通过Telnet进行的. 除此之外,还有SSH.这个我还是知道的.相对于Telnet来说,SSH还是很安全的. 平时使用Telnet时,要么是使用本机自带的Telnet客户端.操作起来还行,但是前提是本机一定

阿里年会的马老师说:认真生活、快乐工作、保持理想

9月8日,阿里巴巴集团18周年年会上,马云老师这样说. 我们要感谢这个时代.感谢互联网.感谢中国.感谢所有的同事,包括那些曾经在阿里巴巴工作过哪怕半个小时的人. 18年来变化最大的,是我们从18个人变成了截至昨晚54421名员工,来自70个不同的国家,我们在21个国家和地区有自己的办事处.以前创业的时候我们天天都开员工大会,现在开员工大会起码得筹备一年,搞得满城风雨.当年创业的时候,我们18人的创业团队讲总有一天,阿里巴巴会美女如云,良将如草.现在,阿里巴巴已经拥有了22000名"美女"

你真的了解:IIS连接数、IIS并发连接数、IIS最大并发工作线程数、应用程序池的队列长度、应用程序池的最大工作进程数 吗?

原文:你真的了解:IIS连接数.IIS并发连接数.IIS最大并发工作线程数.应用程序池的队列长度.应用程序池的最大工作进程数 吗? IIS连接数   一般购买过虚拟主机的朋友都熟悉购买时,会限制IIS连接数,这边先从普通不懂代码用户角度理解IIS连接数 顾名思义即为IIS服务器可以同时容纳客户请求的最高连接数,准确的说应该叫"IIS限制连接数" 这边客户请求的连接内容包括: 1.网站html请求,html中的图片资源,html中的脚本资源,其他需要连接下载的资源等等,任何一个资源的请求