Skip to content

Commit

Permalink
Merge remote-tracking branch 'origin/development' into run_some_filte…
Browse files Browse the repository at this point in the history
…rs_in_diagnostics
  • Loading branch information
kLabz committed Jun 5, 2023
2 parents 494f514 + fb2492f commit 143227a
Show file tree
Hide file tree
Showing 22 changed files with 356 additions and 295 deletions.
4 changes: 0 additions & 4 deletions src/codegen/codegen.ml
Original file line number Diff line number Diff line change
Expand Up @@ -476,10 +476,6 @@ let interpolate_code com code tl f_string f_expr p =
i := !i + String.length txt;
f_string txt;
loop tl
| Str.Delim a :: Str.Delim b :: tl when a = b ->
i := !i + 2;
f_string a;
loop tl
| Str.Delim "{" :: Str.Text n :: Str.Delim "}" :: tl ->
begin try
let expr = Array.get exprs (int_of_string n) in
Expand Down
57 changes: 27 additions & 30 deletions src/compiler/messageReporting.ml
Original file line number Diff line number Diff line change
Expand Up @@ -21,39 +21,36 @@ let resolve_source file l1 p1 l2 p2 =
end
in

try
let read_char line = match input_char_or_done ch line with
| '\n' -> inc 1 line
| '\r' ->
ignore(input_char_or_done ch line);
inc 2 line
| c -> begin
let line = ref (line ^ (String.make 1 c)) in
let rec skip n =
if n > 0 then begin
let c = input_char_or_done ch !line in
line := !line ^ (String.make 1 c);
skip (n - 1)
end
in

let code = int_of_char c in
if code < 0xC0 then ()
else if code < 0xE0 then skip 1
else if code < 0xF0 then skip 2
else skip 3;

(1, !line)
end
in
let read_char line = match input_char_or_done ch line with
| '\n' -> inc 1 line
| '\r' ->
ignore(input_char_or_done ch line);
inc 2 line
| c -> begin
let line = ref (line ^ (String.make 1 c)) in
let rec skip n =
if n > 0 then begin
let c = input_char_or_done ch !line in
line := !line ^ (String.make 1 c);
skip (n - 1)
end
in

let code = int_of_char c in
if code < 0xC0 then ()
else if code < 0xE0 then skip 1
else if code < 0xF0 then skip 2
else skip 3;

(1, !line)
end
in

let (delta, line) = read_char line in
loop (p + delta) line
with End_of_file ->
close_in ch;
let (delta, line) = read_char line in
loop (p + delta) line
in

loop 0 "";
try loop 0 ""; with End_of_file -> close_in ch;
List.rev !lines

let resolve_file ctx f =
Expand Down
44 changes: 22 additions & 22 deletions src/context/display/diagnostics.ml
Original file line number Diff line number Diff line change
Expand Up @@ -44,18 +44,18 @@ let check_other_things com e =
let pointless_compound s p =
add_diagnostics_message com (Printf.sprintf "This %s has no effect, but some of its sub-expressions do" s) p DKCompilerMessage Warning;
in
let rec compound s el p =
let rec compound compiler_generated s el p =
let old = !had_effect in
had_effect := false;
List.iter (loop true) el;
if not !had_effect then no_effect p else pointless_compound s p;
List.iter (loop true compiler_generated) el;
if not !had_effect then no_effect p else if not compiler_generated then pointless_compound s p;
had_effect := old;
and loop in_value e = match e.eexpr with
and loop in_value compiler_generated e = match e.eexpr with
| TBlock el ->
let rec loop2 el = match el with
| [] -> ()
| [e] -> loop in_value e
| e :: el -> loop false e; loop2 el
| [e] -> loop in_value compiler_generated e
| e :: el -> loop false compiler_generated e; loop2 el
in
loop2 el
| TMeta((Meta.Extern,_,_),_) ->
Expand All @@ -67,27 +67,29 @@ let check_other_things com e =
()
| TField (_, fa) when PurityState.is_explicitly_impure fa -> ()
| TFunction tf ->
loop false tf.tf_expr
| TCall({eexpr = TField(e1,fa)},el) when not in_value && PurityState.is_pure_field_access fa -> compound "call" el e.epos
loop false compiler_generated tf.tf_expr
| TCall({eexpr = TField(e1,fa)},el) when not in_value && PurityState.is_pure_field_access fa -> compound compiler_generated "call" el e.epos
| TNew _ | TCall _ | TBinop ((Ast.OpAssignOp _ | Ast.OpAssign),_,_) | TUnop ((Ast.Increment | Ast.Decrement),_,_)
| TReturn _ | TBreak | TContinue | TThrow _ | TCast (_,Some _)
| TIf _ | TTry _ | TSwitch _ | TWhile _ | TFor _ ->
had_effect := true;
Type.iter (loop true) e
Type.iter (loop true compiler_generated) e
| TMeta((Meta.CompilerGenerated,_,_),e1) ->
loop in_value true e1
| TParenthesis e1 | TMeta(_,e1) ->
loop in_value e1
loop in_value compiler_generated e1
| TArray _ | TCast (_,None) | TBinop _ | TUnop _
| TField _ | TArrayDecl _ | TObjectDecl _ when in_value ->
Type.iter (loop true) e;
| TArray(e1,e2) -> compound "array access" [e1;e2] e.epos
| TCast(e1,None) -> compound "cast" [e1] e.epos
| TBinop(op,e1,e2) -> compound (Printf.sprintf "'%s' operator" (s_binop op)) [e1;e2] e.epos
| TUnop(op,_,e1) -> compound (Printf.sprintf "'%s' operator" (s_unop op)) [e1] e.epos
| TField(e1,_) -> compound "field access" [e1] e.epos
| TArrayDecl el -> compound "array declaration" el e.epos
| TObjectDecl fl -> compound "object declaration" (List.map snd fl) e.epos
Type.iter (loop true compiler_generated) e;
| TArray(e1,e2) -> compound compiler_generated "array access" [e1;e2] e.epos
| TCast(e1,None) -> compound compiler_generated "cast" [e1] e.epos
| TBinop(op,e1,e2) -> compound compiler_generated (Printf.sprintf "'%s' operator" (s_binop op)) [e1;e2] e.epos
| TUnop(op,_,e1) -> compound compiler_generated (Printf.sprintf "'%s' operator" (s_unop op)) [e1] e.epos
| TField(e1,_) -> compound compiler_generated "field access" [e1] e.epos
| TArrayDecl el -> compound compiler_generated "array declaration" el e.epos
| TObjectDecl fl -> compound compiler_generated "object declaration" (List.map snd fl) e.epos
in
loop true e
loop true false e

let prepare_field dctx dectx com cf = match cf.cf_expr with
| None -> ()
Expand Down Expand Up @@ -176,9 +178,7 @@ let prepare com =
dctx

let secure_generated_code ctx e =
(* This causes problems and sucks in general... need a different solution. But I forgot which problem this solved anyway. *)
(* mk (TMeta((Meta.Extern,[],e.epos),e)) e.etype e.epos *)
e
if is_diagnostics ctx then mk (TMeta((Meta.CompilerGenerated,[],e.epos),e)) e.etype e.epos else e

let print com =
let dctx = prepare com in
Expand Down
2 changes: 1 addition & 1 deletion src/context/typecore.ml
Original file line number Diff line number Diff line change
Expand Up @@ -374,7 +374,7 @@ let add_local_with_origin ctx origin n t p =
check_local_variable_name ctx n origin p;
add_local ctx (VUser origin) n t p

let gen_local_prefix = "_g"
let gen_local_prefix = "`"

let gen_local ctx t p =
add_local ctx VGenerated gen_local_prefix t p
Expand Down
6 changes: 6 additions & 0 deletions src/filters/renameVars.ml
Original file line number Diff line number Diff line change
Expand Up @@ -358,11 +358,17 @@ and collect_ignore_block ?(in_block=false) rc scope e =
(**
Rename `v` if needed
*)
let trailing_numbers = Str.regexp "[0-9]+$"
let maybe_rename_var rc reserved (v,overlaps) =
let commit name =
v.v_meta <- (Meta.RealPath,[EConst (String(v.v_name,SDoubleQuotes)),null_pos],null_pos) :: v.v_meta;
v.v_name <- name
in
(* chop escape char for all local variables generated *)
if String.unsafe_get v.v_name 0 = String.unsafe_get Typecore.gen_local_prefix 0 then begin
let name = String.sub v.v_name 1 (String.length v.v_name - 1) in
commit ("_g" ^ (Str.replace_first trailing_numbers "" name))
end;
let rec loop name count =
if StringMap.mem name !reserved || Overlaps.has_name name overlaps then begin
let count = count + 1 in
Expand Down
12 changes: 5 additions & 7 deletions src/optimization/inline.ml
Original file line number Diff line number Diff line change
Expand Up @@ -589,7 +589,7 @@ class inline_state ctx ethis params cf f p = object(self)
mk (TBlock (DynArray.to_list el)) tret e.epos
in
let e = inline_metadata e cf.cf_meta in
let e = Diagnostics.secure_generated_code ctx e in
let e = Diagnostics.secure_generated_code ctx.com e in
if has_params then begin
let mt = map_type cf.cf_type in
let unify_func () = unify_raise mt (TFun (tl,tret)) p in
Expand Down Expand Up @@ -656,7 +656,7 @@ let rec type_inline ctx cf f ethis params tret config p ?(self_calling_closure=f
) in
(match api_inline ctx cl cf.cf_name params p with
| None -> raise Exit
| Some e -> Some e)
| Some e -> e)
with Exit ->
let has_params,map_type = match config with Some config -> config | None -> inline_default_config cf ethis.etype in
let params = inline_rest_params ctx f params map_type p in
Expand Down Expand Up @@ -831,10 +831,8 @@ let rec type_inline ctx cf f ethis params tret config p ?(self_calling_closure=f
state#set_side_effect;
begin match follow t with
| TInst({ cl_constructor = Some ({cf_kind = Method MethInline; cf_expr = Some ({eexpr = TFunction tf})} as cf)} as c,_) ->
begin match type_inline_ctor ctx c cf tf ethis el po with
| Some e -> map term false e
| None -> raise_typing_error "Could not inline super constructor call" po
end
let e = type_inline_ctor ctx c cf tf ethis el po in
map term false e
| _ -> raise_typing_error "Cannot inline function containing super" po
end
| TCall(e1,el) ->
Expand Down Expand Up @@ -876,7 +874,7 @@ let rec type_inline ctx cf f ethis params tret config p ?(self_calling_closure=f
(se "\t" e)
);
end;
Some e
e

(* Same as type_inline, but modifies the function body to add field inits *)
and type_inline_ctor ctx c cf tf ethis el po =
Expand Down
92 changes: 41 additions & 51 deletions src/optimization/inlineConstructors.ml
Original file line number Diff line number Diff line change
Expand Up @@ -374,34 +374,29 @@ let inline_constructors ctx original_e =
let argvs, pl = analyze_call_args pl in
let _, cname = c.cl_path in
let v = alloc_var VGenerated ("inl"^cname) e.etype e.epos in
match Inline.type_inline_ctor ctx c cf tf (mk (TLocal v) (TInst (c,tl)) e.epos) pl e.epos with
| Some inlined_expr ->
let inlined_expr = mark_ctors inlined_expr in
let has_untyped = (Meta.has Meta.HasUntyped cf.cf_meta) in
let forced = is_extern_ctor c cf || force_inline in
let io = mk_io (IOKCtor{ioc_class=c; ioc_tparams=tl; ioc_field=cf; ioc_forced=forced}) io_id inlined_expr ~has_untyped:has_untyped in
io.io_dependent_vars <- argvs;
let rec loop (c:tclass) (tl:t list) =
let apply = apply_params c.cl_params tl in
List.iter (fun cf ->
match cf.cf_kind,cf.cf_expr with
| Var _, _ ->
let fieldt = apply cf.cf_type in
ignore(alloc_io_field io cf.cf_name fieldt v.v_pos);
| _ -> ()
) c.cl_ordered_fields;
match c.cl_super with
| Some (c,tl) -> loop c (List.map apply tl)
| None -> ()
in loop c tl;
let iv = add v IVKLocal in
set_iv_alias iv io;
ignore(analyze_aliases_in_ctor cf true io.io_expr);
Some iv
| _ ->
List.iter (fun v -> cancel_v v v.v_pos) argvs;
if is_extern_ctor c cf then display_error ctx.com "Extern constructor could not be inlined" e.epos;
None
let inlined_expr = Inline.type_inline_ctor ctx c cf tf (mk (TLocal v) (TInst (c,tl)) e.epos) pl e.epos in
let inlined_expr = mark_ctors inlined_expr in
let has_untyped = (Meta.has Meta.HasUntyped cf.cf_meta) in
let forced = is_extern_ctor c cf || force_inline in
let io = mk_io (IOKCtor{ioc_class=c; ioc_tparams=tl; ioc_field=cf; ioc_forced=forced}) io_id inlined_expr ~has_untyped:has_untyped in
io.io_dependent_vars <- argvs;
let rec loop (c:tclass) (tl:t list) =
let apply = apply_params c.cl_params tl in
List.iter (fun cf ->
match cf.cf_kind,cf.cf_expr with
| Var _, _ ->
let fieldt = apply cf.cf_type in
ignore(alloc_io_field io cf.cf_name fieldt v.v_pos);
| _ -> ()
) c.cl_ordered_fields;
match c.cl_super with
| Some (c,tl) -> loop c (List.map apply tl)
| None -> ()
in loop c tl;
let iv = add v IVKLocal in
set_iv_alias iv io;
ignore(analyze_aliases_in_ctor cf true io.io_expr);
Some iv
end
| TNew({ cl_constructor = Some ({cf_kind = Method MethInline; cf_expr = Some _} as cf)} as c,_,pl),_ when is_extern_ctor c cf ->
raise_typing_error "Extern constructor could not be inlined" e.epos;
Expand Down Expand Up @@ -501,29 +496,24 @@ let inline_constructors ctx original_e =
let argvs, pl = analyze_call_args call_args in
io.io_dependent_vars <- io.io_dependent_vars @ argvs;
io.io_has_untyped <- io.io_has_untyped or (Meta.has Meta.HasUntyped cf.cf_meta);
begin match Inline.type_inline ctx cf tf (mk (TLocal io_var.iv_var) (TInst (c,tl)) e.epos) pl e.etype None e.epos true with
| Some e ->
let e = mark_ctors e in
io.io_inline_methods <- io.io_inline_methods @ [e];
begin match analyze_aliases captured e with
| Some(iv) ->
(*
The parent inline object might have been cancelled while analyzing the inlined method body
If the parent inline object is cancelled the inlining of this method will no longer happen,
so the return value must be cancelled.
*)
if io.io_cancelled then begin
cancel_iv iv e.epos;
None
end else begin
io.io_dependent_vars <- iv.iv_var :: io.io_dependent_vars;
Some(iv)
end
| None -> None
end
| None ->
cancel_io io e.epos;
None
let e = Inline.type_inline ctx cf tf (mk (TLocal io_var.iv_var) (TInst (c,tl)) e.epos) pl e.etype None e.epos true in
let e = mark_ctors e in
io.io_inline_methods <- io.io_inline_methods @ [e];
begin match analyze_aliases captured e with
| Some(iv) ->
(*
The parent inline object might have been cancelled while analyzing the inlined method body
If the parent inline object is cancelled the inlining of this method will no longer happen,
so the return value must be cancelled.
*)
if io.io_cancelled then begin
cancel_iv iv e.epos;
None
end else begin
io.io_dependent_vars <- iv.iv_var :: io.io_dependent_vars;
Some(iv)
end
| None -> None
end
| IOFInlineVar(iv) ->
cancel_iv iv e.epos;
Expand Down
23 changes: 14 additions & 9 deletions src/optimization/optimizer.ml
Original file line number Diff line number Diff line change
Expand Up @@ -224,6 +224,8 @@ let reduce_expr com e =
) l with
| [] -> ec
| l -> { e with eexpr = TBlock (List.rev (ec :: l)) })
| TMeta ((Meta.CompilerGenerated,_,_),ec) ->
{ ec with epos = e.epos }
| TParenthesis ec ->
{ ec with epos = e.epos }
| TTry (e,[]) ->
Expand Down Expand Up @@ -350,20 +352,23 @@ let rec reduce_loop ctx e =
let cf = mk_field "" ef.etype e.epos null_pos in
let ethis = mk (TConst TThis) t_dynamic e.epos in
let rt = (match follow ef.etype with TFun (_,rt) -> rt | _ -> die "" __LOC__) in
let inl = (try type_inline ctx cf func ethis el rt None e.epos ~self_calling_closure:true false with Error { err_message = Custom _ } -> None) in
(match inl with
| None -> reduce_expr ctx e
| Some e -> reduce_loop ctx e)
begin try
let e = type_inline ctx cf func ethis el rt None e.epos ~self_calling_closure:true false in
reduce_loop ctx e
with Error { err_message = Custom _ } ->
reduce_expr ctx e
end;
| {eexpr = TField(ef,(FStatic(cl,cf) | FInstance(cl,_,cf)))} when needs_inline ctx (Some cl) cf && not (rec_stack_memq cf inline_stack) ->
begin match cf.cf_expr with
| Some {eexpr = TFunction tf} ->
let config = inline_config (Some cl) cf el e.etype in
let rt = (match Abstract.follow_with_abstracts e1.etype with TFun (_,rt) -> rt | _ -> die "" __LOC__) in
let inl = (try type_inline ctx cf tf ef el rt config e.epos false with Error { err_message = Custom _ } -> None) in
(match inl with
| None -> reduce_expr ctx e
| Some e ->
rec_stack_default inline_stack cf (fun cf' -> cf' == cf) (fun () -> reduce_loop ctx e) e)
begin try
let e = type_inline ctx cf tf ef el rt config e.epos false in
rec_stack_default inline_stack cf (fun cf' -> cf' == cf) (fun () -> reduce_loop ctx e) e
with Error { err_message = Custom _ } ->
reduce_expr ctx e
end
| _ ->
reduce_expr ctx e
end
Expand Down
2 changes: 1 addition & 1 deletion src/typing/callUnification.ml
Original file line number Diff line number Diff line change
Expand Up @@ -493,7 +493,7 @@ object(self)
!ethis_f();
raise exc
in
let e = Diagnostics.secure_generated_code ctx e in
let e = Diagnostics.secure_generated_code ctx.com e in
ctx.com.error_ext <- old;
!ethis_f();
e
Expand Down
6 changes: 1 addition & 5 deletions src/typing/calls.ml
Original file line number Diff line number Diff line change
Expand Up @@ -70,11 +70,7 @@ let make_call ctx e params t ?(force_inline=false) p =
(match f.cf_expr_unoptimized,f.cf_expr with
| Some {eexpr = TFunction fd},_
| None,Some { eexpr = TFunction fd } ->
(match Inline.type_inline ctx f fd ethis params t config p force_inline with
| None ->
if force_inline then raise_typing_error "Inline could not be done" p;
raise Exit;
| Some e -> e)
Inline.type_inline ctx f fd ethis params t config p force_inline
| _ ->
(*
we can't inline because there is most likely a loop in the typing.
Expand Down
Loading

0 comments on commit 143227a

Please sign in to comment.