docs: public void authenticate(final PacketOutputStream out, final PacketInputStream in, final AtomicInteger sequence,
                             final String servicePrincipalName, String mechanisms) throws SQLException, IOException {
  
      if ("".equals(servicePrincipalName)) {
        throw new SQLException("No principal name defined on server. "
            + "Please set server variable \"gssapi-principal-name\" or set option \"servicePrincipalName\"", "28000");
      }
  
      if (System.getProperty("java.security.auth.login.config") == null) {
        final File jaasConfFile;
        try {
          jaasConfFile = File.createTempFile("jaas.conf", null);
          try (PrintStream bos = new PrintStream(new FileOutputStream(jaasConfFile))) {
            bos.print("Krb5ConnectorContext {\n"
                + "com.sun.security.auth.module.Krb5LoginModule required "
                + "useTicketCache=true "
                + "debug=true "
                + "renewTGT=true "
                + "doNotPrompt=true; };");
          }
          jaasConfFile.deleteOnExit();
        } catch (final IOException ex) {
          throw new UncheckedIOException(ex);
        }
  
        System.setProperty("java.security.auth.login.config", jaasConfFile.getCanonicalPath());
      }
      try {
        LoginContext loginContext = new LoginContext("Krb5ConnectorContext");
        // attempt authentication
        loginContext.login();
        final Subject mySubject = loginContext.getSubject();
        if (!mySubject.getPrincipals().isEmpty()) {
          try {
            PrivilegedExceptionAction<Void> action = () -> {
              try {
                Oid krb5Mechanism = new Oid("1.2.840.113554.1.2.2");
  
                GSSManager manager = GSSManager.getInstance();
                GSSName peerName = manager.createName(servicePrincipalName, GSSName.NT_USER_NAME);
                GSSContext context =
                    manager.createContext(peerName,
                        krb5Mechanism,
                        null,
                        GSSContext.DEFAULT_LIFETIME);
                context.requestMutualAuth(true);
  
                byte[] inToken = new byte[0];
                byte[] outToken;
                while (!context.isEstablished()) {
  
                  outToken = context.initSecContext(inToken, 0, inToken.length);
  
                  // Send a token to the peer if one was generated by acceptSecContext
                  if (outToken != null) {
                    out.startPacket(sequence.incrementAndGet());
                    out.write(outToken);
                    out.flush();
                  }
                  if (!context.isEstablished()) {
                    Buffer buffer = in.getPacket(true);
                    sequence.set(in.getLastPacketSeq());
                    inToken = buffer.readRawBytes(buffer.remaining());
                  }
                }
  
              } catch (GSSException le) {
                throw new SQLException("GSS-API authentication exception", "28000", 1045, le);
              }
              return null;
            };
            Subject.doAs(mySubject, action);
          } catch (PrivilegedActionException exception) {
            throw new SQLException("GSS-API authentication exception", "28000", 1045, exception);
          }
        } else {
          throw new SQLException("GSS-API authentication exception : no credential cache not found.",
              "28000", 1045);
        }
  
      } catch (LoginException le) {
        throw new SQLException("GSS-API authentication exception", "28000", 1045, le);
      }
    }