Re: JDK11 & BC & TLS with RSASSA-PSS signature

David Hook <dgh-rTAZ0PM/[email protected]> Tue, 25 Dec 2018 11:51:31 +1100
Newsgroups gmane.comp.encryption.bouncy-castle.devel
Message-ID <[email protected]>
I'll post a link to the bug report as soon as one is available. It's
still under review at the moment.

Regards,

David

On 23/12/18 7:52 pm, Michael Schäfer wrote:
>
> Hi David,
>
> thanks a lot. Can you please also provide a link to the discussion?
>
> Regards,
>
> Michael
>
> Am 22.12.2018 um 21:51 schrieb David Hook:
>>
>> We've filled a bug report. Discussions on-going.
>>
>> Regards,
>>
>> David.
>>
>> On 22/12/18 1:08 am, Michael Schäfer wrote:
>>>
>>> Hi David,
>>>
>>>
>>> thanks for the clarification. Are you going to report the issue to
>>> JSSE or should I?
>>>
>>>
>>> Kind regards,
>>>
>>> Michael
>>>
>>>
>>> Am 21.12.2018 um 01:01 schrieb David Hook:
>>>>
>>>> There seem to be a few issues around setParameter() in Java 11.
>>>>
>>>> The convention on this has always been to call setParameter() first.
>>>>
>>>> We're going to treat this one as a bug, but I would suggest filing
>>>> this as either a "bug" or a "request for enhancement". I can
>>>> understand how the current maintainers of the JSSE would not be
>>>> aware of it, but the convention was established 20 years ago, and
>>>> the comment above the modified code in SignatureScheme.java makes
>>>> absolutely no sense. It looks like someone made the change will
>>>> trying to fix something else and got confused as to which change
>>>> actually solved the problem.
>>>>
>>>> Regards,
>>>>
>>>> David
>>>>
>>>> On 21/12/18 2:39 am, MSKnete-S0/[email protected] wrote:
>>>>> Hello all,
>>>>>  
>>>>> I run into an issue, when using JDK11, BC and TLS with RSASSA-PSS
>>>>> signature scheme. From JDK10 to JDK11 the handshake classes have
>>>>> been changed and especially the JDK class
>>>>> 'src/java.base/share/classes/sun/security/ssl/SignatureScheme.java'
>>>>> calls the signer object in an unfavourable manner.
>>>>>  
>>>>> Instead of calling setParameter() first and then initSign(), JDK11
>>>>> does it the other way around (SignatureScheme.java, line 473/480).
>>>>>  
>>>>> Obviously, BC expect calling these two methods in the opposite
>>>>> order
>>>>> (org.bouncycastle.jcajce.provider.asymmetric.rsa.PSSSignatureSpi.java).
>>>>>  
>>>>> My remaining question: Who does it right? BC or JDK? Which side
>>>>> must be fixed?
>>>>>  
>>>>> I also attached a small sample which demonstrates the issue by
>>>>> comparing the BC implementation with the SunRsaSign implementation.
>>>>>  
>>>>> Further I found another mentioning of this behavior on the openjdk
>>>>> mailing list at
>>>>> http://mail.openjdk.java.net/pipermail/security-dev/2018-September/018265.html
>>>>> but sadly without any continuative response.
>>>>>  
>>>>> Any suggestion are welcome, to get RSASSA-PSS and BC working with
>>>>> JDK11.
>>>>>  
>>>>> Kind regards,
>>>>> Michael
>>>>>
>>>>> $ java -version
>>>>> openjdk version "11.0.1" 2018-10-16
>>>>> OpenJDK Runtime Environment 18.9 (build 11.0.1+13)
>>>>> OpenJDK 64-Bit Server VM 18.9 (build 11.0.1+13, mixed mode)
>>>>>  
>>>>> $ javac -cp bcprov-jdk15on-160.jar Demo.java
>>>>> $ java -cp bcprov-jdk15on-160.jar Demo
>>>>> BCprov: [...]
>>>>> SunJCE: [...]
>>>>> FAIL: Signatures are not equal!
>>>>>  
>>>>> ---------------------
>>>>> Sample Source (Demo.java):
>>>>> ---------------------
>>>>> import java.security.KeyPair;
>>>>> import java.security.KeyPairGenerator;
>>>>> import java.security.PrivateKey;
>>>>> import java.security.SecureRandom;
>>>>> import java.security.Security;
>>>>> import java.security.Signature;
>>>>> import java.security.spec.MGF1ParameterSpec;
>>>>> import java.security.spec.PSSParameterSpec;
>>>>> import java.util.Arrays;
>>>>>
>>>>> public class Demo {
>>>>>  
>>>>>   public static void main(final String[] args) throws Exception {
>>>>>     Security.insertProviderAt(new
>>>>> org.bouncycastle.jce.provider.BouncyCastleProvider(), 2);
>>>>>  
>>>>>     KeyPairGenerator keyPairGenerator =
>>>>> KeyPairGenerator.getInstance("RSA");
>>>>>     keyPairGenerator.initialize(2048);
>>>>>     KeyPair keyPair = keyPairGenerator.generateKeyPair();
>>>>>     PrivateKey privateKey = keyPair.getPrivate();
>>>>>  
>>>>>     SecureRandom prngBC = SecureRandom.getInstance("SHA1PRNG");
>>>>>     prngBC.setSeed(12345678L); //we need equal randomness, dont do
>>>>> this in production!
>>>>>     Signature signerBC = Signature.getInstance("RSASSA-PSS", "BC");
>>>>>  
>>>>>     // this breaks BC, since setParameter() is invoked AFTER init()
>>>>>     signerBC.initSign(privateKey, prngBC);
>>>>>     signerBC.setParameter(new PSSParameterSpec("SHA-512", "MGF1",
>>>>> new MGF1ParameterSpec("SHA-512"), 64, 1));
>>>>>     byte[] resultBC = signerBC.sign();
>>>>>  
>>>>>     SecureRandom prngSun = SecureRandom.getInstance("SHA1PRNG");
>>>>>     prngSun.setSeed(12345678L); //we need equal randomness, dont
>>>>> do this in production!
>>>>>     Signature signerSun = Signature.getInstance("RSASSA-PSS",
>>>>> "SunRsaSign");
>>>>>     signerSun.initSign(privateKey, prngSun);
>>>>>     signerSun.setParameter(new PSSParameterSpec("SHA-512", "MGF1",
>>>>> new MGF1ParameterSpec("SHA-512"), 64, 1));
>>>>>     byte[] resultSun = signerSun.sign();
>>>>>  
>>>>>     System.out.println("BCprov: " + Arrays.toString(resultBC));
>>>>>     System.out.println("SunJCE: " + Arrays.toString(resultSun));
>>>>>     if (Arrays.equals(resultBC, resultSun)) {
>>>>>       System.out.println("OK: Signatures are equal!");
>>>>>     } else {
>>>>>       System.err.println("FAIL: Signatures are not equal!");
>>>>>     }
>>>>>   }
>>>>> }
>>>>
>>>>
>>