Skip to content

Commit

Permalink
Relax synchronization on class transformation
Browse files Browse the repository at this point in the history
  • Loading branch information
jbachorik committed Nov 11, 2018
1 parent 5dc1408 commit e601842
Showing 1 changed file with 63 additions and 45 deletions.
108 changes: 63 additions & 45 deletions src/share/classes/com/sun/btrace/runtime/BTraceTransformer.java
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@
import java.util.Collection;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.locks.ReentrantReadWriteLock;
import java.util.regex.Pattern;

/**
Expand Down Expand Up @@ -130,24 +131,35 @@ public Result matchClass(String className) {
}
}
private final DebugSupport debug;
private final ReentrantReadWriteLock setupLock = new ReentrantReadWriteLock();
private final Collection<BTraceProbe> probes = new ArrayList<>(3);
private final Filter filter = new Filter();

public BTraceTransformer(DebugSupport d) {
debug = d;
}

public final synchronized void register(BTraceProbe p) {
probes.add(p);
for(OnMethod om : p.onmethods()) {
filter.add(om);
public final void register(BTraceProbe p) {
try {
setupLock.writeLock().lock();
probes.add(p);
for(OnMethod om : p.onmethods()) {
filter.add(om);
}
} finally {
setupLock.writeLock().unlock();
}
}

public final synchronized void unregister(BTraceProbe p) {
probes.remove(p);
for(OnMethod om : p.onmethods()) {
filter.remove(om);
public final void unregister(BTraceProbe p) {
try {
setupLock.writeLock().lock();
probes.remove(p);
for(OnMethod om : p.onmethods()) {
filter.remove(om);
}
} finally {
setupLock.writeLock().unlock();
}
}

Expand All @@ -156,54 +168,60 @@ Filter getFilter() {
}

@Override
public synchronized byte[] transform(ClassLoader loader, String className, Class<?> classBeingRedefined, ProtectionDomain protectionDomain, byte[] classfileBuffer) throws IllegalClassFormatException {
if (probes.isEmpty()) return null;
public byte[] transform(ClassLoader loader, String className, Class<?> classBeingRedefined, ProtectionDomain protectionDomain, byte[] classfileBuffer) throws IllegalClassFormatException {
try {
setupLock.readLock().lock();
if (probes.isEmpty()) return null;

className = className != null ? className : "<anonymous>";
className = className != null ? className : "<anonymous>";

if ((loader == null || loader.equals(ClassLoader.getSystemClassLoader())) && isSensitiveClass(className)) {
if (isDebug()) {
debugPrint("skipping transform for BTrace class " + className); // NOI18N
if ((loader == null || loader.equals(ClassLoader.getSystemClassLoader())) && isSensitiveClass(className)) {
if (isDebug()) {
debugPrint("skipping transform for BTrace class " + className); // NOI18N
}
return null;
}
return null;
}

if (filter.matchClass(className) == Filter.Result.FALSE) return null;
if (filter.matchClass(className) == Filter.Result.FALSE) return null;

boolean entered = BTraceRuntime.enter();
try {
if (isDebug()) {
debug.dumpClass(className.replace('.', '/') + "_orig", classfileBuffer);
}
BTraceClassReader cr = InstrumentUtils.newClassReader(loader, classfileBuffer);
BTraceClassWriter cw = InstrumentUtils.newClassWriter(cr);
for(BTraceProbe p : probes) {
p.notifyTransform(className);
cw.addInstrumentor(p, loader);
}
byte[] transformed = cw.instrument();
if (transformed == null) {
// no instrumentation necessary
boolean entered = BTraceRuntime.enter();
try {
if (isDebug()) {
debugPrint("skipping class " + cr.getJavaClassName());
debug.dumpClass(className.replace('.', '/') + "_orig", classfileBuffer);
}
return classfileBuffer;
} else {
if (isDebug()) {
debugPrint("transformed class " + cr.getJavaClassName());
BTraceClassReader cr = InstrumentUtils.newClassReader(loader, classfileBuffer);
BTraceClassWriter cw = InstrumentUtils.newClassWriter(cr);
for(BTraceProbe p : probes) {
p.notifyTransform(className);
cw.addInstrumentor(p, loader);
}
byte[] transformed = cw.instrument();
if (transformed == null) {
// no instrumentation necessary
if (isDebug()) {
debugPrint("skipping class " + cr.getJavaClassName());
}
return classfileBuffer;
} else {
if (isDebug()) {
debugPrint("transformed class " + cr.getJavaClassName());
}
if (debug.isDumpClasses()) {
debug.dumpClass(className.replace('.', '/'), transformed);
}
}
if (debug.isDumpClasses()) {
debug.dumpClass(className.replace('.', '/'), transformed);
return transformed;
} catch (Throwable th) {
debugPrint(th);
throw th;
} finally {
if (entered) {
BTraceRuntime.leave();
}
System.err.println("*** <<< Thread: " + Thread.currentThread().getName());
}
return transformed;
} catch (Throwable th) {
debugPrint(th);
throw th;
} finally {
if (entered) {
BTraceRuntime.leave();
}
setupLock.readLock().unlock();
}
}

Expand Down

0 comments on commit e601842

Please sign in to comment.