RSA Encryption with OAEP, Explained
After reading this you will know what RSA encryption actually does to your bytes, why it can only encrypt short messages, why OAEP padding matters, and how real systems use RSA to wrap an AES key rather than encrypt data directly.
What RSA encryption does
RSA is a public-key cipher. You publish one key (the public key) and keep the other secret (the private key). Anyone can encrypt a message with your public key, but only you can decrypt it with the private key. The two keys are mathematically linked, yet deriving the private key from the public key requires factoring a large number, which is infeasible for a well-chosen 2048-bit or larger modulus.
Here is the hook. Suppose you want to send a 32-byte AES key to a server. You take the server's 2048-bit public key, run RSA-OAEP encryption, and get a 256-byte ciphertext (Base64: about 344 characters). The server decrypts it with its private key and recovers your exact 32 bytes. No shared secret was ever transmitted in the clear. That is the whole point of public-key cryptography.
The tool on this page does exactly that operation. It takes a PEM public key and a short plaintext, applies RSA-OAEP, and returns Base64 ciphertext. Paste the matching private key to reverse it.
When to use it, and when not to
Use RSA encryption to protect a small, high-value secret when the sender only has the recipient's public key. The classic case is key wrapping: encrypt a random AES key with RSA, then encrypt your real data (which may be gigabytes) with that AES key. This is called a hybrid scheme, and it is what TLS, PGP, S/MIME and age-style tools all do internally.
Do not use RSA to encrypt bulk data directly. It is slow and size-limited. A 2048-bit key can encrypt at most about 190 bytes with OAEP, and each encryption is roughly a thousand times slower than an AES block. If you need to encrypt a file, encrypt a 32-byte AES-256 key with RSA and encrypt the file with AES-GCM.
RSA encryption gives you confidentiality, not authenticity. Anyone with your public key can produce valid ciphertext, so decrypting successfully does not prove who sent it. To prove origin you need a signature. See RSA Sign & Verify.
The math, with intuition
An RSA key is built from two large primes, p and q. Their product is the modulus:
Here n is the public modulus, and its bit length is what people mean by "2048-bit RSA". The public exponent e is almost always 65537. The private exponent d is chosen so that e \cdot d \equiv 1 \pmod{\lambda(n)}, where \lambda(n) is the Carmichael totient of n.
Raw (textbook) encryption of an integer message m is a single modular exponentiation:
Decryption undoes it with the private exponent:
The symbols: m is the message as a number less than n, c is the ciphertext, e and d are the public and private exponents, and n is the modulus. It works because m^{e \cdot d} \equiv m \pmod{n} by Euler's theorem.
Why textbook RSA is not enough, and what OAEP adds
The formulas above are deterministic. Encrypting the same message twice gives the same ciphertext, so an attacker can detect repeats and even build a dictionary for small message spaces. Textbook RSA is also malleable: if c encrypts m, then c \cdot 2^{e} \bmod n encrypts 2m. That is a real attack, not a curiosity.
OAEP (Optimal Asymmetric Encryption Padding, defined in RFC 8017, PKCS#1 v2.2) fixes this. Before the exponentiation, it expands your message with a random seed and two applications of a mask generation function built on a hash (typically SHA-256). The result is a randomized, full-width block. Two consequences follow:
- Encrypting the same 32 bytes twice gives two different ciphertexts, because a fresh random seed is mixed in each time.
- Any tampering with the ciphertext makes the padding check fail on decryption, so malleability attacks do not survive.
The older PKCS#1 v1.5 encryption padding is vulnerable to Bleichenbacher's padding-oracle attack (1998), which can decrypt a captured ciphertext by sending thousands of modified queries and watching for error differences. Use OAEP for new systems. This tool uses OAEP only.
The size limit, made concrete
OAEP eats space. With SHA-256, the padding overhead is 2 \cdot h + 2 bytes, where h = 32 is the hash output length. So the maximum plaintext you can encrypt is:
Here k is the modulus size in bytes. For 2048-bit RSA, k = 256, so m_{\max} = 256 - 64 - 2 = 190 bytes. The table shows the limit at common key sizes.
| Key bits | Modulus bytes (k) | Ciphertext bytes | Max plaintext bytes |
|---|---|---|---|
| 2048 | 256 | 256 | 190 |
| 3072 | 384 | 384 | 318 |
| 4096 | 512 | 512 | 446 |
Notice the ciphertext is always exactly k bytes regardless of message length, because it is a residue mod n. A 32-byte AES key and a 190-byte message both produce 256 bytes of ciphertext under a 2048-bit key.
Worked example: wrapping a short message
The demo uses the tool's default 2048-bit key pair and a short plaintext. Follow these steps to reproduce the ciphertext.
- Load the default public key (PEM) and the default plaintext, roughly 20 to 40 characters of UTF-8, well under the 190-byte limit.
- Encoding to UTF-8 gives the message bytes m. Say the plaintext is 24 characters, so m is 24 bytes.
- OAEP pads those 24 bytes up to 255 bytes (the modulus is 256 bytes, so the padded block is k - 1 = 255 bytes) using a fresh random seed and SHA-256 masking.
- The tool computes c = m_{\text{padded}}^{e} \bmod n with e = 65537, producing 256 ciphertext bytes.
- Those 256 bytes are Base64-encoded, giving \lceil 256 / 3 \rceil \cdot 4 = 344 characters of output.
Run it twice and the 344-character output changes completely each time. That randomness is OAEP at work. Paste the private key and the ciphertext back in, and you recover the original 24 bytes exactly. If you change a single Base64 character, decryption fails rather than returning garbage, because the OAEP check detects the corruption.
Reading and interpreting the results
The Base64 ciphertext is not meant to be human-readable and carries no structure you can inspect. What you can verify:
- Length
- The decoded ciphertext is always exactly the modulus size, 256 bytes for a 2048-bit key. A different length means a different key size or a corrupted value.
- Nondeterminism
- Encrypting the same input twice must give different ciphertext. If it does not, the padding is broken or missing.
- Round trip
- Decrypting with the matching private key returns your exact input bytes. A key mismatch or corrupted ciphertext produces a decryption error, not partial output.
Common mistakes
Most RSA failures are not broken math. They are misuse.
- Encrypting large data directly. If you hit a "data too large" error, you tried to encrypt more than k - 2h - 2 bytes. Switch to hybrid encryption: RSA-wrap an AES key, then AES-encrypt the payload.
- Mismatched OAEP parameters. Encryption with SHA-256 OAEP will not decrypt if the other side expects SHA-1 OAEP or PKCS#1 v1.5. The hash and padding scheme must match on both ends.
- Using the wrong key. Encrypt with the public key, decrypt with the private key. Reversing them is signing, a different operation with different padding (RSA-PSS).
- Reusing RSA for authenticity. Successful decryption does not authenticate the sender. Pair encryption with a signature if you need to know who sent the message.
- Trusting small keys. 1024-bit RSA is deprecated. NIST SP 800-57 sets 2048 bits as the minimum for use through the near term and recommends 3072 bits for longer protection.
Related tools
To create the keys this tool consumes, use the RSA Key Pair Generator, which outputs 2048/3072/4096-bit keys in PEM format. To prove authorship rather than hide content, use RSA Sign & Verify with RSA-PSS. If you want smaller keys and faster operations for signatures, ECDSA Keys, Sign & Verify covers the elliptic-curve alternative on P-256, P-384 and P-521.
Frequently asked questions
Why can't I encrypt a whole file with RSA?
Because RSA can only encrypt a number smaller than its modulus. A 2048-bit key tops out near 190 bytes with OAEP. Real systems encrypt a random 32-byte AES-256 key with RSA, then encrypt the file with AES-GCM. This is called hybrid encryption.
Why does the ciphertext change every time I encrypt the same text?
OAEP mixes in a fresh random seed before the exponentiation, so identical plaintext produces different ciphertext. This is a security property. It prevents an attacker from detecting repeated messages or building a lookup dictionary.
Is RSA-OAEP quantum-safe?
No. A large-scale quantum computer running Shor's algorithm could factor the modulus and recover the private key. RSA is safe against classical computers today, but for long-term secrecy against future quantum attackers you need a post-quantum key-encapsulation scheme such as ML-KEM (FIPS 203).
What is the difference between RSA encryption and RSA signing?
Encryption uses the public key to hide data and the private key to reveal it, with OAEP padding. Signing uses the private key to prove authorship and the public key to verify, with PSS padding. They are separate operations; do not use one key pair interchangeably without understanding both.
What key size should I use?
Use 2048 bits as a minimum and 3072 bits for data that must stay secret for a decade or more. 4096 bits adds margin at the cost of slower operations. Avoid 1024 bits, which is considered breakable by well-resourced attackers.