Home | History | Annotate | Download | only in rsa
      1 package org.bouncycastle.jcajce.provider.asymmetric.rsa;
      2 
      3 import java.io.EOFException;
      4 import java.io.IOException;
      5 import java.io.ObjectInputStream;
      6 import java.io.ObjectOutputStream;
      7 import java.io.OptionalDataException;
      8 import java.math.BigInteger;
      9 import java.security.interfaces.RSAPublicKey;
     10 import java.security.spec.RSAPublicKeySpec;
     11 
     12 import org.bouncycastle.asn1.DERNull;
     13 import org.bouncycastle.asn1.pkcs.PKCSObjectIdentifiers;
     14 import org.bouncycastle.asn1.x509.AlgorithmIdentifier;
     15 import org.bouncycastle.asn1.x509.SubjectPublicKeyInfo;
     16 import org.bouncycastle.crypto.params.RSAKeyParameters;
     17 import org.bouncycastle.jcajce.provider.asymmetric.util.KeyUtil;
     18 import org.bouncycastle.util.Strings;
     19 
     20 public class BCRSAPublicKey
     21     implements RSAPublicKey
     22 {
     23     private static final AlgorithmIdentifier DEFAULT_ALGORITHM_IDENTIFIER = new AlgorithmIdentifier(PKCSObjectIdentifiers.rsaEncryption, DERNull.INSTANCE);
     24 
     25     static final long serialVersionUID = 2675817738516720772L;
     26 
     27     private BigInteger modulus;
     28     private BigInteger publicExponent;
     29     private transient AlgorithmIdentifier algorithmIdentifier;
     30 
     31     BCRSAPublicKey(
     32         RSAKeyParameters key)
     33     {
     34         this.algorithmIdentifier = DEFAULT_ALGORITHM_IDENTIFIER;
     35         this.modulus = key.getModulus();
     36         this.publicExponent = key.getExponent();
     37     }
     38 
     39     BCRSAPublicKey(
     40         RSAPublicKeySpec spec)
     41     {
     42         this.algorithmIdentifier = DEFAULT_ALGORITHM_IDENTIFIER;
     43         this.modulus = spec.getModulus();
     44         this.publicExponent = spec.getPublicExponent();
     45     }
     46 
     47     BCRSAPublicKey(
     48         RSAPublicKey key)
     49     {
     50         this.algorithmIdentifier = DEFAULT_ALGORITHM_IDENTIFIER;
     51         this.modulus = key.getModulus();
     52         this.publicExponent = key.getPublicExponent();
     53     }
     54 
     55     BCRSAPublicKey(
     56         SubjectPublicKeyInfo info)
     57     {
     58         populateFromPublicKeyInfo(info);
     59     }
     60 
     61     private void populateFromPublicKeyInfo(SubjectPublicKeyInfo info)
     62     {
     63         try
     64         {
     65             org.bouncycastle.asn1.pkcs.RSAPublicKey  pubKey = org.bouncycastle.asn1.pkcs.RSAPublicKey.getInstance(info.parsePublicKey());
     66 
     67             this.algorithmIdentifier = info.getAlgorithm();
     68             this.modulus = pubKey.getModulus();
     69             this.publicExponent = pubKey.getPublicExponent();
     70         }
     71         catch (IOException e)
     72         {
     73             throw new IllegalArgumentException("invalid info structure in RSA public key");
     74         }
     75     }
     76 
     77     /**
     78      * return the modulus.
     79      *
     80      * @return the modulus.
     81      */
     82     public BigInteger getModulus()
     83     {
     84         return modulus;
     85     }
     86 
     87     /**
     88      * return the public exponent.
     89      *
     90      * @return the public exponent.
     91      */
     92     public BigInteger getPublicExponent()
     93     {
     94         return publicExponent;
     95     }
     96 
     97     public String getAlgorithm()
     98     {
     99         return "RSA";
    100     }
    101 
    102     public String getFormat()
    103     {
    104         return "X.509";
    105     }
    106 
    107     public byte[] getEncoded()
    108     {
    109         return KeyUtil.getEncodedSubjectPublicKeyInfo(algorithmIdentifier, new org.bouncycastle.asn1.pkcs.RSAPublicKey(getModulus(), getPublicExponent()));
    110     }
    111 
    112     public int hashCode()
    113     {
    114         return this.getModulus().hashCode() ^ this.getPublicExponent().hashCode();
    115     }
    116 
    117     public boolean equals(Object o)
    118     {
    119         if (o == this)
    120         {
    121             return true;
    122         }
    123 
    124         if (!(o instanceof RSAPublicKey))
    125         {
    126             return false;
    127         }
    128 
    129         RSAPublicKey key = (RSAPublicKey)o;
    130 
    131         return getModulus().equals(key.getModulus())
    132             && getPublicExponent().equals(key.getPublicExponent());
    133     }
    134 
    135     public String toString()
    136     {
    137         StringBuffer    buf = new StringBuffer();
    138         String          nl = Strings.lineSeparator();
    139 
    140         buf.append("RSA Public Key").append(nl);
    141         buf.append("            modulus: ").append(this.getModulus().toString(16)).append(nl);
    142         buf.append("    public exponent: ").append(this.getPublicExponent().toString(16)).append(nl);
    143 
    144         return buf.toString();
    145     }
    146 
    147     private void readObject(
    148         ObjectInputStream in)
    149         throws IOException, ClassNotFoundException
    150     {
    151         in.defaultReadObject();
    152 
    153         try
    154         {
    155             algorithmIdentifier = AlgorithmIdentifier.getInstance(in.readObject());
    156         }
    157         catch (Exception e)
    158         {
    159             algorithmIdentifier = DEFAULT_ALGORITHM_IDENTIFIER;
    160         }
    161     }
    162 
    163     private void writeObject(
    164         ObjectOutputStream out)
    165         throws IOException
    166     {
    167         out.defaultWriteObject();
    168 
    169         if (!algorithmIdentifier.equals(DEFAULT_ALGORITHM_IDENTIFIER))
    170         {
    171             out.writeObject(algorithmIdentifier.getEncoded());
    172         }
    173     }
    174 }
    175