Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
52 changes: 45 additions & 7 deletions wolfCrypt-JNI/src/chapter02.md
Original file line number Diff line number Diff line change
Expand Up @@ -36,9 +36,9 @@ You can build and install a wolfSSL (wolfssl-x.x.x), wolfSSL FIPS release (wolfs

The `--enable-jni` option includes all native wolfSSL features needed by both wolfCrypt JNI/JCE (this package) as well as wolfSSL JNI/JSSE (a separate package). If you want the minimal set of requirements needed for only wolfJCE, you can instead use `--enable-keygen --enable-crl`, where CRL support is needed for the JCE `CertPathValidator (PKIX)` CRL support.

#### Native Feature Requirements for Post-Quantum and Hash-Based Algorithms
#### Native Feature Requirements for Optional Algorithms

Several algorithms supported by wolfJCE are **not** enabled by `--enable-jni` alone and require additional native wolfSSL configure options. If the matching native feature is not compiled into wolfSSL, wolfJCE will still compile and run normally, but the corresponding services will not be registered by the provider.
Several algorithms supported by wolfJCE depend on native wolfSSL features that are not always enabled by `--enable-jni` alone, and may require additional native wolfSSL configure options. The Notes column lists which ones are enabled by default. If the matching native feature is not compiled into wolfSSL, wolfJCE will still compile and run normally, but the corresponding services will not be registered by the provider.

| Algorithm | Native wolfSSL configure option | Notes |
| --- | --- | --- |
Expand All @@ -47,12 +47,29 @@ Several algorithms supported by wolfJCE are **not** enabled by `--enable-jni` al
| SLH-DSA (FIPS 205) | `--enable-slhdsa` | `--enable-slhdsa` builds the six SHAKE parameter sets. Use `--enable-slhdsa=yes,sha2` to build all twelve (recommended, since the `SLH-DSA-SHA2-128f` default lives in the SHA2 family) |
| XMSS / XMSS^MT (RFC 8391) | `--enable-xmss` | Requires wolfSSL 5.9.2 or later. SHAKE-based parameter sets additionally require `--enable-sha3`. Verify-only in wolfJCE |
| LMS / HSS (RFC 8554) | `--enable-lms` | `--enable-lms=verify-only` is also sufficient. SHAKE256 parameter sets additionally require `--enable-sha3`. Verify-only in wolfJCE |
| Ed25519 / Ed448 (RFC 8032) | `--enable-ed25519`, `--enable-ed448` | `--enable-ed448` also enables SHAKE256. Both are included in `--enable-all` |
| AES Key Wrap (RFC 3394) | `--enable-aeskeywrap` | Also enabled by `--enable-all` and `--enable-pkcs7`. Enabled by default in FIPS v6, v7, and FIPS Ready builds |
| AES-XTS | `--enable-aesxts` | Also enabled by `--enable-all` |
| AES-CFB | `--enable-aescfb` | Also enabled by `--enable-all` |
| SHAKE128 / SHAKE256 | `--enable-shake128`, `--enable-shake256` | Enabled by default when SHA-3 is enabled (default on x86_64 and aarch64) for non-FIPS and FIPS v6+ builds |
| DH | `--enable-dh` or `--enable-dh=conditional` | Enabled by default, except in FIPS v7 and FIPS Ready builds starting with wolfSSL 5.9.4. See [DH in FIPS v7 and FIPS Ready Builds](#dh-in-fips-v7-and-fips-ready-builds) |

Note that the post-quantum and hash-based algorithms above (ML-KEM, ML-DSA,
SLH-DSA, XMSS, LMS) are **not** enabled by `--enable-all` or
`--enable-all-crypto`. On wolfSSL versions newer than 5.9.2, all five of these
algorithm families can be enabled at once with `--enable-all-quantum-crypto`,
which enables ML-KEM, ML-DSA, XMSS, LMS, and all twelve SLH-DSA parameter sets
(`yes,sha2`).

The raw RSA `RSA/ECB/NoPadding` Cipher is only registered when native wolfSSL
has raw RSA support compiled in (`WC_RSA_NO_PADDING` or `WC_RSA_DIRECT`).
`--enable-jni` defines `WC_RSA_NO_PADDING`, so no additional options are needed
with it. The minimal `--enable-keygen --enable-crl` build does not define
either one, so add it to that configure line if `RSA/ECB/NoPadding` is needed:

Note that these algorithms are **not** enabled by `--enable-all` or
`--enable-all-crypto`. On wolfSSL versions newer than 5.9.2, all five algorithm
families in the table above can be enabled at once with
`--enable-all-quantum-crypto`, which enables ML-KEM, ML-DSA, XMSS, LMS, and all
twelve SLH-DSA parameter sets (`yes,sha2`).
```
$ ./configure --enable-keygen --enable-crl CPPFLAGS="-DWC_RSA_NO_PADDING"
```

XMSS/XMSS^MT and LMS/HSS support in wolfJCE is signature **verification** and public-key handling only. Key generation and signing are not supported, since stateful hash-based signing belongs in hardware (NIST SP 800-208).

Expand Down Expand Up @@ -97,3 +114,24 @@ This will install the wolfSSL library to your system default installation locati
/usr/local/lib
/usr/local/include
```

#### DH in FIPS v7 and FIPS Ready Builds

wolfCrypt FIPS v7 places DH outside the FIPS module boundary. Starting with
wolfSSL 5.9.4, FIPS v7 and FIPS Ready builds leave DH out by default. Add
`--enable-dh=conditional` to compile DH in but keep it disabled at runtime
until the application calls `Dh.enable()`, or use `--enable-dh` to enable it at
compile time. When DH is disabled, `FeatureDetect.DhEnabled()` returns false
and wolfJCE does not register DH services.

wolfJCE decides which services to register when the provider is created, so
call `Dh.enable()` before creating or installing the wolfJCE provider. If the
provider was created before DH was enabled (for example, when wolfJCE is
registered in `java.security`), refresh its services after calling
`Dh.enable()`:

```
Dh.enable();
WolfCryptProvider prov = (WolfCryptProvider)Security.getProvider("wolfJCE");
prov.refreshServices();
```
24 changes: 23 additions & 1 deletion wolfCrypt-JNI/src/chapter03.md
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,12 @@ $ make clean

wolfCrypt JNI/JCE also supports building with Maven. First, compile the native JNI shared library using `make` as described above.

The included Maven Wrapper, `./mvnw` (or `mvnw.cmd` on Windows), can be used
in place of `mvn` in the commands below. It downloads the Maven release pinned
in `.mvn/wrapper/maven-wrapper.properties`, verifies its SHA-256 checksum, and
runs Maven with `--strict-checksums` so that a dependency or plugin download
that fails its checksum stops the build.

Then compile the Java sources with Maven:

```
Expand Down Expand Up @@ -94,7 +100,7 @@ projects, where the version number will change depending on the current release:
<dependency>
<groupId>com.wolfssl</groupId>
<artifactId>wolfcrypt-jni</artifactId>
<version>1.10.0-SNAPSHOT</version>
<version>1.12.0-SNAPSHOT</version>
</dependency>
```

Expand Down Expand Up @@ -133,6 +139,22 @@ $ ./custom-runtime/bin/java --list-modules
Note that the native wolfCrypt JNI shared library (`libwolfcryptjni.so/dylib`)
must still be available on the native library search path at runtime.

## JDK 15+ Multi-Release JAR (EdDSA)

When built with JDK 15 or later, `wolfcrypt-jni.jar` is a multi-release JAR
(`Multi-Release: true`). Classes under `src/java15` are compiled into the
`META-INF/versions/15` layer of the JAR, so that on JDK 15 and later wolfJCE
EdDSA keys also implement the JDK `java.security.interfaces.EdECPublicKey` and
`EdECPrivateKey` interfaces. This allows wolfJCE Ed25519 and Ed448 keys to be
passed directly to other providers such as SunEC. JDK 8 through 14 and Android
use the base classes. Both `ant` and Maven build this layer automatically when
the build JDK is 15 or later.

Multi-release class selection is done by the JAR loader, so the JDK 15 classes
are only used when wolfJCE is loaded from `wolfcrypt-jni.jar`. A class
directory such as Maven's `target/classes` (used by `mvn test`) uses the base
classes. Run `mvn clean` when switching between build JDKs below and above 15.

## API Javadocs

Running `ant` will generate a set of Javadocs under the `wolfcrypt-jni/docs/javadoc`
Expand Down
4 changes: 4 additions & 0 deletions wolfCrypt-JNI/src/chapter05.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ version of “wolfcrypt-jni.jar” that does not include the JCE provider classe
```
wolfcrypt-jni/
.github GitHub Actions workflows
.mvn/ Maven Wrapper and Maven configuration
AUTHORS
COPYING
ChangeLog.md Version ChangeLog
Expand All @@ -33,11 +34,14 @@ wolfcrypt-jni/
lib/ Compiled library artifacts
makefile.linux Linux-specific Makefile
makefile.macosx macOS-specific Makefile
mvnw, mvnw.cmd Maven Wrapper scripts
pom.xml Maven build file
rpm/ Linux rpm files
scripts/ Test scripts (Facebook Infer, etc)
spotbugs-exclude.xml SpotBugs static analysis exclusions
src/ Source code
java9/ module-info.java (Java 9+ JPMS support)
java15/ JDK 15+ EdDSA multi-release classes
main/java Java source files
test/java JUnit test source files

Expand Down
141 changes: 132 additions & 9 deletions wolfCrypt-JNI/src/chapter06.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,8 @@ wolfJCE currently supports the following algorithms and classes:
SHA3-256
SHA3-384
SHA3-512
SHAKE128-256 (aliased also as: SHAKE128)
SHAKE256-512 (aliased also as: SHAKE256)

SecureRandom Class
DEFAULT (maps to HashDRBG)
Expand All @@ -22,15 +24,28 @@ wolfJCE currently supports the following algorithms and classes:
AES/CBC/NoPadding
AES/CBC/PKCS5Padding
AES/CCM/NoPadding
AES/CFB/NoPadding (aliased also as: AES/CFB128/NoPadding)
AES/CFB8/NoPadding
AES/CFB1/NoPadding
AES/CTR/NoPadding
AES/CTS/NoPadding
AES/ECB/NoPadding
AES/ECB/PKCS5Padding (aliased also as: AES)
AES/GCM/NoPadding
AES/OFB/NoPadding
AES/XTS/NoPadding
AESWrap (aliased also as: AES/KW/NoPadding, AESKW)
AESWrap_128 (aliased also as: AES_128/KW/NoPadding)
AESWrap_192 (aliased also as: AES_192/KW/NoPadding)
AESWrap_256 (aliased also as: AES_256/KW/NoPadding)
AES/KW/PKCS5Padding
AES_128/KW/PKCS5Padding
AES_192/KW/PKCS5Padding
AES_256/KW/PKCS5Padding
DESede/CBC/NoPadding
RSA
RSA/ECB/PKCS1Padding
RSA/ECB/NoPadding
RSA/ECB/OAEPWithSHA-1AndMGF1Padding
RSA/ECB/OAEPWithSHA-256AndMGF1Padding

Expand Down Expand Up @@ -79,6 +94,9 @@ wolfJCE currently supports the following algorithms and classes:
SHA3-256withECDSAinP1363Format
SHA3-384withECDSAinP1363Format
SHA3-512withECDSAinP1363Format
EdDSA (any Ed25519/Ed448 key)
Ed25519
Ed448
ML-DSA (any ML-DSA-44/65/87 key)
ML-DSA-44
ML-DSA-65
Expand Down Expand Up @@ -135,6 +153,9 @@ wolfJCE currently supports the following algorithms and classes:
RSASSA-PSS
EC
DH (aliased also as: DiffieHellman)
EdDSA (defaults to Ed25519, curve overridable via init())
Ed25519
Ed448
ML-DSA (defaults to ML-DSA-65, level overridable via init())
ML-DSA-44
ML-DSA-65
Expand All @@ -161,6 +182,9 @@ wolfJCE currently supports the following algorithms and classes:
RSA
EC
DH (aliased also as: DiffieHellman)
EdDSA (any Ed25519/Ed448 key)
Ed25519
Ed448
ML-DSA
ML-DSA-44
ML-DSA-65
Expand Down Expand Up @@ -196,7 +220,7 @@ wolfJCE currently supports the following algorithms and classes:
PKIX (with PKIXRevocationChecker via getRevocationChecker())

CertPathBuilder Class
PKIX
PKIX (requires native wolfSSL 5.9.2 or later)

SecretKeyFactory Class
PBKDF2WithHmacSHA1
Expand Down Expand Up @@ -225,20 +249,26 @@ wolfJCE currently supports the following algorithms and classes:

In addition to the algorithm names above, many services are also registered
under their standard OID aliases (for example, `Cipher` AES OIDs,
`MessageDigest` SHA-2 OIDs, `Mac` HMAC OIDs, and the ML-DSA, SLH-DSA, ML-KEM,
XMSS, and LMS object identifiers), allowing lookup by OID string. A complete
list of aliases can be found in the wolfcrypt-jni `README_JCE.md` file.
`MessageDigest` SHA-2 and SHAKE OIDs, `Mac` HMAC OIDs, and the Ed25519, Ed448,
ML-DSA, SLH-DSA, ML-KEM, XMSS, and LMS object identifiers), allowing lookup by
OID string. A complete list of aliases can be found in the wolfcrypt-jni
`README_JCE.md` file.

The RSA `Cipher` implementations also support `Cipher.WRAP_MODE` and
`Cipher.UNWRAP_MODE` for RSA-based key wrapping and unwrapping.

## Native wolfSSL Feature Requirements

The ML-KEM, ML-DSA, SLH-DSA, XMSS/XMSS^MT, and LMS/HSS services require the
matching algorithm support to be compiled into the native wolfSSL library.
The ML-KEM, ML-DSA, SLH-DSA, XMSS/XMSS^MT, LMS/HSS, Ed25519, Ed448, AES Key
Wrap, AES-XTS, AES-CFB, SHAKE, and raw RSA (`RSA/ECB/NoPadding`) services
require the matching algorithm support to be compiled into the native wolfSSL
library.
If native support is missing, wolfJCE will still compile and run normally,
but the corresponding services will not be registered. See
[Chapter 2](chapter02.md#native-feature-requirements-for-post-quantum-and-hash-based-algorithms)
but the corresponding services will not be registered. DH services are also
not registered when DH is left out of native wolfSSL or disabled at runtime,
which is the default for wolfCrypt FIPS v7 and FIPS Ready builds starting with
wolfSSL 5.9.4. See
[Chapter 2](chapter02.md#native-feature-requirements-for-optional-algorithms)
for the native wolfSSL configure options required for each algorithm.

## ML-KEM (FIPS 203) Notes
Expand Down Expand Up @@ -266,11 +296,104 @@ input, wolfJCE accepts all three RFC 9935 private key CHOICE forms (`seed`,
implementation uses), defaulting to `expandedKey`, which is importable by the
widest range of providers.

## AES-GCM Notes

When `AES/GCM/NoPadding` is initialized for encryption without an
`AlgorithmParameterSpec`, the 96-bit IV is generated inside native wolfCrypt
using the wolfCrypt DRBG. A `SecureRandom` passed to `init()` is not used for
this IV. `Cipher.getIV()` and `Cipher.getParameters()` return the generated IV,
which must be given to the decrypting side as a `GCMParameterSpec`.

With wolfCrypt FIPS, this internal IV generation is the approved AES-GCM
encryption path (FIPS 140-3 IG C.H). An IV supplied through `GCMParameterSpec`
is an external IV, which the wolfCrypt FIPS security policy only allows in
specific protocol cases (such as TLS 1.2). Applications that need FIPS approved
AES-GCM encryption should let the Cipher generate the IV. When using wolfCrypt
FIPS v5.2.4, or v7 and later, AES-GCM and AES-GMAC IVs shorter than 96 bits are
rejected at `init()`.

## AES-XTS Notes

`AES/XTS/NoPadding` (IEEE 1619, NIST SP 800-38E) differs from the other AES
modes in a few ways:

- The `SecretKey` is two concatenated AES keys of equal size, the data key
followed by the tweak key: 32 bytes for AES-128-XTS or 64 bytes for
AES-256-XTS. The two halves must differ.
- The 16-byte tweak is passed as the `IvParameterSpec`. Encryption generates a
random tweak when none is given, and decryption requires one.
- Each `doFinal()` processes one data unit of 16 to 16,777,216 bytes. Output
length equals input length, using ciphertext stealing for a partial last
block instead of padding.
- `doFinal()` resets the Cipher to its initialized state, so each data unit
should be given its own tweak with a new `init()`. For sector-based use, the
JNI-level `AesXts.updateSector()` method takes the sector number directly.

## AES Key Wrap Notes

wolfJCE provides AES Key Wrap (RFC 3394 / NIST SP 800-38F "KW") through the
`AESWrap` Cipher family. `AESWrap_128`, `AESWrap_192`, and `AESWrap_256` fix the
key encryption key (KEK) size and carry the NIST OIDs. AES Key Wrap with
Padding (RFC 5649 "KWP") is not available in native wolfSSL.

- `WRAP_MODE`/`UNWRAP_MODE` and `ENCRYPT_MODE`/`DECRYPT_MODE` are supported.
Input to wrap must be at least 16 bytes and a multiple of 8 bytes, and the
wrapped output is 8 bytes longer than the input.
- `AES/KW/PKCS5Padding` pads input to the 8-byte block size before wrapping.
This can be used to wrap keys whose encodings are not a multiple of 8 bytes,
such as X.509 public keys and PKCS#8 private keys. This matches SunJCE on
JDK 21 and later, but not JDK 17, which pads to 16-byte blocks.
- The 8-byte IV is the RFC 3394 integrity check value, not a nonce. The
default value `A6A6A6A6A6A6A6A6` is used unless a different 8-byte
`IvParameterSpec` is given, in which case the same value must be used to
unwrap.

## EdDSA (Ed25519 / Ed448) Notes

wolfJCE supports Ed25519 and Ed448 signatures (RFC 8032). The `Ed25519` and
`Ed448` service names are curve specific, while `EdDSA` accepts a key of either
curve. The `EdDSA` `KeyPairGenerator` defaults to Ed25519, or Ed448 when
Ed25519 is not compiled into native wolfSSL. `KeyPairGenerator.initialize()`
accepts a key size (255 or 256 for Ed25519, 448 for Ed448), a
`NamedParameterSpec` (JDK 11+), or an `ECGenParameterSpec` naming `"Ed25519"`
or `"Ed448"` (Java 8).

Generated keys report `getAlgorithm()` of `EdDSA`. Public keys use X.509
SubjectPublicKeyInfo encoding (RFC 8410) and private keys use PKCS#8. wolfJCE
outputs the PKCS#8 v1 form, and accepts both the v1 form and the RFC 5958 v2
form with an embedded public key on input.

Pure EdDSA is used by default. The context and pre-hash variants (Ed25519ctx,
Ed25519ph, Ed448 with a context, and Ed448ph) are selected with
`Signature.setParameter()` using
`com.wolfssl.provider.jce.WolfCryptEdDSAParameterSpec` on any JDK, or the JDK
`java.security.spec.EdDSAParameterSpec` on JDK 15 and later. When wolfJCE is
built with JDK 15 or later and loaded from `wolfcrypt-jni.jar` on a JDK 15 or
later runtime, its EdDSA keys implement the JDK `EdECPublicKey`
and `EdECPrivateKey` interfaces and can be used directly with SunEC (see
[Chapter 3](chapter03.md#jdk-15-multi-release-jar-eddsa)).

## RSA/ECB/NoPadding Notes

`RSA/ECB/NoPadding` performs the raw RSA operation and matches SunJCE
behavior: input is zero padded on the left to the modulus size, output is
always the modulus size, and a private key may encrypt and a public key may
decrypt. Input longer than the modulus fails with `IllegalBlockSizeException`,
and input numerically at or above the modulus fails with `BadPaddingException`.
Unlike SunJCE, wolfJCE also rejects the values 0, 1, and n - 1 with
`BadPaddingException`.

More details on the algorithms above, including differences from SunJCE
behavior, can be found in the wolfcrypt-jni `README_JCE.md` file.

## Example Applications

The `examples/provider` directory in the wolfcrypt-jni package contains
example applications demonstrating several of the algorithm classes above,
including `MlKemExample.java` (ML-KEM encapsulation/decapsulation and key
encoding), `MlDsaExample.java`, `SlhDsaExample.java`, `XmssExample.java`,
and `CertPathBuilderExample.java`.
`EdDSAExample.java` (Ed25519 and Ed448), `AesXtsExample.java`,
`AesKeyWrapExample.java`, `AesCfbExample.java`, `ShakeExample.java`, and
`CertPathBuilderExample.java`. Each example has a matching `.sh` script, which
can be run from any directory.

Loading
Loading