[pycrypto] Confused about some code in PubKey/RSA/_slowmath.py

Shoufu Luo luoshoufu at gmail.com
Tue Nov 6 17:24:42 PST 2012

Hi Lorenz,

Thank you so much for explanation. Now, I think I understand the code. 

The private key is only for decryption and sign, and public key is for encryption and verify. The _sign procedure calls the decryption (which I though should be encryption function), because decrypt and encrypt are the same operation from mathematical standpoint. Yes, that is the confusing part, but diligent! Now, I'm clear.Thank you!

And thank you for advice, I use private key for signature in the standard way not for encryption. My problem was solved. Thanks again.

Yours sincerely,

On Nov 6, 2012, at 2:59 PM, Lorenz Quack wrote:

Hi Shoufu,

first things first:
A) Cryptography is *very* hard to get right even if use a crypto library. So if
you ask these questions out of curiosity or educational purposes that is fine but
please don't use your own crypto in production code where you really need security!

B) I'm myself not a cryptography expert so take my answers with a grain of salt.

First some general explanations that might be helpful.
For answers to your actual questions scroll down to the "---" mark.

From a mathematical standpoint encryption and decryption are the same operation.
Namely raise a number (this is either your plain text "m" or your cipher text "c")
to an exponent modulo a large number (usually called "n"). The only difference is
what you take as the exponent. So in RSA you have two different exponents a private
one (let us call it "d") and a public one (let us call it "e"). combined with "n"
these are in essence your private and public key. So now we have one mathematical
operation but four variables ("m", "c", "d", and "e") giving you these combinations:

1) m**e mod n    --> encryption
2) m**d mod n    --> sign
3) c**e mod n    --> verify
4) c**d mod n    --> decryption


so to answer your first question:
"encrypting" using your private key is called signing. Think of it this way. if you
"encrypt" with your private key everybody would be able to decrypt it because what
could be done with your public key which is ... well *public*

as for the second question:
this question seems to stem from the same misconception as the first one.
encryption happens with the *public* key and decryption with the *private* key.
Everybody (i.e. the public) is allowed to send you encrypted messages but only you
should be able to decrypt them in private!

I hope that answers your questions.

Sincerely yours,

On 11/05/2012 06:26 AM, Shoufu Luo wrote:
> Hi all,
> I'm trying to encrypt a message with my private key and release the encrypted to
> others who will use my public key to decrypt. But, I failed.
> I was confused by the follwing code from PubKey/RSA/_slowmath.py of pyCrypto-2.6.
> If anyone can give any clues to answer the following questions, I will appreciate.
> 1. Theoretically, if I encrypt date using private key, I can decrypt the encrypted
> data using public key, and vice versa. Why the key must be a private key in
> decryption function, line 51-52? Can't I use private key to decrypt?
> 2. _sign() should be the signature process using private key to encrypt a piece of
> data, why it is trying to decrypt at line 70, and it should be decryption in
> '_verify', but why it is _encrypt()?
>  49     def _decrypt(self, c):
>  50         # compute c**d (mod n)
>  51         if not self.has_private():
>  52             raise TypeError("No private key")
>  53         if (hasattr(self,'p') and hasattr(self,'q') and hasattr(self,'u')):
>  54             m1 = pow(c, self.d % (self.p-1), self.p)
>  55             m2 = pow(c, self.d % (self.q-1), self.q)
>  56             h = m2 - m1
>  57             if (h<0):
>  58                 h = h + self.q
>  59             h = h*self.u % self.q
>  60             return h*self.p+m1
>  61         return pow(c, self.d, self.n)
>  62
>  63     def _encrypt(self, m):
>  64         # compute m**d (mod n)
>  65         return pow(m, self.e, self.n)
>  66
>  67     def _sign(self, m):   # alias for _decrypt
>  68         if not self.has_private():
>  69             raise TypeError("No private key")
>  70         return self._decrypt(m)
>  71
>  72     def _verify(self, m, sig):
>  73         return self._encrypt(sig) == m
> Thanks,
> Shoufu

pycrypto mailing list
pycrypto at lists.dlitz.net

More information about the pycrypto mailing list