Archived Forum Post

Index of archived forum posts

Question:

RSA GenerateKey() bug

Jan 08 '16 at 11:06

Hi,

I need to generate tens of thousands RSA public/private key pairs in my code. The following code will give error after 1500...6500 keys are generated. I dunno if error is in GenerateKey(), Import/ExportPrivateKey() or Import/ExportPublicKey(). You can see the bug when calling ImportPrivateKey() in following code (function returns false), look for // Sometimes it fails here. comment in code:

public void Test()
{

    var rsa = new Chilkat.Rsa();
    rsa.OaepPadding = false;
    bool success = rsa.UnlockComponent("*******");
    if (!success)
        throw new ApplicationException("Failed to unlock RSA component");

    var rsa2 = new Chilkat.Rsa();
    rsa2.OaepPadding = false;
    success = rsa2.UnlockComponent("********");
    if (!success)
        throw new ApplicationException("Failed to unlock RSA component 2");

    string publickey = "";
    string privatekey = "";

    for (int i = 0; i < 20000; i++)
    {
        success = rsa.GenerateKey(2048);
        if (!success)
            throw new ApplicationException("rsa key generation failed");

        publickey = rsa.ExportPublicKey();
        privatekey = rsa.ExportPrivateKey();

        success = rsa2.ImportPrivateKey(privatekey);
        if (!success)
        {
            // Sometimes it fails here. i is sometimes like 1500, sometimes 6500 or similar.
            Console.WriteLine("Private key failed:");
            Console.WriteLine(privatekey);
            Console.WriteLine(rsa2.LastErrorText);
            throw new ApplicationException("rsa private key import failed");
        }

        success = rsa2.ImportPublicKey(publickey);
        if (!success)
        {
            // Sometimes it fails here
            Console.WriteLine("Public key failed:");
            Console.WriteLine(publickey);
            Console.WriteLine(rsa2.LastErrorText);
            throw new ApplicationException("rsa public key import failed");
        }

        if(i % 5 == 0)
            Console.WriteLine("Current loop is " + i);
    }

    Console.WriteLine("DONE");
}

I have see failure after varying num of loops, sometimes 1500 rounds, sometimes 6500 rounds, it all varies. Sometimes ImportPrivateKey() returns false, sometimes ImportPublicKey() returns false. The output from one failure is:

Current loop is 6635
Private key failed:     
<RSAKeyValue>
    <Modulus>xL/uQ1FXPok4P0u7eTdPO1V4zT6hmfv7QW0wMuxsVL6XztpKacWpla6UvBGY5NMSwq+vdelfYORi7a5dFou3CCNwyuYlFqFfGEg5mm/ZSOPLjUJU9o/XpPg1zhllyXiYGJNN1c6oGxMJHpzwj3H+qMW3ovXqYf4hodNB5/EzeTVVDq4f2Wx0ShWOL1BDhPvedAkYE2ZW3WBZWR3KFD+XIJGLC/5o0A30mnkADTtY7HEfgwXLh3dN8VXFSQNlQzzGCtrZ5GSLPBqcp4cqqzusEWUCeLUoVH7ygrUEpLNov2VdSdwghwzgyEzjv8hl3PBVHrK5TBUXQxaUiKe1FcQ7tw==</Modulus>
    <Exponent>AQAB</Exponent>
    <D>e0m12PMgk2xTFb60FGonOQv/LcXAaAhxUndES7TA0X25DQLWvF8DPGtwgkUYpNLrH5oNffqmLMYQg9XOOTGFmRD0PgBnXz3xo/qmNfM+miE8TSEysmpCe/qZZLOfh9cMn+G2VXMw/f44qbk4OPr60/FJeFFW9N7VXl1OIDSRx7IdfOZWFH8vIruabkcshcozxfg4nrqdaGGsncWUHVjIk0N3RzSZsIBegiNPGQDdNEQKPTKM0Z4w/ypyr5MqEYg/fjpQQ0gwTOP4BDmJCQnW6lMPySWpEViu0uQKdHO/OWaC4e5D7lQPKSuEFKKtflOeidYc3UqQIRDSiHf/sq/rKQ==</D>
    <P>3/vpLC3YMyVthL8jKDe+aiWzBWwkzlIOdPtMy9zNfbyAFvKRzAeA/rg24Piz+IMLyQW96QPEN6iiL9T9EQjKbhjGV7rfsczI91wx4vUMKfrPwA8UF96UmHMOlcpO4LfP0+Ces1IGm52Ez2OZnhGJ9qSOQjlFgG3q0AoWHU1TI4M=</P>
    <Q>4N90WZrgmd/Zqy9l3BEvp9Uz48UWzn++TXhqGAMdQkCqqZL9HFF/rr9rT/TxXGcRtAMoStDhDo7lh31TjFvLiQ7f9h44e5LDHMMhFWbphcPcnbdvhHOJJGXR0uHoyBrl2A2Kg3n7Xt+fqJc2F3+w0bRa5MDQ8HUHVxjcwgytrL0=</Q>
    <DP>iyFKnLO5eUPFfNDRwNingf367uJXFoXoDwhOks+MIY9mrVpt8CO1IARDqokyGaslNfBIICbDyqMIY9fUfrFMNQlUowgkjagcKXLuVgFLVgRC6hUzsQQEn5HQvIDXcEUdZoo/ajoIer9k0QIYWRSh80ASUdaLcpRUaHfrdrYib4s=</DP>
    <DQ>s9rlUzmlhEze6qTpQj9Yr1K9wuIC4LyZN5skt/ndr/zKwwA2gyzIA7tEGFpfpTkmlqSj2FsCdkNiX6CkbzGINCH6jP4UzPlQJrQGxPhftEY4MMjjX7uMp9jsHk/jgBDLXqdN7uRkYbhYGV5/vAG8Ka2nuShitL/VVBsljerYCb0=</DQ>
    <InverseQ>ddDnyNcIp7gj1m2IlS26iPoGXOUB/EVSmq5Yiqx63fVVocw9BVehfEsHTpTX4dIp8JEnRHllZ60bggdcwO7Ab1HXFw9kLgvSqY22dz/TacbBl1f5mwvISH8xKKyrMJ4LfgEs4dhS8YPAvm5P+anTnnakA/WmJFapaTJZ+PhhXsA=</InverseQ>
</RSAKeyValue>
ChilkatLog:
  ImportPrivateKey:
    DllDate: Nov  4 2015
    ChilkatVersion: 9.5.0.54
    UnlockPrefix: **************
    Username: ************
    Architecture: Little Endian; 32-bit
    Language: .NET 4.5
    VerboseLogging: 0
    Failed.
  --ImportPrivateKey
--ChilkatLog

If you need more info on this, pls let me know.

Thanks, Matt


Answer

I see the problem.

The GenerateKey method is OK.

The ImportPrivateKey method will actually accept any format, such as XML, PEM, etc. The detection for PEM is to look for the string "BEGIN" (case insensitive). Unfortunately, this is not stringent enough. The Base64 data within the XML happens to contain the string "BegiN" --

... HVjIk0N3RzSZsIBegiNPGQDdNEQKPT ...

The fix within Chilkat is to the ImportPrivateKey method to be more careful about detecting formats. I'll post a new build soon..


Answer

Here's a new build:

32-bit Download: http://www.chilkatsoft.com/download/preRelease/ChilkatDotNet45-9.5.0-win32.zip

64-bit Download: http://www.chilkatsoft.com/download/preRelease/ChilkatDotNet45-9.5.0-x64.zip


Answer

Hi,

Great, thanks for the quick fix. Did you also check the ImportPublicKey() as it also fails sometimes? I'll run tests tonight to verify this new build.

Rgds, Matt


Answer

Is this new build already at nuget? It seems that with VS2015 its totally impossible test separate .dlls, as its complains about all kind of stupid problems about incorrect version number, regardless how many times you reinstall nuget packages, restart VS, reboot, etc. The current state of VS/nuget and all that version handling is totally garbage. With my solution there are quite many projects, and updating chilkat component in one place, or in all places, results in a nightmare. It seems that as VS is getting more and more complex, its starting to break down. People are wondering why its so difficult to produce quality software, but one answer is that development tools are in state of flux. Oh damn I miss the times of Windows 1.0 development in late 80s, it was pure C (and little assembler), one make file, everything was command line, debugging was with TTY terminal, but when there was an error, it was YOU causing the error, not the development environment. OK, maybe it wasnt that great, as C compilers didnt always produce correct output, and compilation times were often in minutes or in tens of minutes :-)

Now to the issue: If this bug was in ImportPrivateKey(), not in GenerateKey(), AND nuget has the latest version, then this bug is not yet fixed, as it blew on me after importing about 5500 RSA keypairs (I didnt regenerate key pairs, but loaded old ones from file). BUT if fixed version is NOT yet on nuget, OR bug was also in GenerateKey(), then you can ignore this message. I'll run more tests during this weekend.

Here is a private key that fails to import:

<RSAKeyValue>
    <Modulus>6qZitCpArMSGV2Z0uA+SKAzAHW2g2O2D2axmilGiemUtSXt+nGr4/e+ZzEGHIPQCOH827WEu0B65YXybLF4bdCwDGOUX6SI4M4+1vmRLZMIPfTLC/gN2sWDtpGAmwhmo3wL2whQ5eR9lLygTjKwX6OClaqEhexXhPhcDm40rouGVzlNgZ2xMG9v40zPFnGNiQeWfnxrFecLnWVKG8N5iOfEZSYcCWkshKQxXG5lHmlaTQNslQcXcxggUxF+mOkBvLBSdyhbucE+0yOOjmelbI4wajSMoAprqgFtS8Nn+OzraeUcQ7qWhhMVyRR24kNdoQEW42dWRt8CC6lUlEB7Pew==</Modulus>
    <Exponent>AQAB</Exponent>
    <D>M/WEBcEVcSxTUycs0VUhWBz6rYmJBIAToi+6xQYupEujK5JdBuXpHNHhjIk2EuX1V+1TjFzosM0c36ln8vsjuSXFyc1w7f7V0xUPeYlb6IPQSjjjVLwPnFeKR8vCyVhFPJy7Z15zG48IKNkG+y9gXADioCnt8AN4TPdrpRYtg3Njzq+TuFU1jAuNJaXJTZLUuvsWrv53rZF2BbYUv16P2VKdmgOkkS4deLYCHlG4h7kACTDzRJgok90hB4I0h5CF1FzUq0mpgXWMbLnV3EhRa7kXEY9bnhQ/cwSMgWExJywf42UTgBQYUR4w4aaxnXDqH9a8vjzvACTqUS0i60aSAQ==</D>
    <P>/TBMMomf04GlV6Q4ewK1MZEFWxrvwzc/QlUANYe8mLH4QRLpcsZInabEGInls+XpoUXYRNwHj+nM+X0pW3bkpnuVGSIzh0+3qPHLjw1yvNcp89MgMwOI4mdEaIyGqDZk4GhP8s26h9MBx/fnrmYL2135LjHjb+PfSQY9JebzYys=</P>
    <Q>7UFj/yffa1CG6JJIFOnoSvqL2ITsg5mRaVX11olAAG4+cB9y91xcAq7Q8biViajTjAzGiaYtRigOJIK1qAPnixKshMt7KxgkpMd1vcpO3JqpyxcKWGSuuTjpw56CbUxK/FUumWFrYCorf2cLXMsRaidvUY3O5lMa5xWjWwaRXPE=</Q>
    <DP>F6mk5XBBVLYgKtG5SZ3WK1y/YGVjFR6btepVy6r08FxptEM9ODHZ5YoJd7Wjly2cqSrq7HyX5FZYhtSwwdCZzAluxNuSb0n/AzYd7S+3kniVfik0MDBbYbV/Cjpf92amBOca2blqfnk1CGhd6cm1v/nHaQ7Wj8V/P8bqfhlYk+M=</DP>
    <DQ>nOjFSIfHRAMC5idwkpxL6+KdwHnQrgxPVhnqt5MYB/DhTGgQMbYciA2z1FmeVGeaWSJN39VOVfrBt7XWjCLg7GJSRJUKhWq3OV9M6FM3KsEDEHTRe7pCr+8K8zwOyFhPs2hmpDwAtp3NHLo6kokeoFUqUwZ1UnCd9zyhR98lHhE=</DQ>
    <InverseQ>FmwWypwipYNNuAvQ3curuRgOIjF3lefk/ce7yugmx5v1FMr5tTHxJCWJReZ5/0I/X1QyHmaKa70v5lehEx1hen/TlRZFU4jhMn01vGfSyvjvFYjgd9H+4krMBRmM19UkvvIw3jR3qjqjSNpr+g414z+z0RWUYfiB3KBwn5EO7uE=</InverseQ>
</RSAKeyValue>

Does it import properly on your system?

-Matt


Answer

It's fixed for both public and private keys. Unfortunately, I cannot update official versions after release. I can only offer bug fixes as pre-releases until the next official version is released. Official new version releases must pass a rigorous QA process just prior to release.


Answer

OK, thanks and no worries. I get it on nuget after official version is out. I definately do believe you that its now fixed, I can live with this until official version is out.

Many thanks for you prompt attention to this issue.

Have a good one, Matt