public static void main(String[] argv) throws Exception { mbean = newPlatformMXBeanProxy(server, THREAD_MXBEAN_NAME, ThreadMXBean.class); if (!mbean.isSynchronizerUsageSupported()) { System.out.println("Monitoring of synchronizer usage not supported"); return; } thread.setDaemon(true); thread.start(); // wait until myThread acquires mutex and lock owner is set. while (!(mutex.isLocked() && mutex.getLockOwner() == thread)) { try { Thread.sleep(100); } catch (InterruptedException e) { throw new RuntimeException(e); } } long[] ids = new long[] {thread.getId()}; // validate the local access ThreadInfo[] infos = getThreadMXBean().getThreadInfo(ids, true, true); if (infos.length != 1) { throw new RuntimeException( "Returned ThreadInfo[] of length=" + infos.length + ". Expected to be 1."); } thread.checkThreadInfo(infos[0]); // validate the remote access infos = mbean.getThreadInfo(ids, true, true); if (infos.length != 1) { throw new RuntimeException( "Returned ThreadInfo[] of length=" + infos.length + ". Expected to be 1."); } thread.checkThreadInfo(infos[0]); boolean found = false; infos = mbean.dumpAllThreads(true, true); for (ThreadInfo ti : infos) { if (ti.getThreadId() == thread.getId()) { thread.checkThreadInfo(ti); found = true; } } if (!found) { throw new RuntimeException("No ThreadInfo found for MyThread"); } System.out.println("Test passed"); }
void checkThreadInfo(ThreadInfo info) { if (!getName().equals(info.getThreadName())) { throw new RuntimeException( "Name: " + info.getThreadName() + " not matched. Expected: " + getName()); } MonitorInfo[] monitors = info.getLockedMonitors(); if (monitors.length != OWNED_MONITORS) { throw new RuntimeException( "Number of locked monitors = " + monitors.length + " not matched. Expected: " + OWNED_MONITORS); } MonitorInfo m = monitors[0]; StackTraceElement ste = m.getLockedStackFrame(); int depth = m.getLockedStackDepth(); StackTraceElement[] stacktrace = info.getStackTrace(); if (!ste.equals(stacktrace[depth])) { System.out.println("LockedStackFrame:- " + ste); System.out.println("StackTrace at " + depth + " :-" + stacktrace[depth]); throw new RuntimeException( "LockedStackFrame does not match " + "stack frame in ThreadInfo.getStackTrace"); } String className = lock.getClass().getName(); int hcode = System.identityHashCode(lock); if (!className.equals(m.getClassName()) || hcode != m.getIdentityHashCode() || !m.getLockedStackFrame().getMethodName().equals("run")) { System.out.println(info); throw new RuntimeException("MonitorInfo " + m + " doesn't match."); } LockInfo[] syncs = info.getLockedSynchronizers(); if (syncs.length != OWNED_SYNCS) { throw new RuntimeException( "Number of locked syncs = " + syncs.length + " not matched. Expected: " + OWNED_SYNCS); } AbstractOwnableSynchronizer s = mutex.getSync(); String lockName = s.getClass().getName(); hcode = System.identityHashCode(s); if (!lockName.equals(syncs[0].getClassName())) { throw new RuntimeException( "LockInfo : " + syncs[0] + " class name not matched. Expected: " + lockName); } if (hcode != syncs[0].getIdentityHashCode()) { throw new RuntimeException( "LockInfo: " + syncs[0] + " IdentityHashCode not matched. Expected: " + hcode); } LockInfo li = info.getLockInfo(); if (li == null) { throw new RuntimeException("Expected non-null LockInfo"); } }
public void run() { synchronized (lock) { mutex.lock(); Object o = new Object(); synchronized (o) { try { o.wait(); } catch (InterruptedException e) { throw new RuntimeException(e); } } } }