Skip to main content
Technical docs

HIPAA and related law

Safe Harbor, Expert Determination, 164.514(c) re-identification codes, BAA and Security Rule, breach handling, Washington MHMDA, California CMIA, 42 CFR Part 2, GDPR and PCI. What is in place and what isn't.

HIPAA and related law

This page maps legal requirements to mechanisms and says, for each, whether the mechanism is live. It is not legal advice and not a compliance claim. Whether a deal is under HIPAA, whether an agreement is signed, and whether counsel has approved a procedure are each product's facts, not the engine's.

Status at this version

Item Engine and reference runner Control plane
HIPAA profiles (hipaa_safe_harbor, hipaa_expert) Built and tested; accepted when a claim names them (profiles.MISSING is empty) Not turned on for deals. The control planes that send these profiles do so only behind a HIPAA-deals switch that is off, on development branches
Random stand-ins (164.514(c)) Built; needs the deal's identity map in the claim Map storage built on development branches; tied to the HIPAA switch
Expert Determination certificate check Built (shape and expiry only) Certificate entry on development branches
PHI signal (is this a covered entity's data?) Live, reported as phiSignal Hold-for-decision on development branches
Part 2 signal Live, reported as phiSignal.part2Over Authorization hold on development branches
Business associate agreement – None in force. Each product has a draft template for counsel, marked not in force
Security Rule risk analysis – Draft template per product, not in force
Breach runbook – Draft per product (four-factor assessment, 60-day clock, recall as a trigger), not in force
Workforce training – Draft outline per product, not in force
MHMDA, CMIA Health-category detection (sensitive.py) Authorization hold on development branches; no per-consumer consent tracking

Read the rest of this page as "what would carry the requirement once the switch is on and the agreements exist".

When HIPAA applies

Only when the seller is a covered entity (provider, health plan, clearinghouse), its business associate, or the sponsor of a self-funded employee health plan selling that plan's records. Health details in ordinary business records (injury logs, drug-test results, HR files) are not PHI; the sensitive-attribute rules handle them. The engine's role is the signal: health.phi.Signal scores what the scrub saw and reports over when there is any healthcare-format file, or the score reaches the threshold with at least two kinds of signal. The decision is the control plane's and the desk's.

Safe Harbor, 45 CFR 164.514(b)(2)

Two conditions: the 18 identifiers of the individual and of relatives, employers and household members are removed, and the covered entity has no actual knowledge that what remains could identify the individual.

The engine carries the first condition, partly:

  • hipaa_safe_harbor is strict plus dates: year (every date the engine recognizes cut to the year; ages at 90 and over grouped), stand_ins: random, linkage_table: off, ZIP3 with restricted areas 000.
  • The coverage matrix maps each of the 18 to rules and cases (profiles-and-coverage.md). At this version most rows are partial or planned; each row's note on what it misses is in the auditor edition.
  • What a HIPAA profile can't transform it holds: as-is documents with dates inside, git history (random stand-ins aren't built into the history rewrite), audio with speech, images that would need a content classifier, and every healthcare file a parser refuses or can't finish within its limits.
  • Free-text names depend on detectors (rules, the ensemble, name model A) with the measured recall in detectors.md, not on a guarantee.

So the engine alone does not establish Safe Harbor for arbitrary data. The release gate's HIPAA rows (zero misses of any kind in the reviewed output sample) and the desk's decision sit on top. The second condition (no actual knowledge) is the seller's and the desk's, not software's.

Expert Determination, 45 CFR 164.514(b)(1)

A qualified expert determines, with documented methods and results, that the risk of re-identification by an anticipated recipient is very small.

  • hipaa_expert is strict plus dates: deal_offset, stand_ins: random, and the person-linkage table under risk_checked. The claim must carry the certificate reference (expertCert: id, expert, scope, expiry); a missing or expired one fails the job (profiles.check_certificate). The engine checks shape and dates only.
  • What an expert can use from the report: removals by category, the coverage matrix, the benchmark, k-anonymity on the linked view (kMin, shareUnderK), the miss bound from the desk's output sample, the canary result, the re-check counts, sensitive-category counts, and the engine and model hashes that pin what ran.
  • What isn't measured: redaction precision from the desk sample, and anything about outside data an intruder could join. The motivated-intruder test is reported once the desk runs it (measurement.md); until then the report says "not yet measured".
  • No expert has been engaged through this code; the certificate is a reference the control plane records.

Re-identification codes, 45 CFR 164.514(c)

A covered entity may assign a code to allow re-identification, if the code is not derived from or related to information about the individual and can't be translated to identify them, and the mechanism isn't disclosed.

  • Keyed stand-ins (HMAC(salt, value)) are derived from the value, so they don't qualify. That is why both HIPAA profiles use stand_ins: random.
  • Random stand-ins: each token is CSPRNG output, drawn once per value per deal and stored in the sealed identity map; stable across refreshes; never computed from the value. Person ids are CSPRNG output in every mode.
  • The way back (the map's lookup section) is indexed by HMAC(salt, "rnd:<kind>:<value>"), sealed, held by the control plane, opened only with the narrow lookup key, and never delivered (keys.md).
  • Business-id tokens and mail sender pseudonyms come from the map too under random stand-ins.
  • Still keyed under random stand-ins: mail message and thread ids (they identify messages, not people) and path collision tags. Path hashes: see threat-model.md. Git history is held instead.

Business associate agreement and the Security Rule

A seller that is a covered entity needs a BAA before any PHI moves; a business-associate seller needs a subcontractor BAA. None is in force. Each product keeps a draft template for counsel.

How the Security Rule's technical safeguards (45 CFR 164.312) map to what the reference runner does:

Safeguard Mechanism Status
Access control (a) One job per machine; egress locked to the hosts the job needs; parsers sandboxed; unprivileged user; keys only in the claim for one job Live
Audit controls (b) Runner reports counts, hashes and modes in the finish call; append-only event logs are the control plane's Runner side live
Integrity (c) Merkle root over every delivered record and file; signed report; every model and dependency pinned by hash Live
Person or entity authentication (d) Job tokens per claim; buyer recipient keys Control plane
Transmission security (e) Deliveries encrypted to the buyer's recipient keys; vault objects encrypted with the deal key Live
Encryption at rest (addressable) Vault server-side encryption with the deal key; work directory on tmpfs or an encrypted volume destroyed with the job; swap turned off at boot. In the default mode a host without tmpfs falls back to disk with overwrite-on-wipe (best effort); the mode that ran is in the runner facts, and RUNNER_TMPFS=required fails boot instead Live

Administrative and physical safeguards (risk analysis, workforce training, contingency plans) are each product's, and exist only as drafts.

Breach notification, 45 CFR 164.400-414

What a breach procedure would rely on from the engine and runner: the incident's locations by path hash and the manifest that lists every delivered file with its Merkle leaf (to find affected deliveries), the stand-in list for a person (lookup key), and the watermark for attribution. Each product's draft breach runbook covers the four-factor risk assessment, the 60-calendar-day outer limit, notice to the covered entity as business associate, and treating any privacy recall as a trigger. Drafts, not in force. Recall handling: operations.md.

Washington My Health My Data Act and California CMIA

Consumer health data outside HIPAA. Both turn on consent or authorization for collection and sharing.

  • Engine: health is a special category in sensitive.json; under strict it is held per record or file, under standard and b2b flagged and counted. The report's sensitive section carries counts by category.
  • Control plane (development branches): consumer health data in the scrub holds delivery until the desk records the seller's authorization.
  • Not built: per-consumer consent records, residency tests (whose data falls under which state), MHMDA geofencing rules, and consumer deletion portals. The engine can't tell from the data whose consent exists.

42 CFR Part 2

Substance-use disorder treatment records, with their own consent rules.

  • Engine: health.phi counts Part 2 terms (treatment program wording, the regulation's name) separately from the PHI score; at the minimum count part2Over is set in the report.
  • Control plane (development branches): part2Over holds every delivery until a Part 2 consent is recorded.
  • Not built: Part 2's redisclosure notice on delivered records, and segmentation of Part 2 data from other PHI.

GDPR

Coverage rows gdpr.* map personal data categories, special categories (Art. 9), criminal data (Art. 10) and children's data to rules and cases. Most are partial; what each row misses is in the auditor edition. The engine's output is pseudonymized data (stand-ins are reversible by the lookup key holder), still personal data under the GDPR, unless every key is destroyed. Lawful basis, DPAs, records of processing and transfer mechanisms are each product's. The breach runbook drafts note the GDPR's 72-hour clock.

PCI DSS

Coverage rows pci.*: full track data is covered; primary account numbers (Luhn-valid, 13 to 19 digits; a PAN run straight into more digits is missed), expiry and CVV (labeled only) and cardholder names (named columns and track data; free text depends on the name detectors) are partial. PCI scope of the control planes is each product's.

Engine docs at commit 1c5af8f39ebb. Plain-language versions: what happens to your data, the workflow score.