In RSA crypto, when you generate a key pair, it's completely arbitrary which one you choose to be the public key, and which is the private key. If you encrypt with one, you can decrypt with the other - it works in both directions.

in this question from StackOverflow. I would like to prove myself that this statement is true by actually trying it myself.

I have GnuPG 1.4.16 installed on my linux. I made two keys in pubring:

If I want Bob to decrypt message received from Alice using his private key I type:

gpg --output message.decrypted --decrypt message.encrypted

after which Bob is prompted for passphrase and if it's correct message is decrepted.

Here, I assume gpg handles selecting Bob's public key when encrypting and using Bob's private key for decrypting, because I don't spesify that information myself. (If I am wrong with my assumptions/understanding of how gpg works - please let me know, I am new to it).

Now, I want Alice to send message to Bob again, but this time I want to use Alice's private key to encrypt, and then I want Bob to use Alice's public key to decrypt.

Question(s)

What commands or what parameters should I pass to gpg to achieve that?

Can GnuPG even allow me to do this? Should I use some other program?

Note: I am not trying to --sign that message. I am trying to prove to myself whether quote at the top of question is true or false, and that quote says nothing about signing.

A little bit of background of how I got here

I was trying to understand how RSA/public key/private key "stuff" works. I discovered that there is misunderstanding going on in this area in community. A lot of people say "signing is the same as encrypting with private key". I do not know how RSA internally implement things, and reading and understanding this will take me months, if not years, probably. Nevertheless, after reading this, this, this, this, this, this, this I find answers like this, this, this, this confusing. So far everywhere I looked I only saw people talking, but haven't seen somebody provide concrete example. If this is duplicate - let me know, I will remove this question. Also, I might be asking the wrong question, but I am here to find out.

Edit 1

Using this website you can generate public and private keys and try to encrypt/decrypt some message. If you do it the proper way (encrypt with public, decrypt with private) it works. But if you do it the other way around - it does not work. Which means a few things to me:

it's a bug in javascript library

quote at the beginning of this question is false

there is some if statement in javascript library that says something like (it's a "jQuery pseudocode", hopefully you know what I mean)

if($('#privatekey').value.contains('public') { return false; }

which is meant to restrict people like me from even trying to decrypt messages with public keys.

it's non-intentional bug not in library itself, but in how it was used

Any other reasons?

But I am not worried too much about this website not doing it. I was looking into established program (or even just library) that can achieve what I was describing.

Edit 2

Note: this second edit is more like research notes, rather then valuable addition to question, so I wanted to keep it in smaller letters.

I did diff of encryption and decryption primitives vs signature and verification primitives from this text. Here is a link to diff. It appears that they are a "mirror image" of one another. What message in encryption is what signature in verification, and what ciphertext in decryption is what message in signing. As I understood that is what being called Raw RSA in this answer. But another thing this answer also states is that

It is often mentioned that signing is equivalent to RSA encrypting (the hash over) the message using the private key. This is only true if you disregard the required padding mechanism. The RSA padding mechanisms are different for encryption and signing.

By taking a quick look at padding (which is described in chapter 7 for encryption and chapter 9 for signing), description of padding indeed looks different for both encryption and signing (but I want to/have to look more into it). Which kind of narrows down my question to finding out whether padding implementation of encryption (aka. RSAES-OAEP or RSAES-PKCS1-v1_5) will allow me to encrypt with private key, and decrypt with public key safely, producing original message.

I added "RSA" to the title because while it may be true with RSA that it's an arbitrary choice of which of the keys you call the "public" one, it is most certainly not true of other public key algorithms such as Elliptic Curve (ECC) or any of the post-quantum algs.
– Mike OunsworthAug 11 '17 at 17:33

1

This is an interesting question. Myself, the way I would approach it is by downloading the GPG source code, find the RSA implementation, understand how keygen works, swap which one it declares public, rebuild gpg and see if it still works.
– Mike OunsworthAug 11 '17 at 17:37

2 Answers
2

That statement regarding the key pairs is dangerously false. The public and private keys are mathematically related, and the public key is computed from the private key using the trap door function, meaning it's easy to compute the public key from the private key, but not the other way around. If you share the private key, an attacker could use it to calculate the public key, leaving your cryptosystem broken.

Yes, thank you. I understand that, however for the purposes of my question I don't care about security. Also, I would not want to conclude that that statement is false until I can find real world implementation (program or library) that when keys are just swapped will still display original message. Thank you.
– Alex LAug 11 '17 at 16:50

First, PGP is a bad place to look. Not only does it use different paddings for RSA encryption and signing as it should (and nearly everyone does) making the RSA operations themselves different, it handles variable size and possibly large messages using hybrid cryptography (as nearly everyone does). Thus encrypting a PGP message to an RSA key doesn't RSA-encrypt the message; it encrypts the message with a symmetric algorithm and a nonce key, and then RSA-encrypts only the nonce key. (This also covers an important use case for email, sending one message to multiple recipients; the large message is symmetric-encrypted only once, while the small nonce key is PK-encrypted separately for each recipient.) Signing a PGP message actually computes a hash of the message and RSA-signs that hash. And the format of an encrypted message is different from the format of a signed message, which are both different from the format of a clear message.

Second, I don't see how you can believe that RSA encryption and decryption works using med mod n and signing and verifying works using rde mod n works but not believe ed = de (in Z, as mathematicians call the ring of integers) -- I learned that in about fifth grade IIRC.

But if you still need to see this, OpenSSL's commandline operation rsautl does support raw (and pure) RSA. You need the keypair (see more below) in one of the several PEM formats supported by OpenSSL, and a 'message' file which is exactly the bitsize of the modulus and numerically less -- since RSA moduli are usually chosen to be a 'nice' size like 512 1024 2048 bits (512 is probably fine for your example since you don't want security) it is enough if the top bit of the first byte of your message is zero, which is the case for all ASCII characters. Then:

One thing I glossed over: in addition to the more subtle flaws of raw RSA, swapping d and e is not secure at all if e is small, but small e is more efficient and practically all implementations for the last 30 years or so (including openssl) choose e small precisely we never want to swap. Thus you'll need to do key generation more like the method of the original CACM paper: choose d randomly (and thus at least half the size of pq with overwhelming probability) but coprime to phi(pq)=(p-1)x(q-1) and compute e as its multiplicative inverse mod phi -- or equally good, though they only mention it, mod lambda(pq)=lcm(p-1,q-1) -- or at least choose random large coprime e and compute d as its inverse in the modern fashion. I leave that part to you.