Package net.jini.jeri.ssl

Source Code of net.jini.jeri.ssl.ConnectionContext

/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements.  See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
*      http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

package net.jini.jeri.ssl;

import java.security.Principal;
import java.util.Iterator;
import java.util.Set;
import javax.security.auth.x500.X500Principal;
import net.jini.core.constraint.ClientAuthentication;
import net.jini.core.constraint.ClientMaxPrincipal;
import net.jini.core.constraint.ClientMaxPrincipalType;
import net.jini.core.constraint.ClientMinPrincipal;
import net.jini.core.constraint.ClientMinPrincipalType;
import net.jini.core.constraint.Confidentiality;
import net.jini.core.constraint.ConnectionAbsoluteTime;
import net.jini.core.constraint.ConnectionRelativeTime;
import net.jini.core.constraint.ConstraintAlternatives;
import net.jini.core.constraint.Delegation;
import net.jini.core.constraint.DelegationAbsoluteTime;
import net.jini.core.constraint.DelegationRelativeTime;
import net.jini.core.constraint.Integrity;
import net.jini.core.constraint.InvocationConstraint;
import net.jini.core.constraint.InvocationConstraints;
import net.jini.core.constraint.ServerAuthentication;
import net.jini.core.constraint.ServerMinPrincipal;

/**
* Records information about a connection used for a remote call and determines
* whether the connection could support specific constraints. <p>
*
* Does not support heterogeneous constraint alternatives.  As a result,
* callers can be assured that the choice of possible principals or of
* Integrity.YES is independent of the suites, insuring that those items can be
* picked before negotiating the cipher suite.
*
* @author Sun Microsystems, Inc.
*/
final class ConnectionContext extends Utilities {

    /** Constraints supported, without integrity or connection timeout */
    private static final long OK = Long.MAX_VALUE;

    /** Constraints supported with codebase integrity */
    private static final long INTEGRITY = -3;

    /** Constraints not supported */
    private static final long NOT_SUPPORTED = -4;

    /** The ClientMinPrincipalType supported by the provider. */
    private static final ClientMinPrincipalType clientMinPrincipalType =
  new ClientMinPrincipalType(X500Principal.class);

    /** The cipher suite */
    final String cipherSuite;

    /** The client principal, or null for an anonymous client */
    final Principal client;

    /** The server principal, or null for an anonymous server */
    final Principal server;

    /** Whether codebase integrity should be enforced */
    private final boolean integrity;

    /**
     * Whether the connection is being considered on the client side, which
     * does not support relative time constraints.
     */
    private final boolean clientSide;

    /** Set to true if the principals and cipher suite conflict */
    private boolean notSupported;

    /** Whether the requirements specify Integrity.YES */
    private boolean integrityRequired;

    /** Whether the preferences specify Integrity.YES */
    private boolean integrityPreferred;

    /** The absolute connection time, or Long.MAX_VALUE if not specified */
    private long connectionTime = Long.MAX_VALUE;

    /** The number of preferences satisfied */
    private int preferences;

    /**
     * Creates an instance that represents using the specified cipher suite,
     * client and server principals, whether to guarantee codebase integrity,
     * and constraints.  Null values for the principals mean they are
     * anonymous.  Non-X.500 principals are permitted to allow specifying a
     * dummy principal if the principal is unknown.  Returns null if the
     * constraints are not supported.
     */
    static ConnectionContext getInstance(String cipherSuite,
           Principal client,
           Principal server,
           boolean integrity,
           boolean clientSide,
           InvocationConstraints constraints)
    {
  ConnectionContext context = new ConnectionContext(
      cipherSuite, client, server, integrity, clientSide);
  return context.supported(constraints) ? context : null;
    }

    /** Creates an instance of this class. */
    private ConnectionContext(String cipherSuite,
            Principal client,
            Principal server,
            boolean integrity,
            boolean clientSide)
    {
  this.cipherSuite = cipherSuite;
  this.client = client;
  this.server = server;
  this.integrity = integrity;
  this.clientSide = clientSide;
  boolean serverAuth = doesServerAuthentication(cipherSuite);
  if (serverAuth != (server != null)
      || (client != null && server == null))
  {
      notSupported = true;
  }
    }

    public String toString() {
  StringBuffer sb = new StringBuffer("ConnectionContext[");
  fieldsToString(sb);
  sb.append("]");
  return sb.toString();
    }

    void fieldsToString(StringBuffer sb) {
  sb.append(cipherSuite);
  if (client != null) {
      sb.append(", client: ").append(client);
  }
  if (server != null) {
      sb.append(", server: ").append(server);
  }
  if (integrityRequired) {
      sb.append(", integrity: required");
  } else if (integrityPreferred) {
      sb.append(", integrity: preferred");
  }
  if (connectionTime != Long.MAX_VALUE) {
      sb.append(", connectionTime = ").append(connectionTime);
  }
  sb.append(", preferences: ").append(preferences);
    }

    /** Returns whether integrity is required. */
    boolean getIntegrityRequired() {
  return integrityRequired;
    }

    /** Returns whether integrity is preferred. */
    boolean getIntegrityPreferred() {
  return integrityPreferred;
    }

    /**
     * Returns the absolute time when the connection should be completed, or
     * Long.MAX_VALUE for no limit.
     */
    long getConnectionTime() {
  return connectionTime;
    }

    /** Returns the number of preferences that can be satisfied. */
    int getPreferences() {
  return preferences;
    }

    /**
     * Checks if the specified constraints are supported, computing
     * integrityRequired, integrityPreferred, connectionTime and preferences as
     * a side effect.
     */
    private boolean supported(InvocationConstraints constraints) {
  if (notSupported) {
      return false;
  }
  for (Iterator i = constraints.requirements().iterator(); i.hasNext(); )
  {
      long r = supported((InvocationConstraint) i.next());
      if (r == NOT_SUPPORTED) {
    return false;
      }
      if (r == INTEGRITY) {
    integrityRequired = true;
      } else if (connectionTime > r) {
    connectionTime = r;
      }
  }
  for (Iterator i = constraints.preferences().iterator(); i.hasNext(); ) {
      long r = supported((InvocationConstraint) i.next());
      if (r == NOT_SUPPORTED) {
        continue;
      }
      preferences++;
      if (r == INTEGRITY) {
    if (!integrityRequired) {
        integrityPreferred = true;
    }
      } else if (connectionTime > r) {
    connectionTime = r;
      }
  }
  if (integrity && !integrityRequired && !integrityPreferred) {
      return false;
  } else {
      return true;
  }
    }

    /**
     * Checks if the constraint is supported, returning NOT_SUPPORTED if it is
     * not supported, INTEGRITY if the constraint is Integrity.YES or
     * constraint alternatives with elements of type Integrity, the connection
     * time if the constraint is an instance of ConnectionAbsoluteTime or
     * constraint alternatives of them, and otherwise OK.
     */
    private long supported(InvocationConstraint constraint) {
  if (constraint instanceof ConstraintAlternatives) {
      return supported((ConstraintAlternatives) constraint);
  } else if (constraint instanceof Integrity) {
      return integrity && constraint == Integrity.YES
    ? INTEGRITY : NOT_SUPPORTED;
  } else if (constraint instanceof Confidentiality) {
      return ok(doesEncryption(cipherSuite) ==
          (constraint == Confidentiality.YES));
  } else if (constraint instanceof ConfidentialityStrength) {
      return ok(!doesEncryption(cipherSuite) ||
          (hasStrongCipherAlgorithm(cipherSuite)
           == (constraint == ConfidentialityStrength.STRONG)));
  } else if (constraint instanceof ClientAuthentication) {
      return ok((client == null) ==
          (constraint == ClientAuthentication.NO));
  } else if (constraint instanceof ClientMinPrincipalType) {
      return ok(client == null ||
          constraint.equals(clientMinPrincipalType));
  } else if (constraint instanceof ClientMaxPrincipalType) {
      return ok(client == null ||
          ((ClientMaxPrincipalType) constraint).elements().contains(
        X500Principal.class));
  } else if (constraint instanceof ClientMinPrincipal) {
      if (client == null) {
    return OK;
      }
      Set elements = ((ClientMinPrincipal) constraint).elements();
      return ok(elements.size() == 1 && elements.contains(client));
  } else if (constraint instanceof ClientMaxPrincipal) {
      return ok(client == null ||
          ((ClientMaxPrincipal) constraint).elements().contains(
        client));
  } else if (constraint instanceof Delegation) {
      return ok(client == null || (constraint == Delegation.NO));
  } else if (constraint instanceof DelegationAbsoluteTime) {
      return OK;
  } else if (constraint instanceof DelegationRelativeTime) {
      return ok(!clientSide);
  } else if (constraint instanceof ServerAuthentication) {
      return ok((server == null) ==
          (constraint == ServerAuthentication.NO));
  } else if (constraint instanceof ServerMinPrincipal) {
      if (server == null) {
    return OK;
      }
      Set elements = ((ServerMinPrincipal) constraint).elements();
      return ok(elements.size() == 1 && elements.contains(server));
  } else if (constraint instanceof ConnectionAbsoluteTime) {
      return Math.max(((ConnectionAbsoluteTime) constraint).getTime(), 0);
  } else if (constraint instanceof ConnectionRelativeTime) {
      return ok(!clientSide);
  } else {
      return NOT_SUPPORTED;
  }
    }

    /** Returns OK if the argument is true, else NOT_SUPPORTED. */
    private static long ok(boolean ok) {
  return ok ? OK : NOT_SUPPORTED;
    }

    /**
     * Checks if the constraint alternatives are supported, returning
     * NOT_SUPPORTED if the elements have different types or none are
     * supported, INTEGRITY if the elements are instances of Integrity, the
     * largest connection time if the elements are instances of
     * ConnectionAbsoluteTime, and otherwise OK.
     */
    private long supported(ConstraintAlternatives constraint) {
  Set alts = constraint.elements();
  long connectionTime = -1;
  Class type = null;
  boolean supported = false;
  boolean integrity = false;
  for (Iterator i = alts.iterator(); i.hasNext(); ) {
      InvocationConstraint alt = (InvocationConstraint) i.next();
      if (type == null) {
    type = alt.getClass();
      } else if (type != alt.getClass()) {
    return NOT_SUPPORTED;
      }
      long r = supported(alt);
      if (r != NOT_SUPPORTED) {
    supported = true;
    if (r == INTEGRITY) {
        integrity = true;
    } else if (r > connectionTime) {
        connectionTime = r;
    }
      }
  }
  if (!supported) {
      return NOT_SUPPORTED;
  } else if (integrity) {
      return INTEGRITY;
  } else if (connectionTime >= 0) {
      return connectionTime;
  } else {
      return OK;
  }
    }
}
TOP

Related Classes of net.jini.jeri.ssl.ConnectionContext

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.