Section Model.
Variable domain : Type.
Class kmodel :=
{
nodes : Type ;
reachable : nodes -> nodes -> Prop ;
reach_refl u : reachable u u ;
reach_tran u v w : reachable u v -> reachable v w -> reachable u w ;
k_interp : interp domain ;
k_P : nodes -> forall P : preds, Vector.t domain (ar_preds P) -> Prop ;
(* k_Bot : nodes -> Prop ; *)
mon_P : forall u v, reachable u v -> forall P (t : Vector.t domain (ar_preds P)), k_P u t -> k_P v t;
}.
Variable M : kmodel.
Fixpoint ksat {ff : falsity_flag} u (rho : nat -> domain) (phi : form) : Prop :=
match phi with
| atom P v => k_P u (Vector.map (@eval _ _ _ k_interp rho) v)
| falsity => False
| bin Impl phi psi => forall v, reachable u v -> ksat v rho phi -> ksat v rho psi
| quant All phi => forall j : domain, ksat u (j .: rho) phi
end.

Lemma ksat_iff {ff : falsity_flag} u rho phi :
ksat u rho phi <-> forall v (H : reachable u v), ksat v rho phi.