/// <summary> /// Constructor for a new JPakeParticipant. /// /// After construction, the State state will be STATE_INITIALIZED. /// /// Throws NullReferenceException if any argument is null. Throws /// ArgumentException if password is empty. /// </summary> /// <param name="participantId">Unique identifier of this participant. /// The two participants in the exchange must NOT share the same id.</param> /// <param name="password">Shared secret. /// A defensive copy of this array is made (and cleared once CalculateKeyingMaterial() is called). /// Caller should clear the input password as soon as possible.</param> /// <param name="group">Prime order group. See JPakePrimeOrderGroups for standard groups.</param> /// <param name="digest">Digest to use during zero knowledge proofs and key confirmation /// (SHA-256 or stronger preferred).</param> /// <param name="random">Source of secure random data for x1 and x2, and for the zero knowledge proofs.</param> public JPakeParticipant(string participantId, char[] password, JPakePrimeOrderGroup group, IDigest digest, SecureRandom random) { JPakeUtilities.ValidateNotNull(participantId, "participantId"); JPakeUtilities.ValidateNotNull(password, "password"); JPakeUtilities.ValidateNotNull(group, "p"); JPakeUtilities.ValidateNotNull(digest, "digest"); JPakeUtilities.ValidateNotNull(random, "random"); if (password.Length == 0) { throw new ArgumentException("Password must not be empty."); } this.participantId = participantId; // Create a defensive copy so as to fully encapsulate the password. // // This array will contain the password for the lifetime of this // participant BEFORE CalculateKeyingMaterial() is called. // // i.e. When CalculateKeyingMaterial() is called, the array will be cleared // in order to remove the password from memory. // // The caller is responsible for clearing the original password array // given as input to this constructor. this.password = new char[password.Length]; Array.Copy(password, this.password, password.Length); this.p = group.P; this.q = group.Q; this.g = group.G; this.digest = digest; this.random = random; this.state = STATE_INITIALIZED; }
/// <summary> /// Convenience constructor for a new JPakeParticipant that uses /// a SHA-256 digest, and a default SecureRandom implementation. /// /// After construction, the State state will be STATE_INITIALIZED. /// /// Throws NullReferenceException if any argument is null. Throws /// ArgumentException if password is empty. /// </summary> /// <param name="participantId">Unique identifier of this participant. /// The two participants in the exchange must NOT share the same id.</param> /// <param name="password">Shared secret. /// A defensive copy of this array is made (and cleared once CalculateKeyingMaterial() is called). /// Caller should clear the input password as soon as possible.</param> /// <param name="group">Prime order group. See JPakePrimeOrderGroups for standard groups.</param> public JPakeParticipant(string participantId, char[] password, JPakePrimeOrderGroup group) : this(participantId, password, group, new Sha256Digest(), new SecureRandom()) { }