Package marauroa.common.crypto

Source Code of marauroa.common.crypto.RSAKey

/* $Id: RSAKey.java,v 1.9 2009/12/28 01:15:19 nhnb Exp $ */
/***************************************************************************
*                      (C) Copyright 2003 - Marauroa                      *
***************************************************************************
***************************************************************************
*                                                                         *
*   This program is free software; you can redistribute it and/or modify  *
*   it under the terms of the GNU General Public License as published by  *
*   the Free Software Foundation; either version 2 of the License, or     *
*   (at your option) any later version.                                   *
*                                                                         *
***************************************************************************/
package marauroa.common.crypto;

import java.io.PrintStream;
import java.io.PrintWriter;
import java.math.BigInteger;
import java.security.SecureRandom;

/**
* Implementation of a private RSA Key
*
* @author quisar
*/
public class RSAKey extends RSAPublicKey {

  private final BigInteger d;

  /**
   * creates a new RSAKey object
   *
   * @param n n
   * @param d d
   * @param e e
   */
  public RSAKey(BigInteger n, BigInteger d, BigInteger e) {
    super(n, e);
    this.d = d;
  }

  @Override
  public void print(PrintWriter out) {
    super.print(out);
    out.println("d = " + d);
  }

  @Override
  public void print(PrintStream out) {
    super.print(out);
    out.println("d = " + d);
  }

  /**
   * generates a key pair
   *
   * @param nbBits size of the key
   * @return RSAKey
   */
  public static RSAKey generateKey(int nbBits) {
    BigInteger p;
    BigInteger q;
    BigInteger n;
    BigInteger d;
    BigInteger e = new BigInteger("15");
    BigInteger phi;

    byte[] nonce = new byte[(nbBits / 16) + 1];

    SecureRandom rand;
    try {
      rand = SecureRandom.getInstance("SHA1PRNG");
      rand.nextBytes(nonce);
    } catch (Exception ex) {
      System.err.println("Can't happen...");
      ex.printStackTrace();
    }

    if (nonce[0] >= 0) {
      nonce[0] -= 128;
    }

    p = new BigInteger(1, nonce);

    p = p.subtract(p.remainder(big6)).subtract(big1);
    q = p.subtract(big6);

    // Select two prime numbers, p and q, such
    // that n = p*q > max and the number of
    // characters in n is <= blockSize, where
    // max is the maximum possible data value in
    // a data block.
    // Use the incoming first guess for p and then
    // iterate by increasing the value of p until
    // a highly-probable prime number is
    // found.

    while (!(p.isProbablePrime(1000) && p.multiply(big2).add(big1).isProbablePrime(1000))) {
      p = p.add(big6);
    }// end while loop

    // Make the first guess for q one less than p
    // and then iterate until a highly-probable
    // prime number is found for q that satisfies
    // the two conditions given above.

    // The current value of q satisfies one of
    // the required conditions, but may not be
    // a prime number. Get the next prime number
    // smaller than the current value of q.
    while (!(q.isProbablePrime(1000) && q.multiply(big2).add(big1).isProbablePrime(1000))) {
      q = q.subtract(big6);
    }// end while loop

    p = p.multiply(big2).add(big1);
    q = q.multiply(big2).add(big1);

    // Now we have a prime value for q that
    // satisfies one of the two required
    // conditions. Compute the current value
    // for n and start working to confirm or
    // satisfy the other condition.
    n = p.multiply(q);

    // Compute phi, as (p - 1)*(q - 1).
    BigInteger pPrime = p.subtract(big1);
    BigInteger qPrime = q.subtract(big1);
    phi = pPrime.multiply(qPrime);

    // Compute e. First guess is incoming
    // value.
    while (!e.gcd(phi).equals(big1)) {
      e = e.add(big1);
    }// end while loop

    // Compute the value for d
    d = e.modInverse(phi);
    return new RSAKey(n, d, e);
  }

  /**
   * decodes a BigInteger
   *
   * @param message BigInteger
   * @return decoded BigInteger
   */
  public BigInteger decode(BigInteger message) {
    return message.modPow(d, n);
  }

  /**
   * decodes a byte array
   *
   * @param message array to decode
   * @return decoded array
   */
  public byte[] decodeByteArray(byte[] message) {
    return Hash.bigIntToBytes(decode(new BigInteger(message)));
  }

  /**
   * signs a message
   *
   * @param message message to sign
   * @return signed message
   */
  public BigInteger sign(BigInteger message) {
    return decode(message);
  }

  /**
   * gets the public key
   *
   * @return public key
   */
  public RSAPublicKey getPublicKey() {
    return new RSAPublicKey(n, e);
  }

  /**
   * gets d
   *
   * @return d
   */
  public BigInteger getD() {
    return d;
  }
}
TOP

Related Classes of marauroa.common.crypto.RSAKey

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.