Hint Extern 1 (RElim (_ @@ (_, _)) _ _ _ _) =>
eapply rel_pull_relim : typeclass_instances.
(** ** Pushing a relation along functions *)
Inductive rel_push {A1 A2 B1 B2} f g (R: rel A1 A2): rel B1 B2 :=
rel_push_rintro x y: RIntro (R x y) (rel_push f g R) (f x) (g y).
Hint Extern 1 (RIntro _ (rel_push _ _ _) _ _) =>
eapply rel_push_rintro : typeclass_instances.
(** The level we choose here is to match the notation used for [PTree.get] in Compcert's [Maps] library. *)
Notation "R !! ( f , g )" := (rel_push f g R)
(at level 1) : rel_scope.
Notation "R !! f" := (rel_push f f R)
(at level 1) : rel_scope.
Notation "R !! ( f )" := (rel_push f f R)
(at level 1) : rel_scope.
Global Instance rel_push_subrel {A1 A2 B1 B2} (f: A1 -> B1) (g: A2 -> B2):
Proper (subrel ++> subrel) (rel_push f g).
Global Instance rel_push_subrel_params:
Params (@rel_push) 3.

(* Specifications: *)
Lemma rel_push_corefl {A B} (f: A -> B) (R: rel A A):
Coreflexive R ->
Coreflexive (R !! f).