Skip to content
Snippets Groups Projects
Commit 87d468e8 authored by Jonas Kastberg Hinrichsen's avatar Jonas Kastberg Hinrichsen
Browse files

Changed side matching to inline, making proofs less branchy

parent 9206b460
No related branches found
No related tags found
No related merge requests found
...@@ -2,6 +2,6 @@ ...@@ -2,6 +2,6 @@
-arg -w -arg -notation-overridden,-redundant-canonical-projection,-several-object-files -arg -w -arg -notation-overridden,-redundant-canonical-projection,-several-object-files
theories/list.v theories/list.v
theories/auth_excl.v theories/auth_excl.v
theories/channel.v
theories/typing.v theories/typing.v
theories/channel.v
theories/logrel.v theories/logrel.v
\ No newline at end of file
...@@ -7,6 +7,7 @@ From iris.base_logic.lib Require Import auth. ...@@ -7,6 +7,7 @@ From iris.base_logic.lib Require Import auth.
From iris.heap_lang.lib Require Import spin_lock. From iris.heap_lang.lib Require Import spin_lock.
From osiris Require Import list. From osiris Require Import list.
From osiris Require Import auth_excl. From osiris Require Import auth_excl.
From osiris Require Import typing.
Set Default Proof Using "Type". Set Default Proof Using "Type".
Import uPred. Import uPred.
...@@ -17,20 +18,17 @@ Definition new_chan : val := ...@@ -17,20 +18,17 @@ Definition new_chan : val :=
let: "lk" := newlock #() in let: "lk" := newlock #() in
(("l","r"),"lk"). (("l","r"),"lk").
Inductive side := Left | Right.
Coercion side_to_bool (s : side) : bool := Coercion side_to_bool (s : side) : bool :=
match s with Left => true | Right => false end. match s with Left => true | Right => false end.
Definition side_elim {A} (s : side) (l r : A) : A :=
match s with Left => l | Right => r end.
Definition get_buffs c := Fst c. Definition get_side : val := λ: "c" "s",
Definition get_left c := Fst (get_buffs c). (if: "s" = #Left then Fst (Fst "c") else Snd (Fst "c"))%E.
Definition get_right c := Snd (get_buffs c). Definition get_lock : val := λ: "c", Snd "c".
Definition get_lock c := Snd c.
Definition dual_side s := Definition get_dual_side : val := λ: "s",
(if: s = #Left then #Right else #Left)%E. (if: "s" = #Left then #Right else #Left)%E.
Definition get_side c s :=
(if: s = #Left then get_left c else get_right c)%E.
Definition send : val := Definition send : val :=
λ: "c" "s" "v", λ: "c" "s" "v",
...@@ -44,11 +42,13 @@ Definition try_recv : val := ...@@ -44,11 +42,13 @@ Definition try_recv : val :=
λ: "c" "s", λ: "c" "s",
let: "lk" := get_lock "c" in let: "lk" := get_lock "c" in
acquire "lk";; acquire "lk";;
let: "l" := (get_side "c" (dual_side "s")) in let: "l" := get_side "c" (get_dual_side "s") in
match: !"l" with let: "ret" :=
SOME "p" => "l" <- Snd "p";; release "lk";; SOME (Fst "p") match: !"l" with
| NONE => release "lk";; NONE SOME "p" => "l" <- Snd "p";; SOME (Fst "p")
end. | NONE => NONE
end in
release "lk";; "ret".
Definition recv : val := Definition recv : val :=
rec: "go" "c" "s" := rec: "go" "c" "s" :=
...@@ -69,34 +69,46 @@ Section channel. ...@@ -69,34 +69,46 @@ Section channel.
chan_r_name : gname chan_r_name : gname
}. }.
Definition chan_ctx (γ : chan_name) (c : val) : iProp Σ := Definition chan_inv (γ : chan_name) (l r : val) : iProp Σ :=
( ls rs,
is_list_ref l ls own (chan_l_name γ) ( to_auth_excl ls)
is_list_ref r rs own (chan_r_name γ) ( to_auth_excl rs))%I.
Typeclasses Opaque chan_inv.
Definition is_chan (γ : chan_name) (c : val) : iProp Σ :=
( l r lk : val, ( l r lk : val,
c = ((l, r), lk)%V c = ((l, r), lk)%V
is_lock N (chan_lock_name γ) lk ( ls rs, is_lock N (chan_lock_name γ) lk (chan_inv γ l r))%I.
is_list_ref l ls own (chan_l_name γ) ( to_auth_excl ls)
is_list_ref r rs own (chan_r_name γ) ( to_auth_excl rs)))%I.
Global Instance chan_ctx_persistent : Persistent (chan_ctx γ c). Global Instance is_chan_persistent : Persistent (is_chan γ c).
Proof. by apply _. Qed. Proof. by apply _. Qed.
Definition chan_frag (γ : chan_name) (c : val) (ls rs : list val) : iProp Σ := Definition chan_own (γ : chan_name) (s : side) (vs : list val) : iProp Σ :=
( l r lk : val, own (side_elim s chan_l_name chan_r_name γ) ( to_auth_excl vs)%I.
c = ((l, r), lk)%V
own (chan_l_name γ) ( to_auth_excl ls)
own (chan_r_name γ) ( to_auth_excl rs))%I.
Global Instance chan_frag_timeless : Timeless (chan_frag γ c ls rs). Global Instance chan_own_timeless γ s vs : Timeless (chan_own γ s vs).
Proof. by apply _. Qed. Proof. by apply _. Qed.
Definition is_chan (γ : chan_name) (c : val) (ls rs : list val) : iProp Σ := Lemma get_side_spec Φ s (l r lk : val) :
(chan_ctx γ c chan_frag γ c ls rs)%I. Φ (side_elim s l r) -∗
WP get_side ((l, r), lk)%V #s {{ Φ }}.
Proof. iIntros "?". wp_lam. by destruct s; wp_pures. Qed.
Lemma get_lock_spec Φ (l r lk : val) :
Φ lk -∗
WP get_lock ((l, r), lk)%V {{ Φ }}.
Proof. iIntros "?". wp_lam. by wp_pures. Qed.
Lemma dual_side_spec Φ s :
Φ #(dual_side s) -∗ WP get_dual_side #s {{ Φ }}.
Proof. iIntros "?". wp_lam. by destruct s; wp_pures. Qed.
Lemma new_chan_spec : Lemma new_chan_spec :
{{{ True }}} {{{ True }}}
new_chan #() new_chan #()
{{{ c γ, RET c; is_chan γ c [] [] }}}. {{{ c γ, RET c; is_chan γ c chan_own γ Left [] chan_own γ Right [] }}}.
Proof. Proof.
iIntros (Φ) "_ HΦ". rewrite /is_chan /chan_ctx /chan_frag. iIntros (Φ) "_ HΦ". rewrite /is_chan /chan_own.
wp_lam. wp_lam.
wp_apply (lnil_spec with "[//]"); iIntros (ls Hls). wp_alloc l as "Hl". wp_apply (lnil_spec with "[//]"); iIntros (ls Hls). wp_alloc l as "Hl".
wp_apply (lnil_spec with "[//]"); iIntros (rs Hrs). wp_alloc r as "Hr". wp_apply (lnil_spec with "[//]"); iIntros (rs Hrs). wp_alloc r as "Hr".
...@@ -114,187 +126,120 @@ Section channel. ...@@ -114,187 +126,120 @@ Section channel.
with "[Hl Hr Hls Hrs]"). with "[Hl Hr Hls Hrs]").
{ eauto 10 with iFrame. } { eauto 10 with iFrame. }
iIntros (lk γlk) "#Hlk". wp_pures. iIntros (lk γlk) "#Hlk". wp_pures.
iApply ("HΦ" $! _ (Chan_name γlk lsγ rsγ)). iApply ("HΦ" $! _ (Chan_name γlk lsγ rsγ)); simpl.
eauto 20 with iFrame. rewrite /chan_inv /=. eauto 20 with iFrame.
Qed. Qed.
Definition chan_frag_snoc (γ : chan_name) (c : val) Lemma chan_inv_alt s γ l r :
(l r : list val) (s : side) (v : val) chan_inv γ l r ⊣⊢ ls rs,
: iProp Σ := is_list_ref (side_elim s l r) ls
match s with own (side_elim s chan_l_name chan_r_name γ) ( to_auth_excl ls)
| Left => chan_frag γ c (l ++ [v]) r is_list_ref (side_elim s r l) rs
| Right => chan_frag γ c l (r ++ [v]) own (side_elim s chan_r_name chan_l_name γ) ( to_auth_excl rs).
end. Proof.
destruct s; rewrite /chan_inv //=.
iSplit; iDestruct 1 as (ls rs) "(?&?&?&?)"; iExists rs, ls; iFrame.
Qed.
Lemma send_spec Φ E γ c v s : Lemma send_spec Φ E γ c v s :
chan_ctx γ c -∗ is_chan γ c -∗
(|={,E}=> ls rs, (|={,E}=> vs,
chan_frag γ c ls rs chan_own γ s vs
(chan_frag_snoc γ c ls rs s v ={E,}=∗ Φ #())) -∗ (chan_own γ s (vs ++ [v]) ={E,}=∗ Φ #())) -∗
WP send c #s v {{ Φ }}. WP send c #s v {{ Φ }}.
Proof. Proof.
iIntros "Hc HΦ". wp_lam; wp_pures. iIntros "Hc HΦ". wp_lam; wp_pures.
iDestruct "Hc" as (l r lk ->) "#Hlock"; wp_pures. iDestruct "Hc" as (l r lk ->) "#Hlock"; wp_pures.
wp_apply get_lock_spec; wp_pures.
wp_apply (acquire_spec with "Hlock"); iIntros "[Hlocked Hinv]". wp_apply (acquire_spec with "Hlock"); iIntros "[Hlocked Hinv]".
iDestruct "Hinv" as (ls rs) "(Hl & Hls & Hr & Hrs)". wp_apply get_side_spec; wp_pures.
destruct s. iDestruct (chan_inv_alt s with "Hinv") as
- wp_pures. iDestruct "Hl" as (ll lhd ->) "(Hl & Hll)". (vs ws) "(Href & Hvs & Href' & Hws)".
wp_load. wp_apply (lsnoc_spec with "Hll"). iDestruct "Href" as (ll lhd Hslr) "(Hll & Hlvs)"; rewrite Hslr.
iIntros (hd' Hll). wp_load. wp_apply (lsnoc_spec with "Hlvs"). iIntros (lhd' Hlvs).
wp_bind (_ <- _)%E. iMod "HΦ" as (ls' rs') "[Hchan HΦ]". wp_bind (_ <- _)%E.
iDestruct "Hchan" as (l' r' lk' [= <- <- <-]) "[Hls' Hrs']". iMod "HΦ" as (vs') "[Hchan HΦ]".
iDestruct (excl_eq with "Hls Hls'") as %->. iDestruct (excl_eq with "Hvs Hchan") as %->.
iMod (excl_update _ _ _ (ls ++ [v]) with "Hls Hls'") as "[Hls Hls']". iMod (excl_update _ _ _ (vs ++ [v]) with "Hvs Hchan") as "[Hvs Hchan]".
wp_store. wp_store. iMod ("HΦ" with "Hchan") as "HΦ".
iMod ("HΦ" with "[Hls' Hrs']") as "HΦ". iModIntro.
{ rewrite /= /chan_frag. eauto with iFrame. } wp_apply (release_spec with "[-HΦ $Hlock $Hlocked]"); last eauto.
iModIntro. iApply (chan_inv_alt s).
wp_apply (release_spec with "[-HΦ $Hlock $Hlocked]"); last eauto. rewrite /is_list_ref. eauto 10 with iFrame.
{ rewrite /is_list_ref. eauto 10 with iFrame. }
- wp_pures. iDestruct "Hr" as (lr rhd ->) "(Hr & Hlr)".
wp_load. wp_apply (lsnoc_spec with "Hlr").
iIntros (hd' Hlr). wp_pures.
wp_bind (_ <- _)%E. iMod "HΦ" as (ls' rs') "[Hchan HΦ]".
wp_store.
iDestruct "Hchan" as (l' r' lk' [= <- <- <-]) "[Hls' Hrs']".
iDestruct (excl_eq with "Hrs Hrs'") as %->.
iMod (excl_update _ _ _ (rs ++ [v]) with "Hrs Hrs'") as "[Hrs Hrs']".
iMod ("HΦ" with "[Hls' Hrs']") as "HΦ".
{ rewrite /= /chan_frag. eauto with iFrame. }
iModIntro.
wp_apply (release_spec with "[-HΦ $Hlock $Hlocked]"); last eauto.
{ rewrite /is_list_ref. eauto 10 with iFrame. }
Qed. Qed.
Definition try_recv_fail (γ : chan_name) (c : val)
(l r : list val) (s : side) : iProp Σ :=
match s with
| Left => (chan_frag γ c l r r = [])%I
| Right => (chan_frag γ c l r l = [])%I
end.
Definition try_recv_succ (γ : chan_name) (c : val)
(l r : list val) (s : side) (v : val) : iProp Σ :=
match s with
| Left => ( r', chan_frag γ c l r' r = v::r')%I
| Right => ( l', chan_frag γ c l' r l = v::l')%I
end.
Lemma try_recv_spec Φ E γ c s : Lemma try_recv_spec Φ E γ c s :
chan_ctx γ c -∗ is_chan γ c -∗
(|={,E}=> ls rs, (|={,E}=> vs,
chan_frag γ c ls rs chan_own γ (dual_side s) vs
((try_recv_fail γ c ls rs s ={E,}=∗ Φ NONEV) ((vs = [] -∗ chan_own γ (dual_side s) vs ={E,}=∗ Φ NONEV)
( v, try_recv_succ γ c ls rs s v ={E,}=∗ Φ (SOMEV v)))) -∗ ( v vs', vs = v :: vs' -∗
chan_own γ (dual_side s) vs' ={E,}=∗ Φ (SOMEV v)))) -∗
WP try_recv c #s {{ Φ }}. WP try_recv c #s {{ Φ }}.
Proof. Proof.
iIntros "Hc HΦ". wp_lam; wp_pures. iIntros "Hc HΦ". wp_lam; wp_pures.
iDestruct "Hc" as (l r lk ->) "#Hlock"; wp_pures. iDestruct "Hc" as (l r lk ->) "#Hlock"; wp_pures.
wp_apply (acquire_spec with "Hlock"); iIntros "[Hlocked Hinv]". wp_apply get_lock_spec; wp_pures.
iDestruct "Hinv" as (ls rs) "(Hls & Hlsa & Hrs & Hrsa)". wp_apply (acquire_spec with "Hlock"); iIntros "[Hlocked Hinv]". wp_pures.
destruct s; simpl. wp_apply dual_side_spec. wp_apply get_side_spec; wp_pures.
- iDestruct "Hrs" as (rl rhd ->) "[Hrs #Hrhd]". iDestruct (chan_inv_alt (dual_side s) with "Hinv") as
wp_pures. (vs ws) "(Href & Hvs & Href' & Hws)".
wp_bind (Load _). iDestruct "Href" as (ll lhd Hslr) "(Hll & Hlvs)"; rewrite Hslr.
iMod "HΦ" as (ls' rs') "[Hchan HΦ]". wp_bind (! _)%E.
wp_load. iMod "HΦ" as (vs') "[Hchan HΦ]".
destruct rs; simpl. wp_load.
+ iDestruct "Hrhd" as %->. iDestruct (excl_eq with "Hvs Hchan") as %->.
iDestruct "Hchan" as (l' r' lk' [= <- <- <-]) "[Hlsf Hrsf]". destruct vs as [|v vs]; simpl.
iDestruct (excl_eq with "Hlsa Hlsf") as %->. - iDestruct "Hlvs" as %->.
iDestruct (excl_eq with "Hrsa Hrsf") as %->. iDestruct "HΦ" as "[HΦ _]".
iDestruct "HΦ" as "[HΦ _]". iMod ("HΦ" with "[//] Hchan") as "HΦ".
iMod ("HΦ" with "[Hlsf Hrsf]") as "HΦ". iModIntro.
{ rewrite /try_recv_fail /chan_frag. wp_apply (release_spec with "[-HΦ $Hlocked $Hlock]").
eauto 10 with iFrame. } { iApply (chan_inv_alt (dual_side s)).
iModIntro. rewrite /is_list_ref. eauto 10 with iFrame. }
wp_apply (release_spec with "[-HΦ $Hlocked $Hlock]"). iIntros (_). wp_pures. by iApply "HΦ".
{ rewrite /is_list_ref /is_list. eauto 10 with iFrame. } - iDestruct "Hlvs" as %(hd' & -> & Hhd').
iIntros (_). iMod (excl_update _ _ _ vs with "Hvs Hchan") as "[Hvs Hchan]".
wp_pures. iDestruct "HΦ" as "[_ HΦ]".
by iApply "HΦ". iMod ("HΦ" with "[//] Hchan") as "HΦ".
+ iDestruct "Hrhd" as %[hd' [-> Hrhd']]. iModIntro. wp_store.
iDestruct "Hchan" as (l' r' lk' [= <- <- <-]) "[Hlsf Hrsf]". wp_apply (release_spec with "[-HΦ $Hlocked $Hlock]").
iDestruct (excl_eq with "Hlsa Hlsf") as %->. { iApply (chan_inv_alt (dual_side s)).
iDestruct (excl_eq with "Hrsa Hrsf") as %->. rewrite /is_list_ref. eauto 10 with iFrame. }
iDestruct (excl_update _ _ _ (rs) with "Hrsa Hrsf") as ">[Hrsa Hrsf]". iIntros (_). wp_pures. by iApply "HΦ".
iDestruct "HΦ" as "[_ HΦ]".
iMod ("HΦ" with "[Hlsf Hrsf]") as "HΦ".
{ rewrite /try_recv_succ /chan_frag.
eauto 10 with iFrame. }
iModIntro.
wp_store.
wp_apply (release_spec with "[-HΦ $Hlocked $Hlock]").
{ rewrite /is_list_ref /is_list. eauto 10 with iFrame. }
iIntros (_).
wp_pures.
by iApply "HΦ".
- iDestruct "Hls" as (ll lhd ->) "[Hls #Hlhd]".
wp_pures.
wp_bind (Load _).
iMod "HΦ" as (ls' rs') "[Hchan HΦ]".
wp_load.
destruct ls; simpl.
+ iDestruct "Hlhd" as %->.
iDestruct "Hchan" as (l' r' lk' [= <- <- <-]) "[Hlsf Hrsf]".
iDestruct (excl_eq with "Hlsa Hlsf") as %->.
iDestruct (excl_eq with "Hrsa Hrsf") as %->.
iDestruct "HΦ" as "[HΦ _]".
iMod ("HΦ" with "[Hlsf Hrsf]") as "HΦ".
{ rewrite /try_recv_fail /chan_frag.
eauto 10 with iFrame. }
iModIntro.
wp_apply (release_spec with "[-HΦ $Hlocked $Hlock]").
{ rewrite /is_list_ref /is_list. eauto 10 with iFrame. }
iIntros (_).
wp_pures.
by iApply "HΦ".
+ iDestruct "Hlhd" as %[hd' [-> Hlhd']].
iDestruct "Hchan" as (l' r' lk' [= <- <- <-]) "[Hlsf Hrsf]".
iDestruct (excl_eq with "Hlsa Hlsf") as %->.
iDestruct (excl_eq with "Hrsa Hrsf") as %->.
iDestruct (excl_update _ _ _ (ls) with "Hlsa Hlsf") as ">[Hlsa Hlsf]".
iDestruct "HΦ" as "[_ HΦ]".
iMod ("HΦ" with "[Hlsf Hrsf]") as "HΦ".
{ rewrite /try_recv_succ /chan_frag. eauto 10 with iFrame. }
iModIntro.
wp_store.
wp_apply (release_spec with "[-HΦ $Hlocked $Hlock]").
{ rewrite /is_list_ref /is_list. eauto 10 with iFrame. }
iIntros (_).
wp_pures.
by iApply "HΦ".
Qed. Qed.
Lemma recv_spec Φ E γ c s : Lemma recv_spec Φ E γ c s :
chan_ctx γ c -∗ is_chan γ c -∗
( (|={,E}=> ls rs, ( (|={,E}=> vs,
chan_frag γ c ls rs chan_own γ (dual_side s) vs
((try_recv_fail γ c ls rs s ={E,}=∗ True) ((vs = [] -∗ chan_own γ (dual_side s) vs ={E,}=∗ True)
( v, try_recv_succ γ c ls rs s v ={E,}=∗ Φ v)))) -∗ ( v vs', vs = v :: vs' -∗
chan_own γ (dual_side s) vs' ={E,}=∗ Φ v)))) -∗
WP recv c #s {{ Φ }}. WP recv c #s {{ Φ }}.
Proof. Proof.
iIntros "#Hc #HΦ". iIntros "#Hc #HΦ".
rewrite /recv. rewrite /recv.
iLöb as "IH". iLöb as "IH".
wp_apply (try_recv_spec with "Hc")=> //. wp_apply (try_recv_spec with "Hc")=> //.
iMod "HΦ" as (ls rs) "[Hchan [HΦfail HΦsucc]]". iMod "HΦ" as (vs) "[Hchan [HΦfail HΦsucc]]".
iModIntro. iModIntro.
iExists _, _. iExists _.
iFrame. iFrame.
iNext. iNext.
iSplitL "HΦfail". iSplitL "HΦfail".
- iIntros "Hupd". - iIntros "Hvs Hown".
iDestruct ("HΦfail") as "HΦ". iRename ("HΦfail") into "HΦ".
iMod ("HΦ" with "Hupd") as "HΦ". iDestruct ("HΦ" with "Hvs Hown") as "HΦ".
iMod ("HΦ") as "HΦ".
iModIntro. iModIntro.
wp_match. wp_match.
by iApply ("IH"). by iApply ("IH").
- iDestruct ("HΦsucc") as "HΦ". - iRename ("HΦsucc") into "HΦ".
iIntros (v) "Hupd". iIntros (v vs') "Hvs Hown".
iSpecialize("HΦ" $!v). iMod ("HΦ" with "Hvs Hown") as "HΦ".
iMod ("HΦ" with "Hupd") as "HΦ".
iModIntro. iModIntro.
by wp_pures. by wp_pures.
Qed. Qed.
End channel. End channel.
\ No newline at end of file
...@@ -18,21 +18,11 @@ Section logrel. ...@@ -18,21 +18,11 @@ Section logrel.
st_r_name : gname st_r_name : gname
}. }.
Definition stmapsto_frag γ (st : stype) s : iProp Σ := Definition st_own (γ : st_name) (s : side) (st : stype) : iProp Σ :=
let γ := own (side_elim s st_l_name st_r_name γ) ( to_auth_excl st)%I.
match s with
| Left => st_l_name γ
| Right => st_r_name γ
end in
own γ ( to_auth_excl st)%I.
Definition stmapsto_full γ (st : stype) s : iProp Σ := Definition st_ctx (γ : st_name) (s : side) (st : stype) : iProp Σ :=
let γ := own (side_elim s st_l_name st_r_name γ) ( to_auth_excl st)%I.
match s with
| Left => st_l_name γ
| Right => st_r_name γ
end in
own γ ( to_auth_excl st)%I.
Fixpoint st_eval (vs : list val) (st1 st2 : stype) : Prop := Fixpoint st_eval (vs : list val) (st1 st2 : stype) : Prop :=
match vs with match vs with
...@@ -70,33 +60,34 @@ Section logrel. ...@@ -70,33 +60,34 @@ Section logrel.
Definition inv_st (γ :st_name) (c : val) : iProp Σ := Definition inv_st (γ :st_name) (c : val) : iProp Σ :=
( l r stl str, ( l r stl str,
chan_frag (st_c_name γ) c l r chan_own (st_c_name γ) Left l
stmapsto_full γ stl Left chan_own (st_c_name γ) Right r
stmapsto_full γ str Right st_ctx γ Left stl
st_ctx γ Right str
((r = [] st_eval l stl str) ((r = [] st_eval l stl str)
(l = [] st_eval r str stl)))%I. (l = [] st_eval r str stl)))%I.
Definition st_ctx (γ : st_name) (st : stype) (c : val) : iProp Σ := Definition is_st (γ : st_name) (st : stype) (c : val) : iProp Σ :=
(chan_ctx N (st_c_name γ) c inv N (inv_st γ c))%I. (is_chan N (st_c_name γ) c inv N (inv_st γ c))%I.
Definition st_frag (γ : st_name) (st : stype) (s : side) : iProp Σ :=
stmapsto_frag γ st s.
Definition interp_st (γ : st_name) (st : stype) Definition interp_st (γ : st_name) (st : stype)
(c : val) (s : side) : iProp Σ := (c : val) (s : side) : iProp Σ :=
(st_frag γ st s st_ctx γ st c)%I. (st_own γ s st is_st γ st c)%I.
Notation "⟦ c @ s : sτ ⟧{ γ }" := (interp_st γ c s) Notation "⟦ c @ s : sτ ⟧{ γ }" := (interp_st γ c s)
(at level 10, s at next level, at next level, γ at next level, (at level 10, s at next level, at next level, γ at next level,
format "⟦ c @ s : sτ ⟧{ γ }"). format "⟦ c @ s : sτ ⟧{ γ }").
Lemma new_chan_vs st E c : Lemma new_chan_vs st E c :
is_chan N c [] [] ={E}=∗ is_chan N c
chan_own Left []
chan_own Right []
={E}=∗
, ,
let γ := SessionType_name in let γ := SessionType_name in
c @ Left : st {γ} c @ Right : dual_stype st {γ}. c @ Left : st {γ} c @ Right : dual_stype st {γ}.
Proof. Proof.
iIntros "[#Hcctx Hcf]". iIntros "[#Hcctx [Hcol Hcor]]".
iMod (own_alloc ( (to_auth_excl st) iMod (own_alloc ( (to_auth_excl st)
(to_auth_excl st))) (to_auth_excl st)))
as () "[Hlsta Hlstf]"; first done. as () "[Hlsta Hlstf]"; first done.
...@@ -108,8 +99,7 @@ Section logrel. ...@@ -108,8 +99,7 @@ Section logrel.
{ iNext. rewrite /inv_st. eauto 10 with iFrame. } { iNext. rewrite /inv_st. eauto 10 with iFrame. }
iModIntro. iModIntro.
iExists _, _. iExists _, _.
iFrame. simpl. iFrame "Hlstf Hrstf Hcctx Hinv".
repeat iSplitL=> //.
Qed. Qed.
Lemma new_chan_st_spec st : Lemma new_chan_st_spec st :
...@@ -127,35 +117,32 @@ Section logrel. ...@@ -127,35 +117,32 @@ Section logrel.
{ rewrite /is_chan. eauto with iFrame. } { rewrite /is_chan. eauto with iFrame. }
iDestruct "H" as ( ) "[Hl Hr]". iDestruct "H" as ( ) "[Hl Hr]".
iApply "HΦ". iApply "HΦ".
iModIntro. by iFrame.
iFrame.
Qed. Qed.
Coercion side_to_side (s : side) : channel.side :=
match s with Left => channel.Left | Right => channel.Right end.
Lemma send_vs c γ s (P : val Prop) st E : Lemma send_vs c γ s (P : val Prop) st E :
N E N E
c @ s : TSend P st {γ} ={E,E∖↑N}=∗ c @ s : TSend P st {γ} ={E,E∖↑N}=∗
l r, chan_frag (st_c_name γ) c l r vs, chan_own (st_c_name γ) s vs
( v, P v -∗ ( v, P v -∗
chan_frag_snoc (st_c_name γ) c l r s v chan_own (st_c_name γ) s (vs ++ [v])
={E N,E}=∗ c @ s : st v {γ}). ={E N,E}=∗ c @ s : st v {γ}).
Proof. Proof.
iIntros (Hin) "[Hstf #[Hcctx Hinv]]". iIntros (Hin) "[Hstf #[Hcctx Hinv]]".
iMod (inv_open with "Hinv") as "Hinv'"=> //. iMod (inv_open with "Hinv") as "Hinv'"=> //.
iDestruct "Hinv'" as "[Hinv' Hinvstep]". iDestruct "Hinv'" as "[Hinv' Hinvstep]".
iDestruct "Hinv'" as (l r stl str) "(>Hcf & Hstla & Hstra & Hinv')". iDestruct "Hinv'" as
(l r stl str) "(>Hclf & >Hcrf & Hstla & Hstra & Hinv')".
iModIntro. iModIntro.
rewrite /stmapsto_frag /stmapsto_full.
iExists l, r.
iIntros "{$Hcf} !>" (v HP) "Hcf".
destruct s. destruct s.
- iRename "Hstf" into "Hstlf". - iExists _.
iIntros "{$Hclf} !>" (v HP) "Hclf".
iRename "Hstf" into "Hstlf".
iDestruct (excl_eq with "Hstla Hstlf") as %<-. iDestruct (excl_eq with "Hstla Hstlf") as %<-.
iMod (excl_update _ _ _ (st v) with "Hstla Hstlf") as "[Hstla Hstlf]". iMod (excl_update _ _ _ (st v) with "Hstla Hstlf") as "[Hstla Hstlf]".
iMod ("Hinvstep" with "[-Hstlf]") as "_". iMod ("Hinvstep" with "[-Hstlf]") as "_".
{ iNext. {
iNext.
iExists _,_,_,_. iFrame. iExists _,_,_,_. iFrame.
iLeft. iLeft.
iDestruct "Hinv'" as "[[-> Heval]|[-> Heval]]"; iDestruct "Hinv'" as "[[-> Heval]|[-> Heval]]";
...@@ -172,11 +159,14 @@ Section logrel. ...@@ -172,11 +159,14 @@ Section logrel.
split=> //. split=> //.
} }
iModIntro. iFrame "Hcctx ∗ Hinv". iModIntro. iFrame "Hcctx ∗ Hinv".
- iRename "Hstf" into "Hstrf". - iExists _.
iIntros "{$Hcrf} !>" (v HP) "Hcrf".
iRename "Hstf" into "Hstrf".
iDestruct (excl_eq with "Hstra Hstrf") as %<-. iDestruct (excl_eq with "Hstra Hstrf") as %<-.
iMod (excl_update _ _ _ (st v) with "Hstra Hstrf") as "[Hstra Hstrf]". iMod (excl_update _ _ _ (st v) with "Hstra Hstrf") as "[Hstra Hstrf]".
iMod ("Hinvstep" with "[-Hstrf]") as "_". iMod ("Hinvstep" with "[-Hstrf]") as "_".
{ iNext. {
iNext.
iExists _,_, _, _. iFrame. iExists _,_, _, _. iFrame.
iRight. iRight.
iDestruct "Hinv'" as "[[-> Heval]|[-> Heval]]"; iDestruct "Hinv'" as "[[-> Heval]|[-> Heval]]";
...@@ -190,7 +180,8 @@ Section logrel. ...@@ -190,7 +180,8 @@ Section logrel.
split=> //. split=> //.
- iSplit=> //. - iSplit=> //.
iPureIntro. iPureIntro.
by eapply st_eval_send. } by eapply st_eval_send.
}
iModIntro. iFrame "Hcctx ∗ Hinv". iModIntro. iFrame "Hcctx ∗ Hinv".
Qed. Qed.
...@@ -203,8 +194,8 @@ Section logrel. ...@@ -203,8 +194,8 @@ Section logrel.
iIntros (HP Φ) "Hsend HΦ". iIntros (HP Φ) "Hsend HΦ".
iApply (send_spec with "[#]"). iApply (send_spec with "[#]").
{ iDestruct "Hsend" as "[? [$ ?]]". } { iDestruct "Hsend" as "[? [$ ?]]". }
iMod (send_vs with "Hsend") as (ls lr) "[Hch H]"; first done. iMod (send_vs with "Hsend") as (vs) "[Hch H]"; first done.
iModIntro. iExists ls, lr. iFrame "Hch". iModIntro. iExists vs. iFrame "Hch".
iIntros "!> Hupd". iApply "HΦ". iIntros "!> Hupd". iApply "HΦ".
iApply ("H" $! v HP with "[Hupd]"). by destruct s. iApply ("H" $! v HP with "[Hupd]"). by destruct s.
Qed. Qed.
...@@ -213,33 +204,32 @@ Section logrel. ...@@ -213,33 +204,32 @@ Section logrel.
N E N E
c @ s : TRecv P st {γ} c @ s : TRecv P st {γ}
={E,E∖↑N}=∗ ={E,E∖↑N}=∗
l r, chan_frag (st_c_name γ) c l r vs, chan_own (st_c_name γ) (dual_side s) vs
( ((try_recv_fail (st_c_name γ) c l r s ={E∖↑N,E}=∗ ( ((vs = [] -∗ chan_own (st_c_name γ) (dual_side s) vs ={E∖↑N,E}=∗
c @ s : TRecv P st {γ}) c @ s : TRecv P st {γ})
( v, try_recv_succ (st_c_name γ) c l r s v ={E∖↑N,E}=∗ ( v vs', vs = v :: vs' -∗
chan_own (st_c_name γ) (dual_side s) vs' ={E∖↑N,E}=∗
c @ s : (st v) {γ} P v))). c @ s : (st v) {γ} P v))).
Proof. Proof.
iIntros (Hin) "[Hstf #[Hcctx Hinv]]". iIntros (Hin) "[Hstf #[Hcctx Hinv]]".
iMod (inv_open with "Hinv") as "Hinv'"=> //. iMod (inv_open with "Hinv") as "Hinv'"=> //.
iDestruct "Hinv'" as "[Hinv' Hinvstep]". iDestruct "Hinv'" as "[Hinv' Hinvstep]".
iDestruct "Hinv'" as (l r stl str) "(>Hcf & Hstla & Hstra & Hinv')". iDestruct "Hinv'" as
(l r stl str) "(>Hclf & >Hcrf & Hstla & Hstra & Hinv')".
iModIntro. iModIntro.
rewrite /stmapsto_frag /stmapsto_full.
iExists l, r.
iIntros "{$Hcf} !>".
destruct s. destruct s.
- iRename "Hstf" into "Hstlf". - iExists _.
iIntros "{$Hcrf} !>".
iRename "Hstf" into "Hstlf".
rewrite /st_own /st_ctx. simpl.
iDestruct (excl_eq with "Hstla Hstlf") as %<-. iDestruct (excl_eq with "Hstla Hstlf") as %<-.
iSplit=> //. iSplit=> //.
+ iIntros "[Hfail Hemp]". + iIntros "Hvs Hown".
iMod ("Hinvstep" with "[-Hstlf]") as "_". iMod ("Hinvstep" with "[-Hstlf]") as "_".
{ iNext. iExists l,r,_,_. iFrame. } { iNext. iExists l,r,_,_. iFrame. }
iModIntro. iFrame "Hcctx ∗ Hinv". iModIntro. iFrame "Hcctx ∗ Hinv".
+ simpl. iIntros (v) "Hsucc". + iIntros (v vs Hvs) "Hown".
rewrite /try_recv_succ. simpl. iDestruct "Hinv'" as "[[-> Heval]|[-> Heval]]"; first inversion Hvs.
iDestruct "Hsucc" as (r') "[Hsucc Hr]".
iDestruct "Hr" as %Hr.
iDestruct "Hinv'" as "[[-> Heval]|[-> Heval]]"; first inversion Hr.
iMod (excl_update _ _ _ (st v) with "Hstla Hstlf") as "[Hstla Hstlf]". iMod (excl_update _ _ _ (st v) with "Hstla Hstlf") as "[Hstla Hstlf]".
subst. subst.
iDestruct "Heval" as %Heval. iDestruct "Heval" as %Heval.
...@@ -247,18 +237,17 @@ Section logrel. ...@@ -247,18 +237,17 @@ Section logrel.
iMod ("Hinvstep" with "[-Hstlf]") as "_". iMod ("Hinvstep" with "[-Hstlf]") as "_".
{ iExists _,_,_,_. iFrame. iRight=> //. } { iExists _,_,_,_. iFrame. iRight=> //. }
by iFrame (HP) "Hcctx Hinv". by iFrame (HP) "Hcctx Hinv".
- iRename "Hstf" into "Hstrf". - iExists _.
iIntros "{$Hclf} !>".
iRename "Hstf" into "Hstrf".
iDestruct (excl_eq with "Hstra Hstrf") as %<-. iDestruct (excl_eq with "Hstra Hstrf") as %<-.
iSplit=> //. iSplit=> //.
+ iIntros "[Hfail Hemp]". + iIntros "Hvs Hown".
iMod ("Hinvstep" with "[-Hstrf]") as "_". iMod ("Hinvstep" with "[-Hstrf]") as "_".
{ iNext. iExists l,r,_,_. iFrame. } { iNext. iExists l,r,_,_. iFrame. }
iModIntro. iFrame "Hcctx ∗ Hinv". iModIntro. iFrame "Hcctx ∗ Hinv".
+ simpl. iIntros (v) "Hsucc". + simpl. iIntros (v vs' Hvs) "Hown".
rewrite /try_recv_succ. simpl. iDestruct "Hinv'" as "[[-> Heval]|[-> Heval]]"; last inversion Hvs.
iDestruct "Hsucc" as (r') "[Hsucc Hr]".
iDestruct "Hr" as %Hl.
iDestruct "Hinv'" as "[[-> Heval]|[-> Heval]]"; last inversion Hl.
iMod (excl_update _ _ _ (st v) with "Hstra Hstrf") as "[Hstra Hstrf]". iMod (excl_update _ _ _ (st v) with "Hstra Hstrf") as "[Hstra Hstrf]".
subst. subst.
iDestruct "Heval" as %Heval. iDestruct "Heval" as %Heval.
...@@ -277,19 +266,21 @@ Section logrel. ...@@ -277,19 +266,21 @@ Section logrel.
iIntros (Φ) "Hrecv HΦ". iIntros (Φ) "Hrecv HΦ".
iApply (try_recv_spec with "[#]"). iApply (try_recv_spec with "[#]").
{ iDestruct "Hrecv" as "[? [$ ?]]". } { iDestruct "Hrecv" as "[? [$ ?]]". }
iMod (try_recv_vs with "Hrecv") as (ls lr) "[Hch H]"; first done. iMod (try_recv_vs with "Hrecv") as (vs) "[Hch H]"; first done.
iModIntro. iExists ls, lr. iFrame "Hch". iModIntro. iExists vs. iFrame "Hch".
iIntros "!>". iIntros "!>".
iSplit. iSplit.
- iIntros "Hupd". - iIntros (Hvs) "Hown".
iDestruct "H" as "[H _]". iDestruct "H" as "[H _]".
iMod ("H" with "Hupd") as "H". iSpecialize ("H" $!Hvs).
iMod ("H" with "Hown") as "H".
iModIntro. iModIntro.
iApply "HΦ"=> //. iApply "HΦ"=> //.
eauto with iFrame. eauto with iFrame.
- iIntros (v) "Hupd". - iIntros (v vs' Hvs) "Hown".
iDestruct "H" as "[_ H]". iDestruct "H" as "[_ H]".
iMod ("H" with "Hupd") as "H". iSpecialize ("H" $!v vs' Hvs).
iMod ("H" with "Hown") as "H".
iModIntro. iModIntro.
iApply "HΦ"=> //. iApply "HΦ"=> //.
eauto with iFrame. eauto with iFrame.
......
From iris.heap_lang Require Export lang. From iris.heap_lang Require Export lang.
Require Import FunctionalExtensionality. Require Import FunctionalExtensionality.
Class Involutive {T} (f : T T) :=
involutive : t : T, t = f (f t).
Inductive side : Set := Inductive side : Set :=
| Left | Left
| Right. | Right.
Instance side_inhabited : Inhabited side := populate Left.
Definition dual_side (s : side) : side :=
match s with Left => Right | Right => Left end.
Instance dual_side_involutive : Involutive dual_side.
Proof. intros s; destruct s; eauto. Qed.
Inductive stype := Inductive stype :=
| TEnd | TEnd
| TSend (P : val Prop) (st : val stype) | TSend (P : val Prop) (st : val stype)
...@@ -19,9 +31,6 @@ Fixpoint dual_stype (st :stype) := ...@@ -19,9 +31,6 @@ Fixpoint dual_stype (st :stype) :=
| TRecv P st => TSend P (λ v, dual_stype (st v)) | TRecv P st => TSend P (λ v, dual_stype (st v))
end. end.
Class Involutive {T} (f : T T) :=
involutive : t : T, t = f (f t).
Instance dual_stype_involutive : Involutive dual_stype. Instance dual_stype_involutive : Involutive dual_stype.
Proof. Proof.
intros st. intros st.
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment