/**
   * Generates the localized key for the given password and engine id for the privacy protocol
   * specified by the supplied OID.
   *
   * @param privProtocolID an <code>OID</code> identifying the privacy protocol the key should be
   *     created for.
   * @param authProtocolID an <code>OID</code> identifying the authentication protocol to use.
   * @param passwordString the authentication pass phrase.
   * @param engineID the engine ID of the authoritative engine.
   * @return the localized privacy key.
   */
  public byte[] passwordToKey(
      OID privProtocolID, OID authProtocolID, OctetString passwordString, byte[] engineID) {

    AuthenticationProtocol authProtocol = authProtocols.get(authProtocolID);
    if (authProtocol == null) {
      return null;
    }
    PrivacyProtocol privProtocol = privProtocols.get(privProtocolID);
    if (privProtocol == null) {
      return null;
    }
    byte[] key = authProtocol.passwordToKey(passwordString, engineID);

    if (key == null) {
      return null;
    }
    if (key.length >= privProtocol.getMinKeyLength()) {
      if (key.length > privProtocol.getMaxKeyLength()) {
        // truncate key
        byte[] truncatedKey = new byte[privProtocol.getMaxKeyLength()];
        System.arraycopy(key, 0, truncatedKey, 0, privProtocol.getMaxKeyLength());
        return truncatedKey;
      }
      return key;
    }
    // extend key if necessary
    byte[] extKey = privProtocol.extendShortKey(key, passwordString, engineID, authProtocol);
    return extKey;
  }
  /**
   * Generates the localized key for the given password and engine id for the authentication
   * protocol specified by the supplied OID.
   *
   * @param authProtocolID an <code>OID</code> identifying the authentication protocol to use.
   * @param passwordString the authentication pass phrase.
   * @param engineID the engine ID of the authoritative engine.
   * @return the localized authentication key.
   */
  public byte[] passwordToKey(OID authProtocolID, OctetString passwordString, byte[] engineID) {

    AuthenticationProtocol protocol = authProtocols.get(authProtocolID);
    if (protocol == null) {
      return null;
    }
    return protocol.passwordToKey(passwordString, engineID);
  }
 /**
  * Add the given {@link AuthenticationProtocol}. If an authentication protocol with the supplied
  * ID already exists, the supplied authentication protocol will not be added and the security
  * protocols will not be unchang.
  *
  * @param auth the AuthenticationProtocol to add (an existing authentication protcol with <code>
  *     auth</code>'s ID remains unchanged).
  */
 public synchronized void addAuthenticationProtocol(AuthenticationProtocol auth) {
   if (authProtocols.get(auth.getID()) == null) {
     authProtocols.put(auth.getID(), auth);
     if (auth.getDigestLength() > maxAuthDigestLength) {
       maxAuthDigestLength = auth.getDigestLength();
     }
   }
 }
 /**
  * Remove the given {@link AuthenticationProtocol}.
  *
  * @param auth The protocol to remove
  */
 public void removeAuthenticationProtocol(AuthenticationProtocol auth) {
   authProtocols.remove(auth.getID());
 }