implementation of a flag system in MetaCoq
Require Import MetaCoq.Template.All.
Require Import String.
Import MonadNotation.
Class mode (s:string) := { state: bool }.
Print tmExistingInstance.
Print global_reference.
Definition changeMode (m:string) (value:bool) : TemplateMonad unit :=
ename <- tmEval all m;;
name <- tmFreshName ename;;
tmDefinition name ({| state := value |}:mode m);;
tmExistingInstance name;;
tmMsg (append (append "The mode " m) (append " was " (if value then "set" else "unset"))).
Definition getMode (m:string) : TemplateMonad bool :=
v <- tmInferInstance None (mode m);;
val <- tmEval all (
match v with
my_None => false
| my_Some v' => @state _ v'
end
);;
tmReturn val.
Definition getName (x : nat -> nat) :=
x <- tmEval cbv x;;
t <- tmQuote x;;
match t with
| Ast.tLambda (nNamed na) _ _ => tmReturn na
| _ => tmReturn ""
end.
Notation "'Set' n" := (
name <- getName (fun n:nat => n);;
changeMode name true
)(at level 8).
Notation "'Unset' n" := (
name <- getName (fun n:nat => n);;
changeMode name false
)(at level 8).