Skip to content

Commit

Permalink
Make RESTEasy Reactive handlers calls monomorphic
Browse files Browse the repository at this point in the history
This looks ugly, but it results in better performance

(cherry picked from commit 65dd4d4)
  • Loading branch information
geoand authored and gsmet committed May 16, 2022
1 parent 083e22b commit fa4c991
Show file tree
Hide file tree
Showing 2 changed files with 53 additions and 1 deletion.
Original file line number Diff line number Diff line change
Expand Up @@ -69,4 +69,52 @@ public void handleUnmappedException(Throwable throwable) {
private <E extends Throwable> RuntimeException sneakyThrow(Throwable e) throws E {
throw (E) e;
}

/**
* The implementation looks like it makes no sense, but it in fact does make sense from a performance perspective.
* The idea is to reduce the use instances of megamorphic calls into a series of instance checks and monomorphic calls.
* The rationale behind this is fully explored in
* https://shipilev.net/blog/2015/black-magic-method-dispatch/#_cheating_the_runtime_2
* and this specific instance has been verified experimentally to result in better performance.
*/
@Override
protected void invokeHandler(int pos) throws Exception {
var handler = handlers[pos];
if (handler instanceof org.jboss.resteasy.reactive.server.handlers.MatrixParamHandler) {
handler.handle(this);
} else if (handler instanceof io.quarkus.resteasy.reactive.server.runtime.security.SecurityContextOverrideHandler) {
handler.handle(this);
} else if (handler instanceof org.jboss.resteasy.reactive.server.handlers.RestInitialHandler) {
handler.handle(this);
} else if (handler instanceof org.jboss.resteasy.reactive.server.handlers.ClassRoutingHandler) {
handler.handle(this);
} else if (handler instanceof org.jboss.resteasy.reactive.server.handlers.AbortChainHandler) {
handler.handle(this);
} else if (handler instanceof org.jboss.resteasy.reactive.server.handlers.NonBlockingHandler) {
handler.handle(this);
} else if (handler instanceof org.jboss.resteasy.reactive.server.handlers.BlockingHandler) {
handler.handle(this);
} else if (handler instanceof org.jboss.resteasy.reactive.server.handlers.ResourceRequestFilterHandler) {
handler.handle(this);
} else if (handler instanceof org.jboss.resteasy.reactive.server.handlers.InputHandler) {
handler.handle(this);
} else if (handler instanceof org.jboss.resteasy.reactive.server.handlers.RequestDeserializeHandler) {
handler.handle(this);
} else if (handler instanceof org.jboss.resteasy.reactive.server.handlers.ParameterHandler) {
handler.handle(this);
} else if (handler instanceof org.jboss.resteasy.reactive.server.handlers.InstanceHandler) {
handler.handle(this);
} else if (handler instanceof org.jboss.resteasy.reactive.server.handlers.InvocationHandler) {
handler.handle(this);
} else if (handler instanceof org.jboss.resteasy.reactive.server.handlers.FixedProducesHandler) {
handler.handle(this);
} else if (handler instanceof org.jboss.resteasy.reactive.server.handlers.ResponseHandler) {
handler.handle(this);
} else if (handler instanceof org.jboss.resteasy.reactive.server.handlers.ResponseWriterHandler) {
handler.handle(this);
} else {
// megamorphic call for other handlers
handler.handle(this);
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -138,7 +138,7 @@ public void run() {
int pos = position;
position++; //increment before, as reset may reset it to zero
try {
handlers[pos].handle((T) this);
invokeHandler(pos);
if (suspended) {
synchronized (this) {
// as running is not volatile but instead read from inside the same monitor,
Expand Down Expand Up @@ -215,6 +215,10 @@ public void run() {
}
}

protected void invokeHandler(int pos) throws Exception {
handlers[pos].handle((T) this);
}

protected void beginAsyncProcessing() {

}
Expand Down

0 comments on commit fa4c991

Please sign in to comment.