Fix crash when host does not support midi-in; Add missing file
[juce-lv2.git] / juce / source / src / cryptography / juce_RSAKey.cpp
blobdcb48b9a0e583c120a537534cdb597b4a2cecd10
1 /*
2 ==============================================================================
4 This file is part of the JUCE library - "Jules' Utility Class Extensions"
5 Copyright 2004-11 by Raw Material Software Ltd.
7 ------------------------------------------------------------------------------
9 JUCE can be redistributed and/or modified under the terms of the GNU General
10 Public License (Version 2), as published by the Free Software Foundation.
11 A copy of the license is included in the JUCE distribution, or can be found
12 online at www.gnu.org/licenses.
14 JUCE is distributed in the hope that it will be useful, but WITHOUT ANY
15 WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
16 A PARTICULAR PURPOSE. See the GNU General Public License for more details.
18 ------------------------------------------------------------------------------
20 To release a closed-source product which uses JUCE, commercial licenses are
21 available: visit www.rawmaterialsoftware.com/juce for more information.
23 ==============================================================================
26 #include "../core/juce_StandardHeader.h"
28 BEGIN_JUCE_NAMESPACE
30 #include "juce_RSAKey.h"
31 #include "juce_Primes.h"
34 //==============================================================================
35 RSAKey::RSAKey()
39 RSAKey::RSAKey (const String& s)
41 if (s.containsChar (','))
43 part1.parseString (s.upToFirstOccurrenceOf (",", false, false), 16);
44 part2.parseString (s.fromFirstOccurrenceOf (",", false, false), 16);
46 else
48 // the string needs to be two hex numbers, comma-separated..
49 jassertfalse;
53 RSAKey::~RSAKey()
57 bool RSAKey::operator== (const RSAKey& other) const noexcept
59 return part1 == other.part1 && part2 == other.part2;
62 bool RSAKey::operator!= (const RSAKey& other) const noexcept
64 return ! operator== (other);
67 String RSAKey::toString() const
69 return part1.toString (16) + "," + part2.toString (16);
72 bool RSAKey::applyToValue (BigInteger& value) const
74 if (part1.isZero() || part2.isZero() || value <= 0)
76 jassertfalse; // using an uninitialised key
77 value.clear();
78 return false;
81 BigInteger result;
83 while (! value.isZero())
85 result *= part2;
87 BigInteger remainder;
88 value.divideBy (part2, remainder);
90 remainder.exponentModulo (part1, part2);
92 result += remainder;
95 value.swapWith (result);
96 return true;
99 BigInteger RSAKey::findBestCommonDivisor (const BigInteger& p, const BigInteger& q)
101 // try 3, 5, 9, 17, etc first because these only contain 2 bits and so
102 // are fast to divide + multiply
103 for (int i = 2; i <= 65536; i *= 2)
105 const BigInteger e (1 + i);
107 if (e.findGreatestCommonDivisor (p).isOne() && e.findGreatestCommonDivisor (q).isOne())
108 return e;
111 BigInteger e (4);
113 while (! (e.findGreatestCommonDivisor (p).isOne() && e.findGreatestCommonDivisor (q).isOne()))
114 ++e;
116 return e;
119 void RSAKey::createKeyPair (RSAKey& publicKey, RSAKey& privateKey,
120 const int numBits, const int* randomSeeds, const int numRandomSeeds)
122 jassert (numBits > 16); // not much point using less than this..
123 jassert (numRandomSeeds == 0 || numRandomSeeds >= 2); // you need to provide plenty of seeds here!
125 BigInteger p (Primes::createProbablePrime (numBits / 2, 30, randomSeeds, numRandomSeeds / 2));
126 BigInteger q (Primes::createProbablePrime (numBits - numBits / 2, 30, randomSeeds == nullptr ? 0 : (randomSeeds + numRandomSeeds / 2), numRandomSeeds - numRandomSeeds / 2));
128 const BigInteger n (p * q);
129 const BigInteger m (--p * --q);
130 const BigInteger e (findBestCommonDivisor (p, q));
132 BigInteger d (e);
133 d.inverseModulo (m);
135 publicKey.part1 = e;
136 publicKey.part2 = n;
138 privateKey.part1 = d;
139 privateKey.part2 = n;
143 END_JUCE_NAMESPACE