PQXDH in Lean

5.7. Passive Message Secrecy🔗

Passive message secrecy for X3DH under the Random Oracle Model, using VCV-io for security game definitions.

5.7.1. Random Oracle Model🔗

In the real protocol, the KDF (HKDF-SHA-256, §2.5, p. 473) is a deterministic function. In the security proof, we replace it with a random oracle: a function that, on each new input, returns a uniformly random output and caches it for consistency (same input always gives the same output).

This is the standard ROM assumption from the paper (assumption 4). It lets us argue that the session key is indistinguishable from random whenever the KDF input contains a fresh random component (as happens when DH3 is replaced with a random group element in the DDH reduction).

Definition5.1
Group: Passive message secrecy game, DDH reduction, and tight security bound under the Random Oracle Model. (6)
Hover another entry in this group to preview it.
Preview
Definition 5.2
Blueprint label
  • passive_adversary
Group
  • Passive message secrecy game, DDH reduction, and tight security bound under the Random Oracle Model.
L∃∀Nused by 0

To compute probabilities, the KDF oracle is implemented as fresh uniform samples (equivalent to ROM for single-query games). This bridges VCV-io's oracle computations to concrete probability distributions.

Code for Definition5.11 definition
  • def execGame {GType SKType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  SKType]
      (compOracleComp (unifSpec + KDFOracle (G × G × G × G) SK) Bool : OracleCompOracleComp.{u, v, w} {ι : Type u} (spec : OracleSpec ι) : Type w → Type (max u v w)`OracleComp spec α` represents computations with oracle access to oracles in `spec`,
    where the final return value has type `α`, represented as a free monad over the `PFunctor`
    corresponding to `spec.`  (HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`.unifSpecunifSpec : OracleSpec ℕAccess to oracles for uniformly selecting from `Fin (n + 1)` for arbitrary `n : ℕ`.
    By adding `1` to the index we avoid selection from the empty type `Fin 0 ≃ empty`. +HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`. KDFOracleKDFOracle (I K : Type) : OracleSpec IKDF as a random oracle, for security proofs.  (Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`.GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType)Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. SKType)HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`. BoolBool : TypeThe Boolean values, `true` and `false`.
    
    Logically speaking, this is equivalent to `Prop` (the type of propositions). The distinction is
    public important for programming: both propositions and their proofs are erased in the code generator,
    while `Bool` corresponds to the Boolean type in most programming languages and carries precisely one
    bit of run-time information.
    ) :
      ProbCompProbComp : Type → TypeSimplified notation for computations with no oracles besides random inputs.
    This specific case can be used with `#eval` to run a random program, see `OracleComp.runIO`.
    NOTE: Need to decide if this should be more opaque than `abbrev`, seems like no as of now..  BoolBool : TypeThe Boolean values, `true` and `false`.
    
    Logically speaking, this is equivalent to `Prop` (the type of propositions). The distinction is
    public important for programming: both propositions and their proofs are erased in the code generator,
    while `Bool` corresponds to the Boolean type in most programming languages and carries precisely one
    bit of run-time information.
    
    def execGame {GType SKType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  SKType]
      (compOracleComp (unifSpec + KDFOracle (G × G × G × G) SK) Bool :
        OracleCompOracleComp.{u, v, w} {ι : Type u} (spec : OracleSpec ι) : Type w → Type (max u v w)`OracleComp spec α` represents computations with oracle access to oracles in `spec`,
    where the final return value has type `α`, represented as a free monad over the `PFunctor`
    corresponding to `spec.` 
          (HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`.unifSpecunifSpec : OracleSpec ℕAccess to oracles for uniformly selecting from `Fin (n + 1)` for arbitrary `n : ℕ`.
    By adding `1` to the index we avoid selection from the empty type `Fin 0 ≃ empty`. +HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`.
            KDFOracleKDFOracle (I K : Type) : OracleSpec IKDF as a random oracle, for security proofs.  (Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`.GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType)Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. SKType)HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`.
          BoolBool : TypeThe Boolean values, `true` and `false`.
    
    Logically speaking, this is equivalent to `Prop` (the type of propositions). The distinction is
    public important for programming: both propositions and their proofs are erased in the code generator,
    while `Bool` corresponds to the Boolean type in most programming languages and carries precisely one
    bit of run-time information.
    ) :
      ProbCompProbComp : Type → TypeSimplified notation for computations with no oracles besides random inputs.
    This specific case can be used with `#eval` to run a random program, see `OracleComp.runIO`.
    NOTE: Need to decide if this should be more opaque than `abbrev`, seems like no as of now..  BoolBool : TypeThe Boolean values, `true` and `false`.
    
    Logically speaking, this is equivalent to `Prop` (the type of propositions). The distinction is
    public important for programming: both propositions and their proofs are erased in the code generator,
    while `Bool` corresponds to the Boolean type in most programming languages and carries precisely one
    bit of run-time information.
    
    Execute an oracle computation implementing the KDF as
    fresh uniform samples (equivalent to ROM for single-query games).
    unifSpec queries are forwarded as-is; KDF queries return `$ᵗ SK`. 
    complete

5.7.2. Passive adversary🔗

Definition5.2
Group: Passive message secrecy game, DDH reduction, and tight security bound under the Random Oracle Model. (6)
Hover another entry in this group to preview it.
Preview
Definition 5.1
Blueprint label
  • exec_game
Group
  • Passive message secrecy game, DDH reduction, and tight security bound under the Random Oracle Model.
L∃∀Nused by 0

A passive adversary sees the public transcript (five group elements) and a candidate session key. It has ROM access and outputs a Bool guess.

Code for Definition5.21 definition
  • def PassiveAdversary (GType SKType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. ) : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. 
    def PassiveAdversary (GType SKType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. ) : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. 
    A passive X3DH adversary with ROM access. 
    complete

5.7.3. Two-game formulation🔗

Both games share a common structure that samples keys, computes public values and the DH tuple, then obtains a session key via a callback. The real and random games differ only in how the session key is obtained.

Definition5.3
Group: Passive message secrecy game, DDH reduction, and tight security bound under the Random Oracle Model. (6)
Hover another entry in this group to preview it.
Preview
Definition 5.1
Blueprint label
  • exec_game
Group
  • Passive message secrecy game, DDH reduction, and tight security bound under the Random Oracle Model.
L∃∀Nused by 0

In the real game, the session key is obtained by querying the random oracle on the actual DH tuple.

Code for Definition5.31 definition
  • def passiveReal {FType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [FieldField.{u} (K : Type u) : Type uA `Field` is a `CommRing` with multiplicative inverses for nonzero elements.
    
    An instance of `Field K` includes maps `ratCast : ℚ → K` and `qsmul : ℚ → K → K`.
    Those two fields are needed to implement the `DivisionRing K → Algebra ℚ K` instance since we need
    to control the specific definitions for some special cases of `K` (in particular `K = ℚ` itself).
    See also note [forgetful inheritance].
    
    If the field has positive characteristic `p`, our division by zero convention forces
    `ratCast (1 / p) = 1 / 0 = 0`.  FType] [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  FType] {GType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. }
      [AddCommGroupAddCommGroup.{u} (G : Type u) : Type uAn additive commutative group is an additive group with commutative `(+)`.  GType] [ModuleModule.{u, v} (R : Type u) (M : Type v) [Semiring R] [AddCommMonoid M] : Type (max u v)A module is a generalization of vector spaces to a scalar semiring.
    It consists of a scalar semiring `R` and an additive monoid of "vectors" `M`,
    connected by a "scalar multiplication" operation `r • x : M`
    (where `r : R` and `x : M`) with some natural associativity and
    distributivity axioms similar to those on a ring.  FType GType] {SKType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } (gG : GType)
      (advPassiveAdversary G SK : PassiveAdversaryPassiveAdversary (G SK : Type) : TypeA passive X3DH adversary with ROM access.  GType SKType) :
      OracleCompOracleComp.{u, v, w} {ι : Type u} (spec : OracleSpec ι) : Type w → Type (max u v w)`OracleComp spec α` represents computations with oracle access to oracles in `spec`,
    where the final return value has type `α`, represented as a free monad over the `PFunctor`
    corresponding to `spec.`  (HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`.unifSpecunifSpec : OracleSpec ℕAccess to oracles for uniformly selecting from `Fin (n + 1)` for arbitrary `n : ℕ`.
    By adding `1` to the index we avoid selection from the empty type `Fin 0 ≃ empty`. +HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`. KDFOracleKDFOracle (I K : Type) : OracleSpec IKDF as a random oracle, for security proofs.  (Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`.GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType)Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. SKType)HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`. BoolBool : TypeThe Boolean values, `true` and `false`.
    
    Logically speaking, this is equivalent to `Prop` (the type of propositions). The distinction is
    public important for programming: both propositions and their proofs are erased in the code generator,
    while `Bool` corresponds to the Boolean type in most programming languages and carries precisely one
    bit of run-time information.
    
    def passiveReal {FType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [FieldField.{u} (K : Type u) : Type uA `Field` is a `CommRing` with multiplicative inverses for nonzero elements.
    
    An instance of `Field K` includes maps `ratCast : ℚ → K` and `qsmul : ℚ → K → K`.
    Those two fields are needed to implement the `DivisionRing K → Algebra ℚ K` instance since we need
    to control the specific definitions for some special cases of `K` (in particular `K = ℚ` itself).
    See also note [forgetful inheritance].
    
    If the field has positive characteristic `p`, our division by zero convention forces
    `ratCast (1 / p) = 1 / 0 = 0`.  FType]
      [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  FType] {GType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. }
      [AddCommGroupAddCommGroup.{u} (G : Type u) : Type uAn additive commutative group is an additive group with commutative `(+)`.  GType] [ModuleModule.{u, v} (R : Type u) (M : Type v) [Semiring R] [AddCommMonoid M] : Type (max u v)A module is a generalization of vector spaces to a scalar semiring.
    It consists of a scalar semiring `R` and an additive monoid of "vectors" `M`,
    connected by a "scalar multiplication" operation `r • x : M`
    (where `r : R` and `x : M`) with some natural associativity and
    distributivity axioms similar to those on a ring.  FType GType]
      {SKType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } (gG : GType)
      (advPassiveAdversary G SK : PassiveAdversaryPassiveAdversary (G SK : Type) : TypeA passive X3DH adversary with ROM access.  GType SKType) :
      OracleCompOracleComp.{u, v, w} {ι : Type u} (spec : OracleSpec ι) : Type w → Type (max u v w)`OracleComp spec α` represents computations with oracle access to oracles in `spec`,
    where the final return value has type `α`, represented as a free monad over the `PFunctor`
    corresponding to `spec.` 
        (HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`.unifSpecunifSpec : OracleSpec ℕAccess to oracles for uniformly selecting from `Fin (n + 1)` for arbitrary `n : ℕ`.
    By adding `1` to the index we avoid selection from the empty type `Fin 0 ≃ empty`. +HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`.
          KDFOracleKDFOracle (I K : Type) : OracleSpec IKDF as a random oracle, for security proofs.  (Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`.GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType)Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. SKType)HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`.
        BoolBool : TypeThe Boolean values, `true` and `false`.
    
    Logically speaking, this is equivalent to `Prop` (the type of propositions). The distinction is
    public important for programming: both propositions and their proofs are erased in the code generator,
    while `Bool` corresponds to the Boolean type in most programming languages and carries precisely one
    bit of run-time information.
    
    Real game: session key from ROM applied to the X3DH DH tuple. 
    complete
Definition5.4
Group: Passive message secrecy game, DDH reduction, and tight security bound under the Random Oracle Model. (6)
Hover another entry in this group to preview it.
Preview
Definition 5.1
Blueprint label
  • exec_game
Group
  • Passive message secrecy game, DDH reduction, and tight security bound under the Random Oracle Model.
L∃∀Nused by 0

In the random game, the session key is sampled uniformly at random, independent of the DH tuple.

Code for Definition5.41 definition
  • def passiveRand {FType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [FieldField.{u} (K : Type u) : Type uA `Field` is a `CommRing` with multiplicative inverses for nonzero elements.
    
    An instance of `Field K` includes maps `ratCast : ℚ → K` and `qsmul : ℚ → K → K`.
    Those two fields are needed to implement the `DivisionRing K → Algebra ℚ K` instance since we need
    to control the specific definitions for some special cases of `K` (in particular `K = ℚ` itself).
    See also note [forgetful inheritance].
    
    If the field has positive characteristic `p`, our division by zero convention forces
    `ratCast (1 / p) = 1 / 0 = 0`.  FType] [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  FType] {GType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. }
      [AddCommGroupAddCommGroup.{u} (G : Type u) : Type uAn additive commutative group is an additive group with commutative `(+)`.  GType] [ModuleModule.{u, v} (R : Type u) (M : Type v) [Semiring R] [AddCommMonoid M] : Type (max u v)A module is a generalization of vector spaces to a scalar semiring.
    It consists of a scalar semiring `R` and an additive monoid of "vectors" `M`,
    connected by a "scalar multiplication" operation `r • x : M`
    (where `r : R` and `x : M`) with some natural associativity and
    distributivity axioms similar to those on a ring.  FType GType] {SKType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  SKType] (gG : GType)
      (advPassiveAdversary G SK : PassiveAdversaryPassiveAdversary (G SK : Type) : TypeA passive X3DH adversary with ROM access.  GType SKType) :
      OracleCompOracleComp.{u, v, w} {ι : Type u} (spec : OracleSpec ι) : Type w → Type (max u v w)`OracleComp spec α` represents computations with oracle access to oracles in `spec`,
    where the final return value has type `α`, represented as a free monad over the `PFunctor`
    corresponding to `spec.`  (HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`.unifSpecunifSpec : OracleSpec ℕAccess to oracles for uniformly selecting from `Fin (n + 1)` for arbitrary `n : ℕ`.
    By adding `1` to the index we avoid selection from the empty type `Fin 0 ≃ empty`. +HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`. KDFOracleKDFOracle (I K : Type) : OracleSpec IKDF as a random oracle, for security proofs.  (Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`.GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType)Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. SKType)HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`. BoolBool : TypeThe Boolean values, `true` and `false`.
    
    Logically speaking, this is equivalent to `Prop` (the type of propositions). The distinction is
    public important for programming: both propositions and their proofs are erased in the code generator,
    while `Bool` corresponds to the Boolean type in most programming languages and carries precisely one
    bit of run-time information.
    
    def passiveRand {FType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [FieldField.{u} (K : Type u) : Type uA `Field` is a `CommRing` with multiplicative inverses for nonzero elements.
    
    An instance of `Field K` includes maps `ratCast : ℚ → K` and `qsmul : ℚ → K → K`.
    Those two fields are needed to implement the `DivisionRing K → Algebra ℚ K` instance since we need
    to control the specific definitions for some special cases of `K` (in particular `K = ℚ` itself).
    See also note [forgetful inheritance].
    
    If the field has positive characteristic `p`, our division by zero convention forces
    `ratCast (1 / p) = 1 / 0 = 0`.  FType]
      [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  FType] {GType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. }
      [AddCommGroupAddCommGroup.{u} (G : Type u) : Type uAn additive commutative group is an additive group with commutative `(+)`.  GType] [ModuleModule.{u, v} (R : Type u) (M : Type v) [Semiring R] [AddCommMonoid M] : Type (max u v)A module is a generalization of vector spaces to a scalar semiring.
    It consists of a scalar semiring `R` and an additive monoid of "vectors" `M`,
    connected by a "scalar multiplication" operation `r • x : M`
    (where `r : R` and `x : M`) with some natural associativity and
    distributivity axioms similar to those on a ring.  FType GType]
      {SKType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  SKType] (gG : GType)
      (advPassiveAdversary G SK : PassiveAdversaryPassiveAdversary (G SK : Type) : TypeA passive X3DH adversary with ROM access.  GType SKType) :
      OracleCompOracleComp.{u, v, w} {ι : Type u} (spec : OracleSpec ι) : Type w → Type (max u v w)`OracleComp spec α` represents computations with oracle access to oracles in `spec`,
    where the final return value has type `α`, represented as a free monad over the `PFunctor`
    corresponding to `spec.` 
        (HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`.unifSpecunifSpec : OracleSpec ℕAccess to oracles for uniformly selecting from `Fin (n + 1)` for arbitrary `n : ℕ`.
    By adding `1` to the index we avoid selection from the empty type `Fin 0 ≃ empty`. +HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`.
          KDFOracleKDFOracle (I K : Type) : OracleSpec IKDF as a random oracle, for security proofs.  (Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`.GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType ×Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. GType)Prod.{u, v} (α : Type u) (β : Type v) : Type (max u v)The product type, usually written `α × β`. Product types are also called pair or tuple types.
    Elements of this type are pairs in which the first element is an `α` and the second element is a
    `β`.
    
    Products nest to the right, so `(x, y, z) : α × β × γ` is equivalent to `(x, (y, z)) : α × (β × γ)`.
    
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `×` in identifiers is `Prod`. SKType)HAdd.hAdd.{u, v, w} {α : Type u} {β : Type v} {γ : outParam (Type w)} [self : HAdd α β γ] : α → β → γ`a + b` computes the sum of `a` and `b`.
    The meaning of this notation is type-dependent. 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `+` in identifiers is `add`.
        BoolBool : TypeThe Boolean values, `true` and `false`.
    
    Logically speaking, this is equivalent to `Prop` (the type of propositions). The distinction is
    public important for programming: both propositions and their proofs are erased in the code generator,
    while `Bool` corresponds to the Boolean type in most programming languages and carries precisely one
    bit of run-time information.
    
    Random game: session key sampled uniformly at random. 
    complete

5.7.4. Advantage🔗

Definition5.5
Group: Passive message secrecy game, DDH reduction, and tight security bound under the Random Oracle Model. (6)
Hover another entry in this group to preview it.
Preview
Definition 5.1
Blueprint label
  • exec_game
Group
  • Passive message secrecy game, DDH reduction, and tight security bound under the Random Oracle Model.
L∃∀Nused by 1

The passive secrecy advantage measures an adversary's ability to distinguish the real game from the random game. A value of 0 means the adversary cannot distinguish them.

Code for Definition5.51 definition
  • def passiveSecrecyAdvantage {FType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [FieldField.{u} (K : Type u) : Type uA `Field` is a `CommRing` with multiplicative inverses for nonzero elements.
    
    An instance of `Field K` includes maps `ratCast : ℚ → K` and `qsmul : ℚ → K → K`.
    Those two fields are needed to implement the `DivisionRing K → Algebra ℚ K` instance since we need
    to control the specific definitions for some special cases of `K` (in particular `K = ℚ` itself).
    See also note [forgetful inheritance].
    
    If the field has positive characteristic `p`, our division by zero convention forces
    `ratCast (1 / p) = 1 / 0 = 0`.  FType] [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  FType]
      {GType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [AddCommGroupAddCommGroup.{u} (G : Type u) : Type uAn additive commutative group is an additive group with commutative `(+)`.  GType] [ModuleModule.{u, v} (R : Type u) (M : Type v) [Semiring R] [AddCommMonoid M] : Type (max u v)A module is a generalization of vector spaces to a scalar semiring.
    It consists of a scalar semiring `R` and an additive monoid of "vectors" `M`,
    connected by a "scalar multiplication" operation `r • x : M`
    (where `r : R` and `x : M`) with some natural associativity and
    distributivity axioms similar to those on a ring.  FType GType] {SKType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. }
      [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  SKType] (gG : GType) (advPassiveAdversary G SK : PassiveAdversaryPassiveAdversary (G SK : Type) : TypeA passive X3DH adversary with ROM access.  GType SKType) : Real : TypeThe type `ℝ` of real numbers constructed as equivalence classes of Cauchy sequences of rational
    numbers. 
    def passiveSecrecyAdvantage {FType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. }
      [FieldField.{u} (K : Type u) : Type uA `Field` is a `CommRing` with multiplicative inverses for nonzero elements.
    
    An instance of `Field K` includes maps `ratCast : ℚ → K` and `qsmul : ℚ → K → K`.
    Those two fields are needed to implement the `DivisionRing K → Algebra ℚ K` instance since we need
    to control the specific definitions for some special cases of `K` (in particular `K = ℚ` itself).
    See also note [forgetful inheritance].
    
    If the field has positive characteristic `p`, our division by zero convention forces
    `ratCast (1 / p) = 1 / 0 = 0`.  FType] [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  FType] {GType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. }
      [AddCommGroupAddCommGroup.{u} (G : Type u) : Type uAn additive commutative group is an additive group with commutative `(+)`.  GType] [ModuleModule.{u, v} (R : Type u) (M : Type v) [Semiring R] [AddCommMonoid M] : Type (max u v)A module is a generalization of vector spaces to a scalar semiring.
    It consists of a scalar semiring `R` and an additive monoid of "vectors" `M`,
    connected by a "scalar multiplication" operation `r • x : M`
    (where `r : R` and `x : M`) with some natural associativity and
    distributivity axioms similar to those on a ring.  FType GType]
      {SKType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  SKType] (gG : GType)
      (advPassiveAdversary G SK : PassiveAdversaryPassiveAdversary (G SK : Type) : TypeA passive X3DH adversary with ROM access.  GType SKType) : Real : TypeThe type `ℝ` of real numbers constructed as equivalence classes of Cauchy sequences of rational
    numbers. 
    Passive secrecy advantage under the ROM (two-game formulation). 
    complete

5.7.5. DDH reduction🔗

Definition5.6
Group: Passive message secrecy game, DDH reduction, and tight security bound under the Random Oracle Model. (6)
Hover another entry in this group to preview it.
Preview
Definition 5.1
Blueprint label
  • exec_game
Group
  • Passive message secrecy game, DDH reduction, and tight security bound under the Random Oracle Model.
L∃∀Nused by 1

Given a passive adversary A, we construct a DDH adversary B that embeds the DDH challenge (g, EKa, SPKb, T) as DH3. No internal coin flip: the DDH experiment's own bit handles real/random branching. This makes the bound tight (no factor of 2).

Code for Definition5.61 definition
  • def ddhReduction {FType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [FieldField.{u} (K : Type u) : Type uA `Field` is a `CommRing` with multiplicative inverses for nonzero elements.
    
    An instance of `Field K` includes maps `ratCast : ℚ → K` and `qsmul : ℚ → K → K`.
    Those two fields are needed to implement the `DivisionRing K → Algebra ℚ K` instance since we need
    to control the specific definitions for some special cases of `K` (in particular `K = ℚ` itself).
    See also note [forgetful inheritance].
    
    If the field has positive characteristic `p`, our division by zero convention forces
    `ratCast (1 / p) = 1 / 0 = 0`.  FType] [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  FType] {GType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. }
      [AddCommGroupAddCommGroup.{u} (G : Type u) : Type uAn additive commutative group is an additive group with commutative `(+)`.  GType] [ModuleModule.{u, v} (R : Type u) (M : Type v) [Semiring R] [AddCommMonoid M] : Type (max u v)A module is a generalization of vector spaces to a scalar semiring.
    It consists of a scalar semiring `R` and an additive monoid of "vectors" `M`,
    connected by a "scalar multiplication" operation `r • x : M`
    (where `r : R` and `x : M`) with some natural associativity and
    distributivity axioms similar to those on a ring.  FType GType] {SKType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  SKType]
      (advPassiveAdversary G SK : PassiveAdversaryPassiveAdversary (G SK : Type) : TypeA passive X3DH adversary with ROM access.  GType SKType) : DiffieHellman.DDHAdversaryDiffieHellman.DDHAdversary (_F G : Type) : TypeA DDH adversary receives `(g, A, B, T)` and guesses whether `T = (a * b) • g`
    (real) or `T` is a random group element (random).
    `_F` is a phantom type parameter for the scalar field, enabling Lean to infer `F`
    at call sites of `ddhExp` and related definitions.  FType GType
    def ddhReduction {FType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [FieldField.{u} (K : Type u) : Type uA `Field` is a `CommRing` with multiplicative inverses for nonzero elements.
    
    An instance of `Field K` includes maps `ratCast : ℚ → K` and `qsmul : ℚ → K → K`.
    Those two fields are needed to implement the `DivisionRing K → Algebra ℚ K` instance since we need
    to control the specific definitions for some special cases of `K` (in particular `K = ℚ` itself).
    See also note [forgetful inheritance].
    
    If the field has positive characteristic `p`, our division by zero convention forces
    `ratCast (1 / p) = 1 / 0 = 0`.  FType]
      [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  FType] {GType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. }
      [AddCommGroupAddCommGroup.{u} (G : Type u) : Type uAn additive commutative group is an additive group with commutative `(+)`.  GType] [ModuleModule.{u, v} (R : Type u) (M : Type v) [Semiring R] [AddCommMonoid M] : Type (max u v)A module is a generalization of vector spaces to a scalar semiring.
    It consists of a scalar semiring `R` and an additive monoid of "vectors" `M`,
    connected by a "scalar multiplication" operation `r • x : M`
    (where `r : R` and `x : M`) with some natural associativity and
    distributivity axioms similar to those on a ring.  FType GType]
      {SKType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  SKType]
      (advPassiveAdversary G SK : PassiveAdversaryPassiveAdversary (G SK : Type) : TypeA passive X3DH adversary with ROM access.  GType SKType) :
      DiffieHellman.DDHAdversaryDiffieHellman.DDHAdversary (_F G : Type) : TypeA DDH adversary receives `(g, A, B, T)` and guesses whether `T = (a * b) • g`
    (real) or `T` is a random group element (random).
    `_F` is a phantom type parameter for the scalar field, enabling Lean to infer `F`
    at call sites of `ddhExp` and related definitions.  FType GType
    DDH reduction: embed DDH challenge as DH3, pass ROM output
    to the adversary, return the adversary's guess directly. 
    complete

5.7.6. Distributional equivalences🔗

The core of the reduction: the executed passive games have the same distributions as the DDH games composed with the reduction.

The first equivalence shows that the real passive game equals the DDH real game composed with the reduction (by sampling order independence and smul_smul + mul_comm).

The second equivalence shows that the random passive game equals the DDH random game. The RHS has an extra unused draw from DDH; the proof adds a matching unused draw to the LHS via probOutput_bind_const, then permutes independent draws via the perm_draws tactic.

Both proofs are fully mechanized (no sorry) using the custom perm_draws tactic, which automatically computes the draw permutation via de Bruijn index analysis and emits the minimal swap sequence.

5.7.7. Security theorem🔗

Theorem5.7
Group: Passive message secrecy game, DDH reduction, and tight security bound under the Random Oracle Model. (6)
Hover another entry in this group to preview it.
Preview
Definition 5.1
Blueprint label
  • exec_game
Group
  • Passive message secrecy game, DDH reduction, and tight security bound under the Random Oracle Model.
L∃∀Nused by 0

The passive secrecy advantage of any adversary is bounded by the DDH advantage of Definition 5.6. This is a tight reduction: no factor-of-2 loss.

Code for Theorem5.71 theorem
  • theorem passive_secrecy_le_ddh {FType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [FieldField.{u} (K : Type u) : Type uA `Field` is a `CommRing` with multiplicative inverses for nonzero elements.
    
    An instance of `Field K` includes maps `ratCast : ℚ → K` and `qsmul : ℚ → K → K`.
    Those two fields are needed to implement the `DivisionRing K → Algebra ℚ K` instance since we need
    to control the specific definitions for some special cases of `K` (in particular `K = ℚ` itself).
    See also note [forgetful inheritance].
    
    If the field has positive characteristic `p`, our division by zero convention forces
    `ratCast (1 / p) = 1 / 0 = 0`.  FType] [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  FType]
      {GType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [AddCommGroupAddCommGroup.{u} (G : Type u) : Type uAn additive commutative group is an additive group with commutative `(+)`.  GType] [ModuleModule.{u, v} (R : Type u) (M : Type v) [Semiring R] [AddCommMonoid M] : Type (max u v)A module is a generalization of vector spaces to a scalar semiring.
    It consists of a scalar semiring `R` and an additive monoid of "vectors" `M`,
    connected by a "scalar multiplication" operation `r • x : M`
    (where `r : R` and `x : M`) with some natural associativity and
    distributivity axioms similar to those on a ring.  FType GType] {SKType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. }
      [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  SKType] (gG : GType) (advPassiveAdversary G SK : PassiveAdversaryPassiveAdversary (G SK : Type) : TypeA passive X3DH adversary with ROM access.  GType SKType) :
      passiveSecrecyAdvantagepassiveSecrecyAdvantage {F : Type} [Field F] [SampleableType F] {G : Type} [AddCommGroup G] [Module F G] {SK : Type}
      [SampleableType SK] (g : G) (adv : PassiveAdversary G SK) : ℝPassive secrecy advantage under the ROM (two-game formulation).  gG advPassiveAdversary G SK LE.le.{u} {α : Type u} [self : LE α] : α → α → PropThe less-equal relation: `x ≤ y` 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `≤` in identifiers is `le`.
    
     * The recommended spelling of `<=` in identifiers is `le` (prefer `≤` over `<=`).
        (DiffieHellman.ddhExpRealDiffieHellman.ddhExpReal {F : Type} [Field F] [SampleableType F] {G : Type} [AddCommGroup G] [Module F G] (g : G)
      (adversary : DiffieHellman.DDHAdversary F G) : ProbComp BoolDDH real game: the adversary receives a genuine DH triple `(g, a • g, b • g, (a * b) • g)`.  gG (ddhReductionddhReduction {F : Type} [Field F] [SampleableType F] {G : Type} [AddCommGroup G] [Module F G] {SK : Type}
      [SampleableType SK] (adv : PassiveAdversary G SK) : DiffieHellman.DDHAdversary F GDDH reduction: embed DDH challenge as DH3, pass ROM output
    to the adversary, return the adversary's guess directly.  advPassiveAdversary G SK)).boolDistAdvantageProbComp.boolDistAdvantage (p q : ProbComp Bool) : ℝ
          (DiffieHellman.ddhExpRandDiffieHellman.ddhExpRand {F : Type} [Field F] [SampleableType F] {G : Type} [AddCommGroup G] [Module F G] (g : G)
      (adversary : DiffieHellman.DDHAdversary F G) : ProbComp BoolDDH random game: the adversary receives `(g, a • g, b • g, c • g)` with independent
    `c ← $ᵗ F`.  gG (ddhReductionddhReduction {F : Type} [Field F] [SampleableType F] {G : Type} [AddCommGroup G] [Module F G] {SK : Type}
      [SampleableType SK] (adv : PassiveAdversary G SK) : DiffieHellman.DDHAdversary F GDDH reduction: embed DDH challenge as DH3, pass ROM output
    to the adversary, return the adversary's guess directly.  advPassiveAdversary G SK))
    theorem passive_secrecy_le_ddh {FType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. }
      [FieldField.{u} (K : Type u) : Type uA `Field` is a `CommRing` with multiplicative inverses for nonzero elements.
    
    An instance of `Field K` includes maps `ratCast : ℚ → K` and `qsmul : ℚ → K → K`.
    Those two fields are needed to implement the `DivisionRing K → Algebra ℚ K` instance since we need
    to control the specific definitions for some special cases of `K` (in particular `K = ℚ` itself).
    See also note [forgetful inheritance].
    
    If the field has positive characteristic `p`, our division by zero convention forces
    `ratCast (1 / p) = 1 / 0 = 0`.  FType] [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  FType] {GType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. }
      [AddCommGroupAddCommGroup.{u} (G : Type u) : Type uAn additive commutative group is an additive group with commutative `(+)`.  GType] [ModuleModule.{u, v} (R : Type u) (M : Type v) [Semiring R] [AddCommMonoid M] : Type (max u v)A module is a generalization of vector spaces to a scalar semiring.
    It consists of a scalar semiring `R` and an additive monoid of "vectors" `M`,
    connected by a "scalar multiplication" operation `r • x : M`
    (where `r : R` and `x : M`) with some natural associativity and
    distributivity axioms similar to those on a ring.  FType GType]
      {SKType : TypeA type universe. `Type ≡ Type 0`, `Type u ≡ Sort (u + 1)`. } [SampleableTypeSampleableType (β : Type) : TypeA `SampleableType β` instance means that `β` is a finite inhabited type,
    with a computation `selectElem` that selects uniformly at random from the type.
    This generally requires choosing some "canonical" ordering for the type,
    so we include this to get a computable version of selection.
    We also require that each element has the same probability of being chosen from by `selectElem`,
    see `SampleableType.probOutput_uniformSample` for the reduction when `α` has a fintype instance
    involving the explicit cardinality of the type.  SKType] (gG : GType)
      (advPassiveAdversary G SK : PassiveAdversaryPassiveAdversary (G SK : Type) : TypeA passive X3DH adversary with ROM access.  GType SKType) :
      passiveSecrecyAdvantagepassiveSecrecyAdvantage {F : Type} [Field F] [SampleableType F] {G : Type} [AddCommGroup G] [Module F G] {SK : Type}
      [SampleableType SK] (g : G) (adv : PassiveAdversary G SK) : ℝPassive secrecy advantage under the ROM (two-game formulation).  gG advPassiveAdversary G SK LE.le.{u} {α : Type u} [self : LE α] : α → α → PropThe less-equal relation: `x ≤ y` 
    
    Conventions for notations in identifiers:
    
     * The recommended spelling of `≤` in identifiers is `le`.
    
     * The recommended spelling of `<=` in identifiers is `le` (prefer `≤` over `<=`).
        (DiffieHellman.ddhExpRealDiffieHellman.ddhExpReal {F : Type} [Field F] [SampleableType F] {G : Type} [AddCommGroup G] [Module F G] (g : G)
      (adversary : DiffieHellman.DDHAdversary F G) : ProbComp BoolDDH real game: the adversary receives a genuine DH triple `(g, a • g, b • g, (a * b) • g)`.  gG
              (ddhReductionddhReduction {F : Type} [Field F] [SampleableType F] {G : Type} [AddCommGroup G] [Module F G] {SK : Type}
      [SampleableType SK] (adv : PassiveAdversary G SK) : DiffieHellman.DDHAdversary F GDDH reduction: embed DDH challenge as DH3, pass ROM output
    to the adversary, return the adversary's guess directly. 
                advPassiveAdversary G SK)).boolDistAdvantageProbComp.boolDistAdvantage (p q : ProbComp Bool) : ℝ
          (DiffieHellman.ddhExpRandDiffieHellman.ddhExpRand {F : Type} [Field F] [SampleableType F] {G : Type} [AddCommGroup G] [Module F G] (g : G)
      (adversary : DiffieHellman.DDHAdversary F G) : ProbComp BoolDDH random game: the adversary receives `(g, a • g, b • g, c • g)` with independent
    `c ← $ᵗ F`.  gG
            (ddhReductionddhReduction {F : Type} [Field F] [SampleableType F] {G : Type} [AddCommGroup G] [Module F G] {SK : Type}
      [SampleableType SK] (adv : PassiveAdversary G SK) : DiffieHellman.DDHAdversary F GDDH reduction: embed DDH challenge as DH3, pass ROM output
    to the adversary, return the adversary's guess directly.  advPassiveAdversary G SK))
    X3DH passive secrecy reduces to DDH under the ROM. 
    complete
Proof

Unfold Definition 5.5, show the two boolDistAdvantage expressions are equal via the distributional equivalence lemmas, and conclude by linarith.

-- PROOF-SOURCE
by
  -- Step 1: unfold the LHS to expose the two games
  unfold passiveSecrecyAdvantage
  -- Goal is now:
  -- boolDistAdvantage (execGame (passiveReal g adv))
  --                   (execGame (passiveRand g adv))
  -- ≤ boolDistAdvantage (ddhExpReal g (ddhReduction adv))
  --                     (ddhExpRand g (ddhReduction adv))
  --
  -- We need to show these two pairs of games have the same distributions.
  -- Suffices to show:
  --   execGame (passiveReal g adv) = ddhExpReal g (ddhReduction adv)
  --   execGame (passiveRand g adv) = ddhExpRand g (ddhReduction adv)
  -- (as probability distributions)
  -- It suffices to show equality of the two distribution pairs
  suffices h : ProbComp.boolDistAdvantage
      (execGame (passiveReal (F := F) g adv))
      (execGame (passiveRand (F := F) g adv)) =
    ProbComp.boolDistAdvantage
      (DiffieHellman.ddhExpReal (F := F) g (ddhReduction adv))
      (DiffieHellman.ddhExpRand (F := F) g (ddhReduction adv)) by
    linarith
  -- Both boolDistAdvantage expressions depend only on evalDist.
  -- The distributional equivalences give us equal evalDist, hence
  -- equal probOutput, hence equal boolDistAdvantage.
  unfold ProbComp.boolDistAdvantage
  have hReal := passiveReal_eq_ddhExpReal (F := F) g adv
  have hRand := passiveRand_eq_ddhExpRand (F := F) g adv
  simp only [probOutput, hReal, hRand]