gianebao
gianebao

Reputation: 18948

Bouncy Castle "encoded key spec not recognised"

I'm encountering this particular error after running my jar in an amazon linux. It was working fine in my OsX. I'm using the same public and private key in both machines. The only difference is the java version which is

Machine where I made, test and compiled my script:

Java(TM) SE Runtime Environment (build 1.6.0_65-b14-462-11M4609)

Amazon server:

OpenJDK Runtime Environment (amzn-2.4.7.1.40.amzn1-x86_64 u55-b13)

This is the section of the script that's causing the error:

public PublicKey getPublicKey(String _file)
    throws
        NoSuchAlgorithmException,
        NoSuchProviderException,
        InvalidKeySpecException,
        IOException
{
    X509EncodedKeySpec _spec = new X509EncodedKeySpec(_getFileContents(_file));
    KeyFactory _keyFactory = KeyFactory.getInstance(this._keyFactoryAlgo, this._provider);

    this._publicKey = _keyFactory.generatePublic(_spec);

    return this._publicKey;
}

GetFileContents:

private byte[] _getFileContents(String _fileName) throws IOException
{

    File _file = new File(_fileName);
    FileInputStream _fileStream = new FileInputStream(_file);

    byte[] _contents = new byte[(int) _file.length()];

    _fileStream.read(_contents);

    if(_fileStream != null)
    {
        _fileStream.close();
        _fileStream = null;
    }

    return _contents;
}

Here is the full error message:

java.security.spec.InvalidKeySpecException: encoded key spec not recognised
at org.bouncycastle.jcajce.provider.asymmetric.util.BaseKeyFactorySpi.engineGeneratePublic(Unknown Source)
at org.bouncycastle.jcajce.provider.asymmetric.rsa.KeyFactorySpi.engineGeneratePublic(Unknown Source)
at java.security.KeyFactory.generatePublic(KeyFactory.java:328)
at xxx.CryptKey.getPublicKey(CryptKey.java:167)
at xxx.CryptSession.encryptWithPublicKey(CryptSession.java:316)
at xxx.Crypt.encrypt(Crypt.java:57)
at snippet.Snippet.main(Snippet.java:201)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:606)
at org.eclipse.jdt.internal.jarinjarloader.JarRsrcLoader.main(JarRsrcLoader.java:58)

Upvotes: 0

Views: 8943

Answers (1)

Oleg Estekhin
Oleg Estekhin

Reputation: 8405

You are indeed reading file incorrectly. You are ignoring the return value of the InputStream.read(). You should call this method in cycle because the individual call is not guaranteed to read the entire byte array.

You can read it manually:

int offset = 0;
int read =  _fileStream.read(_contents, 0, contents.length);
while (read > 0) {
    offset += read;
    read = _fileStream.read(_contents, offset , contents.length - offset );

}

Or you can wrap the underlying input stream into DataInputStream and just use DataInputStream.readFully() method.

Upvotes: 2

Related Questions