Skip to content

Commit

Permalink
Improve implementation of double-check idiom by using a temp var to r…
Browse files Browse the repository at this point in the history
…educe the number of accesses to the volatile field in the common scenario
  • Loading branch information
asoldano committed Oct 27, 2015
1 parent a6fe290 commit b8f0a64
Show file tree
Hide file tree
Showing 2 changed files with 48 additions and 41 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -46,18 +46,21 @@ public WSComponent(final WSComponentCreateService createService) {
}

public BasicComponentInstance getComponentInstance() {
if (wsComponentInstance == null) {
synchronized (lock) {
if (wsComponentInstance == null && reference == null) {
wsComponentInstance = (BasicComponentInstance) createInstance();
}
if (wsComponentInstance == null && reference != null) {
wsComponentInstance = (BasicComponentInstance) this.createInstance(reference.getInstance());
}
}
}
return wsComponentInstance;
}
BasicComponentInstance result = wsComponentInstance;
if (result == null) {
synchronized (lock) {
result = wsComponentInstance;
if (result == null) {
if (reference == null) {
wsComponentInstance = result = (BasicComponentInstance) createInstance();
} else {
wsComponentInstance = result = (BasicComponentInstance) this.createInstance(reference.getInstance());
}
}
}
}
return result;
}

public void setReference(ManagedReference reference) {
this.reference = reference;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,7 @@
*/
abstract class AbstractInvocationHandler extends org.jboss.ws.common.invocation.AbstractInvocationHandler {

private ServiceName componentViewName;
private volatile ServiceName componentViewName;
private volatile ComponentView componentView;
protected volatile ManagedReference reference;

Expand All @@ -63,33 +63,36 @@ public void init(final Endpoint endpoint) {
componentViewName = (ServiceName) endpoint.getProperty(COMPONENT_VIEW_NAME);
}

/**
* Gets endpoint container lazily.
*
* @return endpoint container
*/
protected ComponentView getComponentView() {
// we need to check both, otherwise it is possible for
// componentView to be initialized before reference
if (componentView == null) {
synchronized(this) {
if (componentView == null) {
componentView = getMSCService(componentViewName, ComponentView.class);
if (componentView == null) {
throw WSLogger.ROOT_LOGGER.cannotFindComponentView(componentViewName);
}
if (reference == null) {
try {
reference = componentView.createInstance();
} catch (Exception e) {
throw new RuntimeException(e);
}
}
/**
* Gets endpoint container lazily.
*
* @return endpoint container
*/
protected ComponentView getComponentView() {
ComponentView cv = componentView;
// we need to check both, otherwise it is possible for
// componentView to be initialized before reference
if (cv == null) {
synchronized (this) {
cv = componentView;
if (cv == null) {
cv = getMSCService(componentViewName, ComponentView.class);
if (cv == null) {
throw WSLogger.ROOT_LOGGER.cannotFindComponentView(componentViewName);
}
if (reference == null) {
try {
reference = cv.createInstance();
} catch (Exception e) {
throw new RuntimeException(e);
}
}
componentView = cv;
}
}
}
}
return componentView;
}
}
return cv;
}

/**
* Invokes WS endpoint.
Expand All @@ -106,7 +109,8 @@ public void invoke(final Endpoint endpoint, final Invocation wsInvocation) throw
final ComponentView componentView = getComponentView();
Component component = componentView.getComponent();
//in case of @FactoryType annotation we don't need to go into EE interceptors
if(wsInvocation.getInvocationContext().getProperty("forceTargetBean") != null) {
final boolean forceTargetBean = (wsInvocation.getInvocationContext().getProperty("forceTargetBean") != null);
if (forceTargetBean) {
this.reference = new ManagedReference() {
public void release() {
}
Expand All @@ -126,7 +130,7 @@ public Object getInstance() {
context.setParameters(wsInvocation.getArgs());
context.putPrivateData(Component.class, component);
context.putPrivateData(ComponentView.class, componentView);
if(wsInvocation.getInvocationContext().getProperty("forceTargetBean") != null) {
if(forceTargetBean) {
context.putPrivateData(ManagedReference.class, reference);
}
// invoke method
Expand Down

0 comments on commit b8f0a64

Please sign in to comment.