# Encryption Three independent stacks, all optional at build time (`./configure` flags): | Module | Backend | XMPP bridge | |---|---|---| | `src/omemo/` | libsignal-protocol-c | `src/xmpp/omemo.c` | | `src/otr/` | libotr v4 | (in-stream, no separate xmpp bridge) | | `src/pgp/` | gpgme | `src/xmpp/ox.c` (for OX/XEP-0373) | ## Module layouts ### OMEMO (`src/omemo/`) | File | Role | |---|---| | `omemo.c/h` | Public surface: session setup, encrypt/decrypt, key publish/fetch. | | `crypto.c/h` | AES-GCM payload encryption; libsignal-protocol crypto provider. | | `store.c/h` | Persistent identity / pre-key / signed pre-key / session storage. | `src/xmpp/omemo.c` is the bridge — it talks to `src/omemo/omemo.c` and to libstrophe stanza building. ### OTR (`src/otr/`) | File | Role | |---|---| | `otr.c/h` | Public surface: start/end/secure messaging, fingerprint mgmt. | | `otrlib.h` | Compatibility shim across libotr versions. | | `otrlibv4.c` | libotr v4-specific implementation. | OTR runs in-band on the message stream, no separate XMPP bridge file. ### PGP / OX (`src/pgp/`) | File | Role | |---|---| | `gpg.c/h` | Classic PGP signing/encrypting via gpgme. | | `ox.c/h` | XEP-0373 / XEP-0374 (OX): OpenPGP for XMPP. | `src/xmpp/ox.c` is the OX bridge; `gpg.c` is invoked directly from message handlers. ## Conditional compilation Each module is gated by `HAVE_OMEMO`, `HAVE_LIBOTR`, `HAVE_LIBGPGME` (set by `configure.ac`). Code that calls into a module guards with `#ifdef HAVE_` and supplies a graceful fallback. When editing: - Search for the existing `#ifdef` use of the symbol you are touching to confirm the gating macro. - Stubs in `tests/unittests/{omemo,otr,pgp}/stub_*.c` exist regardless — they satisfy the test linker even when the feature is "off" at runtime. ## Encryption-aware tests `tests/unittests/test_forced_encryption.{c,h}` exercises the policy where sending plain text is refused if a session is OMEMO/OTR/PGP-locked. Touching encryption-policy code → check this test does not regress. ## Adding or modifying calls into encryption 1. Locate the bridge: outgoing call → typically `src/xmpp/omemo.c` / `src/xmpp/ox.c` / `src/otr/otr.c`. 2. Confirm the `#ifdef HAVE_*` guard at the call site. 3. If the module's public surface (header) changes, update the corresponding stub in `tests/unittests/{omemo,otr,pgp}/stub_*.c`. 4. Run the relevant unit tests (`test_forced_encryption`, plus anything in `test_cmd_otr.c`, `test_cmd_pgp.c`). See `playbooks/add-encryption.md`.