Uploaded image for project: 'WildFly'
  1. WildFly
  2. WFLY-3514

JASPIAuthenticationMechanism#authenticate installs secureResponse handler twice or more



      JASPIAuthenticationMechanism#authenticate installs a response wrapper to later on handle secureResponse.

      This is correct for the initial call to the SAM/context (prior to entering the Servlet pipeline), but this is most likely not correct for a call following HttpServletRequest#authenticate. In many situations this will lead to exceptions about a "requestChannel" already been opened (perhaps this should be "responseChannel"?).

      JASPIAuthenticationMechanism#authenticate contains the following code:

          public AuthenticationMechanismOutcome authenticate(final HttpServerExchange exchange, final SecurityContext sc) {
              final ServletRequestContext requestContext = exchange.getAttachment(ServletRequestContext.ATTACHMENT_KEY);
              final JASPIServerAuthenticationManager sam = createJASPIAuthenticationManager();
              final GenericMessageInfo messageInfo = createMessageInfo(exchange, sc);
              final String applicationIdentifier = buildApplicationIdentifier(requestContext);
          // ...
             secureResponse(exchange, sc, sam, messageInfo, cbh);
              return outcome;

      With secureResponse:

         private void secureResponse(final HttpServerExchange exchange, final SecurityContext securityContext, final JASPIServerAuthenticationManager sam, final GenericMessageInfo messageInfo, final JASPICallbackHandler cbh) {
              // we add a response wrapper to properly invoke the secureResponse, after processing the destination
              exchange.addResponseWrapper(new ConduitWrapper<StreamSinkConduit>() {
                  public StreamSinkConduit wrap(final ConduitFactory<StreamSinkConduit> factory, final HttpServerExchange exchange) {
                      ServletRequestContext requestContext = exchange.getAttachment(ServletRequestContext.ATTACHMENT_KEY);
                      String applicationIdentifier = buildApplicationIdentifier(requestContext);
                      // ...
                      return factory.create();

      As can be seen, every call to authenticate attempts to install the handler again.

      I guess secureResponse should somehow check if the call was made from request#authenticate, or that it was done at the beginning of the request, or simply remember whether a registration has already been made or not.

      I patched the code locally to use a request attribute to implement the last option and this seems to work.

        Gliffy Diagrams




              • Assignee:
                swd847 Stuart Douglas
                atijms Arjan Tijms
              • Votes:
                0 Vote for this issue
                2 Start watching this issue


                • Created: