java中的monitor

1)从java的视角看synchronized

synchronized使用的锁对象(monitor)存储在java对象头中。

monitor对象:
	1)每个java对象都拥有一个Monitor锁(别问我为什么,虚拟机就是这样设计的)。	
	2)当一个monitor被持有后,它将处于锁定状态。

2)从C++源码看synchronized (参考:https://www.cnblogs.com/dennyzhangdd/p/6734638.html)

oopDesc ---> markOopDesc monitor()方法 --> ObjectMonitor 即 monitor -> monitor enter、monitor exit

1)openjdk\hotspot\src\share\vm\oops\oop.hpp下的oopDesc类是JVM对象的顶级基类,故每个object都包含markOop。

	class oopDesc {
		friend class VMStructs;
		private:
			volatile markOop _mark;		//标记字段(Mark Word)
			union _metadata {
				Klass*      _klass;		//对象类型元数据的指针
				narrowKlass _compressed_klass;
			} _metadata;

			// Fast access to barrier set.  Must be initialized.
			static BarrierSet* _bs;

		public:
			markOop  mark() const         { return _mark; }
			markOop* mark_addr() const    { return (markOop*) &_mark; }

			void set_mark(volatile markOop m)      { _mark = m;   }

			void    release_set_mark(markOop m);
			markOop cas_set_mark(markOop new_mark, markOop old_mark);

			// Used only to re-initialize the mark word (e.g., of promoted
			// objects during a GC) -- requires a valid klass pointer
			void init_mark();

			Klass* klass() const;
			Klass* klass_or_null() const volatile;
			Klass** klass_addr();
			narrowKlass* compressed_klass_addr();
		....省略...
	}
	
2)markOopDesc继承自oopDesc,并拓展了自己的方法monitor(),该方法返回一个ObjectMonitor*对象指针。

	ObjectMonitor* monitor() const {
		assert(has_monitor(), "check");
		// Use xor instead of &~ to provide one extra tag-bit check.
		return (ObjectMonitor*) (value() ^ monitor_value);

		//	-------------- 补充 ---------------------
		//	value()的实现: uintptr_t value() const { return (uintptr_t) this; }
		//		
		//	monitor_value的实现:
		//		enum {
		//			locked_value             = 0,//00偏向锁 
		//			unlocked_value           = 1,//01无锁
		//			monitor_value            = 2,//10监视器锁,又叫重量级锁
		//			marked_value             = 3,//11GC标记
		//			biased_lock_pattern      = 5 //101偏向锁
		//		};
		//	-------------- 补充 ---------------------
	}
	
3)在HotSpot虚拟机中,采用ObjectMonitor类来实现monitor。

	openjdk\hotspot\src\share\vm\runtime\objectMonitor.hpp源码如下:

		ObjectMonitor() {
			_header       = NULL;//markOop对象头
			_count        = 0;
			_waiters      = 0,//等待线程数
			_recursions   = 0;//重入次数
			_object       = NULL;
			_owner        = NULL;//指向获得ObjectMonitor对象的线程或基础锁
			_WaitSet      = NULL;//处于wait状态的线程,会被加入到wait set;
			_WaitSetLock  = 0 ;
			_Responsible  = NULL ;
			_succ         = NULL ;
			_cxq          = NULL ;
			FreeNext      = NULL ;
			_EntryList    = NULL ;//处于等待锁block状态的线程,会被加入到entry set;
			_SpinFreq     = 0 ;
			_SpinClock    = 0 ;
			OwnerIsThread = 0 ;// _owner is (Thread *) vs SP/BasicLock
			_previous_owner_tid = 0;// 监视器前一个拥有者线程的ID
		}

转载于:https://my.oschina.net/u/1399755/blog/1787178

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值