open import Graded.Modality
module Graded.Erasure.Extraction
{a} {M : Set a}
(𝕄 : Modality M)
where
open Modality 𝕄
open import Tools.Bool
open import Tools.Function
open import Tools.List
open import Tools.Nat using (Nat; 2+)
open import Tools.Relation
open import Definition.Untyped M as U
open import Graded.Erasure.Target as T
open import Graded.Erasure.Target.Non-terminating
private
variable
m n l : Nat
Γ : Con U.Term n
A t t′ u : U.Term n
v v′ w : T.Term n
p : M
𝕋 𝕌 : Set _
loop? : Strictness → T.Term n
loop? non-strict = loop non-strict
loop? strict = ↯
erase-prodrecω :
Strictness → M → T.Term n → T.Term (2+ n) → T.Term n
erase-prodrecω s p t u = case is-𝟘? p of λ where
(yes p≡𝟘) → T.lam (u T.[ T.liftSubst (T.sgSubst (loop s)) ])
T.∘⟨ s ⟩ t
(no p≢𝟘) → T.prodrec t u
app-𝟘′ : Bool → Strictness → T.Term n → T.Term n
app-𝟘′ false s t = t T.∘⟨ s ⟩ loop? s
app-𝟘′ true _ t = t
app-𝟘 : Strictness → T.Term n → T.Term n
app-𝟘 s = app-𝟘′ (s == non-strict) s
mutual
erase : Strictness → U.Term n → T.Term n
erase s = erase′ (s == non-strict) s
erase′ : Bool → Strictness → U.Term n → T.Term n
erase′ remove s = erase″
where
erase″ : U.Term n → T.Term n
erase″ (var x) = T.var x
erase″ (defn α) = T.defn α
erase″ (U _) = loop? s
erase″ (ΠΣ⟨ _ ⟩ _ , _ ▷ _ ▹ _) = loop? s
erase″ (U.lam p t) = case remove of λ where
false → T.lam (erase″ t)
true → case is-𝟘? p of λ where
(no _) → T.lam (erase″ t)
(yes _) → erase″ t T.[ loop s ]₀
erase″ (t U.∘⟨ p ⟩ u) = case is-𝟘? p of λ where
(no _) → erase″ t T.∘⟨ s ⟩ erase″ u
(yes _) → app-𝟘′ remove s (erase″ t)
erase″ (U.prod _ p t u) = case is-𝟘? p of λ where
(no _) → prod⟨ s ⟩ (erase″ t) (erase″ u)
(yes _) → erase″ u
erase″ (U.fst p t) = case is-𝟘? p of λ where
(no _) → T.fst (erase″ t)
(yes _) → loop s
erase″ (U.snd p t) = case is-𝟘? p of λ where
(no _) → T.snd (erase″ t)
(yes _) → erase″ t
erase″ (U.prodrec r p _ _ t u) = case is-𝟘? r of λ where
(no _) → erase-prodrecω s p (erase″ t) (erase″ u)
(yes _) → erase″ u T.[ loop s , loop s ]₁₀
erase″ ℕ = loop? s
erase″ U.zero = T.zero
erase″ (U.suc t) = suc⟨ s ⟩ (erase″ t)
erase″ (U.natrec p q r A t u v) =
T.natrec (erase″ t) (erase″ u) (erase″ v)
erase″ Unit! = loop? s
erase″ U.star! = T.star
erase″ (U.unitrec _ p _ _ t u) = case is-𝟘? p of λ where
(no _) → T.unitrec (erase″ t) (erase″ u)
(yes _) → erase″ u
erase″ Empty = loop? s
erase″ (emptyrec p A t) = loop s
erase″ (Id _ _ _) = loop? s
erase″ U.rfl = loop? s
erase″ (J _ _ _ _ _ u _ _) = erase″ u
erase″ (K _ _ _ _ u _) = erase″ u
erase″ ([]-cong _ _ _ _ _) = loop? s
mutual
eraseSubst : Strictness → U.Subst m n → T.Subst m n
eraseSubst = eraseSubst′ false
eraseSubst′ : Bool → Strictness → U.Subst m n → T.Subst m n
eraseSubst′ b s σ x = erase′ b s (σ x)
opaque
eraseDCon″ : (𝕋 → 𝕌) → DCon 𝕋 n → List 𝕌
eraseDCon″ _ ε = []
eraseDCon″ erase (ts ∙⟨ _ ⟩[ t ∷ _ ]) =
eraseDCon″ erase ts ++ (erase t ∷ [])
opaque
unfolding eraseDCon″
eraseDCon′ : Bool → Strictness → DCon (U.Term 0) n → List (T.Term 0)
eraseDCon′ b str = eraseDCon″ (erase′ b str)
eraseDCon : Strictness → DCon (U.Term 0) n → List (T.Term 0)
eraseDCon s = eraseDCon′ (s == non-strict) s