A public-private key pair splits cryptographic responsibility between two mathematically related values: a public key that may be distributed openly and a private key that must remain secret. This avoids sending a shared decryption secret across an insecure channel. Think of the public key as a lock anyone can use and the private key as the only matching physical key. section 8.1
Equation 8.1
\[\text{Keypair}_\text{Alice} = (\text{PubKey}_\text{Alice}, \text{PrivKey}_\text{Alice}) \label{equation:alice-keypair}\]A key pair is represented as an ordered pair containing public and private portions. section 8.1
For confidentiality, a sender encrypts plaintext with the recipient’s public key. An eavesdropper can obtain that public key without gaining the corresponding private key; only the private-key holder can decrypt ciphertext produced for that public key. Public-key operations can also wrap a symmetric key, leaving bulk data encryption to symmetric cryptography. section 8.1
RSA key pair
RSA derives its pair from two secret random primes p and q. Their product n and an exponent e form the public key (n, e); the private exponent d is calculated so that ed ≡ 1 mod φ(n). Encryption computes c = m^e mod n, while decryption computes m = c^d mod n. The security model depends on keeping the factors and derived private values secret. section 8.3.2
Equation 8.9
\[\begin{aligned} \begin{aligned} \text{PubKey}_{\text{Alice}} &= (n, e) \\ \text{PrivKey}_{\text{Alice}} &= (d) \end{aligned} \label{equation:alice-rsa-keypair} \end{aligned}\]RSA makes the division explicit: the public key contains n and e, while the private key contains d. section 8.3.2
The same split supports authenticity through digital signatures. A signer uses the private key to generate a signature, and a verifier uses the matching public key to obtain a yes-or-no result for a message. Unlike a shared-secret MAC verifier, a signature verifier does not receive the secret needed to create valid signatures. section 9.1
Certificates use signatures to extend trust between public keys. An issuer signs a subject’s public key and associated metadata, allowing a party that trusts the issuer’s public key to trust the subject’s key. Certificate chains ultimately depend on explicitly trusted root public keys. section 9.2.1
Treat key-pair security as an implementation concern, not just a mathematical property:
- Keep private keys and RSA’s secret prime-derived values from disclosure; publishing the public portion is intentional. section 8.1 section 8.3.2
- Use a fresh random ephemeral nonce for each ECDSA signature; a fixed reused nonce can leave otherwise valid signatures vulnerable. section 9.5.1
- Distinguish verification authority from signing authority: public-key holders can verify signatures but cannot create valid ones for that key. section 9.1
Listing 9.1 impl_ecdsa_reused_nonce.go
package impl_ecdsa_reused_nonce
import (
"crypto/ecdsa"
"crypto/elliptic"
"crypto/rand"
"fmt"
"math/big"
)
type EcdsaKeyPair struct {
PubKey *ecdsa.PublicKey
privKey *ecdsa.PrivateKey #1
}
var (
Curve elliptic.Curve
notSoNonce *big.Int #2
)
func init() {
Curve = elliptic.P256()
n, err := rand.Int(rand.Reader, Curve.Params().N)
if err != nil {
panic("could not generate fixed value for nonce")
}
notSoNonce = n
fmt.Printf("notSoNonce: 0x%X\n", notSoNonce)
}
func NewEcdsaKeyPair() (*EcdsaKeyPair, error) {
priv, err := ecdsa.GenerateKey(Curve, rand.Reader)
if err != nil {
return nil, err
}
return &EcdsaKeyPair{
PubKey: &priv.PublicKey,
privKey: priv,
}, nil
}
The Go implementation stores an ECDSA public key separately from its private key, then generates the pair on the P-256 curve. section 9.5.1





