Erik Costlow, author and presenter.
This whole presentation gravitates toward the development of Java cryptological
code instead of what I needed which was a detailed account of keys,
certificates, Java key- and trust stores, openssl,
keytool and what's inside.
This is not unappreciated, but it's not primarily what I needed right now.
It's just that it was the only course I could find that even touched upon Java
key- and trust stores, but it did not really even mention the trust store let
alone its relationship with the keystore.
And, you have to buy before you can learn at the detailed level what's in a
Hence, I have added in here emerging notes in the appendices about what I
really needed to learn instead of or in addition to what was taught.
Table of contents
1. Cryptographic Introduction
2. Basic Ciphers
3. Advanced Ciphers, Asymmetry and Public Keys
4. Hacking Technologies: Breaking and By-passing
5. Putting It All Together
Appendix 1: Make up for missing keystore vs. trust store focus
Appendix 2: Where do OSes keep their certificate authorites?
Appendix 3: Where do browsers keep their certificate authorities?
Appendix 4: Questions to answer
Random (incomplete) notes...
...because I skipped over a lot of the early bits of the course, not needing
the elementary introduction nor wishing to spend time conveying them in here.
- Section 1: Cryptographic Introduction
- Concepts That Will Be Important
- Certificates do not contain keys, but are associated with them.
- Certificates are signed with a key.
- Public key cryptosystem (PKCS)
- PKCS1, PKCS4, PKCS12, etc.—the numbers do not matter.
- PKCS 2 isn't "better than" PKCS 1.
- The numbers refer to different cryptosystems, not versions,
so take the name as a whole.
- Algorithm is how something is encrypted and decrypted
- The number of bits used by an algorithm represents the
strength of the encryption
- Move in powers of 2 (block size).
- Cannot be meaningfully compared between algorithms:
- RSA 2048 is stronger than RSA 1024, but
- RSA 2048 isn't string than EC 571, nor is
- RSA stronger than AES, however
- AES is strong than DES (because the latter's successor).
- Section 2: Basic Ciphers
- Symmetric Ciphers and Where They Are Used
- Symmetric ciphers
- Are fast, but
- The same key both encrypts and decrypts:
- Anyone who can encrypt a message can also decrypt it.
- Use when everything is under your control, but
- not when multiple people need to encrypt.
- There is danger, for example, that when someone loses their key,
everyone else is compromised.
- You can't tell, however, who encrypted and who decrypted—could
be anyone since everyone's "key" (password) is the same!
Mathematically, there is no possible repudiation.
- Examples include AES (and DES/3DES), Blowfish, Serpent.
- Can keys be used as passwords?
- No, because passwords are frequently length-dependent
- (and keys can be very long).
- Passwords are measured in characters;
- Keys are measured in bits
- —a 128-bit key (very weak) requires 16 bytes to hold it.
- Basic Encryption with Symmetric Ciphers
- Coded demonstration
SecureRandom sr = new SecureRandom();
byte key = new byte[ 16 ]; // 128-bit key (AES)
byte initializationVector = new byte[ 16 ];
sr.nextBytes( key );
System.out.println( " Random key=" + bytesToHex( key ) );
System.out.println( "Initialization vector=" + bytesToHex( initializationVector ) );
- Hashing and MessageDigest for Validation
- Hashing and message digest
- These are the same thing.
- Used to hash one direction and answer questions such as
- Does this file match?
- How to validate a password without knowing it?
- Command algorithms include
- SHA (out of date)
- MD5 (ibid)
- SHA-256 (SHA-512)
- Hashing is a one-way street from original data to hashed value.
- The original data can never be recovered from its hashed value.
- It's only use is to determine whether two samples of original data
- Collisions (common with out-of-date algorithms) occur when two
different inputs result in the same hashed output.
- Repeatable values are useful under certain circumstances, e.g.:
validating a download.
- Repeatable values are not desired if the data is supposed to be
secret, i.e.: a password. (SALT)
- What happens if we don't salt? Or we reuse salts?
- Someone precomputes a giant dictionary (on the web).
- He looks up your hashed value to reverse it, because...
- if he has it, then he can go back and derive the original.
- —why many websites have bizarre password requirements.
- —such requirements make the needed dictionary
significantly L@Rg3r with MiXeD C4SE, etc.
final String password = "12345";
final String SALT = "[email protected]";
final int keylength = 512;
final int iterations = 32; // (number of times through the SALT)
PBEKeySpec keyspec = new PBEKeySpec( password.toCharArray(), SALT.getBytes(), iterations, keylength );
SecretKeyFactory factory = SecretKeyFactory.getInstance( "PBKDF2WithHmacSHA256" );
byte hashed = factory.generateSecret( keyspec ).getEncoded();
System.out.println( "The SHA-256 value salted with PBKDF2 is " + hashed );
- Common Security Flaws When Using Symmetric Ciphers
- Why all of this?
- Because cryptography is not usually broken, it's by-passed
- Small errors render cryptography ineffective.
- Do everything right except some small thing and security is
- Common flaws
- Exposing symmetric keys.
- Using same symmetric key for different things.
- Failing to salt sensitive hash information.
- Relying on bad algorithms because upgrading is hard.
- Disclosing keys (or passwords) is common.
- Mistakes in logging statements like
logger( "Decrypting text with password: " + password );
- Putting passwords in properties files.
- Section 3: Advanced Ciphers, Asymmetry and Public Keys
- Asymmetric Ciphers and Where They Are Used
- Two people haven't talked before, ...
- They have no shared key (symmetric cipher).
- How to write a message for someone to read?
- Only they can read the message (not even you can).
- How to prove who wrote the message? Etc.
- Because she combined her private key and his public key to
encrypt the data, we know it was sent by her.
- Because it uses his public key, we know that the data is for
- It can only be read by someone who knows her public key and his
- Optimized hybrid approach: Use asymmetry to exchange a unique
symmetric key, then switch to symmetric exchange which is much
- Otherwise, communication will be very (noticeably) slow. However,
this is how most people do it because it takes effort to implement
the hybrid system.
- The name of a populate asymmetric algorithm is RSA, not to be
confused with the company of the same (whose founders implemented
it). Others include Elliptical Curve (EC) and Diffie-Hellman (DH).
- The most common asymmetric system is HTTPS, which employs keys and
certificates as well as a key-signing request such that the private
key remains secret.
- Creating a KeyPairGenerator Instance
- How do I make a public/private key?
- Java class KeyPairGenerator.
- You can use KeyPairGenerator to wrap a key-pair in a
certificates before putting it into a key store.
- Most tend to use OpenSSL rather than Java.
final KeyPairGenerator generator = KeyPairGenerator.getInstance( "RSA" ).initialize( 2048 );
final KeyPair keypair = generator.generateKeyPair();
final PublicKey publickey = keypair.getPublic();
final PrivateKey privatekey = keypair.getPrivate();
System.out.println( " Public key is " + publickey );
System.out.println( "Hex encoding is " + Util.bytesToHex( publickey.getEncoded() ) );
System.out.println( " Private key is " + privatekey );
- Storing the Java Keystore
- What is the point of a keystore?
- To store one or more keys.
- Often, you'll have more than one key.
- A keystore makes it easier to protect keys.
- A keystore can also be hardware.
- Makes it so people know where the keys are (not strewn around).
- There are two types of keystores available to Java developers:
- Java Keystore
- ≤ JDK8
- file extension .jks
- PKCS12 (public-key cryptosystem)
- ≥ JDK9
- Cross-system compatibility
- file extensions .pkcs12, .p12, .pfx
- not needed to list contents, but
- needed to access private-key entries.
- for the keystore, and
- for the private key.
- The Java CA store default is "changeit."
/* Bouncy Castle Java demo */
- The Java keytool
- The Java keytool...
- lists keystore contents,
- changes (adds or removes) keys and certificates,
- generates keys,
- wraps keys in certificates,
- separates keys to a dedicated tool,
- makes it easier to demonstrate to someone how you do cryptography
Useful post covering all of keytool.
- Creating a KeyGenerator Instance
- What is a key generator?
- Class KeyGenerator generates a key for symmetric cryptology
as opposed to
- KeyPairGenerator which is asymmetric.
/* Java key generator demo */
- Basic Encryption with Asymmetric Ciphers
- How asymmetric encryption works
- Generate two key-pairs,
- Encrypt and decrypt a message with a key-pair,
- Show how a signature works.
/* Basic asymmetric encryption demo */
- What to Do When PKIX Validation Fails
- PKIX validation failures are a very common problem in Java
- Public key infrastructure for x.509 (certificates)
- Java error messages about SSL (TLS) and crypto are horrible.
- There are two common solutions to try before anything else:
- For ≤ Java 8, apply unlimited cryptography Java
jce_policy-8.zip; this unlocks cryptography of a
much higher strength.
- Why does one need unlimited JCE on ≤ Java 8? Because prior
to Java 9, the cryptographic base software may not be
speaking the particular dialect, for example, SHA-???,
required in your problem.
- In Java 9, this was fixed.
- Alternatively, ensure that you have the root certificate for
whatever it is that you're connecting to inside of your
keystore by using keytool -importcert.
- Where and how to add a root certificate?
- Look back at the keytool section in this presentation
where this wasn't really covered. The main root certificate
store is in lib/security/cacerts and its password is
- Export the problem certificate from your browser and import
$ keytool -importcert
keytool will perform duplicate-certificate avoidance
- Other tricks:
- At JRE start-up: -Djavax.net.debug=all .
Diagnosing TLS, SSL and HTTPS.
- What should you not do?
- Disable SSL validation (as many suggest in places like
- Java Certificate Chains
- How to analyze these chains
- What is a certificate chain?
- Java trusts a lot of root-certificate authorities
- A root signs one or more intermediaries.
- The last intermediary signs a website certificate.
- (This is a chain.)
- All certificates (along the way) have one or more
- All certificates are x.509.
- Messing with these isn't something you ordinarily do.
/* Java demo certificate chains */
- The Key Escrow Problem
- Escrow, the state of being kept in custody or trust.
Public keys are escrowed in order that they may be shared or
- If you have never talked to someone before...
- If find his public key, how do you know it's his?
- How do you know he even has a private key?
- Therefore, you use an existing certificate authority to distribute
and validate public keys.
- Section 4: Hacking Techniques: Breaking and By-passing
- I'm skipping this because it's 45 minutes long and doesn't
contribute to what I need to learn.
- Section 5: Putting It All Together
- Encrypting and Decrypting Files
- —including streams?
- Don't code advanced, confusing things.
- Enforce correct behavior throught typing, e.g.:
- Classes Random and SecureRandom
- Requiring the latter, it's not possible to do the wrong thing,
accidentally pass in a "wrong type of random number," etc.
- No Java programmer wants to work on objects of type byte
so these are wrapped by closeable streams (e.g.:
CipherInputStream and CipherOutputStream).
- Demonstration that does this:
- Initialize a symmetric cipher (this code already written in
section 2, above),
- encrypt a PowerPoint presentation,
- decrypt that PowerPoint presentation, then
- open the PowerPoint presenation and finish the walk-through.
SecureRandom random = new SecureRandom();
byte key = new byte[ 16 ]; // 128-bit
byte vector = new byte[ 16 ];
random.nextBytes( key );
System.out.println( " Random key=" + Util.bytesToHex( key ) );
System.out.println( "Initialization vector=" + Util.bytesToHex( vector ) );
IvParameterSpec initializationVector = new IvParameterSpec( vector );
SecretKeySpec keyspec = new SecretKeySpec( key, "AES" );
Cipher cipher = Cipher.getInstance( "AES/CBC/PKCS5PADDING" );
cipher.init( Cipher.ENCRYPT_MODE, keyspec, initializationVector );
final String TEMPORARY_DIRECTORY = "packt-crypto";
final String RESOURCE_DIRECTORY = "1 - Encrypting and Decrypting files.pptx";
final String ENCRYPTED_DIRECTORY = RESOURCE_DIRECTORY + ".encrypted";
final Path directory = Files.createTempDirectory( TEMPORARY_DIRECTORY );
final Path path = directory.resolve( ENCRYPTED_DIRECTORY );
try( InputStream inputStream = FileEncryptor.class.getResourcesAsStream( DIRECTORY ),
OutputStream __encrypted__ = Files.newOutputStream( path )
CipherOutputStream cipherOutputStream = new CipherOutputStream( __encrypted__, cipher )
final byte bytes = new byte[ 1024 ];
for( int length = inputStream.read( bytes ); length != EOF; length = inputStream.read( bytes ) )
cipherOutputStream.write( bytes, 0, length );
catch( IOException e )
logger.warn( "Unable to encrypt", e );
logger.info( "Encryption finished; saved at ", path );
- Obtaining Certificates from LetsEncrypt (or AWS)
- Lets Encrypt
- Real certificates cost money
- They validate ownership of keys.
- They prevent impersonation.
- No one knows your self-signed key or shares it.
- Anymore, they don't cost: read on!
- Let's Encrypt provides...
- Free forever certificates.
- Trusted certificates.
- Via fully automatable and scriptable means.
- Full support for on-premise or in any cloud.
- Let's Encrypt FAQ
- Down-sides include
- Short-lived (90 days).
- Work better with Internet-connected systems.
- Qualys SSL Labs for Your Servers
- Qualys SSL Labs is free and scans your servers for health.
- The DeepViolet Security Analyzer
- DeepViolet is a tool to look at SSL.
See Appendices here.