Skip to content

Commit 2b77a2a

Browse files
committed
fix "unroll for" failure (InvalidCPos)
Keep a resolved version of the position so that it can be safely reused later.
1 parent 946f189 commit 2b77a2a

File tree

5 files changed

+51
-21
lines changed

5 files changed

+51
-21
lines changed

src/ecCorePrinting.ml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -66,6 +66,8 @@ module type PrinterAPI = sig
6666
val pp_codepos1 : PPEnv.t -> EcMatching.Position.codepos1 pp
6767
val pp_codeoffset1 : PPEnv.t -> EcMatching.Position.codeoffset1 pp
6868

69+
val pp_codepos : PPEnv.t -> EcMatching.Position.codepos pp
70+
6971
(* ------------------------------------------------------------------ *)
7072
val pp_typedecl : PPEnv.t -> (path * tydecl ) pp
7173
val pp_opdecl : ?long:bool -> PPEnv.t -> (path * operator ) pp

src/ecMatching.ml

Lines changed: 27 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -30,8 +30,8 @@ module Position = struct
3030
| `ByMatch of int option * cp_match
3131
]
3232

33-
type codepos1 = int * cp_base
34-
type codepos = (codepos1 * int) list * codepos1
33+
type codepos1 = int * cp_base
34+
type codepos = (codepos1 * int) list * codepos1
3535
type codeoffset1 = [`ByOffset of int | `ByPosition of codepos1]
3636

3737
let shift1 ~(offset : int) ((o, p) : codepos1) : codepos1 =
@@ -176,30 +176,41 @@ module Zipper = struct
176176
let (s, _) = split_at_cpos1 ~after:`No env cpos s in
177177
1 + List.length s
178178

179-
let zipper_at_nm_cpos1 (env : EcEnv.env) ((cp1, sub) : codepos1 * int) s zpr =
179+
let zipper_at_nm_cpos1
180+
(env : EcEnv.env)
181+
((cp1, sub) : codepos1 * int)
182+
(s : stmt)
183+
(zpr : ipath)
184+
: (ipath * stmt) * (codepos1 * int)
185+
=
180186
let (s1, i, s2) = find_by_cpos1 env cp1 s in
187+
let zpr =
188+
match i.i_node, sub with
189+
| Swhile (e, sw), 0 ->
190+
(ZWhile (e, ((s1, s2), zpr)), sw)
181191

182-
match i.i_node, sub with
183-
| Swhile (e, sw), 0 ->
184-
(ZWhile (e, ((s1, s2), zpr)), sw)
185-
186-
| Sif (e, ifs1, ifs2), 0 ->
187-
(ZIfThen (e, ((s1, s2), zpr), ifs2), ifs1)
192+
| Sif (e, ifs1, ifs2), 0 ->
193+
(ZIfThen (e, ((s1, s2), zpr), ifs2), ifs1)
188194

189-
| Sif (e, ifs1, ifs2), 1 ->
190-
(ZIfElse (e, ifs1, ((s1, s2), zpr)), ifs2)
195+
| Sif (e, ifs1, ifs2), 1 ->
196+
(ZIfElse (e, ifs1, ((s1, s2), zpr)), ifs2)
191197

192-
| _ -> raise InvalidCPos
198+
| _ -> raise InvalidCPos
199+
in zpr, ((0, `ByPos (1 + List.length s1)), sub)
193200

194-
let zipper_of_cpos (env : EcEnv.env) ((nm, cp1) : codepos) s =
195-
let zpr, s =
196-
List.fold_left
201+
let zipper_of_cpos_r (env : EcEnv.env) ((nm, cp1) : codepos) (s : stmt) =
202+
let (zpr, s), nm =
203+
List.fold_left_map
197204
(fun (zpr, s) nm1 -> zipper_at_nm_cpos1 env nm1 s zpr)
198205
(ZTop, s) nm in
199206

200207
let s1, i, s2 = find_by_cpos1 env cp1 s in
208+
let zpr = zipper s1 (i :: s2) zpr in
209+
210+
(zpr, (nm, (0, `ByPos (1 + List.length s1))))
201211

202-
zipper s1 (i :: s2) zpr
212+
let zipper_of_cpos (env : EcEnv.env) (cp : codepos) (s : stmt) =
213+
fst (zipper_of_cpos_r env cp s)
203214

204215
let split_at_cpos1 env cpos1 s =
205216
split_at_cpos1 ~after:`Auto env cpos1 s

src/ecMatching.mli

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -73,7 +73,12 @@ module Zipper : sig
7373
val zipper : instr list -> instr list -> ipath -> zipper
7474

7575
(* Return the zipper for the stmt [stmt] at code position [codepos].
76-
* Raise [InvalidCPos] if [codepos] is not valid for [stmt]. *)
76+
* Raise [InvalidCPos] if [codepos] is not valid for [stmt]. It also
77+
* returns a input code-position, but fully resolved (i.e. with absolute
78+
* positions only). The second variant simply throw away the second
79+
* output.
80+
*)
81+
val zipper_of_cpos_r : env -> codepos -> stmt -> zipper * codepos
7782
val zipper_of_cpos : env -> codepos -> stmt -> zipper
7883

7984
(* Zip the zipper, returning the corresponding statement *)

src/ecPrinting.ml

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ module P = EcPath
1212
module EP = EcParser
1313
module BI = EcBigInt
1414
module EI = EcInductive
15+
module CP = EcMatching.Position
1516

1617
module Ssym = EcSymbols.Ssym
1718
module Msym = EcSymbols.Msym
@@ -2112,7 +2113,7 @@ let pp_scvar ppe fmt vs =
21122113
pp_list "@ " pp_grp fmt vs
21132114

21142115
(* -------------------------------------------------------------------- *)
2115-
let pp_codepos1 (ppe : PPEnv.t) (fmt : Format.formatter) ((off, cp) : EcMatching.Position.codepos1) =
2116+
let pp_codepos1 (ppe : PPEnv.t) (fmt : Format.formatter) ((off, cp) : CP.codepos1) =
21162117
let s : string =
21172118
match cp with
21182119
| `ByPos i ->
@@ -2141,11 +2142,19 @@ let pp_codepos1 (ppe : PPEnv.t) (fmt : Format.formatter) ((off, cp) : EcMatching
21412142
Format.fprintf fmt "%s%s%d" s (if off < 0 then "-" else "+") (abs off)
21422143

21432144
(* -------------------------------------------------------------------- *)
2144-
let pp_codeoffset1 (ppe : PPEnv.t) (fmt : Format.formatter) (offset : EcMatching.Position.codeoffset1) =
2145+
let pp_codeoffset1 (ppe : PPEnv.t) (fmt : Format.formatter) (offset : CP.codeoffset1) =
21452146
match offset with
21462147
| `ByPosition p -> Format.fprintf fmt "%a" (pp_codepos1 ppe) p
21472148
| `ByOffset o -> Format.fprintf fmt "%d" o
21482149

2150+
(* -------------------------------------------------------------------- *)
2151+
let pp_codepos (ppe : PPEnv.t) (fmt : Format.formatter) ((nm, cp1) : CP.codepos) =
2152+
let pp_nm (fmt : Format.formatter) ((cp, i) : CP.codepos1 * int) =
2153+
Format.eprintf "%a%s" (pp_codepos1 ppe) cp (if i = 0 then "." else "?")
2154+
in
2155+
2156+
Format.eprintf "%a%a" (pp_list "" pp_nm) nm (pp_codepos1 ppe) cp1
2157+
21492158
(* -------------------------------------------------------------------- *)
21502159
let pp_opdecl_pr (ppe : PPEnv.t) fmt (basename, ts, ty, op) =
21512160
let ppe = PPEnv.add_locals ppe (List.map fst ts) in

src/phl/ecPhlLoopTx.ml

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -224,8 +224,12 @@ let process_unroll_for side cpos tc =
224224
let env = FApi.tc1_env tc in
225225
let hyps = FApi.tc1_hyps tc in
226226
let _, c = EcLowPhlGoal.tc1_get_stmt side tc in
227+
228+
if not (List.is_empty (fst cpos)) then
229+
tc_error !!tc "cannot use deep code position";
230+
227231
let cpos = EcProofTyping.tc1_process_codepos tc (side, cpos) in
228-
let z = Zpr.zipper_of_cpos env cpos c in
232+
let z, cpos = Zpr.zipper_of_cpos_r env cpos c in
229233
let pos = 1 + List.length z.Zpr.z_head in
230234

231235
(* Extract loop condition / body *)
@@ -323,7 +327,6 @@ let process_unroll_for side cpos tc =
323327
let cpos = EcMatching.Position.shift ~offset:(-1) cpos in
324328
let clen = blen * (List.length zs - 1) in
325329

326-
Format.eprintf "[W]%d %d@." blen (List.length zs);
327330
FApi.t_last (EcPhlCodeTx.t_cfold side cpos (Some clen)) tcenv
328331

329332
(* -------------------------------------------------------------------- *)

0 commit comments

Comments
 (0)