Files
Christopher Fahlin 01e26dd717 feat(openssl): upgrade from 3.0.8 to 3.1.2 (FIPS 140-3 Cert #4985)
- Bump OPENSSL_VERSION default from 3.0.8 to 3.1.2
- Update SHA256 hash for openssl-3.1.2.tar.gz
- Update all compliance checks to validate OpenSSL 3.1.x series
- Update docs: README, install.md, CLAUDE.md, test READMEs
- Previous 3.0.8 had only FIPS 140-2 (Cert #4282); 3.1.2 is the
  first OpenSSL with full FIPS 140-3 validation (Cert #4985,
  valid through March 2030)
2026-05-09 12:38:27 -07:00

6.5 KiB

CLAUDE.md

This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.

Project Overview

A CMake-based cross-compile pipeline producing FIPS 140-3 compliant OpenSSL 3.1.x + SQLCipher 4.6.x for Android and iOS. Outputs: AAR (Android) and XCFramework (iOS). The FIPS provider is the validated cryptographic boundary; post-build binary mutation (strip, compress, re-sign) invalidates the HMAC integrity check.

Build Commands

mise trust && mise install
export ANDROID_NDK_ROOT="$HOME/Library/Android/sdk/ndk/<version>"

# Android
./build.sh android                      # arm64-v8a (default)
ANDROID_ABI=x86_64 ./build.sh android   # emulator

# iOS
./build.sh ios                           # device arm64
./build.sh ios-simulator                 # simulator arm64 + x86_64
./build.sh ios-all                       # all iOS slices

# Everything
./build.sh all

# Packaging
./build.sh package-aar                   # -> dist/fips-sqlcipher.aar
./build.sh package-xcframework           # -> dist/FIPSSQLCipher.xcframework
./build.sh package                       # both

Sample App (samples/android)

cd samples/android
./bootstrap.sh       # extracts native libs from AAR into jniLibs/
./gradlew assembleDebug
./gradlew installDebug

Architecture

Single CMakeLists.txt dispatches on -DTARGET_PLATFORM=Android|iOS:

  • Android path: NDK toolchain, shared libs, dlopen-based FIPS provider
  • iOS path: Xcode SDK, static libs only (App Store constraint), incore FIPS

Platform-specific cmake modules:

Android iOS Purpose
cmake/BuildOpenSSL.cmake cmake/BuildOpenSSL_iOS.cmake Cross-compile OpenSSL
cmake/BuildSQLCipher.cmake cmake/BuildSQLCipher_iOS.cmake Build SQLCipher
cmake/PreserveFipsIntegrity.cmake (shared) Strip kill-switch, guards

Android: Shared libs (libfips.so + libcrypto.so + libsqlcipher.so). FIPS integrity via HMAC in fipsmodule.cnf. Provider loaded at runtime via dlopen.

iOS: Static libs for crypto (libcrypto.a + libssl.a + libsqlcipher.a). FIPS provider is fips.dylib (Mach-O bundle, loaded via OSSL_PROVIDER_load which internally uses dlopen). Integrity via incore HMAC; must never be stripped.

FIPS runtime probe: __attribute__((constructor)) that aborts if the FIPS provider isn't active. On Android linked via --whole-archive; on iOS via -force_load.

Packaging: packaging/package_aar.sh assembles the AAR; packaging/package_xcframework.sh runs libtool + lipo + xcodebuild -create-xcframework.

Key Constraints

  • STRIP=/usr/bin/true in all build env blocks. Never re-enable.
  • libfips.so is chmod 0444 post-staging. Baseline sha256 recorded.
  • fipsmodule.cnf must be generated on matching CPU architecture.
  • CMake COMMAND lists cannot use inline sh -c (semicolons are list separators). Helper scripts emitted instead.
  • Android $ORIGIN RUNPATH: \$$ORIGIN escaping for Make + shell layers.
  • iOS builds use Ninja generator (-G Ninja); Android uses Unix Makefiles.
  • iOS cmake is invoked with -DTARGET_PLATFORM=iOS (same top-level CMakeLists.txt, platform conditional).
  • C++ interop: include/fips_sqlcipher.h wraps headers in extern "C". Use shared libc++ on Android to avoid ODR violations.

Configuration Variables

All settable via env: ANDROID_NDK_ROOT, ANDROID_ABI, ANDROID_PLATFORM, OPENSSL_VERSION, SQLCIPHER_VERSION, OPENSSL_URL_HASH, OPENSSL_HOST_BIN, IOS_DEPLOYMENT_TARGET (default 17.0), BUILD_TYPE, JOBS.

CMake-only options:

  • -DFIPS_DEVELOPER_MODE=ON -- enables -Wall -Wextra -Werror on probe code and CMAKE_EXPORT_COMPILE_COMMANDS
  • -DFIPS_PARALLEL_JOBS=N -- caps make -j in ExternalProject (defaults to host CPU count)

Bumping OPENSSL_VERSION requires updating OPENSSL_URL_HASH and re-running FIPS integrity baselines.

CMake Module Structure

  • cmake/FIPSConfig.cmake -- shared constants (URL/hash, job cap, probe source generator, no-op strip path)
  • cmake/FIPSSQLCipherConfig.cmake.in -- package config template for find_package(FIPSSQLCipher) consumers

FIPS Initialization Helpers

include/fips_init.h + src/fips_init.c -- portable C API for FIPS provider bootstrap at app startup. Uses programmatic APIs (OSSL_PROVIDER_set_default_search_path, OSSL_LIB_CTX_load_config, OSSL_PROVIDER_load) to bypass Android's AT_SECURE which blocks all OPENSSL_* env vars in app processes.

fips_configure_cipher(sqlite3 *db) -- must be called immediately after sqlite3_key() and before any I/O. Pins FIPS-approved cipher PRAGMAs: AES-256-CBC, HMAC-SHA512, PBKDF2-HMAC-SHA512 with 256k iterations, 4096-byte pages. These match SQLCipher 4.x defaults but are set explicitly for FIPS audit trail.

Key material handling in JNI (src/fips_db_jni.c): key is copied into an OPENSSL_malloc buffer and zeroized with OPENSSL_cleanse after use per SP 800-132 §5.3.

Platform-specific wrappers:

  • src/fips_init_android.c -- sets search path + loads config with absolute paths, then loads provider
  • src/fips_init_ios.c -- loads provider from bundle resource path

JNI Bridge

src/fips_init_jni.c -- JNI for com.fips.sqlcipher.FIPSSQLCipher (init, status, self-test) src/fips_db_jni.c -- JNI for com.fips.sqlcipher.FipsDatabase (SQLCipher open/close/exec/prepare/step/bind/column)

Built by packaging/build_jni.sh into libfips_jni.so per ABI. CMake at packaging/jni/CMakeLists.txt links against libcrypto.so and libsqlcipher.so.

AAR Kotlin Classes

packaging/android-lib/ -- Gradle module that compiles into classes.jar:

  • FIPSSQLCipher -- one-call FIPS init (extracts configs, loads libs, activates provider)
  • FipsDatabase -- SupportSQLiteDatabase impl over native SQLCipher JNI
  • FipsSQLiteOpenHelperFactory -- SupportSQLiteOpenHelper.Factory for Room integration

scripts/verify_package_integrity.sh -- CI script that extracts FIPS modules from AAR/XCFramework and validates SHA256, .symtab, and .rodata presence.

Output

./build.sh package stages everything needed for integration into out/:

  • out/android/fips-sqlcipher.aar
  • out/ios/FIPSSQLCipher.xcframework
  • out/include/ and out/src/ -- FIPS init helpers
  • out/install.md -- integration guide

Tooling

Managed by mise.toml: cmake 3.29, ninja 1.12.1, perl 5.40.2, JDK temurin-17, Gradle 8.10.2. NDK and Xcode are NOT mise-managed.