diff --git a/changes/prune-flow-parser.internal.md b/changes/prune-flow-parser.internal.md new file mode 100644 index 00000000000..fe4024901a9 --- /dev/null +++ b/changes/prune-flow-parser.internal.md @@ -0,0 +1 @@ +- Remove dead code from the vendored Flow parser, which is no longer synced with upstream, and include it in `make dead-code`. diff --git a/compiler/flow_parser/README.md b/compiler/flow_parser/README.md index b45114cc913..f9a8fb21e1d 100644 --- a/compiler/flow_parser/README.md +++ b/compiler/flow_parser/README.md @@ -1,6 +1,10 @@ # Vendored Flow parser This directory contains the OCaml Flow parser used by the ReScript compiler. +It is a pruned fork: Flow's parser has moved to Rust, so there are no further +OCaml releases to sync with, and code ReScript does not use is removed like +dead code anywhere else in the repository (`make dead-code` covers it, except +the AST in `parser/flow_ast.ml`). - Upstream repository: https://github.com/facebook/flow - Flow parser version: `0.320.0` @@ -31,8 +35,21 @@ omitted. The core statement, declaration, type, JSX, pattern, comment, and AST modules remain because the parser connects them transitively and `%raw` validates both complete JavaScript programs and individual expressions. +Beyond that, everything reanalyze reports as dead was removed: unused +functions, optional arguments, parse options and the token sink, debug +printers (`[@@deriving show]`), the file-key variants (ReScript parses only +strings), error variants that are never raised, and AST fields that the parser +fills in but nothing reads (template literal quasi values, tolerated-syntax +records, JSX text and fragment locations, comment `on_newline`, accessibility +comments). The AST mapper classes that moved trailing comments between nodes +(`Flow_ast_mapper` and its subclasses in `Comment_attachment`) are gone too: +ReScript never reads trailing comments, and creating the classes was most of +the compiler's startup work. They were also what read every AST field, so most +fields of `flow_ast.ml` are now only written; `make dead-code` does not check +that file. + Vendored sources are excluded from the repository-wide OCamlformat check so -that they remain comparable with their upstream versions. +that they keep Flow's formatting. The Flow parser and retained collection sources are licensed under the MIT licence in `LICENSE` and their source headers. Vendored Sedlex and collection diff --git a/compiler/flow_parser/collections/third-party/flow_map.ml b/compiler/flow_parser/collections/third-party/flow_map.ml index 1646207e016..db1fc3d9ecf 100644 --- a/compiler/flow_parser/collections/third-party/flow_map.ml +++ b/compiler/flow_parser/collections/third-party/flow_map.ml @@ -39,7 +39,9 @@ type ('k, 'v) t0 = } type ('k, 'v) partial_node = { - h: int; + h: int; [@live] + (* Live: keeps the layout of the node this record is cast from with + [~!]. *) v: 'k; d: 'v; l: ('k, 'v) t0; @@ -77,29 +79,6 @@ let create l x d r = else Node { l; v = x; d; r; h } -let rec of_increasing_iterator_unchecked f = function - | 0 -> Empty - | 1 -> - let (v, d) = f () in - Leaf { v; d } - | n -> - let lenl = n lsr 1 in - let lenr = n - lenl - 1 in - let l = of_increasing_iterator_unchecked f lenl in - let (v, d) = f () in - let r = of_increasing_iterator_unchecked f lenr in - Node { l; v; d; r; h = height l + 1 } - -let of_sorted_array_unchecked xs = - let len = Array.length xs in - let i = ref 0 in - let f () = - let x = xs.(!i) in - incr i; - x - in - of_increasing_iterator_unchecked f len - (* The result can not be leaf *) let node l x d r = let hl = height l in @@ -134,61 +113,6 @@ let bal l x d r = let empty = Empty -let[@inline] is_empty = function - | Empty -> true - | _ -> false - -type ('key, 'a) enumeration = - | End - | More of 'key * 'a * ('key, 'a) t0 * ('key, 'a) enumeration - -let rec cons_enum m e = - match m with - | Empty -> e - | Leaf { v; d } -> More (v, d, empty, e) - | Node { l; v; d; r; _ } -> cons_enum l (More (v, d, r, e)) - -let rec min_binding tree = - match tree with - | Empty -> raise Not_found - | Leaf _ -> ~!!tree - | Node { l = Empty; v; d; _ } -> (v, d) - | Node { l; _ } -> min_binding l - -let rec min_binding_from_node_unsafe tree = - let { l; v; d; _ } = ~!tree in - match l with - | Empty -> (v, d) - | Leaf _ -> ~!!l - | Node _ -> min_binding_from_node_unsafe l - -let rec min_binding_opt tree = - match tree with - | Empty -> None - | Leaf { v; d } -> Some (v, d) - | Node { l = Empty; v; d; _ } -> Some (v, d) - | Node { l; _ } -> min_binding_opt l - -let rec max_binding tree = - match tree with - | Empty -> raise Not_found - | Leaf _ -> ~!!tree - | Node { v; d; r = Empty; _ } -> (v, d) - | Node { r; _ } -> max_binding r - -let rec max_binding_opt tree = - match tree with - | Empty -> None - | Leaf { v; d } -> Some (v, d) - | Node { v; d; r = Empty; _ } -> Some (v, d) - | Node { r; _ } -> max_binding_opt r - -let rec remove_min_binding_from_node_unsafe tree = - let { l; v; d; r; _ } = ~!tree in - match l with - | Empty -> r - | Leaf _ -> bal Empty v d r - | Node _ -> bal (remove_min_binding_from_node_unsafe l) v d r (* Beware: those two functions assume that the added k is *strictly* smaller (or bigger) than all the present keys in the tree; it @@ -198,177 +122,13 @@ let rec remove_min_binding_from_node_unsafe tree = respects this precondition. *) -let rec add_min_node node tree = - match tree with - | Empty -> node - | Leaf { v; d } -> sorted_two_nodes_larger node v d - | Node { l; v; d; r; _ } -> bal (add_min_node node l) v d r - -let rec add_min_binding k x tree = - match tree with - | Empty -> singleton k x - | Leaf _ -> sorted_two_nodes_smaller k x tree - | Node { l; v; d; r; _ } -> bal (add_min_binding k x l) v d r - -let rec add_max_node node tree = - match tree with - | Empty -> node - | Leaf { v; d; _ } -> sorted_two_nodes_smaller v d node - | Node { l; v; d; r; _ } -> bal l v d (add_max_node node r) - -let rec add_max_binding k x tree = - match tree with - | Empty -> singleton k x - | Leaf _ -> sorted_two_nodes_larger tree k x - | Node { l; v; d; r; _ } -> bal l v d (add_max_binding k x r) - -let internal_merge t1 t2 = - match (t1, t2) with - | (Empty, t) -> t - | (t, Empty) -> t - | (Leaf _, t) -> add_min_node t1 t - | (t, Leaf _) -> add_max_node t2 t - | (Node _, Node _) -> - let (x, d) = min_binding_from_node_unsafe t2 in - bal t1 x d (remove_min_binding_from_node_unsafe t2) - (* Same as create and bal, but no assumptions are made on the relative heights of l and r. *) -let rec join l v d r = - match (l, r) with - | (Empty, _) -> add_min_binding v d r - | (_, Empty) -> add_max_binding v d l - | (Leaf _, Leaf _) -> Node { l; v; d; r; h = 2 } - | (Leaf _, Node { l = rl; v = rv; d = rd; r = rr; h = rh }) -> - if rh > 3 then - bal (join l v d rl) rv rd rr - else - create l v d r - | (Node { l = ll; v = lv; d = ld; r = lr; h = lh }, Leaf _) -> - if lh > 3 then - bal ll lv ld (join lr v d r) - else - create l v d r - | ( Node { l = ll; v = lv; d = ld; r = lr; h = lh }, - Node { l = rl; v = rv; d = rd; r = rr; h = rh } - ) -> - if lh > rh + 2 then - bal ll lv ld (join lr v d r) - else if rh > lh + 2 then - bal (join l v d rl) rv rd rr - else - create l v d r - (* Merge two trees l and r into one. All elements of l must precede the elements of r. No assumption on the heights of l and r. *) -let concat t1 t2 = - match (t1, t2) with - | (Empty, t) -> t - | (t, Empty) -> t - | (Leaf _, t) -> add_min_node t1 t - | (t, Leaf _) -> add_max_node t2 t - | (Node _, Node _) -> - let (x, d) = min_binding_from_node_unsafe t2 in - join t1 x d (remove_min_binding_from_node_unsafe t2) - -let concat_or_join t1 v d t2 = - match d with - | Some d -> join t1 v d t2 - | None -> concat t1 t2 - -let rec iter f = function - | Empty -> () - | Leaf { v; d } -> f v d - | Node { l; v; d; r; _ } -> - iter f l; - f v d; - iter f r - -let rec map f = function - | Empty -> Empty - | Leaf { v; d } -> - let d' = f d in - Leaf { v; d = d' } - | Node { l; v; d; r; h } -> - let l' = map f l in - let d' = f d in - let r' = map f r in - Node { l = l'; v; d = d'; r = r'; h } - -let rec mapi f = function - | Empty -> Empty - | Leaf { v; d } -> - let d' = f v d in - Leaf { v; d = d' } - | Node { l; v; d; r; h } -> - let l' = mapi f l in - let d' = f v d in - let r' = mapi f r in - Node { l = l'; v; d = d'; r = r'; h } - -let rec fold f m accu = - match m with - | Empty -> accu - | Leaf { v; d } -> f v d accu - | Node { l; v; d; r; _ } -> fold f r (f v d (fold f l accu)) - -let rec keys_aux accu tree = - match tree with - | Empty -> accu - | Leaf { v; _ } -> v :: accu - | Node { l; v; r; _ } -> keys_aux (v :: keys_aux accu r) l - -let keys s = keys_aux [] s - -let ordered_keys = keys - -let rec for_all p = function - | Empty -> true - | Leaf { v; d } -> p v d - | Node { l; v; d; r; _ } -> p v d && for_all p l && for_all p r - -let rec exists p = function - | Empty -> false - | Leaf { v; d } -> p v d - | Node { l; v; d; r; _ } -> p v d || exists p l || exists p r - -let rec filter p tree = - match tree with - | Empty -> Empty - | Leaf { v; d } -> - if p v d then - tree - else - empty - | Node { l; v; d; r; _ } as m -> - (* call [p] in the expected left-to-right order *) - let l' = filter p l in - let pvd = p v d in - let r' = filter p r in - if pvd then - if l == l' && r == r' then - m - else - join l' v d r' - else - concat l' r' - -let rec cardinal = function - | Empty -> 0 - | Leaf _ -> 1 - | Node { l; r; _ } -> cardinal l + 1 + cardinal r - -let rec bindings_aux accu tree = - match tree with - | Empty -> accu - | Leaf _ -> ~!!tree :: accu - | Node { l; v; d; r; _ } -> bindings_aux ((v, d) :: bindings_aux accu r) l - -let bindings s = bindings_aux [] s - type ('k, 'v) t1 = ('k, 'v) t0 = | Empty | Leaf of { @@ -397,76 +157,10 @@ module type S = sig val empty : 'a t - val is_empty : 'a t -> bool - - val mem : key -> 'a t -> bool - val add : key -> 'a -> 'a t -> 'a t - val update : key -> ('a option -> 'a option) -> 'a t -> 'a t - - val adjust : key -> ('a option -> 'a) -> 'a t -> 'a t - - val singleton : key -> 'a -> 'a t - - (* when [remove k map] failed to remove [k], the original [map] is returned *) - val remove : key -> 'a t -> 'a t - - val merge : (key -> 'a option -> 'b option -> 'c option) -> 'a t -> 'b t -> 'c t - - val union : (key -> 'a -> 'a -> 'a option) -> 'a t -> 'a t -> 'a t - - val compare : ('a -> 'a -> int) -> 'a t -> 'a t -> int - - val equal : ('a -> 'a -> bool) -> 'a t -> 'a t -> bool - - val iter : (key -> 'a -> unit) -> 'a t -> unit - - val fold : (key -> 'a -> 'b -> 'b) -> 'a t -> 'b -> 'b - - val for_all : (key -> 'a -> bool) -> 'a t -> bool - - val exists : (key -> 'a -> bool) -> 'a t -> bool - - val filter : (key -> 'a -> bool) -> 'a t -> 'a t - - val partition : (key -> 'a -> bool) -> 'a t -> 'a t * 'a t - - val cardinal : 'a t -> int - - val bindings : 'a t -> (key * 'a) list - - val min_binding : 'a t -> key * 'a - - val min_binding_opt : 'a t -> (key * 'a) option - - val max_binding : 'a t -> key * 'a - - val max_binding_opt : 'a t -> (key * 'a) option - - val keys : 'a t -> key list - - val ordered_keys : 'a t -> key list - - val ident_map_key : ?combine:('a -> 'a -> 'a) -> (key -> key) -> 'a t -> 'a t - - val choose : 'a t -> key * 'a - - val choose_opt : 'a t -> (key * 'a) option - - val split : key -> 'a t -> 'a t * 'a option * 'a t - - val find : key -> 'a t -> 'a - val find_opt : key -> 'a t -> 'a option - val map : ('a -> 'b) -> 'a t -> 'b t - - val mapi : (key -> 'a -> 'b) -> 'a t -> 'b t - - val of_increasing_iterator_unchecked : (unit -> key * 'a) -> int -> 'a t - - val of_sorted_array_unchecked : (key * 'a) array -> 'a t end module Make (Ord : OrderedType) : S with type key = Ord.t = struct @@ -508,27 +202,6 @@ module Make (Ord : OrderedType) : S with type key = Ord.t = struct else bal l v d rr - let rec find x = function - | Empty -> raise Not_found - | Leaf { v; d } -> - let c = Ord.compare x v in - if c = 0 then - d - else - raise Not_found - | Node { l; v; d; r; _ } -> - let c = Ord.compare x v in - if c = 0 then - d - else - find - x - ( if c < 0 then - l - else - r - ) - let rec find_opt x = function | Empty -> None | Leaf { v; d } -> @@ -550,336 +223,6 @@ module Make (Ord : OrderedType) : S with type key = Ord.t = struct r ) - let rec mem x = function - | Empty -> false - | Leaf { v; _ } -> Ord.compare x v = 0 - | Node { l; v; r; _ } -> - let c = Ord.compare x v in - c = 0 - || mem - x - ( if c < 0 then - l - else - r - ) - - let rec remove x tree = - match tree with - | Empty -> tree - | Leaf { v; _ } -> - let c = Ord.compare x v in - if c = 0 then - empty - else - tree - | Node { l; v; d; r; _ } as m -> - let c = Ord.compare x v in - if c = 0 then - internal_merge l r - else if c < 0 then - let ll = remove x l in - if l == ll then - m - else - bal ll v d r - else - let rr = remove x r in - if r == rr then - m - else - bal l v d rr - - let rec adjust x (f : 'a option -> 'a) tree = - match tree with - | Empty -> - let data = f None in - singleton x data - | Leaf { v; d } -> - (* check *) - let c = Ord.compare x v in - if c = 0 then - let data = f (Some d) in - if d == data then - tree - else - Leaf { v; d = data } - else - let data = f None in - if c < 0 then - sorted_two_nodes_smaller x data tree - else - sorted_two_nodes_larger tree x data - | Node { l; v; d; r; h } as m -> - let c = Ord.compare x v in - if c = 0 then - let data = f (Some d) in - if d == data then - m - else - Node { l; v = x; d = data; r; h } - else if c < 0 then - let ll = adjust x f l in - if l == ll then - m - else - bal ll v d r - else - let rr = adjust x f r in - if r == rr then - m - else - bal l v d rr - - let rec update x f tree = - match tree with - | Empty -> begin - match f None with - | None -> Empty - | Some data -> singleton x data - end - | Leaf { v; d } -> - (* check *) - let c = Ord.compare x v in - if c = 0 then - match f (Some d) with - | None -> empty (* It exists, None means deletion *) - | Some data -> - if d == data then - tree - else - Leaf { v; d = data } - else begin - match f None with - | None -> tree - | Some data -> - if c < 0 then - sorted_two_nodes_smaller x data tree - else - sorted_two_nodes_larger tree x data - end - | Node { l; v; d; r; h } as m -> - let c = Ord.compare x v in - if c = 0 then - match f (Some d) with - | None -> internal_merge l r - | Some data -> - if d == data then - m - else - Node { l; v = x; d = data; r; h } - else if c < 0 then - let ll = update x f l in - if l == ll then - m - else - bal ll v d r - else - let rr = update x f r in - if r == rr then - m - else - bal l v d rr - - let rec split x tree = - match tree with - | Empty -> (Empty, None, Empty) - | Leaf { v; d } -> - let c = Ord.compare x v in - if c = 0 then - (empty, Some d, empty) - else if c < 0 then - (empty, None, tree) - else - (tree, None, empty) - | Node { l; v; d; r; _ } -> - let c = Ord.compare x v in - if c = 0 then - (l, Some d, r) - else if c < 0 then - let (ll, pres, rl) = split x l in - (ll, pres, join rl v d r) - else - let (lr, pres, rr) = split x r in - (join l v d lr, pres, rr) - - let rec merge f s1 s2 = - match (s1, s2) with - | (Empty, Empty) -> Empty - | (Leaf { v; d }, Empty) -> begin - match f v (Some d) None with - | None -> empty - | Some data -> Leaf { v; d = data } - end - | (Empty, Leaf { v; d }) -> begin - match f v None (Some d) with - | None -> empty - | Some data -> Leaf { v; d = data } - end - | (Leaf { v = v1; d = d1 }, Leaf _) -> - let (l2, d2, r2) = split v1 s2 in - concat_or_join (merge f empty l2) v1 (f v1 (Some d1) d2) (merge f empty r2) - | (Node { l = l1; v = v1; d = d1; r = r1; h = h1 }, _) when h1 >= height s2 -> - let (l2, d2, r2) = split v1 s2 in - concat_or_join (merge f l1 l2) v1 (f v1 (Some d1) d2) (merge f r1 r2) - | (_, Node { l = l2; v = v2; d = d2; r = r2; _ }) -> - let (l1, d1, r1) = split v2 s1 in - concat_or_join (merge f l1 l2) v2 (f v2 d1 (Some d2)) (merge f r1 r2) - | (Node _, (Empty | Leaf _)) -> assert false - - let rec union f s1 s2 = - match (s1, s2) with - | (Empty, s) - | (s, Empty) -> - s - | (s, Leaf { v; d }) -> - update - v - (fun d2 -> - match d2 with - | None -> Some d - | Some d2 -> f v d2 d) - s - | (Leaf { v; d }, s) -> - (* add v d s *) - update - v - (fun d2 -> - match d2 with - | None -> Some d - | Some d2 -> f v d d2) - s - | ( Node { l = l1; v = v1; d = d1; r = r1; h = h1 }, - Node { l = l2; v = v2; d = d2; r = r2; h = h2 } - ) -> - if h1 >= h2 then - let (l2, d2, r2) = split v1 s2 in - let l = union f l1 l2 and r = union f r1 r2 in - match d2 with - | None -> join l v1 d1 r - | Some d2 -> concat_or_join l v1 (f v1 d1 d2) r - else - let (l1, d1, r1) = split v2 s1 in - let l = union f l1 l2 and r = union f r1 r2 in - (match d1 with - | None -> join l v2 d2 r - | Some d1 -> concat_or_join l v2 (f v2 d1 d2) r) - - let rec partition p tree = - match tree with - | Empty -> (Empty, Empty) - | Leaf { v; d } -> - if p v d then - (tree, empty) - else - (empty, tree) - | Node { l; v; d; r; _ } -> - (* call [p] in the expected left-to-right order *) - let (lt, lf) = partition p l in - let pvd = p v d in - let (rt, rf) = partition p r in - if pvd then - (join lt v d rt, concat lf rf) - else - (concat lt rt, join lf v d rf) - - let compare cmp m1 m2 = - let rec compare_aux e1 e2 = - match (e1, e2) with - | (End, End) -> 0 - | (End, _) -> -1 - | (_, End) -> 1 - | (More (v1, d1, r1, e1), More (v2, d2, r2, e2)) -> - let c = Ord.compare v1 v2 in - if c <> 0 then - c - else - let c = cmp d1 d2 in - if c <> 0 then - c - else - compare_aux (cons_enum r1 e1) (cons_enum r2 e2) - in - compare_aux (cons_enum m1 End) (cons_enum m2 End) - - let equal cmp m1 m2 = - let rec equal_aux e1 e2 = - match (e1, e2) with - | (End, End) -> true - | (End, _) -> false - | (_, End) -> false - | (More (v1, d1, r1, e1), More (v2, d2, r2, e2)) -> - Ord.compare v1 v2 = 0 && cmp d1 d2 && equal_aux (cons_enum r1 e1) (cons_enum r2 e2) - in - equal_aux (cons_enum m1 End) (cons_enum m2 End) - - let cardinal = cardinal - - let bindings = bindings - - let keys = keys - - let choose = min_binding - - let choose_opt = min_binding_opt - let empty = empty - let singleton = singleton - - let is_empty = is_empty - - let min_binding = min_binding - - let min_binding_opt = min_binding_opt - - let max_binding = max_binding - - let max_binding_opt = max_binding_opt - - let fold = fold - - let iter = iter - - let for_all = for_all - - let exists = exists - - let mapi = mapi - - let map = map - - let filter = filter - - let ordered_keys = keys - - let of_increasing_iterator_unchecked = of_increasing_iterator_unchecked - - let of_sorted_array_unchecked = of_sorted_array_unchecked - - let ident_map_key ?combine f map = - let (map_, changed) = - fold - (fun key item (map_, changed) -> - let new_key = f key in - ( (* add ?combine new_key item map_ *) - (match combine with - | None -> add new_key item map_ - | Some combine -> - adjust - new_key - (fun opt -> - match opt with - | None -> item - | Some old_value -> combine old_value item) - map_), - changed || new_key != key - )) - map - (empty, false) - in - if changed then - map_ - else - map end diff --git a/compiler/flow_parser/collections/third-party/flow_set.ml b/compiler/flow_parser/collections/third-party/flow_set.ml index 55f58e8c0c4..6a04ce0aabd 100644 --- a/compiler/flow_parser/collections/third-party/flow_set.ml +++ b/compiler/flow_parser/collections/third-party/flow_set.ml @@ -35,75 +35,12 @@ module type S = sig val empty : t - val is_empty : t -> bool - val mem : elt -> t -> bool val add : elt -> t -> t val singleton : elt -> t - val remove : elt -> t -> t - - val union : t -> t -> t - - val inter : t -> t -> t - - val disjoint : t -> t -> bool - - val diff : t -> t -> t - - val compare : t -> t -> int - - val equal : t -> t -> bool - - val subset : t -> t -> bool - - val iter : (elt -> unit) -> t -> unit - - val map : (elt -> elt) -> t -> t - - val fold : (elt -> 'a -> 'a) -> t -> 'a -> 'a - - val for_all : (elt -> bool) -> t -> bool - - val exists : (elt -> bool) -> t -> bool - - val filter : (elt -> bool) -> t -> t - - val partition : (elt -> bool) -> t -> t * t - - val cardinal : t -> int - - val elements : t -> elt list - - val min_elt : t -> elt - - val min_elt_opt : t -> elt option - - val max_elt : t -> elt - - val max_elt_opt : t -> elt option - - val choose : t -> elt - - val choose_opt : t -> elt option - - val find : elt -> t -> elt - - val find_opt : elt -> t -> elt option - - val to_seq : t -> elt Seq.t - - val of_list : elt list -> t - - val make_pp : (Format.formatter -> elt -> unit) -> Format.formatter -> t -> unit - - val of_increasing_iterator_unchecked : (unit -> elt) -> int -> t - - val of_sorted_array_unchecked : elt array -> t - - val find_first_opt : (elt -> bool) -> t -> elt option end type 'elt t0 = @@ -117,7 +54,9 @@ type 'elt t0 = } type 'elt partial_node = { - h: int; + h: int; [@live] + (* Live: keeps the layout of the node this record is cast from with + [~!]. *) v: 'elt; l: 'elt t0; r: 'elt t0; @@ -125,22 +64,6 @@ type 'elt partial_node = { external ( ~! ) : 'elt t0 -> 'elt partial_node = "%identity" -type ('elt, 't) enumeration0 = - | End - | More of 'elt * 't * ('elt, 't) enumeration0 - -let rec cons_enum s e = - match s with - | Empty -> e - | Leaf v -> More (v, Empty, e) - | Node { l; v; r; _ } -> cons_enum l (More (v, r, e)) - -let rec seq_of_enum_ c () = - match c with - | End -> Seq.Nil - | More (x, t, rest) -> Seq.Cons (x, seq_of_enum_ (cons_enum t rest)) - -let to_seq c = seq_of_enum_ (cons_enum c End) let[@inline] height = function | Empty -> 0 @@ -194,29 +117,6 @@ let create l v r = ); } -let rec of_increasing_iterator_unchecked f = function - | 0 -> Empty - | 1 -> - let v = f () in - Leaf v - | n -> - let lenl = n lsr 1 in - let lenr = n - lenl - 1 in - let l = of_increasing_iterator_unchecked f lenl in - let v = f () in - let r = of_increasing_iterator_unchecked f lenr in - Node { l; v; r; h = height l + 1 } - -let of_sorted_array_unchecked xs = - let len = Array.length xs in - let i = ref 0 in - let f () = - let x = xs.(!i) in - incr i; - x - in - of_increasing_iterator_unchecked f len - (* Same as create, but performs one step of rebalancing if necessary. Assumes l and r balanced and | height l - height r | <= 3. Inline expansion of create for better speed in the most frequent case @@ -257,132 +157,23 @@ let bal l v r = respects this precondition. *) -let rec add_min_element x = function - | Empty -> singleton x - | Leaf v -> unsafe_node ~l:(singleton x) ~v ~r:Empty - | Node { l; v; r; _ } -> bal (add_min_element x l) v r - -let rec add_max_element x = function - | Empty -> singleton x - | Leaf v -> unsafe_node ~l:Empty ~v ~r:(singleton x) - | Node { l; v; r; _ } -> bal l v (add_max_element x r) - (* Same as create and bal, but no assumptions are made on the relative heights of l and r. *) -let rec join l v r = - match (l, r) with - | (Empty, _) -> add_min_element v r - | (_, Empty) -> add_max_element v l - | (Leaf _, Leaf _) -> unsafe_node ~l ~v ~r - | (Leaf _, Node { l = rl; v = rv; r = rr; h = rh }) -> - if rh > 3 then - bal (join l v rl) rv rr - else - create l v r - | (Node { l = ll; v = lv; r = lr; h = lh }, Leaf _) -> - if lh > 3 then - bal ll lv (join lr v r) - else - create l v r - | (Node { l = ll; v = lv; r = lr; h = lh }, Node { l = rl; v = rv; r = rr; h = rh }) -> - if lh > rh + 2 then - bal ll lv (join lr v r) - else if rh > lh + 2 then - bal (join l v rl) rv rr - else - create l v r - (* Smallest and greatest element of a set *) -let rec min_elt = function - | Empty -> raise Not_found - | Leaf v -> v - | Node { l = Empty; v; _ } -> v - | Node { l; _ } -> min_elt l - -let rec min_elt_opt = function - | Empty -> None - | Leaf v -> Some v - | Node { l = Empty; v; _ } -> Some v - | Node { l; _ } -> min_elt_opt l - -let rec max_elt = function - | Empty -> raise Not_found - | Node { v; r = Empty; _ } -> v - | Leaf v -> v - | Node { r; _ } -> max_elt r - -let rec max_elt_opt = function - | Empty -> None - | Node { v; r = Empty; _ } -> Some v - | Leaf v -> Some v - | Node { r; _ } -> max_elt_opt r - (* Remove the smallest element of the given set *) -let rec remove_min_elt = function - | Empty -> invalid_arg "Set.remove_min_elt" - | Leaf _ -> Empty - | Node { l = Empty; r; _ } -> r - | Node { l; v; r; _ } -> bal (remove_min_elt l) v r - (* Merge two trees l and r into one. All elements of l must precede the elements of r. Assume | height l - height r | <= 2. *) -let merge t1 t2 = - match (t1, t2) with - | (Empty, t) -> t - | (t, Empty) -> t - | (_, _) -> bal t1 (min_elt t2) (remove_min_elt t2) - (* Merge two trees l and r into one. All elements of l must precede the elements of r. No assumption on the heights of l and r. *) -let concat t1 t2 = - match (t1, t2) with - | (Empty, t) -> t - | (t, Empty) -> t - | (_, _) -> join t1 (min_elt t2) (remove_min_elt t2) - -let rec cardinal = function - | Empty -> 0 - | Leaf _ -> 1 - | Node { l; r; _ } -> cardinal l + 1 + cardinal r - -let rec elements_aux accu = function - | Empty -> accu - | Leaf v -> v :: accu - | Node { l; v; r; _ } -> elements_aux (v :: elements_aux accu r) l - -let elements s = elements_aux [] s - let empty = Empty -let[@inline] is_empty = function - | Empty -> true - | _ -> false - -let of_sorted_list l = - let rec sub n l = - match (n, l) with - | (0, l) -> (Empty, l) - | (1, x0 :: l) -> (singleton x0, l) - | (2, x0 :: x1 :: l) -> (Node { l = singleton x0; v = x1; r = Empty; h = 2 }, l) - | (3, x0 :: x1 :: x2 :: l) -> (Node { l = singleton x0; v = x1; r = singleton x2; h = 2 }, l) - | (n, l) -> - let nl = n / 2 in - let (left, l) = sub nl l in - (match l with - | [] -> assert false - | mid :: l -> - let (right, l) = sub (n - nl - 1) l in - (create left mid right, l)) - in - fst (sub (List.length l) l) - type 'a t1 = 'a t0 = private | Empty | Leaf of 'a @@ -400,27 +191,8 @@ module Make (Ord : OrderedType) : S with type elt = Ord.t = struct let singleton = singleton - (* Insertion of one element *) - let min_elt_opt = min_elt_opt - - let max_elt_opt = max_elt_opt - - let min_elt = min_elt - - let max_elt = max_elt - - let elements = elements - - let cardinal = cardinal - - let is_empty = is_empty - let empty = empty - let choose = min_elt - - let choose_opt = min_elt_opt - let rec add x t = match t with | Empty -> singleton x @@ -449,35 +221,12 @@ module Make (Ord : OrderedType) : S with type elt = Ord.t = struct else bal l v rr - let ( @> ) = add (* Splitting. split x s returns a triple (l, present, r) where - l is the set of elements of s that are < x - r is the set of elements of s that are > x - present is false if s contains no element equal to x, or true if s contains an element equal to x. *) - let rec split x tree = - match tree with - | Empty -> (empty, false, empty) - | Leaf v -> - let c = Ord.compare x v in - if c = 0 then - (empty, true, empty) - else if c < 0 then - (empty, false, tree) - else - (tree, false, empty) - | Node { l; v; r; _ } -> - let c = Ord.compare x v in - if c = 0 then - (l, true, r) - else if c < 0 then - let (ll, pres, rl) = split x l in - (ll, pres, join rl v r) - else - let (lr, pres, rr) = split x r in - (join l v lr, pres, rr) - (* Implementation of the set operations *) let rec mem x = function @@ -496,370 +245,4 @@ module Make (Ord : OrderedType) : S with type elt = Ord.t = struct r ) - let rec remove x tree = - match tree with - | Empty -> empty - | Leaf v -> - let c = Ord.compare x v in - if c = 0 then - empty - else - tree - | Node { l; v; r; _ } as t -> - let c = Ord.compare x v in - if c = 0 then - merge l r - else if c < 0 then - let ll = remove x l in - if l == ll then - t - else - bal ll v r - else - let rr = remove x r in - if r == rr then - t - else - bal l v rr - - let rec union s1 s2 = - match (s1, s2) with - | (Empty, t2) -> t2 - | (t1, Empty) -> t1 - | (Leaf v, s2) -> add v s2 - | (s1, Leaf v) -> add v s1 - | (Node { l = l1; v = v1; r = r1; h = h1 }, Node { l = l2; v = v2; r = r2; h = h2 }) -> - if h1 >= h2 then - if h2 = 1 then - add v2 s1 - else - let (l2, _, r2) = split v1 s2 in - join (union l1 l2) v1 (union r1 r2) - else if h1 = 1 then - add v1 s2 - else - let (l1, _, r1) = split v2 s1 in - join (union l1 l2) v2 (union r1 r2) - - let rec inter s1 s2 = - match (s1, s2) with - | (Empty, _) -> empty - | (_, Empty) -> empty - | (Leaf v, _) -> - if mem v s2 then - s1 - else - empty - | (Node { l = l1; v = v1; r = r1; _ }, t2) -> - (match split v1 t2 with - | (l2, false, r2) -> concat (inter l1 l2) (inter r1 r2) - | (l2, true, r2) -> join (inter l1 l2) v1 (inter r1 r2)) - - (* Same as split, but compute the left and right subtrees - only if the pivot element is not in the set. The right subtree - is computed on demand. *) - - type split_bis = - | Found - | NotFound of t * (unit -> t) - - let rec split_bis x = function - | Empty -> NotFound (empty, (fun () -> empty)) - | Leaf v -> - let c = Ord.compare x v in - if c = 0 then - Found - else - NotFound (empty, (fun () -> empty)) - | Node { l; v; r; _ } -> - let c = Ord.compare x v in - if c = 0 then - Found - else if c < 0 then - match split_bis x l with - | Found -> Found - | NotFound (ll, rl) -> NotFound (ll, (fun () -> join (rl ()) v r)) - else ( - match split_bis x r with - | Found -> Found - | NotFound (lr, rr) -> NotFound (join l v lr, rr) - ) - - let rec disjoint s1 s2 = - match (s1, s2) with - | (Empty, _) - | (_, Empty) -> - true - | (Leaf v, s) - | (s, Leaf v) -> - not (mem v s) - | (Node { l = l1; v = v1; r = r1; _ }, t2) -> - if s1 == s2 then - false - else ( - match split_bis v1 t2 with - | NotFound (l2, r2) -> disjoint l1 l2 && disjoint r1 (r2 ()) - | Found -> false - ) - - let rec diff s1 s2 = - match (s1, s2) with - | (Empty, _) -> empty - | (t1, Empty) -> t1 - | (Leaf v, _) -> - if mem v s2 then - empty - else - s1 - | (Node { l = l1; v = v1; r = r1; _ }, t2) -> - (match split v1 t2 with - | (l2, false, r2) -> join (diff l1 l2) v1 (diff r1 r2) - | (l2, true, r2) -> concat (diff l1 l2) (diff r1 r2)) - - let rec compare_aux e1 e2 = - match (e1, e2) with - | (End, End) -> 0 - | (End, _) -> -1 - | (_, End) -> 1 - | (More (v1, r1, e1), More (v2, r2, e2)) -> - let c = Ord.compare v1 v2 in - if c <> 0 then - c - else - compare_aux (cons_enum r1 e1) (cons_enum r2 e2) - - let compare s1 s2 = compare_aux (cons_enum s1 End) (cons_enum s2 End) - - let equal s1 s2 = compare s1 s2 = 0 - - let rec subset s1 s2 = - match (s1, s2) with - | (Empty, _) -> true - | (_, Empty) -> false - | (Leaf v1, Leaf v2) -> - let c = Ord.compare v1 v2 in - if c = 0 then - true - else - false - | (Node { v = v1; h; _ }, Leaf v2) -> - h = 1 - && (* conservative here *) - Ord.compare v1 v2 = 0 - | (Leaf v1, Node { l = l2; v = v2; r = r2; _ }) -> - let c = Ord.compare v1 v2 in - if c = 0 then - true - else if c < 0 then - subset s1 l2 - else - subset s1 r2 - | (Node { l = l1; v = v1; r = r1; _ }, (Node { l = l2; v = v2; r = r2; _ } as t2)) -> - let c = Ord.compare v1 v2 in - if c = 0 then - subset l1 l2 && subset r1 r2 - else if c < 0 then - (* Better to keep invariant here, since our unsafe code relies on such invariant - *) - subset (unsafe_node ~l:l1 ~v:v1 ~r:empty) l2 && subset r1 t2 - else - subset (unsafe_node ~l:empty ~v:v1 ~r:r1) r2 && subset l1 t2 - - let rec iter f = function - | Empty -> () - | Leaf v -> f v - | Node { l; v; r; _ } -> - iter f l; - f v; - iter f r - - let rec fold f s accu = - match s with - | Empty -> accu - | Leaf v -> f v accu - | Node { l; v; r; _ } -> fold f r (f v (fold f l accu)) - - let rec for_all p = function - | Empty -> true - | Leaf v -> p v - | Node { l; v; r; _ } -> p v && for_all p l && for_all p r - - let rec exists p = function - | Empty -> false - | Leaf v -> p v - | Node { l; v; r; _ } -> p v || exists p l || exists p r - - let rec filter p tree = - match tree with - | Empty -> empty - | Leaf v -> - let pv = p v in - if pv then - tree - else - empty - | Node { l; v; r; _ } as t -> - (* call [p] in the expected left-to-right order *) - let l' = filter p l in - let pv = p v in - let r' = filter p r in - if pv then - if l == l' && r == r' then - t - else - join l' v r' - else - concat l' r' - - let rec partition p tree = - match tree with - | Empty -> (empty, empty) - | Leaf v -> - let pv = p v in - if pv then - (tree, empty) - else - (empty, tree) - | Node { l; v; r; _ } -> - (* call [p] in the expected left-to-right order *) - let (lt, lf) = partition p l in - let pv = p v in - let (rt, rf) = partition p r in - if pv then - (join lt v rt, concat lf rf) - else - (concat lt rt, join lf v rf) - - let rec find x = function - | Empty -> raise Not_found - | Leaf v -> - let c = Ord.compare x v in - if c = 0 then - v - else - raise Not_found - | Node { l; v; r; _ } -> - let c = Ord.compare x v in - if c = 0 then - v - else - find - x - ( if c < 0 then - l - else - r - ) - - let rec find_opt x = function - | Empty -> None - | Leaf v -> - let c = Ord.compare x v in - if c = 0 then - Some v - else - None - | Node { l; v; r; _ } -> - let c = Ord.compare x v in - if c = 0 then - Some v - else - find_opt - x - ( if c < 0 then - l - else - r - ) - - let try_join l v r = - (* [join l v r] can only be called when (elements of l < v < - elements of r); use [try_join l v r] when this property may - not hold, but you hope it does hold in the common case *) - if (is_empty l || Ord.compare (max_elt l) v < 0) && (is_empty r || Ord.compare v (min_elt r) < 0) - then - join l v r - else - union l (add v r) - - let rec map f tree = - match tree with - | Empty -> empty - | Leaf v -> - let v' = f v in - if v == v' then - tree - else - singleton v' - | Node { l; v; r; _ } as t -> - (* enforce left-to-right evaluation order *) - let l' = map f l in - let v' = f v in - let r' = map f r in - if l == l' && v == v' && r == r' then - t - else - try_join l' v' r' - - let of_list l = - match l with - | [] -> empty - | [x0] -> singleton x0 - | [x0; x1] -> x1 @> singleton x0 - | [x0; x1; x2] -> x2 @> x1 @> singleton x0 - | [x0; x1; x2; x3] -> x3 @> x2 @> x1 @> singleton x0 - | [x0; x1; x2; x3; x4] -> x4 @> x3 @> x2 @> x1 @> singleton x0 - | _ -> of_sorted_list (List.sort_uniq Ord.compare l) - - let to_seq = to_seq - - let make_pp pp_key fmt iset = - Format.fprintf fmt "@[<2>{"; - let elements = elements iset in - (match elements with - | [] -> () - | _ -> Format.fprintf fmt " "); - ignore - (List.fold_left - (fun sep s -> - if sep then Format.fprintf fmt ";@ "; - pp_key fmt s; - true) - false - elements - ); - (match elements with - | [] -> () - | _ -> Format.fprintf fmt " "); - Format.fprintf fmt "@,}@]" - - let of_increasing_iterator_unchecked = of_increasing_iterator_unchecked - - let of_sorted_array_unchecked = of_sorted_array_unchecked - - let rec find_first_opt_aux v0 f = function - | Empty -> Some v0 - | Leaf v -> - if f v then - Some v - else - Some v0 - | Node { l; v; r; _ } -> - if f v then - find_first_opt_aux v f l - else - find_first_opt_aux v0 f r - - let rec find_first_opt f = function - | Empty -> None - | Leaf v -> - if f v then - Some v - else - None - | Node { l; v; r; _ } -> - if f v then - find_first_opt_aux v f l - else - find_first_opt f r end diff --git a/compiler/flow_parser/flow_sedlexing/flow_sedlexing.ml b/compiler/flow_parser/flow_sedlexing/flow_sedlexing.ml index b1ff829ef26..c2c6cac7026 100644 --- a/compiler/flow_parser/flow_sedlexing/flow_sedlexing.ml +++ b/compiler/flow_parser/flow_sedlexing/flow_sedlexing.ml @@ -6,8 +6,6 @@ external ( .!() ) : int array -> int -> int = "%array_unsafe_get" external ( .![] ) : string -> int -> char = "%string_unsafe_get" external ( .![]<- ) : bytes -> int -> char -> unit = "%bytes_unsafe_set" -exception InvalidCodepoint of int - exception MalFormed (* Absolute position from the beginning of the stream *) @@ -40,7 +38,6 @@ type lexbuf = { mutable marked_val: int; } - let lexbuf_clone (x : lexbuf) : lexbuf = { buf = x.buf; @@ -84,15 +81,6 @@ let new_line lexbuf = if lexbuf.curr_line != 0 then lexbuf.curr_line <- lexbuf.curr_line + 1; lexbuf.curr_bol <- lexbuf.pos -let next lexbuf : Stdlib.Uchar.t option = - if lexbuf.pos = lexbuf.len then - None - else - let ret = lexbuf.buf.!(lexbuf.pos) in - lexbuf.pos <- lexbuf.pos + 1; - if ret = 10 then new_line lexbuf; - Some (Stdlib.Uchar.unsafe_of_int ret) - let __private__next_int lexbuf : int = if lexbuf.pos = lexbuf.len then -1 @@ -129,12 +117,8 @@ let lexeme_start lexbuf = lexbuf.start_pos let set_lexeme_start lexbuf pos = lexbuf.start_pos <- pos let lexeme_end lexbuf = lexbuf.pos -let loc lexbuf = (lexbuf.start_pos , lexbuf.pos ) - let lexeme_length lexbuf = lexbuf.pos - lexbuf.start_pos -let sub_lexeme lexbuf pos len = Array.sub lexbuf.buf (lexbuf.start_pos + pos) len - let lexeme lexbuf = Array.sub lexbuf.buf lexbuf.start_pos (lexbuf.pos - lexbuf.start_pos) let current_code_point lexbuf = lexbuf.buf.(lexbuf.start_pos) diff --git a/compiler/flow_parser/flow_sedlexing/flow_sedlexing.mli b/compiler/flow_parser/flow_sedlexing/flow_sedlexing.mli index e0ee791524e..5154cbe4b28 100644 --- a/compiler/flow_parser/flow_sedlexing/flow_sedlexing.mli +++ b/compiler/flow_parser/flow_sedlexing/flow_sedlexing.mli @@ -4,15 +4,12 @@ - Utf8.lexeme_to_buffer - Utf8.lexeme_to_buffer2 *) -exception InvalidCodepoint of int exception MalFormed type apos = int type lexbuf val lexbuf_clone : lexbuf -> lexbuf val from_int_array : int array -> lexbuf -val new_line : lexbuf -> unit -val next : lexbuf -> Uchar.t option (**/**) val __private__next_int : lexbuf -> int @@ -24,9 +21,9 @@ val backtrack : lexbuf -> int val rollback : lexbuf -> unit val lexeme_start : lexbuf -> int val lexeme_end : lexbuf -> int -val loc : lexbuf -> int * int + val lexeme_length : lexbuf -> int -val sub_lexeme : lexbuf -> int -> int -> int array + val lexeme : lexbuf -> int array module Utf8 : sig val from_string : string -> lexbuf diff --git a/compiler/flow_parser/flow_sedlexing_ppx/ppx_sedlex.ml b/compiler/flow_parser/flow_sedlexing_ppx/ppx_sedlex.ml index 1e399790cec..b46f762aa50 100644 --- a/compiler/flow_parser/flow_sedlexing_ppx/ppx_sedlex.ml +++ b/compiler/flow_parser/flow_sedlexing_ppx/ppx_sedlex.ml @@ -172,16 +172,10 @@ module UnicodeProperties = struct end - (* Decision tree for partitions *) let default_loc = Location.none -let lident_loc ~loc s = { - loc; - txt= lident s -} - type decision_tree = | Lte of int * decision_tree * decision_tree | Table of int * int array @@ -252,7 +246,6 @@ let segments_of_partition p = let decision_table p = simplify (-1) (Cset.max_code) (decision_table (segments_of_partition p)) - (* Helpers to build AST *) let appfun s l = @@ -535,7 +528,6 @@ let regexp_of_pattern env = in aux - let previous = ref [] let regexps = ref [] let should_set_cookies = ref false @@ -581,7 +573,6 @@ let mapper = err e.pexp_loc "the %sedlex extension is only recognized on match expressions" | _ -> super # expression e - val toplevel = true method structure_with_regexps l = @@ -625,15 +616,6 @@ let post_handler cookies = let loc = default_loc in Driver.Cookies.set cookies "sedlex.regexps" (pexp_extension ~loc ( {loc; txt="regexps"}, PStr !regexps)) - -let extensions = - [Extension.declare - "sedlex" - Extension.Context.expression - Ast_pattern.(single_expr_payload __) - (fun ~loc:_ ~path:_ expr -> mapper # expression expr); - ] - let () = Driver.Cookies.add_handler pre_handler; Driver.Cookies.add_post_handler post_handler; diff --git a/compiler/flow_parser/flow_sedlexing_ppx/sedlex_cset.ml b/compiler/flow_parser/flow_sedlexing_ppx/sedlex_cset.ml index 1a3df593f7d..c6e3f79be35 100644 --- a/compiler/flow_parser/flow_sedlexing_ppx/sedlex_cset.ml +++ b/compiler/flow_parser/flow_sedlexing_ppx/sedlex_cset.ml @@ -9,7 +9,6 @@ type t = (int * int) list let max_code = 0x10ffff (* must be < max_int *) -let min_code = -1 let empty = [] let singleton i = [i,i] diff --git a/compiler/flow_parser/flow_sedlexing_ppx/sedlex_cset.mli b/compiler/flow_parser/flow_sedlexing_ppx/sedlex_cset.mli index 6a020289f48..b0f94150b27 100644 --- a/compiler/flow_parser/flow_sedlexing_ppx/sedlex_cset.mli +++ b/compiler/flow_parser/flow_sedlexing_ppx/sedlex_cset.mli @@ -6,7 +6,6 @@ type t = (int * int) list -val min_code: int val max_code: int val empty: t diff --git a/compiler/flow_parser/parser/declaration_parser.ml b/compiler/flow_parser/parser/declaration_parser.ml index b3c247a219c..0b172c35a82 100644 --- a/compiler/flow_parser/parser/declaration_parser.ml +++ b/compiler/flow_parser/parser/declaration_parser.ml @@ -261,19 +261,12 @@ module Declaration (Parse : Parser_common.PARSER) (Type : Parser_common.TYPE) : when Peek.ith_is_identifier ~i:1 env -> let ts_accessibility = (with_loc (fun env -> - let leading = Peek.comments env in Eat.token env; - let kind = - match t with - | T_PUBLIC -> Ast.Class.TSAccessibility.Public - | T_PRIVATE -> Ast.Class.TSAccessibility.Private - | T_PROTECTED -> Ast.Class.TSAccessibility.Protected - | _ -> failwith "Must be one of the above" - in - { - Ast.Class.TSAccessibility.kind; - comments = Flow_ast_utils.mk_comments_opt ~leading (); - } + match t with + | T_PUBLIC -> Ast.Class.TSAccessibility.Public + | T_PRIVATE -> Ast.Class.TSAccessibility.Private + | T_PROTECTED -> Ast.Class.TSAccessibility.Protected + | _ -> failwith "Must be one of the above" ) ) env @@ -710,9 +703,9 @@ module Declaration (Parse : Parser_common.PARSER) (Type : Parser_common.TYPE) : let env = env |> with_no_let true in declarations T_LET env - let enum_declaration ?leading ~const_ = + let enum_declaration ~const_ = with_loc (fun env -> - let enum = Enum.declaration ?leading ~const_ env in + let enum = Enum.declaration ~const_ env in Statement.EnumDeclaration enum ) diff --git a/compiler/flow_parser/parser/expression_parser.ml b/compiler/flow_parser/parser/expression_parser.ml index 40540c0b93c..6a32da5fea3 100644 --- a/compiler/flow_parser/parser/expression_parser.ml +++ b/compiler/flow_parser/parser/expression_parser.ml @@ -892,8 +892,9 @@ module Expression ) | _ -> left - and call ?(allow_optional_chain = true) env start_loc left = - as_expression env (call_cover ~allow_optional_chain env start_loc (Cover_expr left)) + and call env start_loc left = + as_expression env + (call_cover ~allow_optional_chain:true env start_loc (Cover_expr left)) and new_expression env = with_loc @@ -1131,7 +1132,7 @@ module Expression start_loc (Cover_expr (loc, member)) in - fun ?(allow_optional_chain = true) ?(in_optional_chain = false) env start_loc left -> + fun ~allow_optional_chain ?(in_optional_chain = false) env start_loc left -> let default_optional = if in_optional_chain then Some Expression.OptionalMember.NonOptional @@ -1234,7 +1235,7 @@ module Expression ) | _ -> left - and member ?(allow_optional_chain = true) env start_loc left = + and member ~allow_optional_chain env start_loc left = as_expression env (member_cover ~allow_optional_chain env start_loc (Cover_expr left)) and _function env = @@ -1500,14 +1501,7 @@ module Expression let case env = let leading = Peek.comments env in let case_match_root_loc = Peek.loc env |> Loc.start_loc in - let invalid_prefix_case = - if Peek.token env = T_CASE then ( - let loc = Peek.loc env in - Eat.token env; - Some loc - ) else - None - in + if Peek.token env = T_CASE then Eat.token env; let pattern = Parse.match_pattern env in let guard = if Eat.maybe env T_IF then ( @@ -1518,40 +1512,20 @@ module Expression ) else None in - let invalid_infix_colon = - if Peek.token env = T_COLON then ( - let loc = Peek.loc env in - Eat.token env; - Some loc - ) else ( - Expect.token env T_ARROW; - None - ) - in + if Peek.token env = T_COLON then + Eat.token env + else + Expect.token env T_ARROW; let body = assignment env in - let invalid_suffix_semicolon = - match Peek.token env with - | T_EOF - | T_RCURLY -> - None - | T_SEMICOLON -> - let loc = Peek.loc env in - Eat.token env; - Some loc - | _ -> - Expect.token env T_COMMA; - None - in + (match Peek.token env with + | T_EOF + | T_RCURLY -> + () + | T_SEMICOLON -> Eat.token env + | _ -> Expect.token env T_COMMA); let trailing = Eat.trailing_comments env in let comments = Flow_ast_utils.mk_comments_opt ~leading ~trailing () in - let invalid_syntax = - { - Match.Case.InvalidSyntax.invalid_prefix_case; - invalid_infix_colon; - invalid_suffix_semicolon; - } - in - { Match.Case.pattern; body; guard; comments; invalid_syntax; case_match_root_loc } + { Match.Case.pattern; body; guard; comments; case_match_root_loc } in let rec case_list env acc = match Peek.token env with @@ -1584,15 +1558,14 @@ module Expression match Peek.token env with | T_RCURLY -> Eat.rescan_as_template_from env prev_lex_env; - let (loc, part, is_tail) = + let (loc, is_tail) = match Peek.token env with - | T_TEMPLATE_PART (loc, cooked, raw, _, tail) -> - let open Ast.Expression.TemplateLiteral in + | T_TEMPLATE_PART (loc, _, _, _, tail) -> Eat.token env; - (loc, { Element.value = { Element.cooked; raw }; tail }, tail) + (loc, tail) | _ -> assert false in - let quasis = (loc, part) :: quasis in + let quasis = loc :: quasis in if is_tail then (loc, List.rev quasis, List.rev expressions) else @@ -1600,35 +1573,16 @@ module Expression | _ -> (* Malformed template *) error_unexpected ~expected:"a template literal part" env; - let imaginary_quasi = - ( fst expr, - { - Expression.TemplateLiteral.Element.value = - { Expression.TemplateLiteral.Element.raw = ""; cooked = "" }; - tail = true; - } - ) - in - (fst expr, List.rev (imaginary_quasi :: quasis), List.rev expressions) + (fst expr, List.rev (fst expr :: quasis), List.rev expressions) in - fun env ((start_loc, cooked, raw, _, is_tail) as part) -> + fun env ((start_loc, _, _, _, is_tail) as part) -> let leading = Peek.comments env in Expect.token env (T_TEMPLATE_PART part); let (end_loc, quasis, expressions) = - let head = - ( start_loc, - { - Ast.Expression.TemplateLiteral.Element.value = - { Ast.Expression.TemplateLiteral.Element.cooked; raw }; - tail = is_tail; - } - ) - in - if is_tail then - (start_loc, [head], []) + (start_loc, [start_loc], []) else - template_parts env [head] [] + template_parts env [start_loc] [] in let trailing = Eat.trailing_comments env in let loc = Loc.btwn start_loc end_loc in @@ -1675,7 +1629,7 @@ module Expression in add_comments ret ~leading ~trailing - and add_comments ?(leading = []) ?(trailing = []) (loc, expression) = + and add_comments ~leading ?(trailing = []) (loc, expression) = let merge_comments inner = Flow_ast_utils.merge_comments ~inner diff --git a/compiler/flow_parser/parser/file_key.ml b/compiler/flow_parser/parser/file_key.ml index 318cac1bd18..048b890d2b0 100644 --- a/compiler/flow_parser/parser/file_key.ml +++ b/compiler/flow_parser/parser/file_key.ml @@ -5,307 +5,17 @@ * LICENSE file in the root directory of this source tree. *) -(* File_key.t stores relative path suffixes internally, following Hack's - Relative_path.t approach. The project root and flowlib root are set once - at startup via global refs. to_string returns the absolute path on demand. +(* The file a location belongs to. ReScript only parses strings, never files, + so there is none: locations always have the source [None]. *) +type t = | - LibFile paths under the flowlib root use a marker prefix internally to - distinguish them from project-root LibFiles. This marker is stripped in - to_string/to_absolute and replaced with the flowlib root. - - IMPORTANT: The global root refs (project_root, flowlib_root) are plain - OCaml ref cells. This is safe with fork-based MultiWorkerLwt workers - (each gets a copy-on-write snapshot). If OCaml 5 domains are ever - introduced, these must become domain-local or atomic. *) - -type t = - | LibFile of string - | SourceFile of string - | JsonFile of string - (* A resource that might get required, like .css, .jpg, etc. We don't parse - these, just check that they exist *) - | ResourceFile of string -[@@deriving show, eq] - -(* Marker for flowlib LibFile paths. This is the single source of truth — - saved_state.ml uses File_key.flowlib_marker, not a separate constant. *) -let flowlib_marker = "///" - -(* Global root refs — set once at startup, before any File_key construction - or to_string calls. All roots have enforced trailing slashes so that - strip_prefix always splits at a directory boundary. - - Using [string option ref] (not [string ref]) so that "not yet initialized" - is distinguishable from "set to empty". Following Hack's Relative_path - convention: accessing an unset root raises an immediate, descriptive error - rather than silently producing a broken path. - - See set_project_root/set_flowlib_root for the setters. *) -let project_root = ref None - -let flowlib_root = ref None - -let enforce_trailing_sep ~dir_sep s = - let len = String.length s in - if len > 0 && s.[len - 1] <> '/' && s.[len - 1] <> '\\' then - s ^ dir_sep - else - s - -(* Normalize a path's directory separators to '/'. The dir_sep_char - parameter specifies which character to treat as a directory separator - (in addition to '/' which is always recognized). On Unix this is '/' - (making this a no-op); on Windows it is '\\'. *) -let normalize_dir_sep_with ~dir_sep_char s = - if Char.equal dir_sep_char '/' then - s - else if String.contains s dir_sep_char then - String.map - (fun c -> - if Char.equal c dir_sep_char then - '/' - else - c) - s - else - s - -let normalize_dir_sep = normalize_dir_sep_with ~dir_sep_char:Filename.dir_sep.[0] - -(* dirname that works with '/' on any platform. Filename.dirname is - platform-specific and won't split on '/' on Windows. *) -let dirname_slash s = - match String.rindex_opt s '/' with - | Some 0 -> "/" - | Some i -> String.sub s 0 i - | None -> s - -(* Resolve a relative suffix against a root directory, handling ".." and "." - segments. Same approach as Files.normalize_path, which can't be used - directly due to parser -> common circular dep. - ~dir_sep controls which character is treated as a directory separator - for normalization (defaults to the platform separator). *) -let resolve_root_with ~is_relative ?(dir_sep = Filename.dir_sep) get_root suffix = - let len = String.length suffix in - if len = 0 || suffix = "-" then - suffix - else if not (is_relative suffix) then - suffix - else - let normalized = normalize_dir_sep_with ~dir_sep_char:dir_sep.[0] suffix in - let parts = String.split_on_char '/' normalized in - let has_dots = List.exists (fun s -> s = "." || s = "..") parts in - if not has_dots then - (* No ".." or "." segments — simple concatenation preserves the - original separators, important for cross-platform round-trips. *) - get_root () ^ suffix - else - let rec resolve dir = function - | [] -> dir - | "." :: rest -> resolve dir rest - | ".." :: rest -> resolve (dirname_slash dir) rest - | remaining -> - let sep = - if String.length dir > 0 && dir.[String.length dir - 1] = '/' then - "" - else - "/" - in - dir ^ sep ^ String.concat "/" remaining - in - (* Normalize root separators so dirname_slash (which only splits on '/') - can traverse up correctly on Windows where roots use backslashes. *) - let root = normalize_dir_sep_with ~dir_sep_char:dir_sep.[0] (get_root ()) in - (* Strip trailing separator — get_root() returns roots with enforced - trailing slashes, but dirname_slash "/foo/" just strips the slash - instead of going up a directory. *) - let rlen = String.length root in - let root = - if rlen > 1 && root.[rlen - 1] = '/' then - String.sub root 0 (rlen - 1) - else - root - in - resolve root parts - -let enforce_trailing_slash s = enforce_trailing_sep ~dir_sep:Filename.dir_sep s - -let set_project_root root = project_root := Some (enforce_trailing_slash root) - -let set_flowlib_root root = flowlib_root := Some (enforce_trailing_slash root) - -(* Retrieve a root, crashing immediately if not set. Following Hack's - Relative_path convention: an unset root is a programmer error that - should be caught at the call site, not masked downstream. *) -let get_project_root () = - match !project_root with - | Some r -> r - | None -> failwith "File_key: project_root has not been set" - -let get_flowlib_root () = - match !flowlib_root with - | Some r -> r - | None -> failwith "File_key: flowlib_root has not been set" - -(* Returns the relative suffix — used internally for comparison and - SharedMem hashing. For flowlib LibFiles, includes the flowlib_marker - prefix. This is the zero-cost path for hot operations like compare. *) -let suffix = function - | LibFile x - | SourceFile x - | JsonFile x - | ResourceFile x -> - x - -(* Resolves a stored suffix back to an absolute path. - - Empty suffix ("") and the stdin sentinel ("-") are returned unchanged. - - Suffixes that are already absolute (Filename.is_relative returns false) - are returned unchanged. - - Relative suffixes (including those with leading ".." for out-of-root - files) are resolved against get_root () via resolve_root_with. *) -let resolve_root get_root suffix = - resolve_root_with ~is_relative:Filename.is_relative get_root suffix - -(* Returns the full absolute path — resolves the root on demand. - Allocates a new string via concatenation. Use suffix for hot paths - that don't need the absolute path (compare, SharedMem hashing). *) -let to_absolute = function - | LibFile x -> - if String.starts_with ~prefix:flowlib_marker x then - let marker_len = String.length flowlib_marker in - resolve_root get_flowlib_root (String.sub x marker_len (String.length x - marker_len)) - else - resolve_root get_project_root x - | SourceFile x - | JsonFile x - | ResourceFile x -> - resolve_root get_project_root x - -(* to_string returns the absolute path so all existing callers - (destructuring, file I/O, display, path manipulation) work correctly - without changes. For hot paths that only need identity/comparison, - use suffix instead to avoid the string allocation. *) -let to_string = to_absolute - -let to_path t = Ok (to_absolute t) - -let compare = - (* libs, then source and json files at the same priority since JSON files are - * basically source files. We don't actually read resource files so they come - * last *) - let order_of_filename = function - | LibFile _ -> 1 - | SourceFile _ -> 2 - | JsonFile _ -> 2 - | ResourceFile _ -> 3 - in - fun a b -> - let k = order_of_filename a - order_of_filename b in - if k <> 0 then - k - else - String.compare (suffix a) (suffix b) - -let compare_opt a b = +let compare_opt (a : t option) (b : t option) = match (a, b) with - | (Some _, None) -> -1 - | (None, Some _) -> 1 | (None, None) -> 0 - | (Some a, Some b) -> compare a b - -let is_lib_file = function - | LibFile _ -> true - | SourceFile _ -> false - | JsonFile _ -> false - | ResourceFile _ -> false - -let map f = function - | LibFile filename -> LibFile (f filename) - | SourceFile filename -> SourceFile (f filename) - | JsonFile filename -> JsonFile (f filename) - | ResourceFile filename -> ResourceFile (f filename) - -let exists f = function - | LibFile filename - | SourceFile filename - | JsonFile filename - | ResourceFile filename -> - f filename - -let check_suffix filename sfx = exists (fun fn -> Filename.check_suffix fn sfx) filename - -let chop_suffix filename sfx = map (fun fn -> Filename.chop_suffix fn sfx) filename - -let with_suffix filename sfx = map (fun fn -> fn ^ sfx) filename - -(* Strip a root prefix from an absolute path. The prefix must have a - trailing slash (enforced by set_project_root/set_flowlib_root) so that - stripping always occurs at a directory boundary — e.g., root "/data/foo/" - won't match "/data/foobar/file.js". *) -let strip_prefix prefix path = - let plen = String.length prefix in - if plen > 0 && String.starts_with ~prefix path then - String.sub path plen (String.length path - plen) - else - path - -(* Compute the relative path from [root] to [path]. Both must be absolute. - Normalizes directory separators to forward slashes, splits on '/', finds - the common prefix, adds ".." for each remaining root component, then - appends the remaining path components. *) -let relative_path_from ?(dir_sep = Filename.dir_sep) root path = - let split s = - String.split_on_char '/' (normalize_dir_sep_with ~dir_sep_char:dir_sep.[0] s) - |> List.filter (fun x -> x <> "") - in - let rec drop_common = function - | (r :: rs, p :: ps) when r = p -> drop_common (rs, ps) - | (rs, ps) -> (rs, ps) - in - let (remaining_root, remaining_path) = drop_common (split root, split path) in - let ups = List.map (fun _ -> "..") remaining_root in - String.concat "/" (ups @ remaining_path) - -(* Strip the project root from an absolute path. If the path is under the - root, the root prefix is stripped to produce a relative suffix. If the path - is NOT under the root (e.g., out-of-root includes like ../../arvr/js/), - compute a relative path from the root — this ensures all suffixes are - portable relative paths, which is critical for saved state portability - across machines with different root paths. - If the root has not been set yet, returns the path unchanged. - The result always uses '/' separators for cross-platform consistency - (saved state generated on Linux must work on Windows and vice versa). *) -let strip_project_root path = - match !project_root with - | Some root -> - if String.starts_with ~prefix:root path then - normalize_dir_sep - (String.sub path (String.length root) (String.length path - String.length root)) - else if not (Filename.is_relative path) then - relative_path_from root path - else - path - | None -> path - -(* Create File_key values from absolute paths, stripping the appropriate root. - Safe to call before roots are initialized — the full path is stored as the - suffix, and to_absolute handles absolute suffixes correctly. *) -let source_file_of_absolute path = SourceFile (strip_project_root path) - -let json_file_of_absolute path = JsonFile (strip_project_root path) - -let resource_file_of_absolute path = ResourceFile (strip_project_root path) - -let lib_file_of_absolute path = - match !flowlib_root with - | Some fl when String.length fl > 0 && String.starts_with ~prefix:fl path -> - LibFile (flowlib_marker ^ normalize_dir_sep (strip_prefix fl path)) - | _ -> LibFile (strip_project_root path) - -module For_tests = struct - let enforce_trailing_sep = enforce_trailing_sep - - let resolve_root_with = resolve_root_with + | (Some _, _) + | (_, Some _) -> + . - let relative_path_from = relative_path_from -end +let check_suffix (file : t) (_ : string) = + match file with + | _ -> . diff --git a/compiler/flow_parser/parser/flow_ast.ml b/compiler/flow_parser/parser/flow_ast.ml index 76479e309c6..7062ad517c3 100644 --- a/compiler/flow_parser/parser/flow_ast.ml +++ b/compiler/flow_parser/parser/flow_ast.ml @@ -12,7 +12,7 @@ module rec Syntax : sig trailing: 'M Comment.t list; internal: 'internal; } - [@@deriving show] + end = Syntax @@ -23,7 +23,7 @@ and Identifier : sig name: string; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end = Identifier @@ -34,7 +34,7 @@ and PrivateName : sig name: string; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end = PrivateName @@ -44,7 +44,7 @@ and StringLiteral : sig raw: string; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end = StringLiteral @@ -54,7 +54,7 @@ and NumberLiteral : sig raw: string; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end = NumberLiteral @@ -65,7 +65,7 @@ and BigIntLiteral : sig raw: string; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end = BigIntLiteral @@ -74,7 +74,7 @@ and BooleanLiteral : sig value: bool; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end = BooleanLiteral @@ -85,7 +85,7 @@ and RegExpLiteral : sig raw: string; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end = RegExpLiteral @@ -98,7 +98,7 @@ and ModuleRefLiteral : sig raw: string; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end = ModuleRefLiteral @@ -118,7 +118,7 @@ and Variance : sig kind: kind; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end = Variance @@ -129,7 +129,7 @@ and ComputedKey : sig expression: ('M, 'T) Expression.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end = ComputedKey @@ -138,7 +138,7 @@ and Variable : sig | Var | Let | Const - [@@deriving show] + end = Variable @@ -151,7 +151,7 @@ and Type : sig false_type: ('M, 'T) Type.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Infer : sig @@ -159,7 +159,7 @@ and Type : sig tparam: ('M, 'T) Type.TypeParam.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Function : sig @@ -174,7 +174,7 @@ and Type : sig optional: bool; } | Destructuring of ('M, 'T) Pattern.t - [@@deriving show] + end module RestParam : sig @@ -184,7 +184,7 @@ and Type : sig argument: ('M, 'T) Param.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module ThisParam : sig @@ -194,7 +194,7 @@ and Type : sig annot: ('M, 'T) Type.annotation; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Params : sig @@ -206,7 +206,7 @@ and Type : sig rest: ('M, 'T) RestParam.t option; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end type ('M, 'T) t = { @@ -221,7 +221,7 @@ and Type : sig | Missing of 'M | Available of ('M, 'T) Type.t | TypeGuard of ('M, 'T) Type.TypeGuard.t - [@@deriving show] + end module Component : sig @@ -233,7 +233,7 @@ and Type : sig annot: ('M, 'T) Type.annotation; optional: bool; } - [@@deriving show] + end module RestParam : sig @@ -245,7 +245,7 @@ and Type : sig optional: bool; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Params : sig @@ -256,7 +256,7 @@ and Type : sig rest: ('M, 'T) RestParam.t option; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end type ('M, 'T) t = { @@ -265,7 +265,7 @@ and Type : sig renders: ('M, 'T) Type.component_renders_annotation; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Generic : sig @@ -288,7 +288,7 @@ and Type : sig argument: 'M * 'M StringLiteral.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end type ('M, 'T) t = { @@ -296,7 +296,7 @@ and Type : sig targs: ('M, 'T) Type.TypeArgs.t option; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module IndexedAccess : sig @@ -305,7 +305,7 @@ and Type : sig index: ('M, 'T) Type.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module OptionalIndexedAccess : sig @@ -313,7 +313,7 @@ and Type : sig indexed_access: ('M, 'T) IndexedAccess.t; optional: bool; } - [@@deriving show] + end module Object : sig @@ -339,7 +339,7 @@ and Type : sig | Init of ('M, 'T) Type.t option | Get of ('M * ('M, 'T) Function.t) | Set of ('M * ('M, 'T) Function.t) - [@@deriving show] + end module SpreadProperty : sig @@ -349,7 +349,7 @@ and Type : sig argument: ('M, 'T) Type.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Indexer : sig @@ -363,7 +363,7 @@ and Type : sig comments: ('M, unit) Syntax.t option; } - and ('M, 'T) t = 'M * ('M, 'T) t' [@@deriving show] + and ('M, 'T) t = 'M * ('M, 'T) t' end module MappedType : sig @@ -373,12 +373,12 @@ and Type : sig | MinusOptional | Optional | NoOptionalFlag - [@@deriving show] + type variance_op = | Add | Remove - [@@deriving show] + type ('M, 'T) t' = { key_tparam: ('M, 'T) Type.TypeParam.t; @@ -391,7 +391,7 @@ and Type : sig comments: ('M, unit) Syntax.t option; } - and ('M, 'T) t = 'M * ('M, 'T) t' [@@deriving show] + and ('M, 'T) t = 'M * ('M, 'T) t' end module CallProperty : sig @@ -402,7 +402,7 @@ and Type : sig static: bool; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module InternalSlot : sig @@ -416,7 +416,7 @@ and Type : sig _method: bool; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module PrivateField : sig @@ -426,7 +426,7 @@ and Type : sig key: 'M PrivateName.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end type ('M, 'T) t = { @@ -451,7 +451,7 @@ and Type : sig | InternalSlot of ('M, 'T) InternalSlot.t | MappedType of ('M, 'T) MappedType.t | PrivateField of ('M, 'T) PrivateField.t - [@@deriving show] + end module Interface : sig @@ -460,7 +460,7 @@ and Type : sig extends: ('M * ('M, 'T) Generic.t) list; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Nullable : sig @@ -468,7 +468,7 @@ and Type : sig argument: ('M, 'T) Type.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Typeof : sig @@ -483,7 +483,7 @@ and Type : sig id: ('M, 'T) Identifier.t; } - and ('M, 'T) qualified = 'T * ('M, 'T) qualified' [@@deriving show] + and ('M, 'T) qualified = 'T * ('M, 'T) qualified' end type ('M, 'T) t = { @@ -491,7 +491,7 @@ and Type : sig targs: ('M, 'T) Type.TypeArgs.t option; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Keyof : sig @@ -499,7 +499,7 @@ and Type : sig argument: ('M, 'T) Type.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Renders : sig @@ -507,7 +507,7 @@ and Type : sig | Normal | Maybe | Star - [@@deriving show] + type ('M, 'T) t = { operator_loc: 'M; @@ -515,7 +515,7 @@ and Type : sig comments: ('M, unit) Syntax.t option; variant: variant; } - [@@deriving show] + end module ReadOnly : sig @@ -523,7 +523,7 @@ and Type : sig argument: ('M, 'T) Type.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module ConstructorType : sig @@ -531,7 +531,7 @@ and Type : sig abstract_: bool; func: ('M, 'T) Function.t; } - [@@deriving show] + end module Tuple : sig @@ -542,7 +542,7 @@ and Type : sig variance: 'M Variance.t option; optional: bool; } - [@@deriving show] + end module UnlabeledElement : sig @@ -550,7 +550,7 @@ and Type : sig annot: ('M, 'T) Type.t; optional: bool; } - [@@deriving show] + end module SpreadElement : sig @@ -558,23 +558,23 @@ and Type : sig name: ('M, 'T) Identifier.t option; annot: ('M, 'T) Type.t; } - [@@deriving show] + end - type ('M, 'T) element = 'M * ('M, 'T) element' [@@deriving show] + type ('M, 'T) element = 'M * ('M, 'T) element' and ('M, 'T) element' = | UnlabeledElement of ('M, 'T) UnlabeledElement.t | LabeledElement of ('M, 'T) LabeledElement.t | SpreadElement of ('M, 'T) SpreadElement.t - [@@deriving show] + and ('M, 'T) t = { elements: ('M, 'T) element list; inexact: bool; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Array : sig @@ -582,7 +582,7 @@ and Type : sig argument: ('M, 'T) Type.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Union : sig @@ -590,7 +590,7 @@ and Type : sig types: ('M, 'T) Type.t * ('M, 'T) Type.t * ('M, 'T) Type.t list; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Intersection : sig @@ -598,31 +598,16 @@ and Type : sig types: ('M, 'T) Type.t * ('M, 'T) Type.t * ('M, 'T) Type.t list; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module TemplateLiteral : sig - module Element : sig - type value = { - raw: string; - cooked: string; - } - - and 'M t = 'M * t' - - and t' = { - value: value; - tail: bool; - } - [@@deriving show] - end - type ('M, 'T) t = { - quasis: 'M Element.t list; + quasis: 'M list; types: ('M, 'T) Type.t list; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end type ('M, 'T) t = 'T * ('M, 'T) t' @@ -685,21 +670,21 @@ and Type : sig and ('M, 'T) annotation_or_hint = | Missing of 'T | Available of ('M, 'T) Type.annotation - [@@deriving show] + and ('M, 'T) component_renders_annotation = | MissingRenders of 'T | AvailableRenders of 'M * ('M, 'T) Type.Renders.t - [@@deriving show] + module TypeParam : sig type bound_kind = | Colon | Extends - [@@deriving show] + module ConstModifier : sig - type 'M t = 'M * ('M, unit) Syntax.t option [@@deriving show] + type 'M t = 'M * ('M, unit) Syntax.t option end type ('M, 'T) t = 'M * ('M, 'T) t' @@ -712,7 +697,7 @@ and Type : sig default: ('M, 'T) Type.t option; const: 'M ConstModifier.t option; } - [@@deriving show] + end module TypeParams : sig @@ -722,7 +707,7 @@ and Type : sig params: ('M, 'T) TypeParam.t list; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end module TypeArgs : sig @@ -732,7 +717,7 @@ and Type : sig arguments: ('M, 'T) Type.t list; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end module Predicate : sig @@ -746,7 +731,7 @@ and Type : sig and ('M, 'T) kind = | Declared of ('M, 'T) Expression.t | Inferred - [@@deriving show] + end module TypeGuard : sig @@ -762,7 +747,7 @@ and Type : sig guard: ('M, 'M) Identifier.t * ('M, 'T) Type.t option; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end end = Type @@ -773,7 +758,7 @@ and Statement : sig body: ('M, 'T) Statement.t list; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end module If : sig @@ -784,7 +769,7 @@ and Statement : sig body: ('M, 'T) Statement.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end type ('M, 'T) t = { @@ -793,7 +778,7 @@ and Statement : sig alternate: ('M, 'T) Alternate.t option; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Labeled : sig @@ -802,7 +787,7 @@ and Statement : sig body: ('M, 'T) Statement.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Break : sig @@ -810,7 +795,7 @@ and Statement : sig label: ('M, 'M) Identifier.t option; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Continue : sig @@ -818,11 +803,11 @@ and Statement : sig label: ('M, 'M) Identifier.t option; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Debugger : sig - type 'M t = { comments: ('M, unit) Syntax.t option } [@@deriving show] + type 'M t = { comments: ('M, unit) Syntax.t option } end module With : sig @@ -831,7 +816,7 @@ and Statement : sig body: ('M, 'T) Statement.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module TypeAlias : sig @@ -841,7 +826,7 @@ and Statement : sig right: ('M, 'T) Type.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module OpaqueType : sig @@ -855,10 +840,10 @@ and Statement : sig (** Invariant: only one of legacy_upper_bound and upper_bound can exist. *) comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end - type ('M, 'T) match_statement = ('M, 'T, ('M, 'T) Statement.t) Match.t [@@deriving show] + type ('M, 'T) match_statement = ('M, 'T, ('M, 'T) Statement.t) Match.t module Switch : sig module Case : sig @@ -870,7 +855,7 @@ and Statement : sig consequent: ('M, 'T) Statement.t list; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end type ('M, 'T) t = { @@ -879,7 +864,7 @@ and Statement : sig comments: ('M, unit) Syntax.t option; exhaustive_out: 'T; } - [@@deriving show] + end module Return : sig @@ -888,7 +873,7 @@ and Statement : sig comments: ('M, unit) Syntax.t option; return_out: 'T; } - [@@deriving show] + end module Throw : sig @@ -896,7 +881,7 @@ and Statement : sig argument: ('M, 'T) Expression.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Try : sig @@ -908,7 +893,7 @@ and Statement : sig body: 'M * ('M, 'T) Block.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end type ('M, 'T) t = { @@ -917,7 +902,7 @@ and Statement : sig finalizer: ('M * ('M, 'T) Block.t) option; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module VariableDeclaration : sig @@ -928,7 +913,7 @@ and Statement : sig id: ('M, 'T) Pattern.t; init: ('M, 'T) Expression.t option; } - [@@deriving show] + end type ('M, 'T) t = { @@ -936,7 +921,7 @@ and Statement : sig kind: Variable.kind; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module While : sig @@ -945,7 +930,7 @@ and Statement : sig body: ('M, 'T) Statement.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module DoWhile : sig @@ -954,7 +939,7 @@ and Statement : sig test: ('M, 'T) Expression.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module For : sig @@ -969,7 +954,7 @@ and Statement : sig and ('M, 'T) init = | InitDeclaration of ('M * ('M, 'T) VariableDeclaration.t) | InitExpression of ('M, 'T) Expression.t - [@@deriving show] + end module ForIn : sig @@ -984,7 +969,7 @@ and Statement : sig and ('M, 'T) left = | LeftDeclaration of ('M * ('M, 'T) VariableDeclaration.t) | LeftPattern of ('M, 'T) Pattern.t - [@@deriving show] + end module ForOf : sig @@ -999,19 +984,19 @@ and Statement : sig and ('M, 'T) left = | LeftDeclaration of ('M * ('M, 'T) VariableDeclaration.t) | LeftPattern of ('M, 'T) Pattern.t - [@@deriving show] + end module EnumDeclaration : sig type 'M member_name = | Identifier of ('M, 'M) Identifier.t | StringLiteral of ('M * 'M StringLiteral.t) - [@@deriving show] + module DefaultedMember : sig type 'M t = 'M * 'M t' - and 'M t' = { id: 'M member_name } [@@deriving show] + and 'M t' = { id: 'M member_name } end module InitializedMember : sig @@ -1021,7 +1006,7 @@ and Statement : sig id: 'M member_name; init: 'M * 'I; } - [@@deriving show] + end type explicit_type = @@ -1030,7 +1015,7 @@ and Statement : sig | String | Symbol | BigInt - [@@deriving ord, show] + [@@deriving ord] type 'M member = | BooleanMember of ('M BooleanLiteral.t, 'M) InitializedMember.t @@ -1038,7 +1023,7 @@ and Statement : sig | StringMember of ('M StringLiteral.t, 'M) InitializedMember.t | BigIntMember of ('M BigIntLiteral.t, 'M) InitializedMember.t | DefaultedMember of 'M DefaultedMember.t - [@@deriving show] + module Body : sig type 'M t = { @@ -1047,7 +1032,7 @@ and Statement : sig has_unknown_members: 'M option; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end type ('M, 'T) t = { @@ -1057,7 +1042,7 @@ and Statement : sig comments: ('M, unit) Syntax.t option; } - and 'M body = 'M * 'M Body.t [@@deriving show] + and 'M body = 'M * 'M Body.t end module ComponentDeclaration : sig @@ -1068,7 +1053,7 @@ and Statement : sig argument: ('M, 'T) Pattern.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Param : sig @@ -1086,7 +1071,7 @@ and Statement : sig and ('M, 'T) param_name = | Identifier of ('M, 'T) Identifier.t | StringLiteral of ('M * 'M StringLiteral.t) - [@@deriving show] + end module Params : sig @@ -1097,7 +1082,7 @@ and Statement : sig rest: ('M, 'T) RestParam.t option; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end type ('M, 'T) t = { @@ -1114,7 +1099,7 @@ and Statement : sig *) sig_loc: 'M; } - [@@deriving show] + end module Interface : sig @@ -1125,19 +1110,10 @@ and Statement : sig body: 'M * ('M, 'T) Type.Object.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module RecordDeclaration : sig - module InvalidPropertySyntax : sig - type 'M t = { - invalid_variance: 'M Variance.t option; - invalid_optional: 'M option; - invalid_suffix_semicolon: 'M option; - } - [@@deriving show] - end - module Property : sig type ('M, 'T) t = 'T * ('M, 'T) t' @@ -1146,9 +1122,8 @@ and Statement : sig annot: ('M, 'T) Type.annotation; default_value: ('M, 'T) Expression.t option; comments: ('M, unit) Syntax.t option; - invalid_syntax: 'M InvalidPropertySyntax.t option; } - [@@deriving show] + end module StaticProperty : sig @@ -1159,9 +1134,8 @@ and Statement : sig annot: ('M, 'T) Type.annotation; value: ('M, 'T) Expression.t; comments: ('M, unit) Syntax.t option; - invalid_syntax: 'M InvalidPropertySyntax.t option; } - [@@deriving show] + end module Body : sig @@ -1176,11 +1150,7 @@ and Statement : sig | Method of ('M, 'T) Class.Method.t | Property of ('M, 'T) Property.t | StaticProperty of ('M, 'T) StaticProperty.t - [@@deriving show] - end - - module InvalidSyntax : sig - type 'M t = { invalid_infix_equals: 'M option } [@@deriving show] + end type ('M, 'T) t = { @@ -1189,9 +1159,8 @@ and Statement : sig implements: ('M, 'T) Class.Implements.t option; body: ('M, 'T) Body.t; comments: ('M, unit) Syntax.t option; - invalid_syntax: 'M InvalidSyntax.t option; } - [@@deriving show] + end module DeclareClass : sig @@ -1201,7 +1170,7 @@ and Statement : sig callee: 'M * ('M, 'T) Type.Generic.t; arg: 'M * ('M, 'T) extends; } - [@@deriving show] + type ('M, 'T) t = { id: ('M, 'T) Identifier.t; @@ -1213,7 +1182,7 @@ and Statement : sig abstract: bool; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module DeclareComponent : sig @@ -1224,7 +1193,7 @@ and Statement : sig renders: ('M, 'T) Type.component_renders_annotation; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module DeclareVariable : sig @@ -1233,7 +1202,7 @@ and Statement : sig kind: Variable.kind; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module DeclareFunction : sig @@ -1244,7 +1213,7 @@ and Statement : sig comments: ('M, unit) Syntax.t option; implicit_declare: bool; } - [@@deriving show] + end module DeclareModule : sig @@ -1257,7 +1226,7 @@ and Statement : sig body: 'M * ('M, 'T) Block.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module DeclareModuleExports : sig @@ -1265,19 +1234,19 @@ and Statement : sig annot: ('M, 'T) Type.annotation; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module DeclareNamespace : sig type keyword = | Namespace | Module - [@@deriving show] + type ('M, 'T) id = | Global of ('M, 'M) Identifier.t | Local of ('M, 'T) Identifier.t - [@@deriving show] + type ('M, 'T) t = { id: ('M, 'T) id; @@ -1286,20 +1255,20 @@ and Statement : sig implicit_declare: bool; keyword: keyword; } - [@@deriving show] + end module ExportAssignment : sig type ('M, 'T) rhs = | Expression of ('M, 'T) Expression.t | DeclareFunction of ('M * ('M, 'T) DeclareFunction.t) - [@@deriving show] + type ('M, 'T) t = { rhs: ('M, 'T) rhs; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module NamespaceExportDeclaration : sig @@ -1307,7 +1276,7 @@ and Statement : sig id: ('M, 'T) Identifier.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module ExportNamedDeclaration : sig @@ -1322,11 +1291,11 @@ and Statement : sig (* Imported name's definition location. It will be populated only in typed AST for `export {foo} from '...'`. *) imported_name_def_loc: 'M option; } - [@@deriving show] + end module ExportBatchSpecifier : sig - type ('M, 'T) t = 'M * ('M, 'T) Identifier.t option [@@deriving show] + type ('M, 'T) t = 'M * ('M, 'T) Identifier.t option end type ('M, 'T) t = { @@ -1340,7 +1309,7 @@ and Statement : sig and ('M, 'T) specifier = | ExportSpecifiers of ('M, 'T) ExportSpecifier.t list | ExportBatchSpecifier of ('M, 'T) ExportBatchSpecifier.t - [@@deriving show] + end module ExportDefaultDeclaration : sig @@ -1353,7 +1322,7 @@ and Statement : sig and ('M, 'T) declaration = | Declaration of ('M, 'T) Statement.t | Expression of ('M, 'T) Expression.t - [@@deriving show] + end module DeclareExportDeclaration : sig @@ -1388,7 +1357,7 @@ and Statement : sig source: ('T * 'M StringLiteral.t) option; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module ImportDeclaration : sig @@ -1438,7 +1407,7 @@ and Statement : sig attributes: ('M * ('M, 'T) import_attribute list) option; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module ImportEqualsDeclaration : sig @@ -1453,7 +1422,7 @@ and Statement : sig is_export: bool; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Expression : sig @@ -1462,11 +1431,11 @@ and Statement : sig directive: string option; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Empty : sig - type 'M t = { comments: ('M, unit) Syntax.t option } [@@deriving show] + type 'M t = { comments: ('M, unit) Syntax.t option } end type export_kind = @@ -1522,7 +1491,7 @@ and Statement : sig | VariableDeclaration of ('M, 'T) VariableDeclaration.t | While of ('M, 'T) While.t | With of ('M, 'T) With.t - [@@deriving show] + end = Statement @@ -1531,13 +1500,13 @@ and Expression : sig module Implicit : sig type ('M, 'T) t = 'T * 'M t' - and 'M t' = { comments: ('M, unit) Syntax.t option } [@@deriving show] + and 'M t' = { comments: ('M, unit) Syntax.t option } end type ('M, 'T) t = | Explicit of ('M, 'T) Type.t | Implicit of ('M, 'T) Implicit.t - [@@deriving show] + end module CallTypeArgs : sig @@ -1547,7 +1516,7 @@ and Expression : sig arguments: ('M, 'T) CallTypeArg.t list; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end module SpreadElement : sig @@ -1557,7 +1526,7 @@ and Expression : sig argument: ('M, 'T) Expression.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Array : sig @@ -1565,38 +1534,23 @@ and Expression : sig | Expression of ('M, 'T) Expression.t | Spread of ('M, 'T) SpreadElement.t | Hole of 'M - [@@deriving show] + type ('M, 'T) t = { elements: ('M, 'T) element list; trailing_comma: bool; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end module TemplateLiteral : sig - module Element : sig - type value = { - raw: string; - cooked: string; - } - - and 'M t = 'M * t' - - and t' = { - value: value; - tail: bool; - } - [@@deriving show] - end - type ('M, 'T) t = { - quasis: 'M Element.t list; + quasis: 'M list; expressions: ('M, 'T) Expression.t list; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module TaggedTemplate : sig @@ -1606,7 +1560,7 @@ and Expression : sig quasi: 'M * ('M, 'T) TemplateLiteral.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Object : sig @@ -1641,7 +1595,7 @@ and Expression : sig value: 'M * ('M, 'T) Function.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module SpreadProperty : sig @@ -1651,7 +1605,7 @@ and Expression : sig argument: ('M, 'T) Expression.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end type ('M, 'T) property = @@ -1662,7 +1616,7 @@ and Expression : sig properties: ('M, 'T) property list; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end module Record : sig @@ -1672,7 +1626,7 @@ and Expression : sig properties: 'M * ('M, 'T) Object.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Sequence : sig @@ -1680,7 +1634,7 @@ and Expression : sig expressions: ('M, 'T) Expression.t list; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Unary : sig @@ -1700,7 +1654,7 @@ and Expression : sig argument: ('M, 'T) Expression.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Binary : sig @@ -1734,7 +1688,7 @@ and Expression : sig right: ('M, 'T) Expression.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Assignment : sig @@ -1761,7 +1715,7 @@ and Expression : sig right: ('M, 'T) Expression.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Update : sig @@ -1775,7 +1729,7 @@ and Expression : sig prefix: bool; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Logical : sig @@ -1790,7 +1744,7 @@ and Expression : sig right: ('M, 'T) Expression.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Conditional : sig @@ -1800,13 +1754,13 @@ and Expression : sig alternate: ('M, 'T) Expression.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end type ('M, 'T) expression_or_spread = | Expression of ('M, 'T) Expression.t | Spread of ('M, 'T) SpreadElement.t - [@@deriving show] + module ArgList : sig type ('M, 'T) t = 'M * ('M, 'T) t' @@ -1815,7 +1769,7 @@ and Expression : sig arguments: ('M, 'T) expression_or_spread list; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end module New : sig @@ -1825,7 +1779,7 @@ and Expression : sig arguments: ('M, 'T) ArgList.t option; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Call : sig @@ -1835,7 +1789,7 @@ and Expression : sig arguments: ('M, 'T) ArgList.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module OptionalCall : sig @@ -1843,14 +1797,14 @@ and Expression : sig | Optional | NonOptional | AssertNonnull - [@@deriving show] + type ('M, 'T) t = { call: ('M, 'T) Call.t; filtered_out: 'T; optional: kind; } - [@@deriving show] + end module Member : sig @@ -1864,7 +1818,7 @@ and Expression : sig property: ('M, 'T) property; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module OptionalMember : sig @@ -1872,14 +1826,14 @@ and Expression : sig | Optional | NonOptional | AssertNonnull - [@@deriving show] + type ('M, 'T) t = { member: ('M, 'T) Member.t; filtered_out: 'T; optional: kind; } - [@@deriving show] + end module Yield : sig @@ -1889,7 +1843,7 @@ and Expression : sig delegate: bool; result_out: 'T; } - [@@deriving show] + end module TypeCast : sig @@ -1898,7 +1852,7 @@ and Expression : sig annot: ('M, 'T) Type.annotation; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module AsExpression : sig @@ -1907,7 +1861,7 @@ and Expression : sig annot: ('M, 'T) Type.annotation; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module AsConstExpression : sig @@ -1915,7 +1869,7 @@ and Expression : sig expression: ('M, 'T) Expression.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module TSSatisfies : sig @@ -1924,7 +1878,7 @@ and Expression : sig annot: ('M, 'T) Type.annotation; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module MetaProperty : sig @@ -1933,15 +1887,15 @@ and Expression : sig property: ('M, 'M) Identifier.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module This : sig - type 'M t = { comments: ('M, unit) Syntax.t option } [@@deriving show] + type 'M t = { comments: ('M, unit) Syntax.t option } end module Super : sig - type 'M t = { comments: ('M, unit) Syntax.t option } [@@deriving show] + type 'M t = { comments: ('M, unit) Syntax.t option } end module Import : sig @@ -1950,10 +1904,10 @@ and Expression : sig options: ('M, 'T) Expression.t option; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end - type ('M, 'T) match_expression = ('M, 'T, ('M, 'T) Expression.t) Match.t [@@deriving show] + type ('M, 'T) match_expression = ('M, 'T, ('M, 'T) Expression.t) Match.t type ('M, 'T) t = 'T * ('M, 'T) t' @@ -1998,7 +1952,7 @@ and Expression : sig | Unary of ('M, 'T) Unary.t | Update of ('M, 'T) Update.t | Yield of ('M, 'T) Yield.t - [@@deriving show] + end = Expression @@ -2010,7 +1964,7 @@ and JSX : sig name: string; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module NamespacedName : sig @@ -2020,7 +1974,7 @@ and JSX : sig namespace: ('M, 'T) Identifier.t; name: ('M, 'T) Identifier.t; } - [@@deriving show] + end module ExpressionContainer : sig @@ -2032,15 +1986,7 @@ and JSX : sig and ('M, 'T) expression = | Expression of ('M, 'T) Expression.t | EmptyExpression - [@@deriving show] - end - - module Text : sig - type t = { - value: string; - raw: string; - } - [@@deriving show] + end module Attribute : sig @@ -2058,7 +2004,7 @@ and JSX : sig name: ('M, 'T) name; value: ('M, 'T) value option; } - [@@deriving show] + end module SpreadAttribute : sig @@ -2068,7 +2014,7 @@ and JSX : sig argument: ('M, 'T) Expression.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module MemberExpression : sig @@ -2082,14 +2028,14 @@ and JSX : sig _object: ('M, 'T) _object; property: ('M, 'T) Identifier.t; } - [@@deriving show] + end type ('M, 'T) name = | Identifier of ('M, 'T) Identifier.t | NamespacedName of ('M, 'T) NamespacedName.t | MemberExpression of ('M, 'T) MemberExpression.t - [@@deriving show] + module Opening : sig type ('M, 'T) t = 'M * ('M, 'T) t' @@ -2104,13 +2050,13 @@ and JSX : sig self_closing: bool; attributes: ('M, 'T) attribute list; } - [@@deriving show] + end module Closing : sig type ('M, 'T) t = 'M * ('M, 'T) t' - and ('M, 'T) t' = { name: ('M, 'T) name } [@@deriving show] + and ('M, 'T) t' = { name: ('M, 'T) name } end module SpreadChild : sig @@ -2118,7 +2064,7 @@ and JSX : sig expression: ('M, 'T) Expression.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end type ('M, 'T) child = 'T * ('M, 'T) child' @@ -2128,7 +2074,7 @@ and JSX : sig | Fragment of ('M, 'T) fragment | ExpressionContainer of ('M, 'T) ExpressionContainer.t | SpreadChild of ('M, 'T) SpreadChild.t - | Text of Text.t + | Text and ('M, 'T) element = { opening_element: ('M, 'T) Opening.t; @@ -2138,26 +2084,15 @@ and JSX : sig } and ('M, 'T) fragment = { - frag_opening_element: 'M; - frag_closing_element: 'M; frag_children: 'M * ('M, 'T) child list; frag_comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end = JSX and Match : sig module Case : sig - module InvalidSyntax : sig - type 'M t = { - invalid_prefix_case: 'M option; - invalid_infix_colon: 'M option; - invalid_suffix_semicolon: 'M option; - } - [@@deriving show] - end - type ('M, 'T, 'B) t = 'M * ('M, 'T, 'B) t' and ('M, 'T, 'B) t' = { @@ -2165,10 +2100,9 @@ and Match : sig body: 'B; guard: ('M, 'T) Expression.t option; comments: ('M, unit) Syntax.t option; - invalid_syntax: 'M InvalidSyntax.t; case_match_root_loc: 'M; } - [@@deriving show] + end type ('M, 'T, 'B) t = { @@ -2177,7 +2111,7 @@ and Match : sig match_keyword_loc: 'M; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end = Match @@ -2196,7 +2130,7 @@ and MatchPattern : sig argument: 'M * 'M argument; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module MemberPattern : sig @@ -2217,7 +2151,7 @@ and MatchPattern : sig property: ('M, 'T) property; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module BindingPattern : sig @@ -2226,7 +2160,7 @@ and MatchPattern : sig id: ('M, 'T) Identifier.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module RestPattern : sig @@ -2236,7 +2170,7 @@ and MatchPattern : sig argument: ('M * ('M, 'T) BindingPattern.t) option; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module ObjectPattern : sig @@ -2260,7 +2194,7 @@ and MatchPattern : sig | Valid of ('M, 'T) property (* Invalid code parsed so we can error with quick-fix. *) | InvalidShorthand of ('M, 'M) Identifier.t - [@@deriving show] + end type ('M, 'T) t = { @@ -2268,7 +2202,7 @@ and MatchPattern : sig rest: ('M, 'T) RestPattern.t option; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end module ArrayPattern : sig @@ -2277,7 +2211,7 @@ and MatchPattern : sig index: 'M; pattern: ('M, 'T) MatchPattern.t; } - [@@deriving show] + end type ('M, 'T) t = { @@ -2285,7 +2219,7 @@ and MatchPattern : sig rest: ('M, 'T) RestPattern.t option; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end module InstancePattern : sig @@ -2298,7 +2232,7 @@ and MatchPattern : sig properties: 'M * ('M, 'T) ObjectPattern.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module OrPattern : sig @@ -2306,7 +2240,7 @@ and MatchPattern : sig patterns: ('M, 'T) MatchPattern.t list; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module AsPattern : sig @@ -2319,7 +2253,7 @@ and MatchPattern : sig target: ('M, 'T) target; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module WildcardPattern : sig @@ -2327,7 +2261,7 @@ and MatchPattern : sig comments: ('M, unit) Syntax.t option; invalid_syntax_default_keyword: bool; } - [@@deriving show] + end type ('M, 'T) t = 'M * ('M, 'T) t' @@ -2348,7 +2282,7 @@ and MatchPattern : sig | InstancePattern of ('M, 'T) InstancePattern.t | OrPattern of ('M, 'T) OrPattern.t | AsPattern of ('M, 'T) AsPattern.t - [@@deriving show] + end = MatchPattern @@ -2360,7 +2294,7 @@ and Pattern : sig argument: ('M, 'T) Pattern.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Object : sig @@ -2380,7 +2314,7 @@ and Pattern : sig default: ('M, 'T) Expression.t option; shorthand: bool; } - [@@deriving show] + end type ('M, 'T) property = @@ -2393,7 +2327,7 @@ and Pattern : sig optional: bool; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end module Array : sig @@ -2404,7 +2338,7 @@ and Pattern : sig argument: ('M, 'T) Pattern.t; default: ('M, 'T) Expression.t option; } - [@@deriving show] + end type ('M, 'T) element = @@ -2418,7 +2352,7 @@ and Pattern : sig optional: bool; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end module Identifier : sig @@ -2427,7 +2361,7 @@ and Pattern : sig annot: ('M, 'T) Type.annotation_or_hint; optional: bool; } - [@@deriving show] + end type ('M, 'T) t = 'T * ('M, 'T) t' @@ -2437,7 +2371,7 @@ and Pattern : sig | Array of ('M, 'T) Array.t | Identifier of ('M, 'T) Identifier.t | Expression of ('M, 'T) Expression.t - [@@deriving show] + end = Pattern @@ -2451,9 +2385,8 @@ and Comment : sig and t' = { kind: kind; text: string; - on_newline: bool; } - [@@deriving show] + end = Comment @@ -2464,13 +2397,8 @@ and Class : sig | Protected | Private - and 'M t = 'M * 'M t' - - and 'M t' = { - kind: kind; - comments: ('M, unit) Syntax.t option; - } - [@@deriving show] + and 'M t = 'M * kind + end module Method : sig @@ -2492,7 +2420,7 @@ and Class : sig decorators: ('M, 'T) Class.Decorator.t list; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module DeclareMethod : sig @@ -2507,7 +2435,7 @@ and Class : sig optional: bool; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module AbstractMethod : sig @@ -2520,7 +2448,7 @@ and Class : sig ts_accessibility: 'M TSAccessibility.t option; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module AbstractProperty : sig @@ -2534,7 +2462,7 @@ and Class : sig variance: 'M Variance.t option; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Property : sig @@ -2557,7 +2485,7 @@ and Class : sig | Declared | Uninitialized | Initialized of ('M, 'T) Expression.t - [@@deriving show] + end module PrivateField : sig @@ -2575,7 +2503,7 @@ and Class : sig decorators: ('M, 'T) Class.Decorator.t list; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module StaticBlock : sig @@ -2585,7 +2513,7 @@ and Class : sig body: ('M, 'T) Statement.t list; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end module Extends : sig @@ -2596,7 +2524,7 @@ and Class : sig targs: ('M, 'T) Type.TypeArgs.t option; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Implements : sig @@ -2607,7 +2535,7 @@ and Class : sig id: ('M, 'T) Type.Generic.Identifier.t; targs: ('M, 'T) Type.TypeArgs.t option; } - [@@deriving show] + end type ('M, 'T) t = 'M * ('M, 'T) t' @@ -2616,7 +2544,7 @@ and Class : sig interfaces: ('M, 'T) Interface.t list; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Body : sig @@ -2636,7 +2564,7 @@ and Class : sig | AbstractMethod of ('M, 'T) AbstractMethod.t | AbstractProperty of ('M, 'T) AbstractProperty.t | IndexSignature of ('M, 'T) Type.Object.Indexer.t - [@@deriving show] + end module Decorator : sig @@ -2646,7 +2574,7 @@ and Class : sig expression: ('M, 'T) Expression.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end type ('M, 'T) t = { @@ -2659,7 +2587,7 @@ and Class : sig abstract: bool; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end = Class @@ -2671,7 +2599,7 @@ and Function : sig argument: ('M, 'T) Pattern.t; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Param : sig @@ -2683,7 +2611,7 @@ and Function : sig default: ('M, 'T) Expression.t option; } | ParamProperty of ('M, 'T) Class.Property.t' - [@@deriving show] + end module ThisParam : sig @@ -2693,7 +2621,7 @@ and Function : sig annot: ('M, 'T) Type.annotation; comments: ('M, unit) Syntax.t option; } - [@@deriving show] + end module Params : sig @@ -2705,7 +2633,7 @@ and Function : sig rest: ('M, 'T) RestParam.t option; comments: ('M, 'M Comment.t list) Syntax.t option; } - [@@deriving show] + end module ReturnAnnot : sig @@ -2713,13 +2641,13 @@ and Function : sig | Missing of 'T | Available of ('M, 'T) Type.annotation | TypeGuard of ('M, 'T) Type.type_guard_annotation - [@@deriving show] + end type effect_ = | Hook | Arbitrary - [@@deriving show] + type ('M, 'T) t = { id: ('M, 'T) Identifier.t option; @@ -2742,7 +2670,7 @@ and Function : sig and ('M, 'T) body = | BodyBlock of ('M * ('M, 'T) Statement.Block.t) | BodyExpression of ('M, 'T) Expression.t - [@@deriving show] + end = Function @@ -2755,6 +2683,6 @@ and Program : sig comments: ('M, unit) Syntax.t option; all_comments: 'M Comment.t list; } - [@@deriving show] + end = Program] diff --git a/compiler/flow_parser/parser/flow_ast_utils.ml b/compiler/flow_parser/parser/flow_ast_utils.ml index 50c177d1365..6a0b6a5ab34 100644 --- a/compiler/flow_parser/parser/flow_ast_utils.ml +++ b/compiler/flow_parser/parser/flow_ast_utils.ml @@ -6,118 +6,13 @@ *) open Flow_ast -module E = Expression module I = Identifier type 'loc binding = 'loc * string -type 'loc ident = 'loc * string [@@deriving show] +type 'loc ident = 'loc * string -type 'loc source = 'loc * string [@@deriving show] - -let rec fold_bindings_of_pattern = - Pattern.( - let property f acc = - Object.( - function - | Property (_, { Property.pattern = p; _ }) - | RestElement (_, { RestElement.argument = p; comments = _ }) -> - fold_bindings_of_pattern f acc p - ) - in - let element f acc = - Array.( - function - | Hole _ -> acc - | Element (_, { Element.argument = p; default = _ }) - | RestElement (_, { RestElement.argument = p; comments = _ }) -> - fold_bindings_of_pattern f acc p - ) - in - fun f acc -> function - | (_, Identifier { Identifier.name; _ }) -> f acc name - | (_, Object { Object.properties; _ }) -> List.fold_left (property f) acc properties - | (_, Array { Array.elements; _ }) -> List.fold_left (element f) acc elements - (* This is for assignment and default param destructuring `[a.b=1]=c`, ignore these for now. *) - | (_, Expression _) -> acc - ) - -let fold_bindings_of_variable_declarations f acc declarations = - let open Statement.VariableDeclaration in - List.fold_left - (fun acc -> function - | (_, { Declarator.id = pattern; _ }) -> - let has_anno = - (* Only the toplevel annotation in a pattern is meaningful *) - let open Pattern in - match pattern with - | (_, Array { Array.annot = Type.Available _; _ }) - | (_, Object { Object.annot = Type.Available _; _ }) - | (_, Identifier { Identifier.annot = Type.Available _; _ }) -> - true - | _ -> false - in - fold_bindings_of_pattern (f has_anno) acc pattern) - acc - declarations - -let rec pattern_has_binding = - let open Pattern in - let property = - let open Object in - function - | Property (_, { Property.pattern = p; _ }) - | RestElement (_, { RestElement.argument = p; comments = _ }) -> - pattern_has_binding p - in - let element = - let open Array in - function - | Hole _ -> false - | Element (_, { Element.argument = p; default = _ }) - | RestElement (_, { RestElement.argument = p; comments = _ }) -> - pattern_has_binding p - in - function - | (_, Identifier _) -> true - | (_, Object { Object.properties; _ }) -> List.exists property properties - | (_, Array { Array.elements; _ }) -> List.exists element elements - | (_, Expression _) -> false - -let rec match_pattern_has_binding = - let open MatchPattern in - let property = function - | (_, ObjectPattern.Property.Valid { ObjectPattern.Property.pattern = p; _ }) -> - match_pattern_has_binding p - | (_, ObjectPattern.Property.InvalidShorthand _) -> false - in - let rest_has_binding = function - | Some (_, { RestPattern.argument = Some _; comments = _ }) -> true - | _ -> false - in - function - | (_, WildcardPattern _) - | (_, NumberPattern _) - | (_, BigIntPattern _) - | (_, StringPattern _) - | (_, BooleanPattern _) - | (_, NullPattern _) - | (_, UnaryPattern _) - | (_, IdentifierPattern _) - | (_, MemberPattern _) -> - false - | (_, BindingPattern _) -> true - | (_, ObjectPattern { ObjectPattern.properties; rest; comments = _ }) -> - rest_has_binding rest || List.exists property properties - | (_, ArrayPattern { ArrayPattern.elements; rest; comments = _ }) -> - rest_has_binding rest - || List.exists - (fun { ArrayPattern.Element.pattern; _ } -> match_pattern_has_binding pattern) - elements - | (_, InstancePattern { InstancePattern.properties = (properties_loc, properties); _ }) -> - match_pattern_has_binding (properties_loc, ObjectPattern properties) - | (_, OrPattern { OrPattern.patterns; _ }) -> List.exists match_pattern_has_binding patterns - | (_, AsPattern _) -> true +type 'loc source = 'loc * string let pattern_has_type_annotation = let open Pattern in @@ -127,416 +22,11 @@ let pattern_has_type_annotation = | (_, Array { Array.annot = Type.Available _; _ }) -> true | _ -> false -let string_of_variable_kind = function - | Variable.Var -> "var" - | Variable.Let -> "let" - | Variable.Const -> "const" - -let partition_directives statements = - let open Statement in - let rec helper directives = function - | ((_, Expression { Expression.directive = Some _; _ }) as directive) :: rest -> - helper (directive :: directives) rest - | rest -> (List.rev directives, rest) - in - helper [] statements - -let hoist_function_and_component_declarations stmts = - let open Statement in - let (func_and_component_decs, other_stmts) = - List.partition - (function - (* function f() {} / component F() {} *) - | (_, (FunctionDeclaration { Function.id = Some _; _ } | ComponentDeclaration _)) - (* export function f() {} / export component F() {} *) - | ( _, - ExportNamedDeclaration - { - ExportNamedDeclaration.declaration = - Some - (_, (FunctionDeclaration { Function.id = Some _; _ } | ComponentDeclaration _)); - _; - } - ) - (* export default function f() {} / export default component F() {} *) - | ( _, - ExportDefaultDeclaration - { - ExportDefaultDeclaration.declaration = - ExportDefaultDeclaration.Declaration - (_, (FunctionDeclaration { Function.id = Some _; _ } | ComponentDeclaration _)); - _; - } - ) - (* TODO(jmbrown): Hoist declared components *) - (* declare function f(): void; *) - | (_, DeclareFunction _) - (* declare export function f(): void; *) - | ( _, - DeclareExportDeclaration DeclareExportDeclaration.{ declaration = Some (Function _); _ } - ) -> - true - | _ -> false) - stmts - in - func_and_component_decs @ other_stmts - -let negate_raw_lit raw = - let raw_len = String.length raw in - if raw_len > 0 && raw.[0] = '-' then - String.sub raw 1 (raw_len - 1) - else - "-" ^ raw - -let negate_number_literal (value, raw) = (~-.value, negate_raw_lit raw) - -let negate_bigint_literal (value, raw) = - match value with - | None -> (None, raw) - | Some value -> (Some (Int64.neg value), negate_raw_lit raw) - -let is_number_literal node = - match node with - | Expression.NumberLiteral _ - | Expression.Unary - { - Expression.Unary.operator = Expression.Unary.Minus; - argument = (_, Expression.NumberLiteral _); - comments = _; - } -> - true - | _ -> false - -let extract_number_literal node = - match node with - | Expression.NumberLiteral { NumberLiteral.value; raw; comments = _ } -> Some (value, raw) - | Expression.Unary - { - Expression.Unary.operator = Expression.Unary.Minus; - argument = (_, Expression.NumberLiteral { NumberLiteral.value; raw; _ }); - comments = _; - } -> - Some (negate_number_literal (value, raw)) - | _ -> None - -let is_bigint_literal node = - match node with - | Expression.BigIntLiteral _ - | Expression.Unary - { - Expression.Unary.operator = Expression.Unary.Minus; - argument = (_, Expression.BigIntLiteral _); - comments = _; - } -> - true - | _ -> false - -let extract_bigint_literal node = - match node with - | Expression.BigIntLiteral { BigIntLiteral.value; raw; comments = _ } -> Some (value, raw) - | Expression.Unary - { - Expression.Unary.operator = Expression.Unary.Minus; - argument = (_, Expression.BigIntLiteral { BigIntLiteral.value; raw; comments = _ }); - comments = _; - } -> - Some (negate_bigint_literal (value, raw)) - | _ -> None - -let is_call_to_invariant callee = - match callee with - | (_, Expression.Identifier (_, { Identifier.name = "invariant"; _ })) -> true - | _ -> false - -let is_call_to_require callee = - match callee with - | (_, Expression.Identifier (_, { Identifier.name = "require"; _ })) -> true - | _ -> false - -let is_call_to_is_array callee = - match callee with - | ( _, - E.Member - { - E.Member._object = (_, E.Identifier (_, { I.name = "Array"; comments = _ })); - property = E.Member.PropertyIdentifier (_, { I.name = "isArray"; comments = _ }); - comments = _; - } - ) -> - true - | _ -> false - -let is_call_to_object_dot_freeze callee = - match callee with - | ( _, - E.Member - { - E.Member._object = (_, E.Identifier (_, { I.name = "Object"; comments = _ })); - property = E.Member.PropertyIdentifier (_, { I.name = "freeze"; comments = _ }); - comments = _; - } - ) -> - true - | _ -> false - -let get_call_to_object_dot_freeze_arg callee targs args = - match (targs, args) with - | (None, (_args_loc, { E.ArgList.arguments = [E.Expression (obj_loc, E.Object o)]; comments = _ })) - when is_call_to_object_dot_freeze callee -> - Some (obj_loc, o) - | _ -> None - -let is_call_to_object_static_method callee = - match callee with - | ( _, - E.Member - { - E.Member._object = (_, E.Identifier (_, { I.name = "Object"; comments = _ })); - property = E.Member.PropertyIdentifier _; - comments = _; - } - ) -> - true - | _ -> false - -let is_module_dot_exports callee = - match callee with - | ( _, - E.Member - { - E.Member._object = (_, E.Identifier (_, { I.name = "module"; comments = _ })); - property = E.Member.PropertyIdentifier (_, { I.name = "exports"; comments = _ }); - comments = _; - } - ) -> - true - | _ -> false - -(** Checks if an expression is a well-known Symbol like Symbol.iterator. - Returns Some "@@iterator" etc. if it is, None otherwise. *) -let well_known_symbol_name expr = - match expr with - | ( _, - E.Member - { - E.Member._object = (_, E.Identifier (_, { I.name = "Symbol"; comments = _ })); - property = E.Member.PropertyIdentifier (_, { I.name; comments = _ }); - comments = _; - } - ) -> - (match name with - | "iterator" -> Some "@@iterator" - | "asyncIterator" -> Some "@@asyncIterator" - | "dispose" -> Some "@@dispose" - | "asyncDispose" -> Some "@@asyncDispose" - | _ -> None) - | _ -> None - -let get_call_to_jest_module_mocking_fn callee arguments = - match (callee, arguments) with - | ( ( _, - E.Member - { - E.Member._object = (_, E.Identifier (jest_loc, { I.name = "jest"; comments = _ })); - property = - E.Member.PropertyIdentifier - ( _, - (* See https://jestjs.io/docs/jest-object#mock-modules *) - { - I.name = - ( "createMockFromModule" | "mock" | "unmock" | "deepUnmock" | "doMock" - | "dontMock" | "setMock" | "requireActual" | "requireMock" ); - comments = _; - } - ); - _; - } - ), - ( _, - { - E.ArgList.arguments = - E.Expression - ( source_loc, - ( E.StringLiteral { StringLiteral.value = name; _ } - | E.TemplateLiteral - { - E.TemplateLiteral.quasis = - [ - ( _, - { - E.TemplateLiteral.Element.value = - { E.TemplateLiteral.Element.cooked = name; _ }; - _; - } - ); - ]; - _; - } ) - ) - :: _; - comments = _; - } - ) - ) -> - Some (jest_loc, source_loc, name) - | _ -> None - -let is_super_member_access = function - | { E.Member._object = (_, E.Super _); _ } -> true - | _ -> false - -let acceptable_statement_in_declaration_context ~in_declare_namespace = - let open Statement in - function - | Block _ -> Error "block" - | Break _ -> Error "break" - | ClassDeclaration _ -> Error "class declaration" - | ComponentDeclaration { ComponentDeclaration.body = None; _ } -> Ok () - | ComponentDeclaration _ -> Error "component declaration" - | Continue _ -> Error "continue" - | Debugger _ -> Error "debugger" - | DoWhile _ -> Error "do while" - | ExportDefaultDeclaration _ -> Error "export default" - | ExportNamedDeclaration { ExportNamedDeclaration.export_kind = ExportValue; _ } -> - Error "value export" - | Expression _ -> Error "expression" - | For _ -> Error "for" - | ForIn _ -> Error "for in" - | ForOf _ -> Error "for of" - | FunctionDeclaration _ -> Error "function declaration" - | If _ -> Error "if" - | Labeled _ -> Error "labeled" - | Match _ -> Error "match" - | RecordDeclaration _ -> Error "record declaration" - | Return _ -> Error "return" - | Switch _ -> Error "switch" - | Throw _ -> Error "throw" - | Try _ -> Error "try" - | VariableDeclaration { VariableDeclaration.declarations; _ } -> - (* Allow variable declarations if all have type annotations and no initializers (ambient) *) - let is_ambient_declarator = function - | (_, { VariableDeclaration.Declarator.id; init = None }) -> pattern_has_type_annotation id - | _ -> false - in - if List.for_all is_ambient_declarator declarations then - Ok () - else - Error "variable declaration" - | While _ -> Error "while" - | With _ -> Error "with" - | ImportDeclaration _ -> - if in_declare_namespace then - Error "import declaration" - else - Ok () - | DeclareModuleExports _ -> - if in_declare_namespace then - Error "declare module.exports" - else - Ok () - | DeclareClass _ - | DeclareComponent _ - | DeclareEnum _ - | DeclareExportDeclaration _ - | DeclareFunction _ - | DeclareInterface _ - | DeclareModule _ - | DeclareNamespace _ - | DeclareOpaqueType _ - | DeclareTypeAlias _ - | DeclareVariable _ - | Empty _ - | EnumDeclaration _ - | ExportAssignment _ - | NamespaceExportDeclaration _ - | ExportNamedDeclaration { ExportNamedDeclaration.export_kind = ExportType; _ } - | ImportEqualsDeclaration _ - | InterfaceDeclaration _ - | OpaqueType _ - | TypeAlias _ -> - Ok () - -let rec is_type_only_declaration_statement (_, stmt') = - let open Statement in - let is_type_only_declaration_statement' = function - | DeclareInterface _ - | DeclareOpaqueType _ - | DeclareTypeAlias _ - | Empty _ - | InterfaceDeclaration _ - | OpaqueType _ - | TypeAlias _ -> - true - | DeclareExportDeclaration - DeclareExportDeclaration. - { declaration = Some (NamedType _ | NamedOpaqueType _ | Interface _); _ } -> - true - | DeclareExportDeclaration - DeclareExportDeclaration. - { - declaration = Some (Namespace (_, { DeclareNamespace.body = (_, { Block.body; _ }); _ })); - _; - } -> - List.for_all is_type_only_declaration_statement body - | DeclareNamespace { DeclareNamespace.body = (_, { Block.body; _ }); _ } -> - List.for_all is_type_only_declaration_statement body - | ExportNamedDeclaration { ExportNamedDeclaration.export_kind; _ } -> export_kind = ExportType - | Block _ - | Break _ - | ClassDeclaration _ - | ComponentDeclaration _ - | Continue _ - | Debugger _ - | DoWhile _ - | EnumDeclaration _ - | ExportAssignment _ - | NamespaceExportDeclaration _ - | ExportDefaultDeclaration _ - | Expression _ - | For _ - | ForIn _ - | ForOf _ - | FunctionDeclaration _ - | If _ - | ImportEqualsDeclaration _ - | Labeled _ - | Match _ - | RecordDeclaration _ - | Return _ - | Switch _ - | Throw _ - | Try _ - | VariableDeclaration _ - | While _ - | With _ - | ImportDeclaration _ - | DeclareClass _ - | DeclareComponent _ - | DeclareEnum _ - | DeclareExportDeclaration _ - | DeclareFunction _ - | DeclareModule _ - | DeclareModuleExports _ - | DeclareVariable _ -> - false - in - is_type_only_declaration_statement' stmt' - -let loc_of_statement = fst - -let loc_of_expression = fst - -let loc_of_pattern = fst - -let loc_of_ident = fst - let name_of_ident (_, { Identifier.name; comments = _ }) = name -let source_of_ident (loc, { Identifier.name; comments = _ }) = (loc, name) - let ident_of_source ?comments (loc, name) = (loc, { Identifier.name; comments }) -let mk_comments ?(leading = []) ?(trailing = []) a = { Syntax.leading; trailing; internal = a } +let mk_comments ~leading ~trailing a = { Syntax.leading; trailing; internal = a } let mk_comments_opt ?(leading = []) ?(trailing = []) () = match (leading, trailing) with @@ -574,332 +64,12 @@ let merge_comments_with_internal ~inner ~outer = ~internal () -let split_comments comments = - match comments with - | None -> (None, None) - | Some { Syntax.leading; trailing; _ } -> - (mk_comments_opt ~leading (), mk_comments_opt ~trailing ()) - -let string_of_assignment_operator op = - let open E.Assignment in - match op with - | PlusAssign -> "+=" - | MinusAssign -> "-=" - | MultAssign -> "*=" - | ExpAssign -> "**=" - | DivAssign -> "/=" - | ModAssign -> "%=" - | LShiftAssign -> "<<=" - | RShiftAssign -> ">>=" - | RShift3Assign -> ">>>=" - | BitOrAssign -> "|=" - | BitXorAssign -> "^=" - | BitAndAssign -> "&=" - | NullishAssign -> "??=" - | AndAssign -> "&&=" - | OrAssign -> "||=" - -let string_of_binary_operator op = - let open E.Binary in - match op with - | Equal -> "==" - | NotEqual -> "!=" - | StrictEqual -> "===" - | StrictNotEqual -> "!==" - | LessThan -> "<" - | LessThanEqual -> "<=" - | GreaterThan -> ">" - | GreaterThanEqual -> ">=" - | LShift -> "<<" - | RShift -> ">>" - | RShift3 -> ">>>" - | Plus -> "+" - | Minus -> "-" - | Mult -> "*" - | Exp -> "**" - | Div -> "/" - | Mod -> "%" - | BitOr -> "|" - | Xor -> "^" - | BitAnd -> "&" - | In -> "in" - | Instanceof -> "instanceof" - -module ExpressionSort = struct - type t = - | Array - | ArrowFunction - | Assignment - | Binary - | Call - | Class - | Conditional - | Function - | Identifier - | Import - | JSXElement - | JSXFragment - | Literal - | Logical - | Match - | Member - | MetaProperty - | New - | Object - | OptionalCall - | OptionalMember - | Record - | Satisfies - | Sequence - | Super - | TaggedTemplate - | TemplateLiteral - | This - | TypeCast - | Unary - | Update - | Yield - [@@deriving show] - - let to_string = function - | Array -> "array" - | ArrowFunction -> "arrow function" - | Assignment -> "assignment expression" - | Binary -> "binary expression" - | Call -> "call expression" - | Class -> "class" - | Conditional -> "conditional expression" - | Function -> "function" - | Identifier -> "identifier" - | Import -> "import expression" - | JSXElement -> "JSX element" - | JSXFragment -> "JSX fragment" - | Literal -> "literal" - | Logical -> "logical expression" - | Match -> "match expression" - | Member -> "member expression" - | MetaProperty -> "metaproperty expression" - | New -> "new expression" - | Object -> "object" - | OptionalCall -> "optional call expression" - | OptionalMember -> "optional member expression" - | Record -> "record expression" - | Satisfies -> "satisfies expression" - | Sequence -> "sequence" - | Super -> "`super` reference" - | TaggedTemplate -> "tagged template expression" - | TemplateLiteral -> "template literal" - | This -> "`this` reference" - | TypeCast -> "type cast" - | Unary -> "unary expression" - | Update -> "update expression" - | Yield -> "yield expression" -end - -let loc_of_annotation_or_hint = - let open Type in - function - | Missing loc - | Available (_, (loc, _)) -> - loc - -let loc_of_return_annot = - let open Function.ReturnAnnot in - function - | Missing loc - | Available (_, (loc, _)) - | TypeGuard (loc, _) -> - loc - -(* Apply type [t] at the toplevel of expression [exp]. This is straightforward overall - * except for the case of Identifier and Member, where we push the type within the - * identifier and member property type position as well. This is to ensure that - * type-at-pos searcher will detect the updated type. *) -let push_toplevel_type t exp = - let open E in - let push_toplevel_identifier id = - let ((id_loc, _), id) = id in - ((id_loc, t), id) - in - let push_to_member mem = - match mem with - | { Member.property = Member.PropertyIdentifier id; _ } -> - { mem with Member.property = Member.PropertyIdentifier (push_toplevel_identifier id) } - | p -> p - in - let ((loc, _), e) = exp in - let e' = - match e with - | Identifier id -> Identifier (push_toplevel_identifier id) - | Member member -> Member (push_to_member member) - | OptionalMember ({ OptionalMember.member; _ } as omem) -> - OptionalMember { omem with OptionalMember.member = push_to_member member } - | _ -> e - in - ((loc, t), e') - -let hook_name s = - let is_cap c = c = Char.uppercase_ascii c in - String.starts_with ~prefix:"use" s && (String.length s = 3 || is_cap s.[3]) - -let hook_function { Function.id; _ } = - match id with - | Some (loc, { I.name; _ }) when hook_name name -> Some loc - | _ -> None - -let hook_call { E.Call.callee; _ } = - (* A.B.C.useFoo() is a hook, A().useFoo() is not *) - let open E in - let rec hook_callee top exp = - match exp with - | (_, Identifier (_, { I.name; _ })) -> hook_name name || not top - | (_, Member { Member._object; property = Member.PropertyIdentifier (_, { I.name; _ }); _ }) -> - (hook_name name || not top) && hook_callee false _object - | _ -> false - in - hook_callee true callee - -(* Match *) -let match_root_name = "" - -let match_root_ident loc = (loc, { Identifier.name = match_root_name; comments = None }) - -let expression_of_match_member_pattern ~visit_expression pattern = - let open MatchPattern in - let rec f (loc, { MemberPattern.base; property; comments }) = - let (_object, root_name) = - match base with - | MemberPattern.BaseIdentifier ((loc, _) as id) -> ((loc, Expression.Identifier id), id) - | MemberPattern.BaseMember mem -> f mem - in - let property = - match property with - | MemberPattern.PropertyIdentifier id -> Expression.Member.PropertyIdentifier id - | MemberPattern.PropertyString (loc, lit) -> - Expression.Member.PropertyExpression (loc, Expression.StringLiteral lit) - | MemberPattern.PropertyNumber (loc, lit) -> - Expression.Member.PropertyExpression (loc, Expression.NumberLiteral lit) - | MemberPattern.PropertyBigInt (loc, lit) -> - Expression.Member.PropertyExpression (loc, Expression.BigIntLiteral lit) - in - let exp = (loc, Expression.Member { Expression.Member._object; property; comments }) in - visit_expression exp; - (exp, root_name) - in - f pattern - -(* Type Guards *) -let get_inferred_type_guard_candidate params body return = - match (body, return) with - | (Function.BodyExpression _, Function.ReturnAnnot.Missing _) -> begin - match params with - | ( _, - { - Function.Params.params = - [ - ( _, - Function.Param.RegularParam - { - argument = - ( _, - Pattern.Identifier - { Pattern.Identifier.name = (loc, { Identifier.name; _ }); _ } - ); - _; - } - ); - ]; - rest = None; - _; - } - ) -> - Some (loc, name) - | _ -> None - end - | _ -> None - -let rec unwrap_nonnull_lhs_expr : - 'loc 'tloc1 'tloc2. - ('loc, 'tloc1) Expression.t -> - ('loc, 'tloc1) Expression.t - * bool - * (('loc, 'tloc2) Expression.t -> - filter_nullish:('tloc1 -> 'tloc2) -> - ('loc, 'tloc2) Expression.t - ) = - fun expr -> - match expr with - | ( loc, - Expression.Unary { Expression.Unary.operator = Expression.Unary.Nonnull; argument; comments } - ) -> - let (argument, _, reconstruct) = unwrap_nonnull_lhs_expr argument in - let reconstruct argument ~filter_nullish = - ( filter_nullish loc, - Expression.Unary - { - Expression.Unary.operator = Expression.Unary.Nonnull; - argument = reconstruct ~filter_nullish argument; - comments; - } - ) - in - (argument, true, reconstruct) - | _ -> (expr, false, (fun argument ~filter_nullish:_ -> argument)) - -let unwrap_nonnull_lhs : 'loc 'tloc. ('loc, 'tloc) Pattern.t -> ('loc, 'tloc) Pattern.t * bool = - fun pat -> - match pat with - | (loc, Pattern.Expression expr) -> - let (expr, optional, _) = unwrap_nonnull_lhs_expr expr in - begin - match expr with - | (e_loc, Expression.Identifier name) -> - assert optional; - ( ( loc, - Pattern.Identifier - { Pattern.Identifier.name; optional = false; annot = Type.Missing e_loc } - ), - true - ) - | _ -> ((loc, Pattern.Expression expr), optional) - end - | _ -> (pat, false) let effective_export_kind ~statement_export_kind specifier_export_kind = match specifier_export_kind with | Statement.ExportType -> Statement.ExportType | Statement.ExportValue -> statement_export_kind -let export_specifiers_has_value_export ~statement_export_kind specs = - let open Statement.ExportNamedDeclaration in - List.exists - (fun (_, { ExportSpecifier.export_kind = specifier_export_kind; _ }) -> - effective_export_kind ~statement_export_kind specifier_export_kind = Statement.ExportValue) - specs - -let pattern_optional = function - | (_, Pattern.Object { Pattern.Object.optional; _ }) -> optional - | (_, Pattern.Array { Pattern.Array.optional; _ }) -> optional - | (_, Pattern.Identifier { Pattern.Identifier.optional; _ }) -> optional - | _ -> false - -let pattern_annot (patt : ('M, 'T) Pattern.t) = - match patt with - | (_, Pattern.Object { Pattern.Object.annot; _ }) -> annot - | (_, Pattern.Array { Pattern.Array.annot; _ }) -> annot - | (_, Pattern.Identifier { Pattern.Identifier.annot; _ }) -> annot - | (_, Pattern.Expression _) -> failwith "Expression patterns have no annotation" - -let function_type_param_parts param = - let open Type.Function.Param in - match param with - | Anonymous annot -> (None, annot, false) - | Labeled { name; annot; optional } -> (Some name, annot, optional) - | Destructuring pattern -> - (match pattern_annot pattern with - | Type.Available (_, annot) -> (None, annot, pattern_optional pattern) - | Type.Missing _ -> failwith "Destructuring function type param must have annotation") - let string_of_enum_explicit_type = let open Statement.EnumDeclaration in function @@ -915,13 +85,3 @@ let string_of_enum_member_name = | Identifier (_, { I.name; _ }) -> name | StringLiteral (_, { StringLiteral.value; _ }) -> value -let string_of_bigint { BigIntLiteral.value; raw; comments = _ } = - (* https://github.com/estree/estree/blob/master/es2020.md#bigintliteral - * `bigint` property is the string representation of the `BigInt` value. - * It must contain only decimal digits and not include numeric separators `_` or the suffix `n`. - *) - match value with - | Some value -> Int64.to_string value - | None -> - (* Remove the 'n' suffix and the underscores. *) - String.sub raw 0 (String.length raw - 1) |> String.split_on_char '_' |> String.concat "" diff --git a/compiler/flow_parser/parser/flow_ast_utils.mli b/compiler/flow_parser/parser/flow_ast_utils.mli index b89717bbfa6..dd76fcc473b 100644 --- a/compiler/flow_parser/parser/flow_ast_utils.mli +++ b/compiler/flow_parser/parser/flow_ast_utils.mli @@ -7,100 +7,17 @@ type 'loc binding = 'loc * string -type 'loc ident = 'loc * string [@@deriving show] +type 'loc ident = 'loc * string -type 'loc source = 'loc * string [@@deriving show] - -val fold_bindings_of_pattern : - ('a -> ('m, 't) Flow_ast.Identifier.t -> 'a) -> 'a -> ('m, 't) Flow_ast.Pattern.t -> 'a - -val fold_bindings_of_variable_declarations : - (bool -> 'a -> ('m, 't) Flow_ast.Identifier.t -> 'a) -> - 'a -> - ('m, 't) Flow_ast.Statement.VariableDeclaration.Declarator.t list -> - 'a - -val pattern_has_binding : ('m, 't) Flow_ast.Pattern.t -> bool - -val match_pattern_has_binding : ('m, 't) Flow_ast.MatchPattern.t -> bool +type 'loc source = 'loc * string val pattern_has_type_annotation : ('m, 't) Flow_ast.Pattern.t -> bool -val string_of_variable_kind : Flow_ast.Variable.kind -> string - -val partition_directives : - (Loc.t, Loc.t) Flow_ast.Statement.t list -> - (Loc.t, Loc.t) Flow_ast.Statement.t list * (Loc.t, Loc.t) Flow_ast.Statement.t list - -val hoist_function_and_component_declarations : - ('a, 'b) Flow_ast.Statement.t list -> ('a, 'b) Flow_ast.Statement.t list - -val is_call_to_invariant : ('a, 'b) Flow_ast.Expression.t -> bool - -val is_call_to_require : ('a, 'b) Flow_ast.Expression.t -> bool - -val is_call_to_is_array : ('a, 'b) Flow_ast.Expression.t -> bool - -val is_call_to_object_dot_freeze : ('a, 'b) Flow_ast.Expression.t -> bool - -val get_call_to_object_dot_freeze_arg : - ('a, 'b) Flow_ast.Expression.t -> - ('a, 'b) Flow_ast.Expression.CallTypeArgs.t option -> - ('a, 'b) Flow_ast.Expression.ArgList.t -> - ('b * ('a, 'b) Flow_ast.Expression.Object.t) option - -val is_call_to_object_static_method : ('a, 'b) Flow_ast.Expression.t -> bool - -val is_module_dot_exports : ('a, 'b) Flow_ast.Expression.t -> bool - -val well_known_symbol_name : ('a, 'b) Flow_ast.Expression.t -> string option - -val get_call_to_jest_module_mocking_fn : - ('loc, 'annot) Flow_ast.Expression.t -> - ('loc, 'annot) Flow_ast.Expression.ArgList.t -> - ('annot * 'annot * string) option - -val is_super_member_access : ('a, 'b) Flow_ast.Expression.Member.t -> bool - -(* Returns Ok () for such statement, and Error kind_of_statement otherwise. *) -val acceptable_statement_in_declaration_context : - in_declare_namespace:bool -> ('a, 'b) Flow_ast.Statement.t' -> (unit, string) result - -val is_type_only_declaration_statement : ('a, 'b) Flow_ast.Statement.t -> bool - -val negate_number_literal : float * string -> float * string - -val negate_bigint_literal : int64 option * string -> int64 option * string - -val is_number_literal : ('a, 'b) Flow_ast.Expression.t' -> bool - -val extract_number_literal : ('a, 'b) Flow_ast.Expression.t' -> (float * string) option - -val is_bigint_literal : ('a, 'b) Flow_ast.Expression.t' -> bool - -val extract_bigint_literal : ('a, 'b) Flow_ast.Expression.t' -> (int64 option * string) option - -val loc_of_expression : ('a, 'a) Flow_ast.Expression.t -> 'a - -val loc_of_statement : ('a, 'a) Flow_ast.Statement.t -> 'a - -val loc_of_pattern : ('a, 'a) Flow_ast.Pattern.t -> 'a - -val loc_of_ident : ('a, 'a) Flow_ast.Identifier.t -> 'a - val name_of_ident : ('loc, 'a) Flow_ast.Identifier.t -> string -val source_of_ident : ('a, 'a) Flow_ast.Identifier.t -> 'a source - val ident_of_source : ?comments:('a, unit) Flow_ast.Syntax.t -> 'a source -> ('a, 'a) Flow_ast.Identifier.t -val mk_comments : - ?leading:'loc Flow_ast.Comment.t list -> - ?trailing:'loc Flow_ast.Comment.t list -> - 'a -> - ('loc, 'a) Flow_ast.Syntax.t - val mk_comments_opt : ?leading:'loc Flow_ast.Comment.t list -> ?trailing:'loc Flow_ast.Comment.t list -> @@ -124,112 +41,13 @@ val merge_comments_with_internal : outer:('M, 'a) Flow_ast.Syntax.t option -> ('M, 'loc Flow_ast.Comment.t list) Flow_ast.Syntax.t option -val split_comments : - ('loc, unit) Flow_ast.Syntax.t option -> - ('loc, unit) Flow_ast.Syntax.t option * ('loc, unit) Flow_ast.Syntax.t option - -module ExpressionSort : sig - type t = - | Array - | ArrowFunction - | Assignment - | Binary - | Call - | Class - | Conditional - | Function - | Identifier - | Import - | JSXElement - | JSXFragment - | Literal - | Logical - | Match - | Member - | MetaProperty - | New - | Object - | OptionalCall - | OptionalMember - | Record - | Satisfies - | Sequence - | Super - | TaggedTemplate - | TemplateLiteral - | This - | TypeCast - | Unary - | Update - | Yield - [@@deriving show] - - val to_string : t -> string -end - -val string_of_assignment_operator : Flow_ast.Expression.Assignment.operator -> string - -val string_of_binary_operator : Flow_ast.Expression.Binary.operator -> string - -val loc_of_annotation_or_hint : ('loc, 'loc) Flow_ast.Type.annotation_or_hint -> 'loc - -val loc_of_return_annot : ('loc, 'loc) Flow_ast.Function.ReturnAnnot.t -> 'loc - -val push_toplevel_type : - 't -> ('loc, 'loc * 't) Flow_ast.Expression.t -> ('loc, 'loc * 't) Flow_ast.Expression.t - -val hook_function : ('a, 'b) Flow_ast.Function.t -> 'b option - -val hook_call : ('a, 'b) Flow_ast.Expression.Call.t -> bool - -val hook_name : string -> bool - -val match_root_name : string - -val match_root_ident : 'loc -> ('loc, 'loc) Flow_ast.Identifier.t - -val expression_of_match_member_pattern : - visit_expression:(('loc, 'loc) Flow_ast.Expression.t -> unit) -> - ('loc, 'loc) Flow_ast.MatchPattern.MemberPattern.t -> - ('loc, 'loc) Flow_ast.Expression.t * ('loc, 'loc) Flow_ast.Identifier.t - -val get_inferred_type_guard_candidate : - ('l, 't) Flow_ast.Function.Params.t -> - ('l, 't) Flow_ast.Function.body -> - ('l, 't) Flow_ast.Function.ReturnAnnot.t -> - ('t * string) option - -val unwrap_nonnull_lhs_expr : - 'loc 'tloc. - ('loc, 'loc) Flow_ast.Expression.t -> - ('loc, 'loc) Flow_ast.Expression.t - * bool - * (('loc, 'tloc) Flow_ast.Expression.t -> - filter_nullish:('loc -> 'tloc) -> - ('loc, 'tloc) Flow_ast.Expression.t - ) - -val unwrap_nonnull_lhs : - 'loc 'tloc. ('loc, 'tloc) Flow_ast.Pattern.t -> ('loc, 'tloc) Flow_ast.Pattern.t * bool val effective_export_kind : statement_export_kind:Flow_ast.Statement.export_kind -> Flow_ast.Statement.export_kind -> Flow_ast.Statement.export_kind -val export_specifiers_has_value_export : - statement_export_kind:Flow_ast.Statement.export_kind -> - ('M, 'T) Flow_ast.Statement.ExportNamedDeclaration.ExportSpecifier.t list -> - bool - -val pattern_optional : ('M, 'T) Flow_ast.Pattern.t -> bool - -val function_type_param_parts : - ('M, 'T) Flow_ast.Type.Function.Param.t' -> - ('M, 'T) Flow_ast.Identifier.t option * ('M, 'T) Flow_ast.Type.t * bool - val string_of_enum_explicit_type : Flow_ast.Statement.EnumDeclaration.explicit_type -> string val string_of_enum_member_name : 'M Flow_ast.Statement.EnumDeclaration.member_name -> string -val string_of_bigint : 'm Flow_ast.BigIntLiteral.t -> string diff --git a/compiler/flow_parser/parser/flow_lexer.ml b/compiler/flow_parser/parser/flow_lexer.ml index 1e7370ad933..4254dddb7cc 100644 --- a/compiler/flow_parser/parser/flow_lexer.ml +++ b/compiler/flow_parser/parser/flow_lexer.ml @@ -240,10 +240,6 @@ let loc_of_token env lex_token = | T_REGEXP (loc, _, _) -> loc | _ -> loc_of_lexbuf env env.lex_lb -let advance_loc_by_char loc = - let open Loc in - { loc with start = loc._end; _end = { loc._end with column = loc._end.column + 1 } } - let lex_error (env : Lex_env.t) loc err : Lex_env.t = let lex_errors_acc = (loc, err) :: env.lex_state.lex_errors_acc in { env with lex_state = { lex_errors_acc } } @@ -287,8 +283,7 @@ let mk_comment else Line in - let on_newline = Loc.(env.lex_last_loc._end.Loc.line < loc.start.Loc.line) in - let c = { kind; text; on_newline } in + let c = { kind; text } in (loc, c) let mk_num_singleton number_type (lexeme : int array) = @@ -1693,35 +1688,6 @@ let jsx_child env start buf raw lexbuf = (env, T_JSX_CHILD_TEXT (loc, value, raw)) | _ -> failwith "unreachable jsx_child" -let template_tail env lexbuf = - match%sedlex lexbuf with - | line_terminator_sequence -> - let env = new_line env lexbuf in - Continue env - | Plus whitespace -> Continue env - | "//" -> - let start_pos = start_pos_of_lexbuf env lexbuf in - let buf = Buffer.create 127 in - let (env, end_pos) = line_comment env buf lexbuf in - Comment (env, mk_comment env start_pos end_pos buf false) - | "/*" -> - let start_pos = start_pos_of_lexbuf env lexbuf in - let buf = Buffer.create 127 in - let (env, end_pos) = comment env buf lexbuf in - Comment (env, mk_comment env start_pos end_pos buf true) - | '}' -> - let start = start_pos_of_lexbuf env lexbuf in - let value = Buffer.create 127 in - let raw = Buffer.create 127 in - let (env, is_tail) = template_part env value raw lexbuf in - let _end = end_pos_of_lexbuf env lexbuf in - let loc = { Loc.source = Lex_env.source env; start; _end } in - Token (env, T_TEMPLATE_PART (loc, Buffer.contents value, Buffer.contents raw, false, is_tail)) - | any -> - let env = illegal env (loc_of_lexbuf env lexbuf) in - Token (env, T_TEMPLATE_PART (loc_of_lexbuf env lexbuf, "", "", false, true)) - | _ -> failwith "unreachable template_tail" - let template_tail_start env = let lexbuf = env.lex_lb in let start_pos = Sedlexing.lexeme_start lexbuf in @@ -1812,15 +1778,7 @@ let regexp = wrap regexp let jsx_tag = wrap jsx_tag -let template_tail = wrap template_tail - let type_token = wrap (token_base ~for_type_token:true) let token = wrap (token_base ~for_type_token:false) -let is_valid_identifier_name lexbuf = - match%sedlex lexbuf with - | js_id_start -> - (* we need handle cases like \u1fa38 so that single code is not enough*) - loop_id_continues lexbuf - | _ -> false diff --git a/compiler/flow_parser/parser/flow_lexer.mli b/compiler/flow_parser/parser/flow_lexer.mli index 46fa3028654..c558a848991 100644 --- a/compiler/flow_parser/parser/flow_lexer.mli +++ b/compiler/flow_parser/parser/flow_lexer.mli @@ -11,14 +11,9 @@ val regexp : Lex_env.t -> Lex_env.t * Lex_result.t val jsx_tag : Lex_env.t -> Lex_env.t * Lex_result.t -val template_tail : Lex_env.t -> Lex_env.t * Lex_result.t - val template_tail_start : Lex_env.t -> Lex_env.t * Lex_result.t -val advance_loc_by_char : Loc.t -> Loc.t - val type_token : Lex_env.t -> Lex_env.t * Lex_result.t val token : Lex_env.t -> Lex_env.t * Lex_result.t -val is_valid_identifier_name : Flow_sedlexing.lexbuf -> bool diff --git a/compiler/flow_parser/parser/jsx_parser.ml b/compiler/flow_parser/parser/jsx_parser.ml index 2a29078dd91..ce1bd1b821e 100644 --- a/compiler/flow_parser/parser/jsx_parser.ml +++ b/compiler/flow_parser/parser/jsx_parser.ml @@ -366,9 +366,9 @@ module JSX (Parse : Parser_common.PARSER) (Expression : Parser_common.EXPRESSION let rec child ~parent_opening_name env = match Peek.token env with | T_LCURLY -> expression_container_or_spread_child env - | T_JSX_CHILD_TEXT (loc, value, raw) as token -> + | T_JSX_CHILD_TEXT (loc, _, _) as token -> Expect.token env token; - (loc, JSX.Text { JSX.Text.value; raw }) + (loc, JSX.Text) | _ -> (match element_or_fragment ~parent_opening_name env with | (loc, `Element element) -> (loc, JSX.Element element) @@ -538,18 +538,11 @@ module JSX (Parse : Parser_common.PARSER) (Expression : Parser_common.EXPRESSION children; comments = Flow_ast_utils.mk_comments_opt ~leading ~trailing (); } - | (start_loc, Ok `Fragment) - | (start_loc, Error `Fragment) -> + | (_, Ok `Fragment) + | (_, Error `Fragment) -> `Fragment { - JSX.frag_opening_element = start_loc; - frag_closing_element = - (match closing_element with - | `Fragment loc -> loc - (* the following are parse erros *) - | `Element (loc, _) -> loc - | _ -> end_loc); - frag_children = children; + JSX.frag_children = children; frag_comments = Flow_ast_utils.mk_comments_opt ~leading ~trailing (); } in diff --git a/compiler/flow_parser/parser/lex_env.ml b/compiler/flow_parser/parser/lex_env.ml index f8ece1aeb31..e12bd695d04 100644 --- a/compiler/flow_parser/parser/lex_env.ml +++ b/compiler/flow_parser/parser/lex_env.ml @@ -49,24 +49,12 @@ let clone env = let lex_lb = Sedlexing.lexbuf_clone env.lex_lb in { env with lex_lb } -let set_lexbuf_pos env pos = - let lexbuf = env.lex_lb in - let start = Sedlexing.lexeme_start lexbuf in - Sedlexing.rollback lexbuf; - Sedlexing.bump lexbuf (pos - start); - Sedlexing.set_lexeme_start lexbuf pos; - env - let set_last_loc env loc = { env with lex_last_loc = loc } let lex_last_loc env = env.lex_last_loc -let lexbuf env = env.lex_lb - let source env = env.lex_source -let state env = env.lex_state - let line env = env.lex_bol.line let bol_offset env = env.lex_bol.offset @@ -81,19 +69,3 @@ let in_comment_syntax is_in env = else env -(* TODO *) -let debug_string_of_lexbuf _lb = "" - -let debug_string_of_lex_env (env : t) = - let source = - match source env with - | None -> "None" - | Some x -> Printf.sprintf "Some %S" (File_key.to_string x) - in - Printf.sprintf - "{\n lex_source = %s\n lex_lb = %s\n lex_in_comment_syntax = %b\n lex_enable_comment_syntax = %b\n lex_state = {errors = (count = %d)}\n}" - source - (debug_string_of_lexbuf env.lex_lb) - (is_in_comment_syntax env) - (is_comment_syntax_enabled env) - (List.length (state env).lex_errors_acc) diff --git a/compiler/flow_parser/parser/lex_result.ml b/compiler/flow_parser/parser/lex_result.ml index 1c6a23bb60e..0a808adc1f8 100644 --- a/compiler/flow_parser/parser/lex_result.ml +++ b/compiler/flow_parser/parser/lex_result.ml @@ -22,10 +22,3 @@ let comments result = result.lex_comments let errors result = result.lex_errors -let debug_string_of_lex_result lex_result = - Printf.sprintf - "{\n lex_token = %s\n lex_value = %S\n lex_errors = (length = %d)\n lex_comments = (length = %d)\n}" - (Token.token_to_string lex_result.lex_token) - (Token.value_of_token lex_result.lex_token) - (List.length lex_result.lex_errors) - (List.length lex_result.lex_comments) diff --git a/compiler/flow_parser/parser/loc.ml b/compiler/flow_parser/parser/loc.ml index 3ccce4d6469..e23130cde9d 100644 --- a/compiler/flow_parser/parser/loc.ml +++ b/compiler/flow_parser/parser/loc.ml @@ -10,7 +10,7 @@ type position = { line: int; column: int; } -[@@deriving eq, show] +[@@deriving eq] (* start is inclusive; end is exclusive *) (* If you are modifying this record, go look at ALoc.ml and make sure you understand the @@ -20,50 +20,12 @@ type t = { start: position; _end: position; } -[@@deriving show] -let none = { source = None; start = { line = 0; column = 0 }; _end = { line = 0; column = 0 } } - -let is_none (x : t) = - x == none - || - match x with - | { source = None; start = { line = 0; column = 0 }; _end = { line = 0; column = 0 } } -> true - | _ -> false -let is_none_ignore_source (x : t) = - x == none - || - match x with - | { source = _; start = { line = 0; column = 0 }; _end = { line = 0; column = 0 } } -> true - | _ -> false +let none = { source = None; start = { line = 0; column = 0 }; _end = { line = 0; column = 0 } } let btwn loc1 loc2 = { source = loc1.source; start = loc1.start; _end = loc2._end } -(* Returns the position immediately before the start of the given loc. If the - given loc is at the beginning of a line, return the position of the first - char on the same line. *) -let char_before loc = - let start = - let { line; column } = loc.start in - let column = - if column > 0 then - column - 1 - else - column - in - { line; column } - in - let _end = loc.start in - { loc with start; _end } - -(* Returns the location of the first character in the given loc. Not accurate if the - * first line is a newline character, but is still consistent with loc orderings. *) -let first_char loc = - let start = loc.start in - let _end = { start with column = start.column + 1 } in - { loc with _end } - let pos_cmp a b = let k = a.line - b.line in if k = 0 then @@ -71,43 +33,6 @@ let pos_cmp a b = else k -(** - * If `a` spans (completely contains) `b`, then returns 0. - * If `b` starts before `a` (even if it ends inside), returns < 0. - * If `b` ends after `a` (even if it starts inside), returns > 0. - *) -let span_compare a b = - let k = File_key.compare_opt a.source b.source in - if k = 0 then - let k = pos_cmp a.start b.start in - if k <= 0 then - let k = pos_cmp a._end b._end in - if k >= 0 then - 0 - else - -1 - else - 1 - else - k - -(** [contains loc1 loc2] returns true if [loc1] entirely overlaps [loc2] *) -let contains loc1 loc2 = span_compare loc1 loc2 = 0 - -(** [intersects loc1 loc2] returns true if [loc1] intersects [loc2] at all *) -let intersects loc1 loc2 = - File_key.compare_opt loc1.source loc2.source = 0 - && not (pos_cmp loc1._end loc2.start < 0 || pos_cmp loc1.start loc2._end > 0) - -(** [lines_intersect loc1 loc2] returns true if [loc1] and [loc2] cover any part of - the same line, even if they don't actually intersect. - - For example, if [loc1] ends and then [loc2] begins later on the same line, - [intersects loc1 loc2] is false, but [lines_intersect loc1 loc2] is true. *) -let lines_intersect loc1 loc2 = - File_key.compare_opt loc1.source loc2.source = 0 - && not (loc1._end.line < loc2.start.line || loc1.start.line > loc2._end.line) - let compare_ignore_source loc1 loc2 = match pos_cmp loc1.start loc2.start with | 0 -> pos_cmp loc1._end loc2._end @@ -120,71 +45,11 @@ let compare loc1 loc2 = else k -let equal loc1 loc2 = compare loc1 loc2 = 0 - -(** - * This is mostly useful for debugging purposes. - * Please don't dead-code delete this! - *) -let debug_to_string ?(include_source = false) loc = - let source = - if include_source then - Printf.sprintf - "%S: " - (match loc.source with - | Some src -> File_key.to_string src - | None -> "") - else - "" - in - let pos = - Printf.sprintf - "(%d, %d) to (%d, %d)" - loc.start.line - loc.start.column - loc._end.line - loc._end.column - in - source ^ pos - -let to_string_no_source loc = - let line = loc.start.line in - let start = loc.start.column + 1 in - let end_ = loc._end.column in - if line <= 0 then - "0:0" - else if line = loc._end.line && start = end_ then - Printf.sprintf "%d:%d" line start - else if line != loc._end.line then - Printf.sprintf "%d:%d,%d:%d" line start loc._end.line end_ - else - Printf.sprintf "%d:%d-%d" line start end_ - -let start_pos_to_string_for_vscode_loc_uri_fragment loc = - let line = loc.start.line in - let start = loc.start.column + 1 in - let (line, start) = - if line <= 0 then - (0, 0) - else - (line, start) - in - Printf.sprintf "#L%d,%d" line start - -let mk_loc ?source (start_line, start_column) (end_line, end_column) = - { - source; - start = { line = start_line; column = start_column }; - _end = { line = end_line; column = end_column }; - } - -let source loc = loc.source - -(** Produces a zero-width Loc.t, where start = end *) -let cursor source line column = { source; start = { line; column }; _end = { line; column } } +(* Live: used by the equality [Token] derives with [@@deriving eq], whose + generated references reanalyze does not see. *) +let[@live] equal loc1 loc2 = compare loc1 loc2 = 0 let start_loc loc = { loc with _end = loc.start } let end_loc loc = { loc with start = loc._end } -let update_source f loc = { loc with source = f loc.source } diff --git a/compiler/flow_parser/parser/loc.mli b/compiler/flow_parser/parser/loc.mli index b3a6788228d..e0f5fc9b5d4 100644 --- a/compiler/flow_parser/parser/loc.mli +++ b/compiler/flow_parser/parser/loc.mli @@ -9,65 +9,25 @@ type position = { line: int; column: int; } -[@@deriving eq, show] +[@@deriving eq] type t = { source: File_key.t option; start: position; _end: position; } -[@@deriving show] -val none : t - -val is_none : t -> bool -val is_none_ignore_source : t -> bool +val none : t val btwn : t -> t -> t -val char_before : t -> t - -val first_char : t -> t - -(** [contains loc1 loc2] returns true if [loc1] entirely overlaps [loc2] *) -val contains : t -> t -> bool - -(** [intersects loc1 loc2] returns true if [loc1] intersects [loc2] at all *) -val intersects : t -> t -> bool - -(** [lines_intersect loc1 loc2] returns true if [loc1] and [loc2] cover any part of - the same line, even if they don't actually intersect. - - For example, if [loc1] ends and then [loc2] begins later on the same line, - [intersects loc1 loc2] is false, but [lines_intersect loc1 loc2] is true. *) -val lines_intersect : t -> t -> bool - val pos_cmp : position -> position -> int -val span_compare : t -> t -> int - -val compare_ignore_source : t -> t -> int - val compare : t -> t -> int -val equal : t -> t -> bool - -val debug_to_string : ?include_source:bool -> t -> string - -(* Relatively compact; suitable for use as a unique string identifier *) -val to_string_no_source : t -> string - -(* In VSCode, clicking file://foo.js#L1,1 will jump the specific line and column. - * This function generates the fragment part (starting with #). *) -val start_pos_to_string_for_vscode_loc_uri_fragment : t -> string - -val mk_loc : ?source:File_key.t -> int * int -> int * int -> t - -val source : t -> File_key.t option - -(** Produces a zero-width Loc.t, where start = end *) -val cursor : File_key.t option -> int -> int -> t +val equal : t -> t -> bool [@@live] +(* Live: used by the equality [Token] derives with [@@deriving eq]. *) (* Produces a location at the start of the input location *) val start_loc : t -> t @@ -75,4 +35,3 @@ val start_loc : t -> t (* Produces a location at the end of the input location *) val end_loc : t -> t -val update_source : (File_key.t option -> File_key.t option) -> t -> t diff --git a/compiler/flow_parser/parser/match_pattern_parser.ml b/compiler/flow_parser/parser/match_pattern_parser.ml index d0a9aec07c4..1b0e2302410 100644 --- a/compiler/flow_parser/parser/match_pattern_parser.ml +++ b/compiler/flow_parser/parser/match_pattern_parser.ml @@ -408,7 +408,7 @@ module Match_pattern (Parse : PARSER) : Parser_common.MATCH_PATTERN = struct { RestPattern.argument; comments }) env - and add_comments ?(leading = []) ?(trailing = []) (loc, pattern) = + and add_comments ~leading ~trailing (loc, pattern) = let merge_comments inner = Flow_ast_utils.merge_comments ~inner diff --git a/compiler/flow_parser/parser/object_parser.ml b/compiler/flow_parser/parser/object_parser.ml index 5d66fb5c944..12a7fc84acc 100644 --- a/compiler/flow_parser/parser/object_parser.ml +++ b/compiler/flow_parser/parser/object_parser.ml @@ -1473,9 +1473,8 @@ module Object let leading = Peek.comments env in let start = Peek.loc env in Eat.token env; - let trailing = Eat.trailing_comments env in - let comments = Flow_ast_utils.mk_comments_opt ~leading ~trailing () in - (Some (start, { Ast.Class.TSAccessibility.kind; comments }), leading) + ignore (Eat.trailing_comments env); + (Some (start, kind), leading) | _ -> (None, []) in let static = @@ -1672,7 +1671,7 @@ module Object Reject modifiers that are not valid on index signatures. *) error_unsupported_declare env declare; (match ts_accessibility with - | Some (loc, { Ast.Class.TSAccessibility.kind; _ }) -> + | Some (loc, kind) -> let keyword = match kind with | Ast.Class.TSAccessibility.Public -> "public" @@ -1995,45 +1994,14 @@ module Object (key_loc, Parse_error.RecordInvalidPropertyName { name = key_name; static; method_ }) | _ -> () in - let empty_invalid_syntax = - { - InvalidPropertySyntax.invalid_suffix_semicolon = None; - invalid_optional = None; - invalid_variance = None; - } - in - let invalid_syntax = - Option.map - (fun variance -> - { empty_invalid_syntax with InvalidPropertySyntax.invalid_variance = Some variance }) - variance - in - let invalid_syntax = - if Peek.token env = T_PLING then ( - let error_loc = Peek.loc env in - Eat.token env; - let invalid_syntax = Option.value invalid_syntax ~default:empty_invalid_syntax in - Some { invalid_syntax with InvalidPropertySyntax.invalid_optional = Some error_loc } - ) else - invalid_syntax - in + if Peek.token env = T_PLING then Eat.token env; let end_property () = match Peek.token env with | T_EOF | T_RCURLY -> - invalid_syntax - | T_SEMICOLON -> - let semicolon_loc = Peek.loc env in - Eat.token env; - let invalid_syntax = Option.value invalid_syntax ~default:empty_invalid_syntax in - Some - { - invalid_syntax with - InvalidPropertySyntax.invalid_suffix_semicolon = Some semicolon_loc; - } - | _ -> - Expect.token env T_COMMA; - invalid_syntax + () + | T_SEMICOLON -> Eat.token env + | _ -> Expect.token env T_COMMA in (match Peek.token env with | T_COLON when static -> @@ -2045,9 +2013,9 @@ module Object let annot = Type.annotation env in Expect.token env T_ASSIGN; let value = Expression.assignment env in - let invalid_syntax = end_property () in + end_property (); let comments = Flow_ast_utils.mk_comments_opt ~leading () in - { StaticProperty.key; annot; value; comments; invalid_syntax }) + { StaticProperty.key; annot; value; comments }) env in elements env (Body.StaticProperty prop :: acc) @@ -2064,9 +2032,9 @@ module Object else None in - let invalid_syntax = end_property () in + end_property (); let comments = Flow_ast_utils.mk_comments_opt ~leading () in - { Property.key; annot; default_value; comments; invalid_syntax }) + { Property.key; annot; default_value; comments }) env in elements env (Body.Property prop :: acc) @@ -2137,19 +2105,7 @@ module Object (remove_trailing tparams ) in - let invalid_syntax = - if Peek.token env = T_ASSIGN then ( - let invalid_syntax = - { - Ast.Statement.RecordDeclaration.InvalidSyntax.invalid_infix_equals = - Some (Peek.loc env); - } - in - Eat.token env; - Some invalid_syntax - ) else - None - in + if Peek.token env = T_ASSIGN then Eat.token env; if Peek.token env = T_EXTENDS then ( error_at env (Peek.loc env, Parse_error.RecordExtendsUnsupported); let leading = Peek.comments env in @@ -2171,7 +2127,6 @@ module Object implements; body; comments; - invalid_syntax; } ) end diff --git a/compiler/flow_parser/parser/parse_error.ml b/compiler/flow_parser/parser/parse_error.ml index 7392b5c81a6..593b7755ead 100644 --- a/compiler/flow_parser/parser/parse_error.ml +++ b/compiler/flow_parser/parser/parse_error.ml @@ -11,8 +11,6 @@ type t = | AbstractPrivateMember | AbstractPropertyInNonAbstractClass | AbstractPropertyWithInitializer - | AccessorDataProperty - | AccessorGetSet | AdjacentJSXElements | AmbiguousLetBracket | AsyncFunctionAsStatement @@ -83,8 +81,6 @@ type t = | InvalidLHSInForIn | InvalidLHSInForOf | InvalidOptionalIndexedAccess - | InvalidRegExp - | InvalidRegExpFlags of string | InvalidSciBigInt | InvalidTupleOptionalSpread | InvalidTupleVariance @@ -131,7 +127,6 @@ type t = | StaticAbstractMethod | StrictCatchVariable | StrictDelete - | StrictDuplicateProperty | StrictFunctionName | StrictLHSAssignment | StrictLHSPostfix @@ -171,7 +166,6 @@ type t = | UnexpectedTypeAnnotation | UnexpectedTypeDeclaration | UnexpectedTypeExport - | UnexpectedTypeImport | UnexpectedTypeInterface | UnexpectedVariance | UnexpectedWithExpected of string * string @@ -185,8 +179,6 @@ type t = exception Error of (Loc.t * t) * (Loc.t * t) list -let error loc e = raise (Error ((loc, e), [])) - module PP = struct let error = function | AbstractMethodInNonAbstractClass -> @@ -196,9 +188,6 @@ module PP = struct | AbstractPropertyInNonAbstractClass -> "Abstract properties can only appear within an abstract class." | AbstractPropertyWithInitializer -> "Abstract properties cannot have an initializer." - | AccessorDataProperty -> - "Object literal may not have data and accessor property with the same name" - | AccessorGetSet -> "Object literal may not have multiple get/set accessors with the same name" | AdjacentJSXElements -> "Unexpected token <. Remember, adjacent JSX elements must be wrapped in an enclosing parent tag" | AmbiguousLetBracket -> @@ -364,9 +353,6 @@ module PP = struct | InvalidLHSInForOf -> "Invalid left-hand side in for-of" | InvalidOptionalIndexedAccess -> "Invalid optional indexed access. Indexed access uses bracket notation. Use the format `T?.[K]`." - | InvalidRegExp -> "Invalid regular expression" - | InvalidRegExpFlags flags -> - Printf.sprintf "Invalid flags supplied to RegExp constructor '%s'" flags | InvalidSciBigInt -> "A bigint literal cannot use exponential notation" | InvalidTypeof -> "`typeof` can only be used to get the type of variables." | InvalidTupleOptionalSpread -> "Tuple spread elements cannot be optional." @@ -436,8 +422,6 @@ module PP = struct | StaticAbstractMethod -> "`static` modifier can't be used with the `abstract` modifier." | StrictCatchVariable -> "Catch variable may not be eval or arguments in strict mode" | StrictDelete -> "Delete of an unqualified identifier in strict mode." - | StrictDuplicateProperty -> - "Duplicate data property in object literal not allowed in strict mode" | StrictFunctionName -> "Function name may not be eval or arguments in strict mode" | StrictLHSAssignment -> "Assignment to eval or arguments is not allowed in strict mode" | StrictLHSPostfix -> @@ -488,7 +472,6 @@ module PP = struct | UnexpectedTypeAnnotation -> "Type annotations are not allowed in untyped mode" | UnexpectedTypeDeclaration -> "Type declarations are not allowed in untyped mode" | UnexpectedTypeExport -> "Type exports are not allowed in untyped mode" - | UnexpectedTypeImport -> "Type imports are not allowed in untyped mode" | UnexpectedTypeInterface -> "Interfaces are not allowed in untyped mode" | UnexpectedVariance -> "Unexpected variance sigil" | UnexpectedWithExpected (unexpected, expected) -> diff --git a/compiler/flow_parser/parser/parser_common.ml b/compiler/flow_parser/parser/parser_common.ml index 432116ce699..925d95a6300 100644 --- a/compiler/flow_parser/parser/parser_common.ml +++ b/compiler/flow_parser/parser/parser_common.ml @@ -212,7 +212,7 @@ module type STATEMENT = sig val debugger : env -> (Loc.t, Loc.t) Statement.t - val declare : ?in_module_or_namespace:bool -> env -> (Loc.t, Loc.t) Statement.t + val declare : env -> (Loc.t, Loc.t) Statement.t val declare_export_declaration : env -> (Loc.t, Loc.t) Statement.t @@ -313,8 +313,7 @@ module type DECLARATION = sig val _function : env -> (Loc.t, Loc.t) Statement.t - val enum_declaration : - ?leading:Loc.t Comment.t list -> const_:bool -> env -> (Loc.t, Loc.t) Statement.t + val enum_declaration : const_:bool -> env -> (Loc.t, Loc.t) Statement.t val component_params : env -> (Loc.t, Loc.t) Statement.ComponentDeclaration.Params.t @@ -520,13 +519,13 @@ let with_loc ?start_loc fn env = in (loc, result) -let with_loc_opt ?start_loc fn env = - match with_loc ?start_loc fn env with +let with_loc_opt fn env = + match with_loc fn env with | (loc, Some x) -> Some (loc, x) | (_, None) -> None -let with_loc_extra ?start_loc fn env = - let (loc, (x, extra)) = with_loc ?start_loc fn env in +let with_loc_extra fn env = + let (loc, (x, extra)) = with_loc fn env in ((loc, x), extra) let is_start_of_type_guard env = diff --git a/compiler/flow_parser/parser/parser_env.ml b/compiler/flow_parser/parser/parser_env.ml index ca6a65620dd..8b05965ee81 100644 --- a/compiler/flow_parser/parser/parser_env.ml +++ b/compiler/flow_parser/parser/parser_env.ml @@ -17,13 +17,6 @@ module Lex_mode = struct | JSX_CHILD | REGEXP - let debug_string_of_lex_mode (mode : t) = - match mode with - | NORMAL -> "NORMAL" - | TYPE -> "TYPE" - | JSX_TAG -> "JSX_TAG" - | JSX_CHILD -> "JSX_CHILD" - | REGEXP -> "REGEXP" end (* READ THIS BEFORE YOU MODIFY: @@ -51,8 +44,6 @@ module Lookahead : sig val junk : t -> unit - val rescan_template_part : t -> Lex_env.t -> unit - val rescan_template_part_from : t -> Lex_env.t -> Lex_env.t -> unit end = struct type la_result = (Lex_env.t * Lex_result.t) option @@ -117,18 +108,6 @@ end = struct t.la_results_0 <- t.la_results_1; t.la_results_1 <- None - (* Rescan the current position using the template tail lexer. - This replaces push_lex_mode(TEMPLATE) by directly lexing a template - continuation without modifying the lex mode stack. *) - let rescan_template_part t lex_env = - t.la_lex_env <- Lex_env.clone lex_env; - t.la_results_0 <- None; - t.la_results_1 <- None; - let (lex_env, lex_result) = Flow_lexer.template_tail t.la_lex_env in - let cloned_env = Lex_env.clone lex_env in - t.la_lex_env <- lex_env; - t.la_results_0 <- Some (cloned_env, lex_result) - let rescan_template_part_from t lex_env prev_lex_env = let existing_comments = match t.la_results_0 with @@ -147,11 +126,6 @@ end = struct t.la_results_0 <- Some (cloned_env, lex_result) end -type token_sink_result = { - token_loc: Loc.t; - token: Token.t; - token_context: Lex_mode.t; -} type parse_options = { components: bool; (* enable parsing of Flow component syntax *) @@ -182,20 +156,6 @@ let default_parse_options = allow_return_outside_function = false; } -let permissive_parse_options = - { - components = true; - enums = true; - assert_operator = false; - pattern_matching = true; - records = true; - esproposal_decorators = true; - types = true; - use_strict = false; - module_ref_prefix = None; - allow_return_outside_function = false; - } - type allowed_super = | No_super | Super_prop @@ -234,7 +194,6 @@ type env = { lex_env: Lex_env.t ref; (* This needs to be cleared whenever we advance. *) lookahead: Lookahead.t ref; - token_sink: (token_sink_result -> unit) option ref; parse_options: parse_options; source: File_key.t option; (* It is a syntax error to reference private fields not in scope. In order to enforce this, @@ -245,7 +204,7 @@ type env = { } (* constructor *) -let init_env ?(token_sink = None) ?(parse_options = None) source content = +let init_env source content = (* let lb = Sedlexing.Utf16.from_string content (Some Sedlexing.Utf16.Little_endian) in *) let (lb, errors) = @@ -253,11 +212,7 @@ let init_env ?(token_sink = None) ?(parse_options = None) source content = | Sedlexing.MalFormed -> (Sedlexing.Utf8.from_string "", [({ Loc.none with Loc.source }, Parse_error.MalformedUnicode)]) in - let parse_options = - match parse_options with - | Some opts -> opts - | None -> default_parse_options - in + let parse_options = default_parse_options in let enable_types_in_comments = parse_options.types in let lex_env = Lex_env.new_lex_env source lb ~enable_types_in_comments in { @@ -291,7 +246,6 @@ let init_env ?(token_sink = None) ?(parse_options = None) source content = lex_mode_stack = ref [Lex_mode.NORMAL]; lex_env = ref lex_env; lookahead = ref (Lookahead.create lex_env Lex_mode.NORMAL); - token_sink = ref token_sink; parse_options; source; privates = ref []; @@ -1189,38 +1143,6 @@ let function_as_statement_error_at env loc = module Eat = struct (* Consume a single token *) let token env = - (* If there's a token_sink, emit the lexed token before moving forward. - Skip T_EOF — upstream Hermes' token stream does not include a sentinel - end-of-input token, so neither should ours. The Rust port mirrors this - in `parser_env.rs::token::token`. *) - (match !(env.token_sink) with - | None -> () - | Some _ when Peek.token env = Token.T_EOF -> () - | Some token_sink -> - let token_loc = Peek.loc env in - let token = Peek.token env in - let token_loc = - match token with - | Token.T_INTERPRETER (loc, _) -> loc - | _ -> token_loc - in - token_sink - { - token_loc; - token; - (* - * The lex mode is useful because it gives context to some - * context-sensitive tokens. - * - * Some examples of such tokens include: - * - * `=>` - Part of an arrow function? or part of a type annotation? - * `<` - A less-than? Or an opening to a JSX element? - * ...etc... - *) - token_context = lex_mode env; - }); - env.lex_env := Peek.lex_env env; error_list env (Peek.errors env); @@ -1257,11 +1179,6 @@ module Eat = struct env.lex_mode_stack := new_stack; env.lookahead := Lookahead.create !(env.lex_env) (lex_mode env) - (* Rescan the current position as a template continuation (template middle/tail). - This replaces the pattern of push_lex_mode(TEMPLATE) + pop_lex_mode() - by directly lexing a template tail without modifying the lex mode stack. *) - let rescan_as_template env = Lookahead.rescan_template_part !(env.lookahead) !(env.lex_env) - let rescan_as_template_from env prev_lex_env = Lookahead.rescan_template_part_from !(env.lookahead) !(env.lex_env) prev_lex_env @@ -1391,18 +1308,9 @@ module Try = struct saved_lex_mode_stack: Lex_mode.t list; saved_lex_env: Lex_env.t; saved_consumed_comments_pos: Loc.position; - token_buffer: ((token_sink_result -> unit) * token_sink_result Queue.t) option; } let save_state env = - let token_buffer = - match !(env.token_sink) with - | None -> None - | Some orig_token_sink -> - let buffer = Queue.create () in - env.token_sink := Some (fun token_data -> Queue.add token_data buffer); - Some (orig_token_sink, buffer) - in { saved_errors = !(env.errors); saved_comments = !(env.comments); @@ -1410,18 +1318,9 @@ module Try = struct saved_lex_mode_stack = !(env.lex_mode_stack); saved_lex_env = !(env.lex_env); saved_consumed_comments_pos = !(env.consumed_comments_pos); - token_buffer; } - let reset_token_sink ~flush env token_buffer_info = - match token_buffer_info with - | None -> () - | Some (orig_token_sink, token_buffer) -> - env.token_sink := Some orig_token_sink; - if flush then Queue.iter orig_token_sink token_buffer - let rollback_state env saved_state = - reset_token_sink ~flush:false env saved_state.token_buffer; env.errors := saved_state.saved_errors; env.comments := saved_state.saved_comments; env.last_lex_result := saved_state.saved_last_lex_result; @@ -1432,13 +1331,9 @@ module Try = struct FailedToParse - let success env saved_state result = - reset_token_sink ~flush:true env saved_state.token_buffer; - ParsedSuccessfully result - let to_parse env parse = let saved_state = save_state env in - try success env saved_state (parse env) with + try ParsedSuccessfully (parse env) with | Rollback -> rollback_state env saved_state let or_else env ~fallback parse = diff --git a/compiler/flow_parser/parser/parser_env.mli b/compiler/flow_parser/parser/parser_env.mli index 8170e3798ad..d0c221585d1 100644 --- a/compiler/flow_parser/parser/parser_env.mli +++ b/compiler/flow_parser/parser/parser_env.mli @@ -18,15 +18,8 @@ module Lex_mode : sig | JSX_CHILD | REGEXP - val debug_string_of_lex_mode : t -> string end -type token_sink_result = { - token_loc: Loc.t; - token: Token.t; - token_context: Lex_mode.t; -} - type parse_options = { components: bool; (* enable parsing of Flow component syntax *) enums: bool; (** enable parsing of Flow enums *) @@ -42,10 +35,6 @@ type parse_options = { statements; matches hermes-parser [allowReturnOutsideFunction] *) } -val default_parse_options : parse_options - -val permissive_parse_options : parse_options - type env type allowed_super = @@ -55,8 +44,6 @@ type allowed_super = (* constructor: *) val init_env : - ?token_sink:(token_sink_result -> unit) option -> - ?parse_options:parse_options option -> File_key.t option -> string -> env @@ -68,8 +55,6 @@ val last_loc : env -> Loc.t option val last_token : env -> Token.t option -val in_export : env -> bool - val in_export_default : env -> bool val labels : env -> SSet.t @@ -207,8 +192,6 @@ val is_contextually_reserved : string -> bool val is_reserved : string -> bool -val token_is_reserved : Token.t -> bool - val token_is_reserved_type : Token.t -> bool val token_is_type_identifier : env -> Token.t -> bool @@ -217,8 +200,6 @@ val token_is_variance : Token.t -> bool val is_strict_reserved : string -> bool -val token_is_strict_reserved : Token.t -> bool - val is_restricted : string -> bool val is_reserved_type : string -> bool @@ -258,10 +239,6 @@ module Peek : sig val ith_loc : i:int -> env -> Loc.t - val ith_errors : i:int -> env -> (Loc.t * Parse_error.t) list - - val ith_comments : i:int -> env -> Loc.t Flow_ast.Comment.t list - val ith_is_line_terminator : i:int -> env -> bool val ith_is_implicit_semicolon : i:int -> env -> bool @@ -288,8 +265,6 @@ module Eat : sig val double_pop_lex_mode : env -> unit - val rescan_as_template : env -> unit - val rescan_as_template_from : env -> Lex_env.t -> unit val trailing_comments : env -> Loc.t Flow_ast.Comment.t list diff --git a/compiler/flow_parser/parser/parser_flow.ml b/compiler/flow_parser/parser/parser_flow.ml index 48d49a5c4c4..fe5ca8979e0 100644 --- a/compiler/flow_parser/parser/parser_flow.ml +++ b/compiler/flow_parser/parser/parser_flow.ml @@ -592,87 +592,7 @@ let do_parse env parser fail = | e :: es when fail -> raise (Parse_error.Error (e, es)) | _ -> (ast, error_list) -let parse_program fail ?(token_sink = None) ?(parse_options = None) filename content = - let env = init_env ~token_sink ~parse_options filename content in +let parse_program fail filename content = + let env = init_env filename content in do_parse env Parse.program fail -let program ?(fail = true) ?(token_sink = None) ?(parse_options = None) content = - parse_program fail ~token_sink ~parse_options None content - -let program_file ?(fail = true) ?(token_sink = None) ?(parse_options = None) content filename = - parse_program fail ~token_sink ~parse_options filename content - -let parse_annot ?(parse_options = None) filename content = - let env = init_env ~token_sink:None ~parse_options filename content in - do_parse env Parse.annot false - -let package_json_file = - let parser env = - let (loc, obj, { if_expr; _ }) = Parse.object_initializer env in - List.iter (error_at env) if_expr; - (loc, obj) - in - fun ?(fail = true) ?(token_sink = None) ?(parse_options = None) content filename -> - let env = init_env ~token_sink ~parse_options filename content in - do_parse env parser fail - -(* even if fail=false, still raises an error on a totally invalid token, since - there's no legitimate fallback. *) -let json_file = - let null_fallback _env = Ast.Expression.NullLiteral None in - let parser env = - match Peek.token env with - | T_LBRACKET - | T_LCURLY - | T_STRING _ - | T_NUMBER _ - | T_TRUE - | T_FALSE - | T_NULL -> - Parse.expression env - | T_MINUS -> - (match Peek.ith_token ~i:1 env with - | T_NUMBER _ -> Parse.expression env - | _ -> - error_unexpected ~expected:"a number" env; - with_loc null_fallback env) - | _ -> - error_unexpected ~expected:"a valid JSON value" env; - with_loc null_fallback env - in - fun ?(fail = true) ?(token_sink = None) ?(parse_options = None) content filename -> - let env = init_env ~token_sink ~parse_options filename content in - do_parse env parser fail - -let jsx_pragma_expression = - let left_hand_side env = - let ast = Parse.left_hand_side (with_no_new true env) in - Expect.token env T_EOF; - ast - in - fun content filename -> - let env = init_env ~token_sink:None ~parse_options:None filename content in - do_parse env left_hand_side true - -let string_is_valid_identifier_name str = - let lexbuf = Sedlexing.Utf8.from_string str in - Flow_lexer.is_valid_identifier_name lexbuf - -(** - * Returns the string and location of the first identifier in [input] for which - * [predicate] holds. - *) -let find_ident ~predicate input = - let env = init_env ~token_sink:None ~parse_options:None None input in - let rec loop token = - match token with - | T_EOF -> None - | _ -> - let loc = Peek.loc env in - (match token with - | T_IDENTIFIER { value = s; _ } when predicate s -> Some (loc, s) - | _ -> - Eat.token env; - loop (Peek.token env)) - in - loop (Peek.token env) diff --git a/compiler/flow_parser/parser/statement_parser.ml b/compiler/flow_parser/parser/statement_parser.ml index ed58962f276..14ad7abd49e 100644 --- a/compiler/flow_parser/parser/statement_parser.ml +++ b/compiler/flow_parser/parser/statement_parser.ml @@ -584,14 +584,7 @@ module Statement let case env = let leading = Peek.comments env in let case_match_root_loc = Peek.loc env |> Loc.start_loc in - let invalid_prefix_case = - if Peek.token env = T_CASE then ( - let loc = Peek.loc env in - Eat.token env; - Some loc - ) else - None - in + if Peek.token env = T_CASE then Eat.token env; let pattern = Parse.match_pattern env in let guard = if Eat.maybe env T_IF then ( @@ -602,28 +595,15 @@ module Statement ) else None in - let invalid_infix_colon = - if Peek.token env = T_COLON then ( - let loc = Peek.loc env in - Eat.token env; - Some loc - ) else ( - Expect.token env T_ARROW; - None - ) - in + if Peek.token env = T_COLON then + Eat.token env + else + Expect.token env T_ARROW; let body = Parse.statement ~allow_sequence:false (env |> with_in_match_statement true) in ignore @@ Eat.maybe env T_COMMA; let trailing = Eat.trailing_comments env in let comments = Flow_ast_utils.mk_comments_opt ~leading ~trailing () in - let invalid_syntax = - { - Case.InvalidSyntax.invalid_prefix_case; - invalid_infix_colon; - invalid_suffix_semicolon = None; - } - in - { Case.pattern; body; guard; comments; invalid_syntax; case_match_root_loc } + { Case.pattern; body; guard; comments; case_match_root_loc } in let rec case_list env acc = match Peek.token env with @@ -1643,7 +1623,7 @@ module Statement let comments = Flow_ast_utils.mk_comments_opt ~leading ~trailing () in Statement.DeclareModuleExports { Statement.DeclareModuleExports.annot; comments } - and declare ?(in_module_or_namespace = false) env = + and declare env = if not (should_parse_types env) then error env Parse_error.UnexpectedTypeDeclaration; (* eventually, just emit a wrapper AST node *) @@ -1653,10 +1633,7 @@ module Statement | T_CONST -> declare_const_or_enum env | T_ENUM when (parse_options env).enums -> declare_enum ~const_:false env | T_INTERFACE -> declare_interface env - | T_TYPE -> - (match Peek.token env with - | T_IMPORT when in_module_or_namespace -> import_declaration env - | _ -> declare_type_alias env) + | T_TYPE -> declare_type_alias env | T_OPAQUE -> declare_opaque_type env | T_TYPEOF when Peek.token env = T_IMPORT -> import_declaration env | T_FUNCTION -> declare_function_statement env @@ -1665,7 +1642,6 @@ module Statement declare_function_statement env | T_VAR -> declare_var_statement ~kind:Ast.Variable.Var env | T_LET -> declare_var_statement ~kind:Ast.Variable.Let env - | T_EXPORT when in_module_or_namespace -> declare_export_declaration env | T_IDENTIFIER { raw = "module"; _ } -> declare_module env | T_IDENTIFIER { raw = "global"; _ } -> declare_namespace ~global:true ~implicit_declare:false env @@ -1673,13 +1649,6 @@ module Statement declare_namespace ~global:false ~implicit_declare:false env | T_IDENTIFIER { raw = "component"; _ } when (parse_options env).components -> declare_component_statement env - | _ when in_module_or_namespace -> - (match Peek.token env with - | T_IMPORT -> import_declaration env - | _ -> - (* Oh boy, found some bad stuff in a declare module. Let's just - * pretend it's a declare var (arbitrary choice) *) - declare_var_statement ~kind:Ast.Variable.Var env) | _ -> Parse.statement env and export_source env = diff --git a/compiler/flow_parser/parser/type_parser.ml b/compiler/flow_parser/parser/type_parser.ml index 1f8ea5ca08c..0b864526bc6 100644 --- a/compiler/flow_parser/parser/type_parser.ml +++ b/compiler/flow_parser/parser/type_parser.ml @@ -634,15 +634,14 @@ module Type (Parse : Parser_common.PARSER) : Parser_common.TYPE = struct match Peek.token env with | T_RCURLY -> Eat.rescan_as_template_from env prev_lex_env; - let (loc, part, is_tail) = + let (loc, is_tail) = match Peek.token env with - | T_TEMPLATE_PART (loc, cooked, raw, _, tail) -> - let open Ast.Type.TemplateLiteral in + | T_TEMPLATE_PART (loc, _, _, _, tail) -> Eat.token env; - (loc, { Element.value = { Element.cooked; raw }; tail }, tail) + (loc, tail) | _ -> assert false in - let quasis = (loc, part) :: quasis in + let quasis = loc :: quasis in if is_tail then (loc, List.rev quasis, List.rev types) else @@ -650,34 +649,16 @@ module Type (Parse : Parser_common.PARSER) : Parser_common.TYPE = struct | _ -> (* Malformed template *) error_unexpected ~expected:"a template literal part" env; - let imaginary_quasi = - ( fst t, - { - Ast.Type.TemplateLiteral.Element.value = - { Ast.Type.TemplateLiteral.Element.raw = ""; cooked = "" }; - tail = true; - } - ) - in - (fst t, List.rev (imaginary_quasi :: quasis), List.rev types) + (fst t, List.rev (fst t :: quasis), List.rev types) in - fun env ((start_loc, cooked, raw, _, is_tail) as part) -> + fun env ((start_loc, _, _, _, is_tail) as part) -> let leading = Peek.comments env in Expect.token env (T_TEMPLATE_PART part); let (end_loc, quasis, types) = - let head = - ( start_loc, - { - Ast.Type.TemplateLiteral.Element.value = - { Ast.Type.TemplateLiteral.Element.cooked; raw }; - tail = is_tail; - } - ) - in if is_tail then - (start_loc, [head], []) + (start_loc, [start_loc], []) else - template_parts env [head] [] + template_parts env [start_loc] [] in let trailing = Eat.trailing_comments env in let loc = Loc.btwn start_loc end_loc in @@ -2181,7 +2162,7 @@ module Type (Parse : Parser_common.PARSER) : Parser_common.TYPE = struct let leading = leading @ Peek.comments env in Eat.token env; let ts_accessibility = - Some (acc_loc, { Ast.Class.TSAccessibility.kind; comments = None }) + Some (acc_loc, kind) in property env diff --git a/compiler/frontend/ast_literal.ml b/compiler/frontend/ast_literal.ml index 6c8a8e64205..490e7624cfb 100644 --- a/compiler/frontend/ast_literal.ml +++ b/compiler/frontend/ast_literal.ml @@ -66,11 +66,7 @@ let type_string ?loc () = | Some loc -> Ast_helper.Typ.mk ~loc (Ptyp_constr ({txt = Lid.type_string; loc}, [])) -let type_bool ?loc () = - match loc with - | None -> No_loc.type_bool - | Some loc -> - Ast_helper.Typ.mk ~loc (Ptyp_constr ({txt = Lid.type_bool; loc}, [])) +let type_bool () = No_loc.type_bool let type_int ?loc () = match loc with diff --git a/compiler/frontend/ast_literal.mli b/compiler/frontend/ast_literal.mli index 4e9e195ca50..42e08c6462b 100644 --- a/compiler/frontend/ast_literal.mli +++ b/compiler/frontend/ast_literal.mli @@ -44,7 +44,7 @@ type core_type_lit = Parsetree.core_type lit val type_string : core_type_lit -val type_bool : core_type_lit +val type_bool : unit -> Parsetree.core_type val type_int : core_type_lit diff --git a/scripts/dead_code.sh b/scripts/dead_code.sh index 7b873fbb53a..a89fecdd154 100755 --- a/scripts/dead_code.sh +++ b/scripts/dead_code.sh @@ -25,9 +25,11 @@ ln -s "$PWD/_build/default" "$root/native" ln -s "$PWD/_build_playground/default" "$root/playground" # Not reported: -# - compiler/flow_parser is vendored. # - compiler/ml/parsetree0.ml is the frozen AST of PPXs, which build the # constructors the compiler itself never builds; it must not change. +# - compiler/flow_parser/parser/flow_ast.ml is the vendored Flow parser's AST: +# the parser fills in every field, the compiler reads only the few it needs +# to classify %raw code. "$reanalyze" -dce-cmt "$root" \ - -suppress compiler/flow_parser,compiler/ml/parsetree0.ml \ + -suppress compiler/ml/parsetree0.ml,compiler/flow_parser/parser/flow_ast.ml \ -set-exit-code