Parcourir la source

Split up typer context (#11534)

* add ctx.c

* create class context earlier to avoid some heritage awkwardness

* add ctx.e

* start on ctx.f

* curfield

* vthis

* untyped

* in_loop

* bypass_accessor & meta

* with_type_stack & call_argument_stack

* in_call_args & in_overload_call_args

* in_display

* is_display_file

* in_call_args needs to be on ctx.f

also do some cleanup

* why did I change that

* macro_depth

* delayed_display

* allow_inline & allow_tranform

* rename to ctx_c to make difference visible

* more renaming, less ctx

because that will totally fix something

* I'm committed now

* make some context cloning explicit

* clone for enum fields too

and random cleanup

* Revert "allow_inline & allow_tranform"

This reverts commit f35e83c526d583c3ef2f25ed76625308c2a82684.

---------

Co-authored-by: Rudy Ges <[email protected]>
Simon Krajewski il y a 1 an
Parent
commit
2b0e8cead3

+ 4 - 4
src/context/abstractCast.ml

@@ -12,12 +12,12 @@ let rec make_static_call ctx c cf a pl args t p =
 		match args with
 			| [e] ->
 				let e,f = push_this ctx e in
-				ctx.with_type_stack <- (WithType.with_type t) :: ctx.with_type_stack;
+				ctx.e.with_type_stack <- (WithType.with_type t) :: ctx.e.with_type_stack;
 				let e = match ctx.g.do_macro ctx MExpr c.cl_path cf.cf_name [e] p with
 					| MSuccess e -> type_expr ctx e (WithType.with_type t)
 					| _ ->  type_expr ctx (EConst (Ident "null"),p) WithType.value
 				in
-				ctx.with_type_stack <- List.tl ctx.with_type_stack;
+				ctx.e.with_type_stack <- List.tl ctx.e.with_type_stack;
 				let e = try cast_or_unify_raise ctx t e p with Error { err_message = Unify _ } -> raise Not_found in
 				f();
 				e
@@ -40,7 +40,7 @@ and do_check_cast ctx uctx tleft eright p =
 					raise_error_msg (Unify l) eright.epos)
 			| _ -> ()
 		end;
-		if cf == ctx.curfield || rec_stack_memq cf cast_stack then raise_typing_error "Recursive implicit cast" p;
+		if cf == ctx.f.curfield || rec_stack_memq cf cast_stack then raise_typing_error "Recursive implicit cast" p;
 		rec_stack_loop cast_stack cf f ()
 	in
 	let make (a,tl,(tcf,cf)) =
@@ -118,7 +118,7 @@ and cast_or_unify ctx tleft eright p =
 		eright
 
 let prepare_array_access_field ctx a pl cf p =
-	let monos = List.map (fun _ -> spawn_monomorph ctx p) cf.cf_params in
+	let monos = List.map (fun _ -> spawn_monomorph ctx.e p) cf.cf_params in
 	let map t = apply_params a.a_params pl (apply_params cf.cf_params monos t) in
 	let check_constraints () =
 		List.iter2 (fun m ttp -> match get_constraints ttp with

+ 1 - 1
src/context/display/displayEmitter.ml

@@ -71,7 +71,7 @@ let check_display_type ctx t ptp =
 		ctx.g.type_hints <- (ctx.m.curmod.m_extra.m_display,ptp.pos_full,t) :: ctx.g.type_hints;
 	in
 	let maybe_display_type () =
-		if ctx.is_display_file && display_position#enclosed_in ptp.pos_full then
+		if ctx.m.is_display_file && display_position#enclosed_in ptp.pos_full then
 			display_type ctx t ptp.pos_path
 	in
 	add_type_hint();

+ 5 - 5
src/context/display/displayFields.ml

@@ -49,7 +49,7 @@ let collect_static_extensions ctx items e p =
 	let rec dup t = Type.map dup t in
 	let handle_field c f acc =
 		let f = { f with cf_type = opt_type f.cf_type } in
-		let monos = List.map (fun _ -> spawn_monomorph ctx p) f.cf_params in
+		let monos = List.map (fun _ -> spawn_monomorph ctx.e p) f.cf_params in
 		let map = apply_params f.cf_params monos in
 		match follow (map f.cf_type) with
 		| TFun((_,_,TType({t_path=["haxe";"macro"], "ExprOf"}, [t])) :: args, ret)
@@ -112,7 +112,7 @@ let collect ctx e_ast e dk with_type p =
 	let opt_args args ret = TFun(List.map(fun (n,o,t) -> n,true,t) args,ret) in
 	let should_access c cf stat =
 		if Meta.has Meta.NoCompletion cf.cf_meta then false
-		else if c != ctx.curclass && not (has_class_field_flag cf CfPublic) && String.length cf.cf_name > 4 then begin match String.sub cf.cf_name 0 4 with
+		else if c != ctx.c.curclass && not (has_class_field_flag cf CfPublic) && String.length cf.cf_name > 4 then begin match String.sub cf.cf_name 0 4 with
 			| "get_" | "set_" -> false
 			| _ -> can_access ctx c cf stat
 		end else
@@ -402,9 +402,9 @@ let handle_missing_field_raise ctx tthis i mode with_type pfield =
 	display.module_diagnostics <- MissingFields diag :: display.module_diagnostics
 
 let handle_missing_ident ctx i mode with_type p =
-	match ctx.curfun with
+	match ctx.e.curfun with
 	| FunStatic ->
-		let e_self = Texpr.Builder.make_static_this ctx.curclass p in
+		let e_self = Texpr.Builder.make_static_this ctx.c.curclass p in
 		begin try
 			handle_missing_field_raise ctx e_self.etype i mode with_type p
 		with Exit ->
@@ -412,7 +412,7 @@ let handle_missing_ident ctx i mode with_type p =
 		end
 	| _ ->
 		begin try
-			handle_missing_field_raise ctx ctx.tthis i mode with_type p
+			handle_missing_field_raise ctx ctx.c.tthis i mode with_type p
 		with Exit ->
 			()
 		end

+ 0 - 1
src/context/display/displayPath.ml

@@ -165,7 +165,6 @@ let resolve_position_by_path ctx path p =
 	let p = (t_infos mt).mt_pos in
 	raise_positions [p]
 
-
 let handle_path_display ctx path p =
 	let class_field c name =
 		ignore(c.cl_build());

+ 2 - 2
src/context/display/displayTexpr.ml

@@ -140,8 +140,8 @@ let check_display_module ctx decls m =
 		| (EImport _ | EUsing _),_ -> true
 		| _ -> false
 	) decls in
-	let imports = TypeloadModule.ModuleLevel.handle_import_hx ctx m imports null_pos in
-	let ctx = TypeloadModule.type_types_into_module ctx m imports null_pos in
+	let imports = TypeloadModule.ModuleLevel.handle_import_hx ctx.com ctx.g m imports null_pos in
+	let ctx = TypeloadModule.type_types_into_module ctx.com ctx.g m imports null_pos in
 	List.iter (fun md ->
 		let infos = t_infos md in
 		if display_position#enclosed_in infos.mt_name_pos then

+ 13 - 13
src/context/display/displayToplevel.ml

@@ -227,7 +227,7 @@ let is_pack_visible pack =
 let collect ctx tk with_type sort =
 	let t = Timer.timer ["display";"toplevel collect"] in
 	let cctx = CollectionContext.create ctx in
-	let curpack = fst ctx.curclass.cl_path in
+	let curpack = fst ctx.c.curclass.cl_path in
 	(* Note: This checks for the explicit `ServerConfig.legacy_completion` setting instead of using
 	   `is_legacy_completion com` because the latter is always false for the old protocol, yet we have
 	   tests which assume advanced completion even in the old protocol. This means that we can only
@@ -302,7 +302,7 @@ let collect ctx tk with_type sort =
 		PMap.iter (fun _ v ->
 			if not (is_gen_local v) then
 				add (make_ci_local v (tpair ~values:(get_value_meta v.v_meta) v.v_type)) (Some v.v_name)
-		) ctx.locals;
+		) ctx.f.locals;
 		t();
 
 		let add_field scope origin cf =
@@ -331,22 +331,22 @@ let collect ctx tk with_type sort =
 
 		let t = Timer.timer ["display";"toplevel collect";"fields"] in
 		(* member fields *)
-		if ctx.curfun <> FunStatic then begin
-			let all_fields = Type.TClass.get_all_fields ctx.curclass (extract_param_types ctx.curclass.cl_params) in
+		if ctx.e.curfun <> FunStatic then begin
+			let all_fields = Type.TClass.get_all_fields ctx.c.curclass (extract_param_types ctx.c.curclass.cl_params) in
 			PMap.iter (fun _ (c,cf) ->
-				let origin = if c == ctx.curclass then Self (TClassDecl c) else Parent (TClassDecl c) in
+				let origin = if c == ctx.c.curclass then Self (TClassDecl c) else Parent (TClassDecl c) in
 				maybe_add_field CFSMember origin cf
 			) all_fields;
 			(* TODO: local using? *)
 		end;
 
 		(* statics *)
-		begin match ctx.curclass.cl_kind with
+		begin match ctx.c.curclass.cl_kind with
 		| KAbstractImpl ({a_impl = Some c} as a) ->
 			let origin = Self (TAbstractDecl a) in
 			List.iter (fun cf ->
 				if has_class_field_flag cf CfImpl then begin
-					if ctx.curfun = FunStatic then ()
+					if ctx.e.curfun = FunStatic then ()
 					else begin
 						let cf = prepare_using_field cf in
 						maybe_add_field CFSMember origin cf
@@ -355,7 +355,7 @@ let collect ctx tk with_type sort =
 					maybe_add_field CFSStatic origin cf
 			) c.cl_ordered_statics
 		| _ ->
-			List.iter (maybe_add_field CFSStatic (Self (TClassDecl ctx.curclass))) ctx.curclass.cl_ordered_statics
+			List.iter (maybe_add_field CFSStatic (Self (TClassDecl ctx.c.curclass))) ctx.c.curclass.cl_ordered_statics
 		end;
 		t();
 
@@ -363,7 +363,7 @@ let collect ctx tk with_type sort =
 		(* enum constructors *)
 		let rec enum_ctors t =
 			match t with
-			| TAbstractDecl ({a_impl = Some c} as a) when a.a_enum && not (path_exists cctx a.a_path) && ctx.curclass != c ->
+			| TAbstractDecl ({a_impl = Some c} as a) when a.a_enum && not (path_exists cctx a.a_path) && ctx.c.curclass != c ->
 				add_path cctx a.a_path;
 				List.iter (fun cf ->
 					let ccf = CompletionClassField.make cf CFSMember (Self (decl_of_class c)) true in
@@ -433,16 +433,16 @@ let collect ctx tk with_type sort =
 		add (make_ci_literal "null" (tpair t_dynamic)) (Some "null");
 		add (make_ci_literal "true" (tpair ctx.com.basic.tbool)) (Some "true");
 		add (make_ci_literal "false" (tpair ctx.com.basic.tbool)) (Some "false");
-		begin match ctx.curfun with
+		begin match ctx.e.curfun with
 			| FunMember | FunConstructor | FunMemberClassLocal ->
-				let t = TInst(ctx.curclass,extract_param_types ctx.curclass.cl_params) in
+				let t = TInst(ctx.c.curclass,extract_param_types ctx.c.curclass.cl_params) in
 				add (make_ci_literal "this" (tpair t)) (Some "this");
-				begin match ctx.curclass.cl_super with
+				begin match ctx.c.curclass.cl_super with
 					| Some(c,tl) -> add (make_ci_literal "super" (tpair (TInst(c,tl)))) (Some "super")
 					| None -> ()
 				end
 			| FunMemberAbstract ->
-				let t = TInst(ctx.curclass,extract_param_types ctx.curclass.cl_params) in
+				let t = TInst(ctx.c.curclass,extract_param_types ctx.c.curclass.cl_params) in
 				add (make_ci_literal "abstract" (tpair t)) (Some "abstract");
 			| _ ->
 				()

+ 1 - 1
src/context/display/importHandling.ml

@@ -113,7 +113,7 @@ let init_import ctx path mode p =
 		let check_alias mt name pname =
 			if not (name.[0] >= 'A' && name.[0] <= 'Z') then
 				raise_typing_error "Type aliases must start with an uppercase letter" pname;
-			if ctx.is_display_file && DisplayPosition.display_position#enclosed_in pname then
+			if ctx.m.is_display_file && DisplayPosition.display_position#enclosed_in pname then
 				DisplayEmitter.display_alias ctx name (type_of_module_type mt) pname;
 		in
 		let add_static_init t name s =

+ 166 - 56
src/context/typecore.ml

@@ -73,6 +73,13 @@ type typer_module = {
 	mutable enum_with_type : module_type option;
 	mutable module_using : (tclass * pos) list;
 	mutable import_statements : import list;
+	mutable is_display_file : bool;
+}
+
+type typer_class = {
+	mutable curclass : tclass; (* TODO: should not be mutable *)
+	mutable tthis : t;
+	mutable get_build_infos : unit -> (module_type * t list * class_field list) option;
 }
 
 type build_kind =
@@ -118,6 +125,7 @@ type typer_globals = {
 	mutable return_partial_type : bool;
 	mutable build_count : int;
 	mutable t_dynamic_def : Type.t;
+	mutable delayed_display : DisplayTypes.display_exception_kind option;
 	(* api *)
 	do_macro : typer -> macro_mode -> path -> string -> expr list -> pos -> macro_result;
 	do_load_macro : typer -> bool -> path -> string -> pos -> ((string * bool * t) list * t * tclass * Type.tclass_field);
@@ -128,43 +136,45 @@ type typer_globals = {
 	do_load_core_class : typer -> tclass -> tclass;
 }
 
+(* typer_expr holds information that is specific to a (function) expresssion, whereas typer_field
+   is shared by local TFunctions. *)
+and typer_expr = {
+	mutable ret : t;
+	mutable curfun : current_fun;
+	mutable opened : anon_status ref list;
+	mutable monomorphs : monomorphs;
+	mutable in_function : bool;
+	mutable in_loop : bool;
+	mutable bypass_accessor : int;
+	mutable with_type_stack : WithType.t list;
+	mutable call_argument_stack : expr list list;
+	mutable macro_depth : int;
+}
+
+and typer_field = {
+	mutable curfield : tclass_field;
+	mutable locals : (string, tvar) PMap.t;
+	mutable vthis : tvar option;
+	mutable untyped : bool;
+	mutable meta : metadata;
+	mutable in_display : bool;
+	mutable in_call_args : bool;
+	mutable in_overload_call_args : bool;
+}
+
 and typer = {
 	(* shared *)
 	com : context;
 	t : basic_types;
 	g : typer_globals;
-	mutable bypass_accessor : int;
-	mutable meta : metadata;
-	mutable with_type_stack : WithType.t list;
-	mutable call_argument_stack : expr list list;
-	(* variable *)
-	mutable pass : typer_pass;
-	(* per-module *)
 	mutable m : typer_module;
-	mutable is_display_file : bool;
-	(* per-class *)
-	mutable curclass : tclass;
-	mutable tthis : t;
+	c : typer_class;
+	f : typer_field;
+	mutable e : typer_expr;
+	mutable pass : typer_pass;
 	mutable type_params : type_params;
-	mutable get_build_infos : unit -> (module_type * t list * class_field list) option;
-	(* per-function *)
 	mutable allow_inline : bool;
 	mutable allow_transform : bool;
-	mutable curfield : tclass_field;
-	mutable untyped : bool;
-	mutable in_function : bool;
-	mutable in_loop : bool;
-	mutable in_display : bool;
-	mutable macro_depth : int;
-	mutable curfun : current_fun;
-	mutable ret : t;
-	mutable locals : (string, tvar) PMap.t;
-	mutable opened : anon_status ref list;
-	mutable vthis : tvar option;
-	mutable in_call_args : bool;
-	mutable in_overload_call_args : bool;
-	mutable delayed_display : DisplayTypes.display_exception_kind option;
-	mutable monomorphs : monomorphs;
 	(* events *)
 	memory_marker : float array;
 }
@@ -173,6 +183,106 @@ and monomorphs = {
 	mutable perfunction : (tmono * pos) list;
 }
 
+module TyperManager = struct
+	let create com g m c f e pass params = {
+		com = com;
+		g = g;
+		t = com.basic;
+		m = m;
+		c = c;
+		f = f;
+		e = e;
+		pass = pass;
+		allow_inline = true;
+		allow_transform = true;
+		type_params = params;
+		memory_marker = memory_marker;
+	}
+
+	let create_ctx_c c =
+		{
+			curclass = c;
+			tthis = (match c.cl_kind with
+				| KAbstractImpl a ->
+					(match a.a_this with
+					| TMono r when r.tm_type = None -> TAbstract (a,extract_param_types c.cl_params)
+					| t -> t)
+				| _ ->
+					TInst (c,extract_param_types c.cl_params)
+			);
+			get_build_infos = (fun () -> None);
+		}
+
+	let create_ctx_f cf =
+		{
+			locals = PMap.empty;
+			curfield = cf;
+			vthis = None;
+			untyped = false;
+			meta = [];
+			in_display = false;
+			in_overload_call_args = false;
+			in_call_args = false;
+		}
+
+	let create_ctx_e () =
+		{
+			ret = t_dynamic;
+			curfun = FunStatic;
+			opened = [];
+			in_function = false;
+			monomorphs = {
+				perfunction = [];
+			};
+			in_loop = false;
+			bypass_accessor = 0;
+			with_type_stack = [];
+			call_argument_stack = [];
+			macro_depth = 0;
+		}
+
+	let create_for_module com g m =
+		let c = create_ctx_c null_class in
+		let f = create_ctx_f null_field in
+		let e = create_ctx_e () in
+		create com g m c f e PBuildModule []
+
+	let clone_for_class ctx c =
+		let c = create_ctx_c c in
+		let f = create_ctx_f null_field in
+		let e = create_ctx_e () in
+		let params = match c.curclass.cl_kind with KAbstractImpl a -> a.a_params | _ -> c.curclass.cl_params in
+		create ctx.com ctx.g ctx.m c f e PBuildClass params
+
+	let clone_for_enum ctx en =
+		let c = create_ctx_c null_class in
+		let f = create_ctx_f null_field in
+		let e = create_ctx_e () in
+		create ctx.com ctx.g ctx.m c f e PBuildModule en.e_params
+
+	let clone_for_typedef ctx td =
+		let c = create_ctx_c null_class in
+		let f = create_ctx_f null_field in
+		let e = create_ctx_e () in
+		create ctx.com ctx.g ctx.m c f e PBuildModule td.t_params
+
+	let clone_for_abstract ctx a =
+		let c = create_ctx_c null_class in
+		let f = create_ctx_f null_field in
+		let e = create_ctx_e () in
+		create ctx.com ctx.g ctx.m c f e PBuildModule a.a_params
+
+	let clone_for_field ctx cf params =
+		let f = create_ctx_f cf in
+		let e = create_ctx_e () in
+		create ctx.com ctx.g ctx.m ctx.c f e PBuildClass params
+
+	let clone_for_enum_field ctx params =
+		let f = create_ctx_f null_field in
+		let e = create_ctx_e () in
+		create ctx.com ctx.g ctx.m ctx.c f e PBuildClass params
+end
+
 type field_host =
 	| FHStatic of tclass
 	| FHInstance of tclass * tparams
@@ -252,7 +362,7 @@ let pass_name = function
 	| PFinal -> "final"
 
 let warning ?(depth=0) ctx w msg p =
-	let options = (Warning.from_meta ctx.curclass.cl_meta) @ (Warning.from_meta ctx.curfield.cf_meta) in
+	let options = (Warning.from_meta ctx.c.curclass.cl_meta) @ (Warning.from_meta ctx.f.curfield.cf_meta) in
 	match Warning.get_mode w options with
 	| WMEnable ->
 		module_warning ctx.com ctx.m.curmod w options msg p
@@ -279,7 +389,7 @@ let make_static_field_access c cf t p =
 	mk (TField (ethis,(FStatic (c,cf)))) t p
 
 let make_static_call ctx c cf map args t p =
-	let monos = List.map (fun _ -> spawn_monomorph ctx p) cf.cf_params in
+	let monos = List.map (fun _ -> spawn_monomorph ctx.e p) cf.cf_params in
 	let map t = map (apply_params cf.cf_params monos t) in
 	let ef = make_static_field_access c cf (map cf.cf_type) p in
 	make_call ctx ef args (map t) p
@@ -288,17 +398,17 @@ let raise_with_type_error ?(depth = 0) msg p =
 	raise (WithTypeError (make_error ~depth (Custom msg) p))
 
 let raise_or_display ctx l p =
-	if ctx.untyped then ()
-	else if ctx.in_call_args then raise (WithTypeError (make_error (Unify l) p))
+	if ctx.f.untyped then ()
+	else if ctx.f.in_call_args then raise (WithTypeError (make_error (Unify l) p))
 	else display_error_ext ctx.com (make_error (Unify l) p)
 
 let raise_or_display_error ctx err =
-	if ctx.untyped then ()
-	else if ctx.in_call_args then raise (WithTypeError err)
+	if ctx.f.untyped then ()
+	else if ctx.f.in_call_args then raise (WithTypeError err)
 	else display_error_ext ctx.com err
 
 let raise_or_display_message ctx msg p =
-	if ctx.in_call_args then raise_with_type_error msg p
+	if ctx.f.in_call_args then raise_with_type_error msg p
 	else display_error ctx.com msg p
 
 let unify ctx t1 t2 p =
@@ -319,8 +429,8 @@ let unify_raise_custom uctx t1 t2 p =
 let unify_raise = unify_raise_custom default_unification_context
 
 let save_locals ctx =
-	let locals = ctx.locals in
-	(fun() -> ctx.locals <- locals)
+	let locals = ctx.f.locals in
+	(fun() -> ctx.f.locals <- locals)
 
 let add_local ctx k n t p =
 	let v = alloc_var k n t p in
@@ -328,7 +438,7 @@ let add_local ctx k n t p =
 		match k with
 		| VUser _ ->
 			begin try
-				let v' = PMap.find n ctx.locals in
+				let v' = PMap.find n ctx.f.locals in
 				(* ignore std lib *)
 				if not (List.exists (fun path -> ExtLib.String.starts_with p.pfile (path#path)) ctx.com.class_paths#get_std_paths) then begin
 					warning ctx WVarShadow "This variable shadows a previously declared variable" p;
@@ -340,7 +450,7 @@ let add_local ctx k n t p =
 		| _ ->
 			()
 	end;
-	ctx.locals <- PMap.add n v ctx.locals;
+	ctx.f.locals <- PMap.add n v ctx.f.locals;
 	v
 
 let display_identifier_error ctx ?prepend_msg msg p =
@@ -523,7 +633,7 @@ let clone_type_parameter map path ttp =
 let can_access ctx c cf stat =
 	if (has_class_field_flag cf CfPublic) then
 		true
-	else if c == ctx.curclass then
+	else if c == ctx.c.curclass then
 		true
 	else match ctx.m.curmod.m_statics with
 		| Some c' when c == c' ->
@@ -576,24 +686,24 @@ let can_access ctx c cf stat =
 		in
 		loop c.cl_meta || loop f.cf_meta
 	in
-	let module_path = ctx.curclass.cl_module.m_path in
+	let module_path = ctx.c.curclass.cl_module.m_path in
 	let cur_paths = ref [fst module_path @ [snd module_path], false] in
 	let rec loop c is_current_path =
-		cur_paths := (make_path c ctx.curfield, is_current_path) :: !cur_paths;
+		cur_paths := (make_path c ctx.f.curfield, is_current_path) :: !cur_paths;
 		begin match c.cl_super with
 			| Some (csup,_) -> loop csup false
 			| None -> ()
 		end;
 		List.iter (fun (c,_) -> loop c false) c.cl_implements;
 	in
-	loop ctx.curclass true;
+	loop ctx.c.curclass true;
 	let is_constr = cf.cf_name = "new" in
 	let rec loop c =
 		try
-			has Meta.Access ctx.curclass ctx.curfield ((make_path c cf), true)
+			has Meta.Access ctx.c.curclass ctx.f.curfield ((make_path c cf), true)
 			|| (
 				(* if our common ancestor declare/override the field, then we can access it *)
-				let allowed f = extends ctx.curclass c || (List.exists (has Meta.Allow c f) !cur_paths) in
+				let allowed f = extends ctx.c.curclass c || (List.exists (has Meta.Allow c f) !cur_paths) in
 				if is_constr then (
 					match c.cl_constructor with
 					| Some cf ->
@@ -616,10 +726,10 @@ let can_access ctx c cf stat =
 		| KTypeParameter ttp ->
 			List.exists (fun t -> match follow t with TInst(c,_) -> loop c | _ -> false) (get_constraints ttp)
 		| _ -> false)
-	|| (Meta.has Meta.PrivateAccess ctx.meta)
+	|| (Meta.has Meta.PrivateAccess ctx.f.meta)
 
 let check_field_access ctx c f stat p =
-	if not ctx.untyped && not (can_access ctx c f stat) then
+	if not ctx.f.untyped && not (can_access ctx c f stat) then
 		display_error ctx.com ("Cannot access private field " ^ f.cf_name) p
 
 (** removes the first argument of the class field's function type and all its overloads *)
@@ -703,11 +813,11 @@ let mk_infos ctx p params =
 	(EObjectDecl (
 		(("fileName",null_pos,NoQuotes) , (EConst (String(file,SDoubleQuotes)) , p)) ::
 		(("lineNumber",null_pos,NoQuotes) , (EConst (Int (string_of_int (Lexer.get_error_line p), None)),p)) ::
-		(("className",null_pos,NoQuotes) , (EConst (String (s_type_path ctx.curclass.cl_path,SDoubleQuotes)),p)) ::
-		if ctx.curfield.cf_name = "" then
+		(("className",null_pos,NoQuotes) , (EConst (String (s_type_path ctx.c.curclass.cl_path,SDoubleQuotes)),p)) ::
+		if ctx.f.curfield.cf_name = "" then
 			params
 		else
-			(("methodName",null_pos,NoQuotes), (EConst (String (ctx.curfield.cf_name,SDoubleQuotes)),p)) :: params
+			(("methodName",null_pos,NoQuotes), (EConst (String (ctx.f.curfield.cf_name,SDoubleQuotes)),p)) :: params
 	) ,p)
 
 let rec is_pos_infos = function
@@ -754,8 +864,8 @@ let push_this ctx e = match e.eexpr with
 
 let create_deprecation_context ctx = {
 	(DeprecationCheck.create_context ctx.com) with
-	class_meta = ctx.curclass.cl_meta;
-	field_meta = ctx.curfield.cf_meta;
+	class_meta = ctx.c.curclass.cl_meta;
+	field_meta = ctx.f.curfield.cf_meta;
 	curmod = ctx.m.curmod;
 }
 
@@ -801,14 +911,14 @@ let debug com (path : string list) str =
 	end
 
 let init_class_done ctx =
-	let path = fst ctx.curclass.cl_path @ [snd ctx.curclass.cl_path] in
-	debug ctx.com path ("init_class_done " ^ s_type_path ctx.curclass.cl_path);
+	let path = fst ctx.c.curclass.cl_path @ [snd ctx.c.curclass.cl_path] in
+	debug ctx.com path ("init_class_done " ^ s_type_path ctx.c.curclass.cl_path);
 	init_class_done ctx
 
 let ctx_pos ctx =
 	let inf = fst ctx.m.curmod.m_path @ [snd ctx.m.curmod.m_path]in
-	let inf = (match snd ctx.curclass.cl_path with "" -> inf | n when n = snd ctx.m.curmod.m_path -> inf | n -> inf @ [n]) in
-	let inf = (match ctx.curfield.cf_name with "" -> inf | n -> inf @ [n]) in
+	let inf = (match snd ctx.c.curclass.cl_path with "" -> inf | n when n = snd ctx.m.curmod.m_path -> inf | n -> inf @ [n]) in
+	let inf = (match ctx.f.curfield.cf_name with "" -> inf | n -> inf @ [n]) in
 	inf
 
 let pass_infos ctx p =

+ 2 - 2
src/filters/exceptions.ml

@@ -39,7 +39,7 @@ let haxe_exception_static_call ctx method_name args p =
 		| TFun(_,t) -> t
 		| _ -> raise_typing_error ("haxe.Exception." ^ method_name ^ " is not a function and cannot be called") p
 	in
-	add_dependency ctx.typer.curclass.cl_module ctx.haxe_exception_class.cl_module;
+	add_dependency ctx.typer.c.curclass.cl_module ctx.haxe_exception_class.cl_module;
 	make_static_call ctx.typer ctx.haxe_exception_class method_field (fun t -> t) args return_type p
 
 (**
@@ -605,7 +605,7 @@ let insert_save_stacks tctx =
 				in
 				let catch_local = mk (TLocal catch_var) catch_var.v_type catch_var.v_pos in
 				begin
-					add_dependency tctx.curclass.cl_module native_stack_trace_cls.cl_module;
+					add_dependency tctx.c.curclass.cl_module native_stack_trace_cls.cl_module;
 					make_static_call tctx native_stack_trace_cls method_field (fun t -> t) [catch_local] return_type catch_var.v_pos
 				end
 			else

+ 3 - 3
src/filters/filters.ml

@@ -545,7 +545,7 @@ let destruction tctx detail_times main locals =
 		check_private_path com;
 		Naming.apply_native_paths;
 		add_rtti com;
-		(match com.platform with | Java | Cs -> (fun _ -> ()) | _ -> (fun mt -> AddFieldInits.add_field_inits tctx.curclass.cl_path locals com mt));
+		(match com.platform with | Java | Cs -> (fun _ -> ()) | _ -> (fun mt -> AddFieldInits.add_field_inits tctx.c.curclass.cl_path locals com mt));
 		(match com.platform with Hl -> (fun _ -> ()) | _ -> add_meta_field com);
 		check_void_field;
 		(match com.platform with | Cpp -> promote_first_interface_to_super | _ -> (fun _ -> ()));
@@ -560,7 +560,7 @@ let destruction tctx detail_times main locals =
 		List.iter (fun t ->
 			begin match t with
 			| TClassDecl c ->
-				tctx.curclass <- c
+				tctx.c.curclass <- c
 			| _ ->
 				()
 			end;
@@ -811,7 +811,7 @@ let run tctx main before_destruction =
 		"RenameVars",(match com.platform with
 		| Eval -> (fun e -> e)
 		| Java when defined com Jvm -> (fun e -> e)
-		| _ -> (fun e -> RenameVars.run tctx.curclass.cl_path locals e));
+		| _ -> (fun e -> RenameVars.run tctx.c.curclass.cl_path locals e));
 		"mark_switch_break_loops",mark_switch_break_loops;
 	] in
 	List.iter (run_expression_filters tctx detail_times filters) new_types;

+ 3 - 3
src/filters/filtersCommon.ml

@@ -63,11 +63,11 @@ let run_expression_filters ?(ignore_processed_status=false) ctx detail_times fil
 	match t with
 	| TClassDecl c when is_removable_class c -> ()
 	| TClassDecl c ->
-		ctx.curclass <- c;
-		ctx.m <- TypeloadModule.make_curmod ctx c.cl_module;
+		ctx.c.curclass <- c;
+		ctx.m <- TypeloadModule.make_curmod ctx.com ctx.g c.cl_module;
 		let rec process_field f =
 			if ignore_processed_status || not (has_class_field_flag f CfPostProcessed) then begin
-				ctx.curfield <- f;
+				ctx.f.curfield <- f;
 				(match f.cf_expr with
 				| Some e when not (is_removable_field com f) ->
 					let identifier = Printf.sprintf "%s.%s" (s_type_path c.cl_path) f.cf_name in

+ 3 - 3
src/filters/localStatic.ml

@@ -10,8 +10,8 @@ type lscontext = {
 }
 
 let promote_local_static lsctx run v eo =
-	let name = Printf.sprintf "%s_%s" lsctx.ctx.curfield.cf_name v.v_name in
-	let c = lsctx.ctx.curclass in
+	let name = Printf.sprintf "%s_%s" lsctx.ctx.f.curfield.cf_name v.v_name in
+	let c = lsctx.ctx.c.curclass in
 	begin try
 		let cf = PMap.find name c.cl_statics in
 		display_error lsctx.ctx.com (Printf.sprintf "The expanded name of this local (%s) conflicts with another static field" name) v.v_pos;
@@ -56,7 +56,7 @@ let run ctx e =
 		lut = Hashtbl.create 0;
 		added_fields = [];
 	} in
-	let c = ctx.curclass in
+	let c = ctx.c.curclass in
 	let rec run e = match e.eexpr with
 		| TBlock el ->
 			let el = ExtList.List.filter_map (fun e -> match e.eexpr with

+ 5 - 5
src/filters/tre.ml

@@ -206,19 +206,19 @@ let run ctx =
 			match e.eexpr with
 			| TFunction fn ->
 				let is_tre_eligible =
-					match ctx.curfield.cf_kind with
+					match ctx.f.curfield.cf_kind with
 					| Method MethDynamic -> false
 					| Method MethInline -> true
 					| Method MethNormal ->
-						PMap.mem ctx.curfield.cf_name ctx.curclass.cl_statics
+						PMap.mem ctx.f.curfield.cf_name ctx.c.curclass.cl_statics
 					| _ ->
-						has_class_field_flag ctx.curfield CfFinal
+						has_class_field_flag ctx.f.curfield CfFinal
 					in
 				let is_recursive_call callee args =
-					is_tre_eligible && is_recursive_method_call ctx.curclass ctx.curfield callee args
+					is_tre_eligible && is_recursive_method_call ctx.c.curclass ctx.f.curfield callee args
 				in
 				if has_tail_recursion is_recursive_call false true fn.tf_expr then
-					(* print_endline ("TRE: " ^ ctx.curfield.cf_pos.pfile ^ ": " ^ ctx.curfield.cf_name); *)
+					(* print_endline ("TRE: " ^ ctx.f.curfield.cf_pos.pfile ^ ": " ^ ctx.f.curfield.cf_name); *)
 					let fn = transform_function ctx is_recursive_call fn in
 					{ e with eexpr = TFunction fn }
 				else

+ 2 - 2
src/optimization/inline.ml

@@ -546,7 +546,7 @@ class inline_state ctx ethis params cf f p = object(self)
 		in
 		let e = (if PMap.is_empty subst then e else inline_params false false e) in
 		let init = match vars with [] -> None | l -> Some l in
-		let md = ctx.curclass.cl_module.m_extra.m_display in
+		let md = ctx.c.curclass.cl_module.m_extra.m_display in
 		md.m_inline_calls <- (cf.cf_name_pos,{p with pmax = p.pmin + String.length cf.cf_name}) :: md.m_inline_calls;
 		let wrap e =
 			(* we can't mute the type of the expression because it is not correct to do so *)
@@ -866,7 +866,7 @@ let rec type_inline ctx cf f ethis params tret config p ?(self_calling_closure=f
 	in
 	let tl = arg_types params f.tf_args in
 	let e = state#finalize e tl tret has_params map_type p in
-	if Meta.has (Meta.Custom ":inlineDebug") ctx.meta then begin
+	if Meta.has (Meta.Custom ":inlineDebug") ctx.f.meta then begin
 		let se t = s_expr_ast true t (s_type (print_context())) in
 		print_endline (Printf.sprintf "Inline %s:\n\tArgs: %s\n\tExpr: %s\n\tResult: %s"
 			cf.cf_name

+ 2 - 2
src/optimization/inlineConstructors.ml

@@ -111,7 +111,7 @@ and inline_object_field =
 	inline_expression_handled
 	Defines what will happen to the expression being analized by analyze_aliases
 *)
-and inline_expression_handled = 
+and inline_expression_handled =
 	| IEHCaptured (* The expression will be assigned to a variable *)
 	| IEHIgnored (* The result of the expression will not be used *)
 	| IEHNotHandled (* Cases that are not handled (usually leads to cancelling inlining *)
@@ -728,7 +728,7 @@ let inline_constructors ctx original_e =
 		original_e
 	end else begin
 		let el,_ = final_map e in
-		let cf = ctx.curfield in
+		let cf = ctx.f.curfield in
 		if !included_untyped && not (Meta.has Meta.HasUntyped cf.cf_meta) then cf.cf_meta <- (Meta.HasUntyped,[],e.epos) :: cf.cf_meta;
 		let e = make_expr_for_rev_list el e.etype e.epos in
 		let rec get_pretty_name iv = match iv.iv_kind with

+ 1 - 1
src/optimization/optimizer.ml

@@ -384,7 +384,7 @@ let reduce_expression ctx e =
 	if ctx.com.foptimize then
 		(* We go through rec_stack_default here so that the current field is on inline_stack. This prevents self-recursive
 		   inlining (#7569). *)
-		rec_stack_default inline_stack ctx.curfield (fun cf' -> cf' == ctx.curfield) (fun () -> reduce_loop ctx e) e
+		rec_stack_default inline_stack ctx.f.curfield (fun cf' -> cf' == ctx.f.curfield) (fun () -> reduce_loop ctx e) e
 	else
 		e
 

+ 22 - 22
src/typing/callUnification.ml

@@ -144,7 +144,7 @@ let unify_call_args ctx el args r callp inline force_inline in_overload =
 		| (e,p) :: el, [] ->
 			begin match List.rev !skipped with
 				| [] ->
-					if ctx.is_display_file && not (Diagnostics.error_in_diagnostics_run ctx.com p) then begin
+					if ctx.m.is_display_file && not (Diagnostics.error_in_diagnostics_run ctx.com p) then begin
 						ignore(type_expr ctx (e,p) WithType.value);
 						ignore(loop el [])
 					end;
@@ -168,13 +168,13 @@ let unify_call_args ctx el args r callp inline force_inline in_overload =
 			end
 	in
 	let restore =
-		let in_call_args = ctx.in_call_args in
-		let in_overload_call_args = ctx.in_overload_call_args in
-		ctx.in_call_args <- true;
-		ctx.in_overload_call_args <- in_overload;
+		let in_call_args = ctx.f.in_call_args in
+		let in_overload_call_args = ctx.f.in_overload_call_args in
+		ctx.f.in_call_args <- true;
+		ctx.f.in_overload_call_args <- in_overload;
 		(fun () ->
-			ctx.in_call_args <- in_call_args;
-			ctx.in_overload_call_args <- in_overload_call_args;
+			ctx.f.in_call_args <- in_call_args;
+			ctx.f.in_overload_call_args <- in_overload_call_args;
 		)
 	in
 	let el = try loop el args with exc -> restore(); raise exc; in
@@ -241,14 +241,14 @@ let unify_field_call ctx fa el_typed el p inline =
 		else if fa.fa_field.cf_overloads <> [] then OverloadMeta
 		else OverloadNone
 	in
-	(* Delayed display handling works like this: If ctx.in_overload_call_args is set (via attempt_calls calling unify_call_args' below),
-	   the code which normally raises eager Display exceptions (in typerDisplay.ml handle_display) instead stores them in ctx.delayed_display.
+	(* Delayed display handling works like this: If ctx.e.in_overload_call_args is set (via attempt_calls calling unify_call_args' below),
+	   the code which normally raises eager Display exceptions (in typerDisplay.ml handle_display) instead stores them in ctx.g.delayed_display.
 	   The overload handling here extracts them and associates the exception with the field call candidates. Afterwards, normal overload resolution
 	   can take place and only then the display callback is actually committed.
 	*)
-	let extract_delayed_display () = match ctx.delayed_display with
+	let extract_delayed_display () = match ctx.g.delayed_display with
 		| Some f ->
-			ctx.delayed_display <- None;
+			ctx.g.delayed_display <- None;
 			Some f
 		| None ->
 			None
@@ -328,11 +328,11 @@ let unify_field_call ctx fa el_typed el p inline =
 			| cf :: candidates ->
 				let known_monos = List.map (fun (m,_) ->
 					m,m.tm_type,m.tm_down_constraints
-				) ctx.monomorphs.perfunction in
-				let current_monos = ctx.monomorphs.perfunction in
+				) ctx.e.monomorphs.perfunction in
+				let current_monos = ctx.e.monomorphs.perfunction in
 				begin try
 					let candidate = attempt_call cf true in
-					ctx.monomorphs.perfunction <- current_monos;
+					ctx.e.monomorphs.perfunction <- current_monos;
 					if overload_kind = OverloadProper then begin
 						let candidates,failures = loop candidates in
 						candidate :: candidates,failures
@@ -343,7 +343,7 @@ let unify_field_call ctx fa el_typed el p inline =
 						if t != m.tm_type then m.tm_type <- t;
 						if constr != m.tm_down_constraints then m.tm_down_constraints <- constr;
 					) known_monos;
-					ctx.monomorphs.perfunction <- current_monos;
+					ctx.e.monomorphs.perfunction <- current_monos;
 					check_unknown_ident err;
 					let candidates,failures = loop candidates in
 					candidates,(cf,err,extract_delayed_display()) :: failures
@@ -362,7 +362,7 @@ let unify_field_call ctx fa el_typed el p inline =
 	in
 	(* There's always a chance that we never even came across the EDisplay in an argument, so let's look for it (issue #11422). *)
 	let check_display_args () =
-		if ctx.is_display_file then begin
+		if ctx.m.is_display_file then begin
 			let rec loop el = match el with
 				| [] ->
 					()
@@ -465,9 +465,9 @@ object(self)
 		end
 
 	method private macro_call (ethis : texpr) (cf : tclass_field) (el : expr list) =
-		if ctx.macro_depth > 300 then raise_typing_error "Stack overflow" p;
-		ctx.macro_depth <- ctx.macro_depth + 1;
-		ctx.with_type_stack <- with_type :: ctx.with_type_stack;
+		if ctx.e.macro_depth > 300 then raise_typing_error "Stack overflow" p;
+		ctx.e.macro_depth <- ctx.e.macro_depth + 1;
+		ctx.e.with_type_stack <- with_type :: ctx.e.with_type_stack;
 		let ethis_f = ref (fun () -> ()) in
 		let macro_in_macro () =
 			(fun () ->
@@ -506,8 +506,8 @@ object(self)
 				loop c
 			| _ -> die "" __LOC__))
 		in
-		ctx.macro_depth <- ctx.macro_depth - 1;
-		ctx.with_type_stack <- List.tl ctx.with_type_stack;
+		ctx.e.macro_depth <- ctx.e.macro_depth - 1;
+		ctx.e.with_type_stack <- List.tl ctx.e.with_type_stack;
 		let old = ctx.com.error_ext in
 		ctx.com.error_ext <- (fun err ->
 			let ep = err.err_pos in
@@ -538,7 +538,7 @@ object(self)
 			let el = el_typed @ List.map (fun e -> type_expr ctx e WithType.value) el in
 			let t = if t == t_dynamic then
 				t_dynamic
-			else if ctx.untyped then
+			else if ctx.f.untyped then
 				mk_mono()
 			else
 				raise_typing_error (s_type (print_context()) e.etype ^ " cannot be called") e.epos

+ 10 - 10
src/typing/calls.ml

@@ -51,8 +51,8 @@ let make_call ctx e params t ?(force_inline=false) p =
 		end;
 		let config = Inline.inline_config cl f params t in
 		ignore(follow f.cf_type); (* force evaluation *)
-		(match cl, ctx.curclass.cl_kind, params with
-			| Some c, KAbstractImpl _, { eexpr = TLocal { v_meta = v_meta } } :: _ when c == ctx.curclass ->
+		(match cl, ctx.c.curclass.cl_kind, params with
+			| Some c, KAbstractImpl _, { eexpr = TLocal { v_meta = v_meta } } :: _ when c == ctx.c.curclass ->
 				if
 					f.cf_name <> "_new"
 					&& has_meta Meta.This v_meta
@@ -60,7 +60,7 @@ let make_call ctx e params t ?(force_inline=false) p =
 				then
 					if assign_to_this_is_allowed ctx then
 						(* Current method needs to infer CfModifiesThis flag, since we are calling a method, which modifies `this` *)
-						add_class_field_flag ctx.curfield CfModifiesThis
+						add_class_field_flag ctx.f.curfield CfModifiesThis
 					else
 						raise_typing_error ("Abstract 'this' value can only be modified inside an inline function. '" ^ f.cf_name ^ "' modifies 'this'") p;
 			| _ -> ()
@@ -206,7 +206,7 @@ let rec acc_get ctx g =
 	| AKAccess _ -> die "" __LOC__
 	| AKResolve(sea,name) ->
 		(dispatcher sea.se_access.fa_pos)#resolve_call sea name
-	| AKUsingAccessor sea | AKUsingField sea when ctx.in_display ->
+	| AKUsingAccessor sea | AKUsingField sea when ctx.f.in_display ->
 		(* Generate a TField node so we can easily match it for position/usage completion (issue #1968) *)
 		let e_field = FieldAccess.get_field_expr sea.se_access FGet in
 		let id,_ = store_typed_expr ctx.com sea.se_this e_field.epos in
@@ -220,7 +220,7 @@ let rec acc_get ctx g =
 		begin match fa.fa_field.cf_kind with
 		| Method MethMacro ->
 			(* If we are in display mode, we're probably hovering a macro call subject. Just generate a normal field. *)
-			if ctx.in_display then
+			if ctx.f.in_display then
 				FieldAccess.get_field_expr fa FRead
 			else
 				raise_typing_error "Invalid macro access" fa.fa_pos
@@ -328,9 +328,9 @@ let call_to_string ctx ?(resume=false) e =
 	else
 	let gen_to_string e =
 		(* Ignore visibility of the toString field. *)
-		ctx.meta <- (Meta.PrivateAccess,[],e.epos) :: ctx.meta;
+		ctx.f.meta <- (Meta.PrivateAccess,[],e.epos) :: ctx.f.meta;
 		let acc = type_field (TypeFieldConfig.create resume) ctx e "toString" e.epos (MCall []) (WithType.with_type ctx.t.tstring) in
-		ctx.meta <- List.tl ctx.meta;
+		ctx.f.meta <- List.tl ctx.f.meta;
 		build_call ctx acc [] (WithType.with_type ctx.t.tstring) e.epos
 	in
 	if ctx.com.config.pf_static && not (is_nullable e.etype) then
@@ -359,7 +359,7 @@ let type_bind ctx (e : texpr) (args,ret) params p =
 	let vexpr v = mk (TLocal v) v.v_type p in
 	let acount = ref 0 in
 	let alloc_name n =
-		if n = "" && not ctx.is_display_file then begin
+		if n = "" && not ctx.m.is_display_file then begin
 			incr acount;
 			"a" ^ string_of_int !acount;
 		end else
@@ -468,12 +468,12 @@ let array_access ctx e1 e2 mode p =
 				let skip_abstract = fast_eq et at in
 				loop ~skip_abstract at
 			| _, _ ->
-				let pt = spawn_monomorph ctx p in
+				let pt = spawn_monomorph ctx.e p in
 				let t = ctx.t.tarray pt in
 				begin try
 					unify_raise et t p
 				with Error { err_message = Unify _ } ->
-					if not ctx.untyped then begin
+					if not ctx.f.untyped then begin
 						let msg = if !has_abstract_array_access then
 							"No @:arrayAccess function accepts an argument of " ^ (s_type (print_context()) e2.etype)
 						else

+ 23 - 23
src/typing/fields.ml

@@ -77,7 +77,7 @@ let no_abstract_constructor c p =
 
 let check_constructor_access ctx c f p =
 	if (Meta.has Meta.CompilerGenerated f.cf_meta) then display_error ctx.com (error_msg (No_constructor (TClassDecl c))) p;
-	if not (can_access ctx c f true || extends ctx.curclass c) && not ctx.untyped then display_error ctx.com (Printf.sprintf "Cannot access private constructor of %s" (s_class_path c)) p
+	if not (can_access ctx c f true || extends ctx.c.curclass c) && not ctx.f.untyped then display_error ctx.com (Printf.sprintf "Cannot access private constructor of %s" (s_class_path c)) p
 
 let check_no_closure_meta ctx cf fa mode p =
 	match mode with
@@ -109,12 +109,12 @@ let field_access ctx mode f fh e pfield =
 	let pfull = punion e.epos pfield in
 	let is_set = match mode with MSet _ -> true | _ -> false in
 	check_no_closure_meta ctx f fh mode pfield;
-	let bypass_accessor () = if ctx.bypass_accessor > 0 then (ctx.bypass_accessor <- ctx.bypass_accessor - 1; true) else false in
+	let bypass_accessor () = if ctx.e.bypass_accessor > 0 then (ctx.e.bypass_accessor <- ctx.e.bypass_accessor - 1; true) else false in
 	let make_access inline = FieldAccess.create e f fh (inline && ctx.allow_inline) pfull in
 	match f.cf_kind with
 	| Method m ->
 		let normal () = AKField(make_access false) in
-		if is_set && m <> MethDynamic && not ctx.untyped then raise_typing_error "Cannot rebind this method : please use 'dynamic' before method declaration" pfield;
+		if is_set && m <> MethDynamic && not ctx.f.untyped then raise_typing_error "Cannot rebind this method : please use 'dynamic' before method declaration" pfield;
 		let maybe_check_visibility c static =
 			(* For overloads we have to resolve the actual field before we can check accessibility. *)
 			begin match mode with
@@ -191,30 +191,30 @@ let field_access ctx mode f fh e pfield =
 			AKNo((normal false),pfield)
 		in
 		match (match mode with MGet | MCall _ -> v.v_read | MSet _ -> v.v_write) with
-		| AccNo when not (Meta.has Meta.PrivateAccess ctx.meta) ->
+		| AccNo when not (Meta.has Meta.PrivateAccess ctx.f.meta) ->
 			(match follow e.etype with
-			| TInst (c,_) when extends ctx.curclass c || can_access ctx c { f with cf_flags = unset_flag f.cf_flags (int_of_class_field_flag CfPublic) } false ->
+			| TInst (c,_) when extends ctx.c.curclass c || can_access ctx c { f with cf_flags = unset_flag f.cf_flags (int_of_class_field_flag CfPublic) } false ->
 				normal false
 			| TAnon a ->
 				(match !(a.a_status) with
-				| ClassStatics c2 when ctx.curclass == c2 || can_access ctx c2 { f with cf_flags = unset_flag f.cf_flags (int_of_class_field_flag CfPublic) } true -> normal false
-				| _ -> if ctx.untyped then normal false else normal_failure())
+				| ClassStatics c2 when ctx.c.curclass == c2 || can_access ctx c2 { f with cf_flags = unset_flag f.cf_flags (int_of_class_field_flag CfPublic) } true -> normal false
+				| _ -> if ctx.f.untyped then normal false else normal_failure())
 			| _ ->
-				if ctx.untyped then normal false else normal_failure())
+				if ctx.f.untyped then normal false else normal_failure())
 		| AccNormal | AccNo ->
 			normal false
-		| AccCall when (not ctx.allow_transform) || (ctx.in_display && DisplayPosition.display_position#enclosed_in pfull) ->
+		| AccCall when (not ctx.allow_transform) || (ctx.f.in_display && DisplayPosition.display_position#enclosed_in pfull) ->
 			normal false
 		| AccCall ->
 			let m = (match mode with MSet _ -> "set_" | _ -> "get_") ^ f.cf_name in
 			let bypass_accessor =
 				(
-					m = ctx.curfield.cf_name
+					m = ctx.f.curfield.cf_name
 					&&
 					match e.eexpr with
 					| TConst TThis -> true
-					| TLocal v -> Option.map_default (fun vthis -> v == vthis) false ctx.vthis
-					| TTypeExpr (TClassDecl c) when c == ctx.curclass -> true
+					| TLocal v -> Option.map_default (fun vthis -> v == vthis) false ctx.f.vthis
+					| TTypeExpr (TClassDecl c) when c == ctx.c.curclass -> true
 					| _ -> false
 				) || bypass_accessor ()
 			in
@@ -234,15 +234,15 @@ let field_access ctx mode f fh e pfield =
 				AKAccessor (make_access false)
 			end
 		| AccNever ->
-			if ctx.untyped then normal false else normal_failure()
+			if ctx.f.untyped then normal false else normal_failure()
 		| AccInline ->
 			normal true
 		| AccCtor ->
 			let is_child_of_abstract c =
-				has_class_flag c CAbstract && extends ctx.curclass c
+				has_class_flag c CAbstract && extends ctx.c.curclass c
 			in
-			(match ctx.curfun, fh with
-				| FunConstructor, FHInstance(c,_) when c == ctx.curclass || is_child_of_abstract c -> normal false
+			(match ctx.e.curfun, fh with
+				| FunConstructor, FHInstance(c,_) when c == ctx.c.curclass || is_child_of_abstract c -> normal false
 				| _ -> normal_failure()
 			)
 		| AccRequire (r,msg) ->
@@ -382,8 +382,8 @@ let type_field cfg ctx e i p mode (with_type : WithType.t) =
 			| CTypes tl ->
 				type_field_by_list (fun (t,_) -> type_field_by_et type_field_by_type e t) tl
 			| CUnknown ->
-				if not (List.exists (fun (m,_) -> m == r) ctx.monomorphs.perfunction) && not (ctx.untyped && ctx.com.platform = Neko) then
-					ctx.monomorphs.perfunction <- (r,p) :: ctx.monomorphs.perfunction;
+				if not (List.exists (fun (m,_) -> m == r) ctx.e.monomorphs.perfunction) && not (ctx.f.untyped && ctx.com.platform = Neko) then
+					ctx.e.monomorphs.perfunction <- (r,p) :: ctx.e.monomorphs.perfunction;
 				let f = mk_field() in
 				Monomorph.add_down_constraint r (MField f);
 				Monomorph.add_down_constraint r MOpenStructure;
@@ -426,9 +426,9 @@ let type_field cfg ctx e i p mode (with_type : WithType.t) =
 					check cfl
 				| cf :: cfl ->
 					(* We always want to reset monomorphs here because they will be handled again when making the actual call. *)
-					let current_monos = ctx.monomorphs.perfunction in
+					let current_monos = ctx.e.monomorphs.perfunction in
 					let check () =
-						ctx.monomorphs.perfunction <- current_monos;
+						ctx.e.monomorphs.perfunction <- current_monos;
 						check cfl
 					in
 					try
@@ -441,7 +441,7 @@ let type_field cfg ctx e i p mode (with_type : WithType.t) =
 							else begin
 								let e = unify_static_extension ctx e t0 p in
 								ImportHandling.mark_import_position ctx pc;
-								ctx.monomorphs.perfunction <- current_monos;
+								ctx.e.monomorphs.perfunction <- current_monos;
 								AKUsingField (make_static_extension_access c cf e false p)
 							end
 						| _ ->
@@ -572,7 +572,7 @@ let type_field cfg ctx e i p mode (with_type : WithType.t) =
 	with Not_found -> try
 		type_field_by_module e t
 	with Not_found when not (TypeFieldConfig.do_resume cfg) ->
-		if not ctx.untyped then begin
+		if not ctx.f.untyped then begin
 			let has_special_field a =
 				List.exists (fun (_,cf) -> cf.cf_name = i) a.a_ops
 				|| List.exists (fun (_,_,cf) -> cf.cf_name = i) a.a_unops
@@ -594,7 +594,7 @@ let type_field cfg ctx e i p mode (with_type : WithType.t) =
 				with Exit ->
 					display_error ctx.com (StringError.string_error i (string_source tthis) (s_type (print_context()) tthis ^ " has no field " ^ i)) pfield
 		end;
-		AKExpr (mk (TField (e,FDynamic i)) (spawn_monomorph ctx p) p)
+		AKExpr (mk (TField (e,FDynamic i)) (spawn_monomorph ctx.e p) p)
 
 let type_field_default_cfg = type_field TypeFieldConfig.default
 

+ 4 - 4
src/typing/forLoop.ml

@@ -458,9 +458,9 @@ type iteration_kind =
 	| IKKeyValue of iteration_ident * iteration_ident
 
 let type_for_loop ctx handle_display ik e1 e2 p =
-	let old_loop = ctx.in_loop in
+	let old_loop = ctx.e.in_loop in
 	let old_locals = save_locals ctx in
-	ctx.in_loop <- true;
+	ctx.e.in_loop <- true;
 	let e2 = Expr.ensure_block e2 in
 	let check_display (i,pi,dko) = match dko with
 		| None -> ()
@@ -472,7 +472,7 @@ let type_for_loop ctx handle_display ik e1 e2 p =
 		let i = add_local_with_origin ctx TVOForVariable i iterator.it_type pi in
 		let e2 = type_expr ctx e2 NoValue in
 		check_display (i,pi,dko);
-		ctx.in_loop <- old_loop;
+		ctx.e.in_loop <- old_loop;
 		old_locals();
 		begin try
 			IterationKind.to_texpr ctx i iterator e2 p
@@ -509,7 +509,7 @@ let type_for_loop ctx handle_display ik e1 e2 p =
 			mk (TVar(vtmp,Some e1)) ctx.t.tvoid e1.epos;
 			mk (TWhile(ehasnext,ebody,NormalWhile)) ctx.t.tvoid p;
 		]) ctx.t.tvoid p in
-		ctx.in_loop <- old_loop;
+		ctx.e.in_loop <- old_loop;
 		old_locals();
 		e
 

+ 3 - 3
src/typing/functionArguments.ml

@@ -131,9 +131,9 @@ object(self)
 		in
 		loop (abstract_this <> None) syntax with_default
 
-	(* Brings arguments into context by adding them to `ctx.locals`. *)
-	method bring_into_context =
+	(* Brings arguments into context by adding them to `ctx.f.locals`. *)
+	method bring_into_context ctx =
 		List.iter (fun (v,_) ->
-			ctx.locals <- PMap.add v.v_name v ctx.locals
+			ctx.f.locals <- PMap.add v.v_name v ctx.f.locals
 		) self#for_expr
 end

+ 2 - 2
src/typing/generic.ml

@@ -26,7 +26,7 @@ let make_generic ctx ps pt debug p =
 				begin match c.cl_kind with
 					| KExpr e ->
 						let name = ident_safe (Ast.Printer.s_expr e) in
-						let e = type_expr {ctx with locals = PMap.empty} e WithType.value in
+						let e = type_expr {ctx with f = {ctx.f with locals = PMap.empty}} e WithType.value in
 						name,(t,Some e)
 					| _ ->
 						((ident_safe (s_type_path_underscore c.cl_path)) ^ (loop_tl top tl),(t,None))
@@ -354,7 +354,7 @@ let build_generic_class ctx c p tl =
 				if gctx.generic_debug then print_endline (Printf.sprintf "[GENERIC] %s" (Printer.s_tclass_field "  " cf_new));
 				t
 			in
-			let t = spawn_monomorph ctx p in
+			let t = spawn_monomorph ctx.e p in
 			let r = make_lazy ctx t (fun r ->
 				let t0 = f() in
 				unify_raise t0 t p;

+ 13 - 13
src/typing/instanceBuilder.ml

@@ -14,8 +14,8 @@ let get_macro_path ctx e args p =
 	let path = match e with
 		| (EConst(Ident i)),_ ->
 			let path = try
-				if not (PMap.mem i ctx.curclass.cl_statics) then raise Not_found;
-				ctx.curclass.cl_path
+				if not (PMap.mem i ctx.c.curclass.cl_statics) then raise Not_found;
+				ctx.c.curclass.cl_path
 			with Not_found -> try
 				(t_infos (let path,_,_ = PMap.find i (ctx.m.import_resolution#extract_field_imports) in path)).mt_path
 			with Not_found ->
@@ -37,12 +37,12 @@ let build_macro_type ctx pl p =
 		| _ ->
 			raise_typing_error "MacroType requires a single expression call parameter" p
 	) in
-	let old = ctx.ret in
+	let old = ctx.e.ret in
 	let t = (match ctx.g.do_macro ctx MMacroType path field args p with
-		| MError | MMacroInMacro -> spawn_monomorph ctx p
-		| MSuccess _ -> ctx.ret
+		| MError | MMacroInMacro -> spawn_monomorph ctx.e p
+		| MSuccess _ -> ctx.e.ret
 	) in
-	ctx.ret <- old;
+	ctx.e.ret <- old;
 	t
 
 let build_macro_build ctx c pl cfl p =
@@ -55,14 +55,14 @@ let build_macro_build ctx c pl cfl p =
 		| _,[ECall(e,args),_],_ -> get_macro_path ctx e args p
 		| _ -> raise_typing_error "genericBuild requires a single expression call parameter" p
 	in
-	let old = ctx.ret,ctx.get_build_infos in
-	ctx.get_build_infos <- (fun() -> Some (TClassDecl c, pl, cfl));
+	let old = ctx.e.ret,ctx.c.get_build_infos in
+	ctx.c.get_build_infos <- (fun() -> Some (TClassDecl c, pl, cfl));
 	let t = (match ctx.g.do_macro ctx MMacroType path field args p with
-		| MError | MMacroInMacro -> spawn_monomorph ctx p
-		| MSuccess _ -> ctx.ret
+		| MError | MMacroInMacro -> spawn_monomorph ctx.e p
+		| MSuccess _ -> ctx.e.ret
 	) in
-	ctx.ret <- fst old;
-	ctx.get_build_infos <- snd old;
+	ctx.e.ret <- fst old;
+	ctx.c.get_build_infos <- snd old;
 	t
 
 (* -------------------------------------------------------------------------- *)
@@ -73,7 +73,7 @@ let get_build_info ctx mtype p =
 	| TClassDecl c ->
 		if ctx.pass > PBuildClass then ignore(c.cl_build());
 		let build f s tl =
-			let t = spawn_monomorph ctx p in
+			let t = spawn_monomorph ctx.e p in
 			let r = make_lazy ctx t (fun r ->
 				let tf = f tl in
 				unify_raise tf t p;

+ 19 - 17
src/typing/macroContext.ml

@@ -79,7 +79,7 @@ let macro_timer com l =
 
 let typing_timer ctx need_type f =
 	let t = Timer.timer ["typing"] in
-	let old = ctx.com.error_ext and oldp = ctx.pass and oldlocals = ctx.locals in
+	let old = ctx.com.error_ext and oldp = ctx.pass and oldlocals = ctx.f.locals in
 	let restore_report_mode = disable_report_mode ctx.com in
 	(*
 		disable resumable errors... unless we are in display mode (we want to reach point of completion)
@@ -94,7 +94,7 @@ let typing_timer ctx need_type f =
 		t();
 		ctx.com.error_ext <- old;
 		ctx.pass <- oldp;
-		ctx.locals <- oldlocals;
+		ctx.f.locals <- oldlocals;
 		restore_report_mode ();
 	in
 	try
@@ -453,7 +453,7 @@ let make_macro_api ctx mctx p =
 			tp.tp_meta <- tp.tp_meta @ (List.map (fun (m,el,_) -> (m,el,p)) ml);
 		);
 		MacroApi.get_local_type = (fun() ->
-			match ctx.get_build_infos() with
+			match ctx.c.get_build_infos() with
 			| Some (mt,tl,_) ->
 				Some (match mt with
 					| TClassDecl c -> TInst (c,tl)
@@ -462,23 +462,23 @@ let make_macro_api ctx mctx p =
 					| TAbstractDecl a -> TAbstract(a,tl)
 				)
 			| _ ->
-				if ctx.curclass == null_class then
+				if ctx.c.curclass == null_class then
 					None
 				else
-					Some (TInst (ctx.curclass,[]))
+					Some (TInst (ctx.c.curclass,[]))
 		);
 		MacroApi.get_expected_type = (fun() ->
-			match ctx.with_type_stack with
+			match ctx.e.with_type_stack with
 				| (WithType.WithType(t,_)) :: _ -> Some t
 				| _ -> None
 		);
 		MacroApi.get_call_arguments = (fun() ->
-			match ctx.call_argument_stack with
+			match ctx.e.call_argument_stack with
 				| [] -> None
 				| el :: _ -> Some el
 		);
 		MacroApi.get_local_method = (fun() ->
-			ctx.curfield.cf_name;
+			ctx.f.curfield.cf_name;
 		);
 		MacroApi.get_local_using = (fun() ->
 			List.map fst ctx.m.module_using;
@@ -487,10 +487,10 @@ let make_macro_api ctx mctx p =
 			ctx.m.import_statements;
 		);
 		MacroApi.get_local_vars = (fun () ->
-			ctx.locals;
+			ctx.f.locals;
 		);
 		MacroApi.get_build_fields = (fun() ->
-			match ctx.get_build_infos() with
+			match ctx.c.get_build_infos() with
 			| None -> Interp.vnull
 			| Some (_,_,fields) -> Interp.encode_array (List.map Interp.encode_field fields)
 		);
@@ -537,7 +537,7 @@ let make_macro_api ctx mctx p =
 			let mpath = Ast.parse_path m in
 			begin try
 				let m = ctx.com.module_lut#find mpath in
-				ignore(TypeloadModule.type_types_into_module ctx m types pos)
+				ignore(TypeloadModule.type_types_into_module ctx.com ctx.g m types pos)
 			with Not_found ->
 				let mnew = TypeloadModule.type_module ctx mpath (Path.UniqueKey.lazy_path ctx.m.curmod.m_extra.m_file) types pos in
 				mnew.m_extra.m_kind <- MFake;
@@ -682,7 +682,7 @@ and flush_macro_context mint mctx =
 	let type_filters = [
 		FiltersCommon.remove_generic_base;
 		Exceptions.patch_constructors mctx;
-		(fun mt -> AddFieldInits.add_field_inits mctx.curclass.cl_path (RenameVars.init mctx.com) mctx.com mt);
+		(fun mt -> AddFieldInits.add_field_inits mctx.c.curclass.cl_path (RenameVars.init mctx.com) mctx.com mt);
 		minimal_restore;
 	] in
 	let ready = fun t ->
@@ -750,7 +750,7 @@ let create_macro_context com =
 	com2.platform <- Eval;
 	Common.init_platform com2;
 	let mctx = !create_context_ref com2 None in
-	mctx.is_display_file <- false;
+	mctx.m.is_display_file <- false;
 	CommonCache.lock_signature com2 "get_macro_context";
 	mctx
 
@@ -780,6 +780,7 @@ let load_macro_module mctx com cpath display p =
 		enum_with_type = None;
 		module_using = [];
 		import_statements = [];
+		is_display_file = (com.display.dms_kind <> DMNone && DisplayPosition.display_position#is_in_file (Path.UniqueKey.lazy_key mloaded.m_extra.m_file));
 	};
 	mloaded,(fun () -> mctx.com.display <- old)
 
@@ -821,6 +822,7 @@ let load_macro'' com mctx display cpath f p =
 			enum_with_type = None;
 			module_using = [];
 			import_statements = [];
+			is_display_file = false;
 		};
 		t();
 		meth
@@ -1002,7 +1004,7 @@ let type_macro ctx mode cpath f (el:Ast.expr list) p =
 				| MBuild ->
 					"Array<Field>",(fun () ->
 						let fields = if v = Interp.vnull then
-								(match ctx.get_build_infos() with
+								(match ctx.c.get_build_infos() with
 								| None -> die "" __LOC__
 								| Some (_,_,fields) -> fields)
 							else
@@ -1013,14 +1015,14 @@ let type_macro ctx mode cpath f (el:Ast.expr list) p =
 				| MMacroType ->
 					"ComplexType",(fun () ->
 						let t = if v = Interp.vnull then
-							spawn_monomorph ctx p
+							spawn_monomorph ctx.e p
 						else try
 							let ct = Interp.decode_ctype v in
 							Typeload.load_complex_type ctx false ct;
 						with MacroApi.Invalid_expr  | EvalContext.RunTimeException _ ->
 							Interp.decode_type v
 						in
-						ctx.ret <- t;
+						ctx.e.ret <- t;
 						MSuccess (EBlock [],p)
 					)
 			in
@@ -1034,7 +1036,7 @@ let type_macro ctx mode cpath f (el:Ast.expr list) p =
 	e
 
 let call_macro mctx args margs call p =
-	mctx.curclass <- null_class;
+	mctx.c.curclass <- null_class;
 	let el, _ = CallUnification.unify_call_args mctx args margs t_dynamic p false false false in
 	call (List.map (fun e -> try Interp.make_const e with Exit -> raise_typing_error "Argument should be a constant" e.epos) el)
 

+ 1 - 1
src/typing/matcher.ml

@@ -26,7 +26,7 @@ module Match = struct
 	open Typecore
 
 	let match_expr ctx e cases def with_type postfix_match p =
-		let match_debug = Meta.has (Meta.Custom ":matchDebug") ctx.curfield.cf_meta in
+		let match_debug = Meta.has (Meta.Custom ":matchDebug") ctx.f.curfield.cf_meta in
 		let rec loop e = match fst e with
 			| EArrayDecl el when (match el with [(EFor _ | EWhile _),_] -> false | _ -> true) ->
 				let el = List.map (fun e -> type_expr ctx e WithType.value) el in

+ 5 - 5
src/typing/matcher/case.ml

@@ -29,13 +29,13 @@ let make ctx t el eg eo_ast with_type postfix_match p =
 		let t_old = v.v_type in
 		v.v_type <- map v.v_type;
 		(v,t_old) :: acc
-	) ctx.locals [] in
-	let old_ret = ctx.ret in
-	ctx.ret <- map ctx.ret;
+	) ctx.f.locals [] in
+	let old_ret = ctx.e.ret in
+	ctx.e.ret <- map ctx.e.ret;
 	let pctx = {
 		ctx = ctx;
 		current_locals = PMap.empty;
-		ctx_locals = ctx.locals;
+		ctx_locals = ctx.f.locals;
 		or_locals = None;
 		in_reification = false;
 		is_postfix_match = postfix_match;
@@ -63,7 +63,7 @@ let make ctx t el eg eo_ast with_type postfix_match p =
 			let e = type_expr ctx e with_type in
 			Some e
 	in
-	ctx.ret <- old_ret;
+	ctx.e.ret <- old_ret;
 	List.iter (fun (v,t) -> v.v_type <- t) old_types;
 	save();
 	{

+ 11 - 11
src/typing/matcher/exprToPattern.ml

@@ -63,7 +63,7 @@ let get_general_module_type ctx mt p =
 let unify_type_pattern ctx mt t p =
 	let tcl = get_general_module_type ctx mt p in
 	match tcl with
-		| TAbstract(a,_) -> unify ctx (TAbstract(a,[spawn_monomorph ctx p])) t p
+		| TAbstract(a,_) -> unify ctx (TAbstract(a,[spawn_monomorph ctx.e p])) t p
 		| _ -> die "" __LOC__
 
 let rec make pctx toplevel t e =
@@ -93,7 +93,7 @@ let rec make pctx toplevel t e =
 			let v = alloc_var (VUser TVOPatternVariable) name t p in
 			if final then add_var_flag v VFinal;
 			pctx.current_locals <- PMap.add name (v,p) pctx.current_locals;
-			ctx.locals <- PMap.add name v ctx.locals;
+			ctx.f.locals <- PMap.add name v ctx.f.locals;
 			v
 	in
 	let con_enum en ef p =
@@ -166,18 +166,18 @@ let rec make pctx toplevel t e =
 		)
 	in
 	let try_typing e =
-		let old = ctx.untyped in
-		ctx.untyped <- true;
+		let old = ctx.f.untyped in
+		ctx.f.untyped <- true;
 		let restore = catch_errors () in
 		let e = try
 			type_expr ctx e (WithType.with_type t)
 		with exc ->
 			restore();
-			ctx.untyped <- old;
+			ctx.f.untyped <- old;
 			raise exc
 		in
 		restore();
-		ctx.untyped <- old;
+		ctx.f.untyped <- old;
 		let pat = check_expr e in
 		begin match pat with
 			| PatConstructor((ConTypeExpr mt,_),_) -> unify_type_pattern ctx mt t e.epos;
@@ -405,7 +405,7 @@ let rec make pctx toplevel t e =
 			loop None e1
 		| EBinop(OpArrow,e1,e2) ->
 			let restore = save_locals ctx in
-			ctx.locals <- pctx.ctx_locals;
+			ctx.f.locals <- pctx.ctx_locals;
 			let v = add_local false "_" null_pos in
 			(* Tricky stuff: Extractor expressions are like normal expressions, so we don't want to deal with GADT-applied types here.
 			   Let's unapply, then reapply after we're done with the extractor (#5952). *)
@@ -422,12 +422,12 @@ let rec make pctx toplevel t e =
 		(* Special case for completion on a pattern local: We don't want to add the local to the context
 		   while displaying (#7319) *)
 		| EDisplay((EConst (Ident _),_ as e),dk) when pctx.ctx.com.display.dms_kind = DMDefault ->
-			let locals = ctx.locals in
+			let locals = ctx.f.locals in
 			let pat = loop e in
-			let locals' = ctx.locals in
-			ctx.locals <- locals;
+			let locals' = ctx.f.locals in
+			ctx.f.locals <- locals;
 			ignore(TyperDisplay.handle_edisplay ctx e (display_mode()) MGet (WithType.with_type t));
-			ctx.locals <- locals';
+			ctx.f.locals <- locals';
 			pat
 		(* For signature completion, we don't want to recurse into the inner pattern because there's probably
 		   a EDisplay(_,DMMarked) in there. We can handle display immediately because inner patterns should not

+ 1 - 1
src/typing/operators.ml

@@ -94,7 +94,7 @@ let check_assign ctx e =
 		raise_typing_error "Cannot assign to final" e.epos
 	| TLocal {v_extra = None} | TArray _ | TField _ | TIdent _ ->
 		()
-	| TConst TThis | TTypeExpr _ when ctx.untyped ->
+	| TConst TThis | TTypeExpr _ when ctx.f.untyped ->
 		()
 	| _ ->
 		if not (Common.ignore_error ctx.com) then

+ 8 - 13
src/typing/typeload.ml

@@ -229,11 +229,6 @@ let load_type_def ctx p t =
 	let timer = Timer.timer ["typing";"load_type_def"] in
 	Std.finally timer (load_type_def ctx p) t *)
 
-let resolve_position_by_path ctx path p =
-	let mt = load_type_def ctx p path in
-	let p = (t_infos mt).mt_pos in
-	raise_positions [p]
-
 let generate_args_meta com cls_opt add_meta args =
 	let values = List.fold_left (fun acc ((name,p),_,_,_,eo) -> match eo with Some e -> ((name,p,NoQuotes),e) :: acc | _ -> acc) [] args in
 	(match values with
@@ -280,11 +275,11 @@ let check_param_constraints ctx t map ttp p =
 			unify_raise t ti p
 		with Error ({ err_message = Unify l } as err) ->
 			let fail() =
-				if not ctx.untyped then display_error_ext ctx.com { err with err_message = (Unify (Constraint_failure (s_type_path ttp.ttp_class.cl_path) :: l)) }
+				if not ctx.f.untyped then display_error_ext ctx.com { err with err_message = (Unify (Constraint_failure (s_type_path ttp.ttp_class.cl_path) :: l)) }
 			in
 			match follow t with
 			| TInst({cl_kind = KExpr e},_) ->
-				let e = type_expr {ctx with locals = PMap.empty} e (WithType.with_type ti) in
+				let e = type_expr {ctx with f = {ctx.f with locals = PMap.empty}} e (WithType.with_type ti) in
 				begin try unify_raise e.etype ti p
 				with Error { err_message = Unify _ } -> fail() end
 			| _ ->
@@ -449,7 +444,7 @@ and load_instance ctx ?(allow_display=false) ptp get_params =
 		let t = load_instance' ctx ptp get_params in
 		if allow_display then DisplayEmitter.check_display_type ctx t ptp;
 		t
-	with Error { err_message = Module_not_found path } when ctx.macro_depth <= 0 && (ctx.com.display.dms_kind = DMDefault) && DisplayPosition.display_position#enclosed_in ptp.pos_path ->
+	with Error { err_message = Module_not_found path } when ctx.e.macro_depth <= 0 && (ctx.com.display.dms_kind = DMDefault) && DisplayPosition.display_position#enclosed_in ptp.pos_path ->
 		let s = s_type_path path in
 		DisplayToplevel.collect_and_raise ctx TKType NoValue CRTypeHint (s,ptp.pos_full) ptp.pos_path
 
@@ -459,7 +454,7 @@ and load_instance ctx ?(allow_display=false) ptp get_params =
 and load_complex_type' ctx allow_display (t,p) =
 	match t with
 	| CTParent t -> load_complex_type ctx allow_display t
-	| CTPath { path = {tpackage = ["$"]; tname = "_hx_mono" }} -> spawn_monomorph ctx p
+	| CTPath { path = {tpackage = ["$"]; tname = "_hx_mono" }} -> spawn_monomorph ctx.e p
 	| CTPath ptp -> load_instance ~allow_display ctx ptp ParamNormal
 	| CTOptional _ -> raise_typing_error "Optional type not allowed here" p
 	| CTNamed _ -> raise_typing_error "Named type not allowed here" p
@@ -610,7 +605,7 @@ and load_complex_type' ctx allow_display (t,p) =
 			} in
 			if !final then add_class_field_flag cf CfFinal;
 			init_meta_overloads ctx None cf;
-			if ctx.is_display_file then begin
+			if ctx.m.is_display_file then begin
 				DisplayEmitter.check_display_metadata ctx cf.cf_meta;
 				if DisplayPosition.display_position#enclosed_in cf.cf_name_pos then displayed_field := Some cf;
 			end;
@@ -708,7 +703,7 @@ let t_iterator ctx p =
 	match load_qualified_type_def ctx [] "StdTypes" "Iterator" p with
 	| TTypeDecl t ->
 		add_dependency ctx.m.curmod t.t_module;
-		let pt = spawn_monomorph ctx p in
+		let pt = spawn_monomorph ctx.e p in
 		apply_typedef t [pt], pt
 	| _ ->
 		die "" __LOC__
@@ -718,7 +713,7 @@ let t_iterator ctx p =
 *)
 let load_type_hint ?(opt=false) ctx pcur t =
 	let t = match t with
-		| None -> spawn_monomorph ctx pcur
+		| None -> spawn_monomorph ctx.e pcur
 		| Some (t,p) ->	load_complex_type ctx true (t,p)
 	in
 	if opt then ctx.t.tnull t else t
@@ -733,7 +728,7 @@ let rec type_type_param ctx host path p tp =
 	c.cl_meta <- tp.Ast.tp_meta;
 	if host = TPHEnumConstructor then c.cl_meta <- (Meta.EnumConstructorParam,[],null_pos) :: c.cl_meta;
 	let ttp = mk_type_param c host None None in
-	if ctx.is_display_file && DisplayPosition.display_position#enclosed_in (pos tp.tp_name) then
+	if ctx.m.is_display_file && DisplayPosition.display_position#enclosed_in (pos tp.tp_name) then
 		DisplayEmitter.display_type ctx ttp.ttp_type (pos tp.tp_name);
 	ttp
 

+ 7 - 8
src/typing/typeloadCheck.ml

@@ -39,11 +39,11 @@ let is_generic_parameter ctx c =
 	(* first check field parameters, then class parameters *)
 	let name = snd c.cl_path in
 	try
-		ignore(lookup_param name ctx.curfield.cf_params);
-		has_class_field_flag ctx.curfield CfGeneric
+		ignore(lookup_param name ctx.f.curfield.cf_params);
+		has_class_field_flag ctx.f.curfield CfGeneric
 	with Not_found -> try
 		ignore(lookup_param name ctx.type_params);
-		(match ctx.curclass.cl_kind with | KGeneric -> true | _ -> false);
+		(match ctx.c.curclass.cl_kind with | KGeneric -> true | _ -> false);
 	with Not_found ->
 		false
 
@@ -287,7 +287,7 @@ let class_field_no_interf c i =
 
 let rec return_flow ctx e =
 	let error() =
-		display_error ctx.com (Printf.sprintf "Missing return: %s" (s_type (print_context()) ctx.ret)) e.epos; raise Exit
+		display_error ctx.com (Printf.sprintf "Missing return: %s" (s_type (print_context()) ctx.e.ret)) e.epos; raise Exit
 	in
 	let return_flow = return_flow ctx in
 	match e.eexpr with
@@ -332,7 +332,7 @@ let check_global_metadata ctx meta f_add mpath tpath so =
 		let add = ((field_mode && to_fields) || (not field_mode && to_types)) && (match_path recursive sl1 sl2) in
 		if add then f_add m
 	) ctx.com.global_metadata;
-	if ctx.is_display_file then delay ctx PCheckConstraint (fun () -> DisplayEmitter.check_display_metadata ctx meta)
+	if ctx.m.is_display_file then delay ctx PCheckConstraint (fun () -> DisplayEmitter.check_display_metadata ctx meta)
 
 module Inheritance = struct
 	let is_basic_class_path path = match path with
@@ -510,7 +510,6 @@ module Inheritance = struct
 
 	let set_heritance ctx c herits p =
 		let is_lib = Meta.has Meta.LibType c.cl_meta in
-		let ctx = { ctx with curclass = c; type_params = c.cl_params; } in
 		let old_meta = c.cl_meta in
 		let process_meta csup =
 			List.iter (fun m ->
@@ -638,7 +637,7 @@ let check_final_vars ctx e =
 		| _ ->
 			()
 	in
-	loop ctx.curclass;
+	loop ctx.c.curclass;
 	if Hashtbl.length final_vars > 0 then begin
 		let rec find_inits e = match e.eexpr with
 			| TBinop(OpAssign,{eexpr = TField({eexpr = TConst TThis},fa)},e2) ->
@@ -649,7 +648,7 @@ let check_final_vars ctx e =
 		in
 		find_inits e;
 		if Hashtbl.length final_vars > 0 then
-			display_error ctx.com "Some final fields are uninitialized in this class" ctx.curclass.cl_name_pos;
+			display_error ctx.com "Some final fields are uninitialized in this class" ctx.c.curclass.cl_name_pos;
 		DynArray.iter (fun (c,cf) ->
 			if Hashtbl.mem final_vars cf.cf_name then
 				display_error ~depth:1 ctx.com "Uninitialized field" cf.cf_name_pos

+ 41 - 62
src/typing/typeloadFields.ml

@@ -31,7 +31,7 @@ open Common
 open Error
 
 type class_init_ctx = {
-	tclass : tclass; (* I don't trust ctx.curclass because it's mutable. *)
+	tclass : tclass; (* I don't trust ctx.c.curclass because it's mutable. *)
 	is_lib : bool;
 	is_native : bool;
 	is_core_api : bool;
@@ -466,10 +466,10 @@ let build_module_def ctx mt meta fvars fbuild =
 						raise_typing_error "Invalid macro path" p
 				in
 				if ctx.com.is_macro_context then raise_typing_error "You cannot use @:build inside a macro : make sure that your type is not used in macro" p;
-				let old = ctx.get_build_infos in
-				ctx.get_build_infos <- (fun() -> Some (mt, extract_param_types (t_infos mt).mt_params, fvars()));
-				let r = try ctx.g.do_macro ctx MBuild cpath meth el p with e -> ctx.get_build_infos <- old; raise e in
-				ctx.get_build_infos <- old;
+				let old = ctx.c.get_build_infos in
+				ctx.c.get_build_infos <- (fun() -> Some (mt, extract_param_types (t_infos mt).mt_params, fvars()));
+				let r = try ctx.g.do_macro ctx MBuild cpath meth el p with e -> ctx.c.get_build_infos <- old; raise e in
+				ctx.c.get_build_infos <- old;
 				(match r with
 				| MError | MMacroInMacro -> raise_typing_error "Build failure" p
 				| MSuccess e -> fbuild e)
@@ -554,19 +554,7 @@ let create_typer_context_for_class ctx cctx p =
 	let c = cctx.tclass in
 	if cctx.is_lib && not (has_class_flag c CExtern) then ctx.com.error "@:libType can only be used in extern classes" c.cl_pos;
 	if Meta.has Meta.Macro c.cl_meta then display_error ctx.com "Macro classes are no longer allowed in haxe 3" c.cl_pos;
-	let ctx = {
-		ctx with
-		curclass = c;
-		type_params = (match c.cl_kind with KAbstractImpl a -> a.a_params | _ -> c.cl_params);
-		pass = PBuildClass;
-		tthis = (match cctx.abstract with
-			| Some a ->
-				(match a.a_this with
-				| TMono r when r.tm_type = None -> TAbstract (a,extract_param_types c.cl_params)
-				| t -> t)
-			| None -> TInst (c,extract_param_types c.cl_params));
-	} in
-	ctx
+	TyperManager.clone_for_class ctx c
 
 let create_field_context ctx cctx cff is_display_file display_modifier =
 	let is_static = List.mem_assoc AStatic cff.cff_access in
@@ -627,17 +615,9 @@ let create_field_context ctx cctx cff is_display_file display_modifier =
 	fctx
 
 let create_typer_context_for_field ctx cctx fctx cff =
-	DeprecationCheck.check_is ctx.com ctx.m.curmod ctx.curclass.cl_meta cff.cff_meta (fst cff.cff_name) cff.cff_meta (snd cff.cff_name);
-	let ctx = {
-		ctx with
-		pass = PBuildClass; (* will be set later to PTypeExpr *)
-		locals = PMap.empty;
-		opened = [];
-		monomorphs = {
-			perfunction = [];
-		};
-		type_params = if fctx.is_static && not fctx.is_abstract_member && not (Meta.has Meta.LibType cctx.tclass.cl_meta) (* TODO: remove this *) then [] else ctx.type_params;
-	} in
+	DeprecationCheck.check_is ctx.com ctx.m.curmod ctx.c.curclass.cl_meta cff.cff_meta (fst cff.cff_name) cff.cff_meta (snd cff.cff_name);
+	let params = if fctx.is_static && not fctx.is_abstract_member && not (Meta.has Meta.LibType cctx.tclass.cl_meta) (* TODO: remove this *) then [] else ctx.type_params in
+	let ctx = TyperManager.clone_for_field ctx null_field params in
 
 	let c = cctx.tclass in
 	if (fctx.is_abstract && not (has_meta Meta.LibType c.cl_meta)) then begin
@@ -696,7 +676,7 @@ let transform_field (ctx,cctx) c f fields p =
 	f
 
 let type_var_field ctx t e stat do_display p =
-	if stat then ctx.curfun <- FunStatic else ctx.curfun <- FunMember;
+	if stat then ctx.e.curfun <- FunStatic else ctx.e.curfun <- FunMember;
 	let e = if do_display then Display.preprocess_expr ctx.com e else e in
 	let e = type_expr ctx e (WithType.with_type t) in
 	let e = AbstractCast.cast_or_unify ctx t e p in
@@ -850,7 +830,7 @@ module TypeBinding = struct
 		let r = make_lazy ~force:false ctx t (fun r ->
 			(* type constant init fields (issue #1956) *)
 			if not ctx.g.return_partial_type || (match fst e with EConst _ -> true | _ -> false) then begin
-				enter_field_typing_pass ctx ("bind_var_expression",fst ctx.curclass.cl_path @ [snd ctx.curclass.cl_path;ctx.curfield.cf_name]);
+				enter_field_typing_pass ctx ("bind_var_expression",fst ctx.c.curclass.cl_path @ [snd ctx.c.curclass.cl_path;ctx.f.curfield.cf_name]);
 				if (Meta.has (Meta.Custom ":debug.typing") (c.cl_meta @ cf.cf_meta)) then ctx.com.print (Printf.sprintf "Typing field %s.%s\n" (s_type_path c.cl_path) cf.cf_name);
 				let e = type_var_field ctx t e fctx.is_static fctx.is_display_field p in
 				let maybe_run_analyzer e = match e.eexpr with
@@ -880,7 +860,7 @@ module TypeBinding = struct
 							| TConst TThis ->
 								display_error ctx.com "Cannot access this or other member field in variable initialization" e.epos;
 								raise Exit
-							| TLocal v when (match ctx.vthis with Some v2 -> v == v2 | None -> false) ->
+							| TLocal v when (match ctx.f.vthis with Some v2 -> v == v2 | None -> false) ->
 								display_error ctx.com "Cannot access this or other member field in variable initialization" e.epos;
 								raise Exit
 							| _ ->
@@ -1031,7 +1011,7 @@ let create_variable (ctx,cctx,fctx) c f t eo p =
 		add_class_field_flag cf CfImpl;
 	end;
 	if is_abstract_enum_field then add_class_field_flag cf CfEnum;
-	ctx.curfield <- cf;
+	ctx.f.curfield <- cf;
 	TypeBinding.bind_var ctx cctx fctx cf eo;
 	cf
 
@@ -1274,7 +1254,7 @@ let setup_args_ret ctx cctx fctx name fd p =
 		| _ ->
 			None
 	in
-	let is_extern = fctx.is_extern || has_class_flag ctx.curclass CExtern in
+	let is_extern = fctx.is_extern || has_class_flag ctx.c.curclass CExtern in
 	let type_arg i opt cto p =
 		let def () =
 			type_opt (ctx,cctx,fctx) p cto
@@ -1341,7 +1321,7 @@ let create_method (ctx,cctx,fctx) c f fd p =
 			begin match fd.f_type with
 				| None -> ()
 				| Some (CTPath ({ path = {tpackage = []; tname = "Void" } as tp}),p) ->
-					if ctx.is_display_file && DisplayPosition.display_position#enclosed_in p then
+					if ctx.m.is_display_file && DisplayPosition.display_position#enclosed_in p then
 						ignore(load_instance ~allow_display:true ctx (make_ptp tp p) ParamNormal);
 				| _ -> raise_typing_error "A class constructor can't have a return type" p;
 			end
@@ -1386,7 +1366,7 @@ let create_method (ctx,cctx,fctx) c f fd p =
 	| Some p ->
 		begin match ctx.com.platform with
 		| Java ->
-			if not (has_class_flag ctx.curclass CExtern) || not (has_class_flag c CInterface) then invalid_modifier_only ctx.com fctx "default" "on extern interfaces" p;
+			if not (has_class_flag ctx.c.curclass CExtern) || not (has_class_flag c CInterface) then invalid_modifier_only ctx.com fctx "default" "on extern interfaces" p;
 			add_class_field_flag cf CfDefault;
 		| _ ->
 			invalid_modifier_only ctx.com fctx "default" "on the Java target" p
@@ -1428,7 +1408,7 @@ let create_method (ctx,cctx,fctx) c f fd p =
 		()
 	end;
 	init_meta_overloads ctx (Some c) cf;
-	ctx.curfield <- cf;
+	ctx.f.curfield <- cf;
 	if fctx.do_bind then
 		TypeBinding.bind_method ctx cctx fctx cf t args ret fd.f_expr (match fd.f_expr with Some e -> snd e | None -> f.cff_pos)
 	else begin
@@ -1586,7 +1566,7 @@ let create_property (ctx,cctx,fctx) c f (get,set,t,eo) p =
 	cf.cf_kind <- Var { v_read = get; v_write = set };
 	if fctx.is_extern then add_class_field_flag cf CfExtern;
 	if List.mem_assoc AEnum f.cff_access then add_class_field_flag cf CfEnum;
-	ctx.curfield <- cf;
+	ctx.f.curfield <- cf;
 	TypeBinding.bind_var ctx cctx fctx cf eo;
 	cf
 
@@ -1694,7 +1674,7 @@ let check_overloads ctx c =
 	List.iter check_field c.cl_ordered_statics;
 	Option.may check_field c.cl_constructor
 
-let finalize_class ctx cctx =
+let finalize_class cctx =
 	(* push delays in reverse order so they will be run in correct order *)
 	List.iter (fun (ctx,r) ->
 		init_class_done ctx;
@@ -1727,19 +1707,18 @@ let check_functional_interface ctx c =
 		add_class_flag c CFunctionalInterface;
 		ctx.g.functional_interface_lut#add c.cl_path cf
 
-let init_class ctx c p herits fields =
-	let cctx = create_class_context c p in
-	let ctx = create_typer_context_for_class ctx cctx p in
+let init_class ctx_c cctx c p herits fields =
+	let com = ctx_c.com in
 	if cctx.is_class_debug then print_endline ("Created class context: " ^ dump_class_context cctx);
-	let fields = patch_class ctx c fields in
-	let fields = build_fields (ctx,cctx) c fields in
-	if cctx.is_core_api && ctx.com.display.dms_check_core_api then delay ctx PForce (fun() -> init_core_api ctx c);
+	let fields = patch_class ctx_c c fields in
+	let fields = build_fields (ctx_c,cctx) c fields in
+	if cctx.is_core_api && com.display.dms_check_core_api then delay ctx_c PForce (fun() -> init_core_api ctx_c c);
 	if not cctx.is_lib then begin
-		delay ctx PForce (fun() -> check_overloads ctx c);
+		delay ctx_c PForce (fun() -> check_overloads ctx_c c);
 		begin match c.cl_super with
 		| Some(csup,tl) ->
 			if (has_class_flag csup CAbstract) && not (has_class_flag c CAbstract) then
-				delay ctx PForce (fun () -> TypeloadCheck.Inheritance.check_abstract_class ctx c csup tl);
+				delay ctx_c PForce (fun () -> TypeloadCheck.Inheritance.check_abstract_class ctx_c c csup tl);
 		| None ->
 			()
 		end
@@ -1760,7 +1739,7 @@ let init_class ctx c p herits fields =
 						| EBinop ((OpEq|OpNotEq|OpGt|OpGte|OpLt|OpLte) as op,(EConst (Ident s),_),(EConst ((Int (_,_) | Float (_,_) | String _) as c),_)) -> s ^ s_binop op ^ s_constant c
 						| _ -> ""
 					in
-					if not (ParserEntry.is_true (ParserEntry.eval ctx.com.defines e)) then
+					if not (ParserEntry.is_true (ParserEntry.eval com.defines e)) then
 						Some (sc,(match List.rev l with (EConst (String(msg,_)),_) :: _ -> Some msg | _ -> None))
 					else
 						loop l
@@ -1773,10 +1752,10 @@ let init_class ctx c p herits fields =
 	let has_init = ref false in
 	List.iter (fun f ->
 		let p = f.cff_pos in
+		let display_modifier = Typeload.check_field_access ctx_c f in
+		let fctx = create_field_context ctx_c cctx f ctx_c.m.is_display_file display_modifier in
+		let ctx = create_typer_context_for_field ctx_c cctx fctx f in
 		try
-			let display_modifier = Typeload.check_field_access ctx f in
-			let fctx = create_field_context ctx cctx f ctx.is_display_file display_modifier in
-			let ctx = create_typer_context_for_field ctx cctx fctx f in
 			if fctx.is_field_debug then print_endline ("Created field context: " ^ dump_field_context fctx);
 			let cf = init_field (ctx,cctx,fctx) f in
 			if fctx.field_kind = CfrInit then begin
@@ -1842,7 +1821,7 @@ let init_class ctx c p herits fields =
 		with Error ({ err_message = Custom _; err_pos = p2 } as err) when p = p2 ->
 			display_error_ext ctx.com err
 	) fields;
-		begin match cctx.abstract with
+	begin match cctx.abstract with
 		| Some a ->
 			a.a_to_field <- List.rev a.a_to_field;
 			a.a_from_field <- List.rev a.a_from_field;
@@ -1850,11 +1829,11 @@ let init_class ctx c p herits fields =
 			a.a_unops <- List.rev a.a_unops;
 			a.a_array <- List.rev a.a_array;
 		| None ->
-			if (has_class_flag c CInterface) && ctx.com.platform = Java then check_functional_interface ctx c;
+			if (has_class_flag c CInterface) && com.platform = Java then check_functional_interface ctx_c c;
 	end;
 	c.cl_ordered_statics <- List.rev c.cl_ordered_statics;
 	c.cl_ordered_fields <- List.rev c.cl_ordered_fields;
-	delay ctx PConnectField (fun () -> match follow c.cl_type with
+	delay ctx_c PConnectField (fun () -> match follow c.cl_type with
 		| TAnon an ->
 			an.a_fields <- c.cl_statics
 		| _ ->
@@ -1872,28 +1851,28 @@ let init_class ctx c p herits fields =
 	in
 	if has_struct_init then
 		if (has_class_flag c CInterface) then
-			display_error ctx.com "@:structInit is not allowed on interfaces" struct_init_pos
+			display_error com "@:structInit is not allowed on interfaces" struct_init_pos
 		else
-			ensure_struct_init_constructor ctx c fields p;
+			ensure_struct_init_constructor ctx_c c fields p;
 	begin match cctx.uninitialized_final with
 		| cf :: cfl when c.cl_constructor = None && not (has_class_flag c CAbstract) ->
-			if Diagnostics.error_in_diagnostics_run ctx.com cf.cf_name_pos then begin
+			if Diagnostics.error_in_diagnostics_run com cf.cf_name_pos then begin
 				let diag = {
 					mf_pos = c.cl_name_pos;
 					mf_on = TClassDecl c;
 					mf_fields = [];
 					mf_cause = FinalFields (cf :: cfl);
 				} in
-				let display = ctx.com.display_information in
+				let display = com.display_information in
 				display.module_diagnostics <- MissingFields diag :: display.module_diagnostics
 			end else begin
-				display_error ctx.com "This class has uninitialized final vars, which requires a constructor" p;
-				display_error ctx.com "Example of an uninitialized final var" cf.cf_name_pos;
+				display_error com "This class has uninitialized final vars, which requires a constructor" p;
+				display_error com "Example of an uninitialized final var" cf.cf_name_pos;
 			end
 		| _ ->
 			()
 	end;
 	if not has_struct_init then
 		(* add_constructor does not deal with overloads correctly *)
-		if not ctx.com.config.pf_overload then TypeloadFunction.add_constructor ctx c cctx.force_constructor p;
-	finalize_class ctx cctx
+		if not com.config.pf_overload then TypeloadFunction.add_constructor ctx_c c cctx.force_constructor p;
+	finalize_class cctx

+ 27 - 37
src/typing/typeloadFunction.ml

@@ -28,32 +28,25 @@ open Error
 open FunctionArguments
 
 let save_field_state ctx =
-	let old_ret = ctx.ret in
-	let old_fun = ctx.curfun in
-	let old_opened = ctx.opened in
-	let old_monos = ctx.monomorphs.perfunction in
-	let old_in_function = ctx.in_function in
-	let locals = ctx.locals in
+	let old_e = ctx.e in
+	ctx.e <- TyperManager.create_ctx_e ();
+	let locals = ctx.f.locals in
 	(fun () ->
-		ctx.locals <- locals;
-		ctx.ret <- old_ret;
-		ctx.curfun <- old_fun;
-		ctx.opened <- old_opened;
-		ctx.monomorphs.perfunction <- old_monos;
-		ctx.in_function <- old_in_function;
+		ctx.f.locals <- locals;
+		ctx.e <- old_e;
 	)
 
 let type_function_params ctx fd host fname p =
 	Typeload.type_type_params ctx host ([],fname) p fd.f_params
 
 let type_function ctx (args : function_arguments) ret fmode e do_display p =
-	ctx.in_function <- true;
-	ctx.curfun <- fmode;
-	ctx.ret <- ret;
-	ctx.opened <- [];
-	ctx.monomorphs.perfunction <- [];
-	enter_field_typing_pass ctx ("type_function",fst ctx.curclass.cl_path @ [snd ctx.curclass.cl_path;ctx.curfield.cf_name]);
-	args#bring_into_context;
+	ctx.e.in_function <- true;
+	ctx.e.curfun <- fmode;
+	ctx.e.ret <- ret;
+	ctx.e.opened <- [];
+	ctx.e.monomorphs.perfunction <- [];
+	enter_field_typing_pass ctx ("type_function",fst ctx.c.curclass.cl_path @ [snd ctx.c.curclass.cl_path;ctx.f.curfield.cf_name]);
+	args#bring_into_context ctx;
 	let e = match e with
 		| None ->
 			if ignore_error ctx.com then
@@ -63,18 +56,18 @@ let type_function ctx (args : function_arguments) ret fmode e do_display p =
 				*)
 				EBlock [],p
 			else
-				if fmode = FunMember && has_class_flag ctx.curclass CAbstract then
+				if fmode = FunMember && has_class_flag ctx.c.curclass CAbstract then
 					raise_typing_error "Function body or abstract modifier required" p
 				else
 					raise_typing_error "Function body required" p
 		| Some e -> e
 	in
-	let is_position_debug = Meta.has (Meta.Custom ":debug.position") ctx.curfield.cf_meta in
+	let is_position_debug = Meta.has (Meta.Custom ":debug.position") ctx.f.curfield.cf_meta in
 	let e = if not do_display then begin
 		if is_position_debug then print_endline ("syntax:\n" ^ (Expr.dump_with_pos e));
 		type_expr ctx e NoValue
 	end else begin
-		let is_display_debug = Meta.has (Meta.Custom ":debug.display") ctx.curfield.cf_meta in
+		let is_display_debug = Meta.has (Meta.Custom ":debug.display") ctx.f.curfield.cf_meta in
 		if is_display_debug then print_endline ("before processing:\n" ^ (Expr.dump_with_pos e));
 		let e = if !Parser.had_resume then e else Display.preprocess_expr ctx.com e in
 		if is_display_debug then print_endline ("after processing:\n" ^ (Expr.dump_with_pos e));
@@ -110,7 +103,7 @@ let type_function ctx (args : function_arguments) ret fmode e do_display p =
 		| _ -> Type.iter loop e
 	in
 	let has_super_constr() =
-		match ctx.curclass.cl_super with
+		match ctx.c.curclass.cl_super with
 		| None ->
 			None
 		| Some (csup,tl) ->
@@ -141,9 +134,9 @@ let type_function ctx (args : function_arguments) ret fmode e do_display p =
 		| None ->
 			e
 	end in
-	let e = match ctx.curfun, ctx.vthis with
+	let e = match ctx.e.curfun, ctx.f.vthis with
 		| (FunMember|FunConstructor), Some v ->
-			let ev = mk (TVar (v,Some (mk (TConst TThis) ctx.tthis p))) ctx.t.tvoid p in
+			let ev = mk (TVar (v,Some (mk (TConst TThis) ctx.c.tthis p))) ctx.t.tvoid p in
 			(match e.eexpr with
 			| TBlock l ->
 				if ctx.com.config.pf_this_before_super then
@@ -168,8 +161,8 @@ let type_function ctx (args : function_arguments) ret fmode e do_display p =
 			| _ -> mk (TBlock [ev;e]) e.etype p)
 		| _ -> e
 	in
-	List.iter (fun r -> r := Closed) ctx.opened;
-	List.iter (fun (m,p) -> safe_mono_close ctx m p) ctx.monomorphs.perfunction;
+	List.iter (fun r -> r := Closed) ctx.e.opened;
+	List.iter (fun (m,p) -> safe_mono_close ctx m p) ctx.e.monomorphs.perfunction;
 	if is_position_debug then print_endline ("typing:\n" ^ (Texpr.dump_with_pos "" e));
 	e
 
@@ -177,7 +170,7 @@ let type_function ctx args ret fmode e do_display p =
 	let save = save_field_state ctx in
 	Std.finally save (type_function ctx args ret fmode e do_display) p
 
-let add_constructor ctx c force_constructor p =
+let add_constructor ctx_c c force_constructor p =
 	if c.cl_constructor <> None then () else
 	let constructor = try Some (Type.get_constructor_class c (extract_param_types c.cl_params)) with Not_found -> None in
 	match constructor with
@@ -186,12 +179,9 @@ let add_constructor ctx c force_constructor p =
 		cf.cf_kind <- cfsup.cf_kind;
 		cf.cf_params <- cfsup.cf_params;
 		cf.cf_meta <- List.filter (fun (m,_,_) -> m = Meta.CompilerGenerated) cfsup.cf_meta;
-		let t = spawn_monomorph ctx p in
-		let r = make_lazy ctx t (fun r ->
-			let ctx = { ctx with
-				curfield = cf;
-				pass = PConnectField;
-			} in
+		let t = spawn_monomorph ctx_c.e p in
+		let r = make_lazy ctx_c t (fun r ->
+			let ctx = TyperManager.clone_for_field ctx_c cf cf.cf_params in
 			ignore (follow cfsup.cf_type); (* make sure it's typed *)
 			List.iter (fun cf -> ignore (follow cf.cf_type)) cf.cf_overloads;
 			let map_arg (v,def) =
@@ -242,9 +232,9 @@ let add_constructor ctx c force_constructor p =
 	| _ when force_constructor ->
 		let constr = mk (TFunction {
 			tf_args = [];
-			tf_type = ctx.t.tvoid;
-			tf_expr = mk (TBlock []) ctx.t.tvoid p;
-		}) (tfun [] ctx.t.tvoid) p in
+			tf_type = ctx_c.t.tvoid;
+			tf_expr = mk (TBlock []) ctx_c.t.tvoid p;
+		}) (tfun [] ctx_c.t.tvoid) p in
 		let cf = mk_field "new" constr.etype p null_pos in
 		cf.cf_expr <- Some constr;
 		cf.cf_type <- constr.etype;

+ 121 - 157
src/typing/typeloadModule.ml

@@ -44,30 +44,30 @@ let field_of_static_definition d p =
 	}
 
 module ModuleLevel = struct
-	let make_module ctx mpath file loadp =
+	let make_module com g mpath file loadp =
 		let m = {
 			m_id = alloc_mid();
 			m_path = mpath;
 			m_types = [];
 			m_statics = None;
-			m_extra = module_extra (Path.get_full_path file) (Define.get_signature ctx.com.defines) (file_time file) (if ctx.com.is_macro_context then MMacro else MCode) ctx.com.compilation_step (get_policy ctx.g mpath);
+			m_extra = module_extra (Path.get_full_path file) (Define.get_signature com.defines) (file_time file) (if com.is_macro_context then MMacro else MCode) com.compilation_step (get_policy g mpath);
 		} in
 		m
 
-	let add_module ctx m p =
-		ctx.com.module_lut#add m.m_path m
+	let add_module com m p =
+		com.module_lut#add m.m_path m
 
 	(*
 		Build module structure : should be atomic - no type loading is possible
 	*)
-	let create_module_types ctx m tdecls loadp =
-		let com = ctx.com in
+	let create_module_types ctx_m m tdecls loadp =
+		let com = ctx_m.com in
 		let decls = ref [] in
 		let statics = ref [] in
 		let check_name name meta also_statics p =
-			DeprecationCheck.check_is com ctx.m.curmod meta [] name meta p;
+			DeprecationCheck.check_is com ctx_m.m.curmod meta [] name meta p;
 			let error prev_pos =
-				display_error ctx.com ("Name " ^ name ^ " is already defined in this module") p;
+				display_error com ("Name " ^ name ^ " is already defined in this module") p;
 				raise_typing_error ~depth:1 (compl_msg "Previous declaration here") prev_pos;
 			in
 			List.iter (fun (t2,(_,p2)) ->
@@ -87,7 +87,7 @@ module ModuleLevel = struct
 			let p = snd decl in
 			let check_type_name type_name meta =
 				let module_name = snd m.m_path in
-				if type_name <> module_name && not (Meta.has Meta.Native meta) then Typecore.check_uppercase_identifier_name ctx type_name "type" p;
+				if type_name <> module_name && not (Meta.has Meta.Native meta) then Typecore.check_uppercase_identifier_name ctx_m type_name "type" p;
 			in
 			let acc = (match fst decl with
 			| EImport _ | EUsing _ ->
@@ -119,8 +119,8 @@ module ModuleLevel = struct
 				) d.d_flags;
 				if not (has_class_flag c CExtern) then check_type_name name d.d_meta;
 				if has_class_flag c CAbstract then begin
-					if has_class_flag c CInterface then display_error ctx.com "An interface may not be abstract" c.cl_name_pos;
-					if has_class_flag c CFinal then display_error ctx.com "An abstract class may not be final" c.cl_name_pos;
+					if has_class_flag c CInterface then display_error com "An interface may not be abstract" c.cl_name_pos;
+					if has_class_flag c CFinal then display_error com "An abstract class may not be final" c.cl_name_pos;
 				end;
 				decls := (TClassDecl c, decl) :: !decls;
 				acc
@@ -152,7 +152,7 @@ module ModuleLevel = struct
 					t_meta = d.d_meta;
 				} in
 				(* failsafe in case the typedef is not initialized (see #3933) *)
-				delay ctx PBuildModule (fun () ->
+				delay ctx_m PBuildModule (fun () ->
 					match t.t_type with
 					| TMono r -> (match r.tm_type with None -> Monomorph.bind r com.basic.tvoid | _ -> ())
 					| _ -> ()
@@ -195,7 +195,7 @@ module ModuleLevel = struct
 					| None -> ()
 					| Some p ->
 						let options = Warning.from_meta d.d_meta in
-						module_warning ctx.com ctx.m.curmod WDeprecatedEnumAbstract options "`@:enum abstract` is deprecated in favor of `enum abstract`" p
+						module_warning com ctx_m.m.curmod WDeprecatedEnumAbstract options "`@:enum abstract` is deprecated in favor of `enum abstract`" p
 				end;
 				decls := (TAbstractDecl a, decl) :: !decls;
 				match d.d_data with
@@ -267,8 +267,7 @@ module ModuleLevel = struct
 		let decls = List.rev !decls in
 		decls, List.rev tdecls
 
-	let handle_import_hx ctx m decls p =
-		let com = ctx.com in
+	let handle_import_hx com g m decls p =
 		let path_split = match List.rev (Path.get_path_parts (Path.UniqueKey.lazy_path m.m_extra.m_file)) with
 			| [] -> []
 			| _ :: l -> l
@@ -283,7 +282,7 @@ module ModuleLevel = struct
 		let make_import_module path r =
 			com.parser_cache#add path r;
 			(* We use the file path as module name to make it unique. This may or may not be a good idea... *)
-			let m_import = make_module ctx ([],path) path p in
+			let m_import = make_module com g ([],path) path p in
 			m_import.m_extra.m_kind <- MImport;
 			m_import
 		in
@@ -295,13 +294,13 @@ module ModuleLevel = struct
 				r
 			with Not_found ->
 				if Sys.file_exists path then begin
-					let _,r = match !TypeloadParse.parse_hook com (ClassPaths.create_resolved_file path ctx.com.empty_class_path) p with
+					let _,r = match !TypeloadParse.parse_hook com (ClassPaths.create_resolved_file path com.empty_class_path) p with
 						| ParseSuccess(data,_,_) -> data
 						| ParseError(_,(msg,p),_) -> Parser.error msg p
 					in
 					List.iter (fun (d,p) -> match d with EImport _ | EUsing _ -> () | _ -> raise_typing_error "Only import and using is allowed in import.hx files" p) r;
 					let m_import = make_import_module path r in
-					add_module ctx m_import p;
+					add_module com m_import p;
 					add_dependency m m_import;
 					r
 				end else begin
@@ -314,39 +313,39 @@ module ModuleLevel = struct
 			decls @ acc
 		) decls candidates
 
-	let init_type_params ctx decls =
+	let init_type_params ctx_m decls =
 		(* here is an additional PASS 1 phase, which define the type parameters for all module types.
 		 Constraints are handled lazily (no other type is loaded) because they might be recursive anyway *)
 		 List.iter (fun d ->
 			match d with
 			| (TClassDecl c, (EClass d, p)) ->
-				c.cl_params <- type_type_params ctx TPHType c.cl_path p d.d_params;
+				c.cl_params <- type_type_params ctx_m TPHType c.cl_path p d.d_params;
 				if Meta.has Meta.Generic c.cl_meta && c.cl_params <> [] then c.cl_kind <- KGeneric;
 				if Meta.has Meta.GenericBuild c.cl_meta then begin
-					if ctx.com.is_macro_context then raise_typing_error "@:genericBuild cannot be used in macros" c.cl_pos;
+					if ctx_m.com.is_macro_context then raise_typing_error "@:genericBuild cannot be used in macros" c.cl_pos;
 					c.cl_kind <- KGenericBuild d.d_data;
 				end;
 				if c.cl_path = (["haxe";"macro"],"MacroType") then c.cl_kind <- KMacroType;
 			| (TEnumDecl e, (EEnum d, p)) ->
-				e.e_params <- type_type_params ctx TPHType e.e_path p d.d_params;
+				e.e_params <- type_type_params ctx_m TPHType e.e_path p d.d_params;
 			| (TTypeDecl t, (ETypedef d, p)) ->
-				t.t_params <- type_type_params ctx TPHType t.t_path p d.d_params;
+				t.t_params <- type_type_params ctx_m TPHType t.t_path p d.d_params;
 			| (TAbstractDecl a, (EAbstract d, p)) ->
-				a.a_params <- type_type_params ctx TPHType a.a_path p d.d_params;
+				a.a_params <- type_type_params ctx_m TPHType a.a_path p d.d_params;
 			| _ ->
 				die "" __LOC__
 		) decls
 end
 
 module TypeLevel = struct
-	let load_enum_field ctx e et is_flat index c =
+	let load_enum_field ctx_en e et is_flat index c =
 		let p = c.ec_pos in
-		let params = type_type_params ctx TPHEnumConstructor ([],fst c.ec_name) c.ec_pos c.ec_params in
-		let ctx = { ctx with type_params = params @ ctx.type_params } in
+		let params = type_type_params ctx_en TPHEnumConstructor ([],fst c.ec_name) c.ec_pos c.ec_params in
+		let ctx_ef = TyperManager.clone_for_enum_field ctx_en (params @ ctx_en.type_params) in
 		let rt = (match c.ec_type with
 			| None -> et
 			| Some (t,pt) ->
-				let t = load_complex_type ctx true (t,pt) in
+				let t = load_complex_type ctx_ef true (t,pt) in
 				(match follow t with
 				| TEnum (te,_) when te == e ->
 					()
@@ -363,7 +362,7 @@ module TypeLevel = struct
 					(match t with CTPath({path = {tpackage=[];tname="Void"}}) -> raise_typing_error "Arguments of type Void are not allowed in enum constructors" tp | _ -> ());
 					if PMap.mem s (!pnames) then raise_typing_error ("Duplicate argument `" ^ s ^ "` in enum constructor " ^ fst c.ec_name) p;
 					pnames := PMap.add s () (!pnames);
-					s, opt, load_type_hint ~opt ctx p (Some (t,tp))
+					s, opt, load_type_hint ~opt ctx_ef p (Some (t,tp))
 				) l, rt)
 		) in
 		let f = {
@@ -376,44 +375,46 @@ module TypeLevel = struct
 			ef_params = params;
 			ef_meta = c.ec_meta;
 		} in
-		DeprecationCheck.check_is ctx.com ctx.m.curmod e.e_meta f.ef_meta f.ef_name f.ef_meta f.ef_name_pos;
-		if ctx.is_display_file && DisplayPosition.display_position#enclosed_in f.ef_name_pos then
-			DisplayEmitter.display_enum_field ctx e f p;
+		DeprecationCheck.check_is ctx_ef.com ctx_ef.m.curmod e.e_meta f.ef_meta f.ef_name f.ef_meta f.ef_name_pos;
+		if ctx_ef.m.is_display_file && DisplayPosition.display_position#enclosed_in f.ef_name_pos then
+			DisplayEmitter.display_enum_field ctx_ef e f p;
 		f
 
-	let init_class ctx c d p =
-		if ctx.is_display_file && DisplayPosition.display_position#enclosed_in (pos d.d_name) then
-			DisplayEmitter.display_module_type ctx (match c.cl_kind with KAbstractImpl a -> TAbstractDecl a | _ -> TClassDecl c) (pos d.d_name);
-		TypeloadCheck.check_global_metadata ctx c.cl_meta (fun m -> c.cl_meta <- m :: c.cl_meta) c.cl_module.m_path c.cl_path None;
+	let init_class ctx_m c d p =
+		if ctx_m.m.is_display_file && DisplayPosition.display_position#enclosed_in (pos d.d_name) then
+			DisplayEmitter.display_module_type ctx_m (match c.cl_kind with KAbstractImpl a -> TAbstractDecl a | _ -> TClassDecl c) (pos d.d_name);
+		TypeloadCheck.check_global_metadata ctx_m c.cl_meta (fun m -> c.cl_meta <- m :: c.cl_meta) c.cl_module.m_path c.cl_path None;
 		let herits = d.d_flags in
 		List.iter (fun (m,_,p) ->
 			if m = Meta.Final then begin
 				add_class_flag c CFinal;
 			end
 		) d.d_meta;
-		let prev_build_count = ref (ctx.g.build_count - 1) in
+		let prev_build_count = ref (ctx_m.g.build_count - 1) in
 		let build() =
 			c.cl_build <- (fun()-> Building [c]);
-			let fl = TypeloadCheck.Inheritance.set_heritance ctx c herits p in
+			let cctx = TypeloadFields.create_class_context c p in
+			let ctx_c = TypeloadFields.create_typer_context_for_class ctx_m cctx p in
+			let fl = TypeloadCheck.Inheritance.set_heritance ctx_c c herits p in
 			let rec build() =
 				c.cl_build <- (fun()-> Building [c]);
 				try
 					List.iter (fun f -> f()) fl;
-					TypeloadFields.init_class ctx c p d.d_flags d.d_data;
+					TypeloadFields.init_class ctx_c cctx c p d.d_flags d.d_data;
 					c.cl_build <- (fun()-> Built);
-					ctx.g.build_count <- ctx.g.build_count + 1;
+					ctx_c.g.build_count <- ctx_c.g.build_count + 1;
 					List.iter (fun tp -> ignore(follow tp.ttp_type)) c.cl_params;
 					Built;
 				with TypeloadCheck.Build_canceled state ->
-					c.cl_build <- make_pass ctx build;
+					c.cl_build <- make_pass ctx_c build;
 					let rebuild() =
-						delay_late ctx PBuildClass (fun() -> ignore(c.cl_build()));
+						delay_late ctx_c PBuildClass (fun() -> ignore(c.cl_build()));
 					in
 					(match state with
 					| Built -> die "" __LOC__
 					| Building cl ->
-						if ctx.g.build_count = !prev_build_count then raise_typing_error ("Loop in class building prevent compiler termination (" ^ String.concat "," (List.map (fun c -> s_type_path c.cl_path) cl) ^ ")") c.cl_pos;
-						prev_build_count := ctx.g.build_count;
+						if ctx_c.g.build_count = !prev_build_count then raise_typing_error ("Loop in class building prevent compiler termination (" ^ String.concat "," (List.map (fun c -> s_type_path c.cl_path) cl) ^ ")") c.cl_pos;
+						prev_build_count := ctx_c.g.build_count;
 						rebuild();
 						Building (c :: cl)
 					| BuildMacro f ->
@@ -425,18 +426,16 @@ module TypeLevel = struct
 			in
 			build()
 		in
-		ctx.curclass <- c;
-		c.cl_build <- make_pass ctx build;
-		ctx.curclass <- null_class;
-		delay ctx PBuildClass (fun() -> ignore(c.cl_build()));
+		c.cl_build <- make_pass ctx_m build;
+		delay ctx_m PBuildClass (fun() -> ignore(c.cl_build()));
 		if Meta.has Meta.InheritDoc c.cl_meta then
-				delay ctx PConnectField (fun() -> InheritDoc.build_class_doc ctx c);
-		if (ctx.com.platform = Java || ctx.com.platform = Cs) && not (has_class_flag c CExtern) then
-			delay ctx PTypeField (fun () ->
-				let metas = StrictMeta.check_strict_meta ctx c.cl_meta in
+			delay ctx_m PConnectField (fun() -> InheritDoc.build_class_doc ctx_m c);
+		if (ctx_m.com.platform = Java || ctx_m.com.platform = Cs) && not (has_class_flag c CExtern) then
+			delay ctx_m PTypeField (fun () ->
+				let metas = StrictMeta.check_strict_meta ctx_m c.cl_meta in
 				if metas <> [] then c.cl_meta <- metas @ c.cl_meta;
 				let rec run_field cf =
-					let metas = StrictMeta.check_strict_meta ctx cf.cf_meta in
+					let metas = StrictMeta.check_strict_meta ctx_m cf.cf_meta in
 					if metas <> [] then cf.cf_meta <- metas @ cf.cf_meta;
 					List.iter run_field cf.cf_overloads
 				in
@@ -447,12 +446,12 @@ module TypeLevel = struct
 					| _ -> ()
 			)
 
-	let init_enum ctx e d p =
-		if ctx.is_display_file && DisplayPosition.display_position#enclosed_in (pos d.d_name) then
-			DisplayEmitter.display_module_type ctx (TEnumDecl e) (pos d.d_name);
-		let ctx = { ctx with type_params = e.e_params } in
-		let h = (try Some (Hashtbl.find ctx.g.type_patches e.e_path) with Not_found -> None) in
-		TypeloadCheck.check_global_metadata ctx e.e_meta (fun m -> e.e_meta <- m :: e.e_meta) e.e_module.m_path e.e_path None;
+	let init_enum ctx_m e d p =
+		if ctx_m.m.is_display_file && DisplayPosition.display_position#enclosed_in (pos d.d_name) then
+			DisplayEmitter.display_module_type ctx_m (TEnumDecl e) (pos d.d_name);
+		let ctx_en = TyperManager.clone_for_enum ctx_m e in
+		let h = (try Some (Hashtbl.find ctx_en.g.type_patches e.e_path) with Not_found -> None) in
+		TypeloadCheck.check_global_metadata ctx_en e.e_meta (fun m -> e.e_meta <- m :: e.e_meta) e.e_module.m_path e.e_path None;
 		(match h with
 		| None -> ()
 		| Some (h,hcl) ->
@@ -473,7 +472,7 @@ module TypeLevel = struct
 				}
 			) (!constructs)
 		in
-		TypeloadFields.build_module_def ctx (TEnumDecl e) e.e_meta get_constructs (fun (e,p) ->
+		TypeloadFields.build_module_def ctx_en (TEnumDecl e) e.e_meta get_constructs (fun (e,p) ->
 			match e with
 			| EVars [{ ev_type = Some (CTAnonymous fields,p); ev_expr = None }] ->
 				constructs := List.map (fun f ->
@@ -503,35 +502,35 @@ module TypeLevel = struct
 		let is_flat = ref true in
 		List.iter (fun c ->
 			if PMap.mem (fst c.ec_name) e.e_constrs then raise_typing_error ("Duplicate constructor " ^ fst c.ec_name) (pos c.ec_name);
-			let f = load_enum_field ctx e et is_flat index c in
+			let f = load_enum_field ctx_en e et is_flat index c in
 			e.e_constrs <- PMap.add f.ef_name f e.e_constrs;
 			incr index;
 			names := (fst c.ec_name) :: !names;
 			if Meta.has Meta.InheritDoc f.ef_meta then
-				delay ctx PConnectField (fun() -> InheritDoc.build_enum_field_doc ctx f);
+				delay ctx_en PConnectField (fun() -> InheritDoc.build_enum_field_doc ctx_en f);
 		) (!constructs);
 		e.e_names <- List.rev !names;
 		e.e_extern <- e.e_extern;
-		unify ctx (TType(enum_module_type e,[])) e.e_type p;
+		unify ctx_en (TType(enum_module_type e,[])) e.e_type p;
 		if !is_flat then e.e_meta <- (Meta.FlatEnum,[],null_pos) :: e.e_meta;
 		if Meta.has Meta.InheritDoc e.e_meta then
-			delay ctx PConnectField (fun() -> InheritDoc.build_enum_doc ctx e);
-		if (ctx.com.platform = Java || ctx.com.platform = Cs) && not e.e_extern then
-			delay ctx PTypeField (fun () ->
-				let metas = StrictMeta.check_strict_meta ctx e.e_meta in
+			delay ctx_en PConnectField (fun() -> InheritDoc.build_enum_doc ctx_en e);
+		if (ctx_en.com.platform = Java || ctx_en.com.platform = Cs) && not e.e_extern then
+			delay ctx_en PTypeField (fun () ->
+				let metas = StrictMeta.check_strict_meta ctx_en e.e_meta in
 				e.e_meta <- metas @ e.e_meta;
 				PMap.iter (fun _ ef ->
-					let metas = StrictMeta.check_strict_meta ctx ef.ef_meta in
+					let metas = StrictMeta.check_strict_meta ctx_en ef.ef_meta in
 					if metas <> [] then ef.ef_meta <- metas @ ef.ef_meta
 				) e.e_constrs
 			)
 
-	let init_typedef ctx t d p =
-		if ctx.is_display_file && DisplayPosition.display_position#enclosed_in (pos d.d_name) then
-			DisplayEmitter.display_module_type ctx (TTypeDecl t) (pos d.d_name);
-		TypeloadCheck.check_global_metadata ctx t.t_meta (fun m -> t.t_meta <- m :: t.t_meta) t.t_module.m_path t.t_path None;
-		let ctx = { ctx with type_params = t.t_params } in
-		let tt = load_complex_type ctx true d.d_data in
+	let init_typedef ctx_m t d p =
+		if ctx_m.m.is_display_file && DisplayPosition.display_position#enclosed_in (pos d.d_name) then
+			DisplayEmitter.display_module_type ctx_m (TTypeDecl t) (pos d.d_name);
+		TypeloadCheck.check_global_metadata ctx_m t.t_meta (fun m -> t.t_meta <- m :: t.t_meta) t.t_module.m_path t.t_path None;
+		let ctx_td = TyperManager.clone_for_typedef ctx_m t in
+		let tt = load_complex_type ctx_td true d.d_data in
 		let tt = (match fst d.d_data with
 		| CTExtend _ -> tt
 		| CTPath { path = {tpackage = ["haxe";"macro"]; tname = "MacroType" }} ->
@@ -557,7 +556,7 @@ module TypeLevel = struct
 					| _ ->
 						()
 				in
-				let r = make_lazy ctx tt (fun r ->
+				let r = make_lazy ctx_td tt (fun r ->
 					check_rec tt;
 					tt
 				) "typedef_rec_check" in
@@ -570,25 +569,25 @@ module TypeLevel = struct
 			| None -> Monomorph.bind r tt;
 			| Some t' -> die (Printf.sprintf "typedef %s is already initialized to %s, but new init to %s was attempted" (s_type_path t.t_path) (s_type_kind t') (s_type_kind tt)) __LOC__);
 		| _ -> die "" __LOC__);
-		TypeloadFields.build_module_def ctx (TTypeDecl t) t.t_meta (fun _ -> []) (fun _ -> ());
-		if ctx.com.platform = Cs && t.t_meta <> [] then
-			delay ctx PTypeField (fun () ->
-				let metas = StrictMeta.check_strict_meta ctx t.t_meta in
+		TypeloadFields.build_module_def ctx_td (TTypeDecl t) t.t_meta (fun _ -> []) (fun _ -> ());
+		if ctx_td.com.platform = Cs && t.t_meta <> [] then
+			delay ctx_td PTypeField (fun () ->
+				let metas = StrictMeta.check_strict_meta ctx_td t.t_meta in
 				if metas <> [] then t.t_meta <- metas @ t.t_meta;
 			)
 
-	let init_abstract ctx a d p =
-		if ctx.is_display_file && DisplayPosition.display_position#enclosed_in (pos d.d_name) then
-			DisplayEmitter.display_module_type ctx (TAbstractDecl a) (pos d.d_name);
-		TypeloadCheck.check_global_metadata ctx a.a_meta (fun m -> a.a_meta <- m :: a.a_meta) a.a_module.m_path a.a_path None;
-		let ctx = { ctx with type_params = a.a_params } in
+	let init_abstract ctx_m a d p =
+		if ctx_m.m.is_display_file && DisplayPosition.display_position#enclosed_in (pos d.d_name) then
+			DisplayEmitter.display_module_type ctx_m (TAbstractDecl a) (pos d.d_name);
+		TypeloadCheck.check_global_metadata ctx_m a.a_meta (fun m -> a.a_meta <- m :: a.a_meta) a.a_module.m_path a.a_path None;
+		let ctx_a = TyperManager.clone_for_abstract ctx_m a in
 		let is_type = ref false in
 		let load_type t from =
 			let _, pos = t in
-			let t = load_complex_type ctx true t in
+			let t = load_complex_type ctx_a true t in
 			let t = if not (Meta.has Meta.CoreType a.a_meta) then begin
 				if !is_type then begin
-					let r = make_lazy ctx t (fun r ->
+					let r = make_lazy ctx_a t (fun r ->
 						(try (if from then Type.unify t a.a_this else Type.unify a.a_this t) with Unify_error _ -> raise_typing_error "You can only declare from/to with compatible types" pos);
 						t
 					) "constraint" in
@@ -608,8 +607,8 @@ module TypeLevel = struct
 			| AbOver t ->
 				if a.a_impl = None then raise_typing_error "Abstracts with underlying type must have an implementation" a.a_pos;
 				if Meta.has Meta.CoreType a.a_meta then raise_typing_error "@:coreType abstracts cannot have an underlying type" p;
-				let at = load_complex_type ctx true t in
-				delay ctx PForce (fun () ->
+				let at = load_complex_type ctx_a true t in
+				delay ctx_a PForce (fun () ->
 					let rec loop stack t =
 						match follow t with
 						| TAbstract(a,_) when not (Meta.has Meta.CoreType a.a_meta) ->
@@ -636,54 +635,55 @@ module TypeLevel = struct
 				raise_typing_error "Abstract is missing underlying type declaration" a.a_pos
 		end;
 		if Meta.has Meta.InheritDoc a.a_meta then
-			delay ctx PConnectField (fun() -> InheritDoc.build_abstract_doc ctx a)
+			delay ctx_a PConnectField (fun() -> InheritDoc.build_abstract_doc ctx_a a)
 
 	(*
 		In this pass, we can access load and access other modules types, but we cannot follow them or access their structure
 		since they have not been setup. We also build a list that will be evaluated the first time we evaluate
 		an expression into the context
 	*)
-	let init_module_type ctx (decl,p) =
+	let init_module_type ctx_m (decl,p) =
+		let com = ctx_m.com in
 		let get_type name =
-			try List.find (fun t -> snd (t_infos t).mt_path = name) ctx.m.curmod.m_types with Not_found -> die "" __LOC__
+			try List.find (fun t -> snd (t_infos t).mt_path = name) ctx_m.m.curmod.m_types with Not_found -> die "" __LOC__
 		in
 		let check_path_display path p =
-			if DisplayPosition.display_position#is_in_file (ctx.com.file_keys#get p.pfile) then DisplayPath.handle_path_display ctx path p
+			if DisplayPosition.display_position#is_in_file (com.file_keys#get p.pfile) then DisplayPath.handle_path_display ctx_m path p
 			in
 		match decl with
 		| EImport (path,mode) ->
 			begin try
 				check_path_display path p;
-				ImportHandling.init_import ctx path mode p;
-				ImportHandling.commit_import ctx path mode p;
+				ImportHandling.init_import ctx_m path mode p;
+				ImportHandling.commit_import ctx_m path mode p;
 			with Error err ->
-				display_error_ext ctx.com err
+				display_error_ext com err
 			end
 		| EUsing path ->
 			check_path_display path p;
-			ImportHandling.init_using ctx path p
+			ImportHandling.init_using ctx_m path p
 		| EClass d ->
 			let c = (match get_type (fst d.d_name) with TClassDecl c -> c | _ -> die "" __LOC__) in
-			init_class ctx c d p
+			init_class ctx_m c d p
 		| EEnum d ->
 			let e = (match get_type (fst d.d_name) with TEnumDecl e -> e | _ -> die "" __LOC__) in
-			init_enum ctx e d p
+			init_enum ctx_m e d p
 		| ETypedef d ->
 			let t = (match get_type (fst d.d_name) with TTypeDecl t -> t | _ -> die "" __LOC__) in
-			init_typedef ctx t d p
+			init_typedef ctx_m t d p
 		| EAbstract d ->
 			let a = (match get_type (fst d.d_name) with TAbstractDecl a -> a | _ -> die "" __LOC__) in
-			init_abstract ctx a d p
+			init_abstract ctx_m a d p
 		| EStatic _ ->
 			(* nothing to do here as module fields are collected into a special EClass *)
 			()
 end
 
-let make_curmod ctx m =
+let make_curmod com g m =
 	let rl = new resolution_list ["import";s_type_path m.m_path] in
 	List.iter (fun mt ->
 		rl#add (module_type_resolution mt None null_pos))
-	(List.rev ctx.g.std_types.m_types);
+	(List.rev g.std_types.m_types);
 	{
 		curmod = m;
 		import_resolution = rl;
@@ -691,79 +691,43 @@ let make_curmod ctx m =
 		enum_with_type = None;
 		module_using = [];
 		import_statements = [];
-	}
-
-let create_typer_context_for_module ctx m = {
-		com = ctx.com;
-		g = ctx.g;
-		t = ctx.com.basic;
-		m = make_curmod ctx m;
-		is_display_file = (ctx.com.display.dms_kind <> DMNone && DisplayPosition.display_position#is_in_file (Path.UniqueKey.lazy_key m.m_extra.m_file));
-		bypass_accessor = 0;
-		meta = [];
-		with_type_stack = [];
-		call_argument_stack = [];
-		pass = PBuildModule;
-		get_build_infos = (fun() -> None);
-		macro_depth = 0;
-		curclass = null_class;
-		allow_inline = true;
-		allow_transform = true;
-		curfield = null_field;
-		tthis = mk_mono();
-		ret = mk_mono();
-		locals = PMap.empty;
-		type_params = [];
-		curfun = FunStatic;
-		untyped = false;
-		in_display = false;
-		in_function = false;
-		in_loop = false;
-		opened = [];
-		in_call_args = false;
-		in_overload_call_args = false;
-		delayed_display = None;
-		monomorphs = {
-			perfunction = [];
-		};
-		vthis = None;
-		memory_marker = Typecore.memory_marker;
+		is_display_file = (com.display.dms_kind <> DMNone && DisplayPosition.display_position#is_in_file (Path.UniqueKey.lazy_key m.m_extra.m_file));
 	}
 
 (*
 	Creates a module context for [m] and types [tdecls] using it.
 *)
-let type_types_into_module ctx m tdecls p =
-	let ctx = create_typer_context_for_module ctx m in
-	let decls,tdecls = ModuleLevel.create_module_types ctx m tdecls p in
+let type_types_into_module com g m tdecls p =
+	let ctx_m = TyperManager.create_for_module com g (make_curmod com g m) in
+	let decls,tdecls = ModuleLevel.create_module_types ctx_m m tdecls p in
 	let types = List.map fst decls in
 	(* During the initial module_lut#add in type_module, m has no m_types yet by design.
 	   We manually add them here. This and module_lut#add itself should be the only places
 	   in the compiler that call add_module_type. *)
-	List.iter (fun mt -> ctx.com.module_lut#add_module_type m mt) types;
+	List.iter (fun mt -> ctx_m.com.module_lut#add_module_type m mt) types;
 	m.m_types <- m.m_types @ types;
 	(* define the per-module context for the next pass *)
-	if ctx.g.std_types != null_module then begin
-		add_dependency m ctx.g.std_types;
+	if ctx_m.g.std_types != null_module then begin
+		add_dependency m ctx_m.g.std_types;
 		(* this will ensure both String and (indirectly) Array which are basic types which might be referenced *)
-		ignore(load_instance ctx (make_ptp (mk_type_path (["std"],"String")) null_pos) ParamNormal)
+		ignore(load_instance ctx_m (make_ptp (mk_type_path (["std"],"String")) null_pos) ParamNormal)
 	end;
-	ModuleLevel.init_type_params ctx decls;
+	ModuleLevel.init_type_params ctx_m decls;
 	(* setup module types *)
-	List.iter (TypeLevel.init_module_type ctx) tdecls;
+	List.iter (TypeLevel.init_module_type ctx_m) tdecls;
 	(* Make sure that we actually init the context at some point (issue #9012) *)
-	delay ctx PConnectField (fun () -> ctx.m.import_resolution#resolve_lazies);
-	ctx
+	delay ctx_m PConnectField (fun () -> ctx_m.m.import_resolution#resolve_lazies);
+	ctx_m
 
 (*
 	Creates a new module and types [tdecls] into it.
 *)
-let type_module ctx mpath file ?(dont_check_path=false) ?(is_extern=false) tdecls p =
-	let m = ModuleLevel.make_module ctx mpath file p in
-	ctx.com.module_lut#add m.m_path m;
-	let tdecls = ModuleLevel.handle_import_hx ctx m tdecls p in
-	let ctx = type_types_into_module ctx m tdecls p in
-	if is_extern then m.m_extra.m_kind <- MExtern else if not dont_check_path then Typecore.check_module_path ctx m.m_path p;
+let type_module ctx_from mpath file ?(dont_check_path=false) ?(is_extern=false) tdecls p =
+	let m = ModuleLevel.make_module ctx_from.com ctx_from.g mpath file p in
+	ctx_from.com.module_lut#add m.m_path m;
+	let tdecls = ModuleLevel.handle_import_hx ctx_from.com ctx_from.g m tdecls p in
+	let ctx_m = type_types_into_module ctx_from.com ctx_from.g m tdecls p in
+	if is_extern then m.m_extra.m_kind <- MExtern else if not dont_check_path then Typecore.check_module_path ctx_m m.m_path p;
 	m
 
 (* let type_module ctx mpath file ?(is_extern=false) tdecls p =
@@ -778,7 +742,7 @@ class hxb_reader_api_typeload
 	(p : pos)
 = object(self)
 	method make_module (path : path) (file : string) =
-		let m = ModuleLevel.make_module ctx path file p in
+		let m = ModuleLevel.make_module ctx.com ctx.g path file p in
 		m.m_extra.m_processed <- 1;
 		m
 

+ 88 - 88
src/typing/typer.ml

@@ -40,7 +40,7 @@ let mono_or_dynamic ctx with_type p = match with_type with
 	| WithType.NoValue ->
 		t_dynamic
 	| Value _ | WithType _ ->
-		spawn_monomorph ctx p
+		spawn_monomorph ctx.e p
 
 let get_iterator_param t =
 	match follow t with
@@ -144,7 +144,7 @@ let maybe_type_against_enum ctx f with_type iscall p =
 let rec unify_min_raise ctx (el:texpr list) : t =
 	let basic = ctx.com.basic in
 	match el with
-	| [] -> spawn_monomorph ctx null_pos
+	| [] -> spawn_monomorph ctx.e null_pos
 	| [e] -> e.etype
 	| _ ->
 		let rec chk_null e = is_null e.etype || is_explicit_null e.etype ||
@@ -172,7 +172,7 @@ let rec unify_min_raise ctx (el:texpr list) : t =
 				with Unify_error _ ->
 					true, t
 		in
-		let has_error, t = loop (spawn_monomorph ctx null_pos) el in
+		let has_error, t = loop (spawn_monomorph ctx.e null_pos) el in
 		if not has_error then
 			t
 		else try
@@ -263,7 +263,7 @@ let rec unify_min_raise ctx (el:texpr list) : t =
 let unify_min ctx el =
 	try unify_min_raise ctx el
 	with Error ({ err_message = Unify l } as err) ->
-		if not ctx.untyped then display_error_ext ctx.com err;
+		if not ctx.f.untyped then display_error_ext ctx.com err;
 		(List.hd el).etype
 
 let unify_min_for_type_source ctx el src =
@@ -350,8 +350,8 @@ let rec type_ident_raise ctx i p mode with_type =
 		let acc = AKExpr(get_this ctx p) in
 		begin match mode with
 		| MSet _ ->
-			add_class_field_flag ctx.curfield CfModifiesThis;
-			begin match ctx.curclass.cl_kind with
+			add_class_field_flag ctx.f.curfield CfModifiesThis;
+			begin match ctx.c.curclass.cl_kind with
 			| KAbstractImpl _ ->
 				if not (assign_to_this_is_allowed ctx) then
 					raise_typing_error "Abstract 'this' value can only be modified inside an inline function" p;
@@ -360,7 +360,7 @@ let rec type_ident_raise ctx i p mode with_type =
 				AKNo(acc,p)
 			end
 		| MCall _ ->
-			begin match ctx.curclass.cl_kind with
+			begin match ctx.c.curclass.cl_kind with
 			| KAbstractImpl _ ->
 				acc
 			| _ ->
@@ -370,7 +370,7 @@ let rec type_ident_raise ctx i p mode with_type =
 			acc
 		end;
 	| "abstract" ->
-		begin match mode, ctx.curclass.cl_kind with
+		begin match mode, ctx.c.curclass.cl_kind with
 			| MSet _, KAbstractImpl ab -> raise_typing_error "Property 'abstract' is read-only" p;
 			| (MGet, KAbstractImpl ab)
 			| (MCall _, KAbstractImpl ab) ->
@@ -382,11 +382,11 @@ let rec type_ident_raise ctx i p mode with_type =
 				raise_typing_error "Property 'abstract' is reserved and only available in abstracts" p
 		end
 	| "super" ->
-		let t = (match ctx.curclass.cl_super with
+		let t = (match ctx.c.curclass.cl_super with
 			| None -> raise_typing_error "Current class does not have a superclass" p
 			| Some (c,params) -> TInst(c,params)
 		) in
-		(match ctx.curfun with
+		(match ctx.e.curfun with
 		| FunMember | FunConstructor -> ()
 		| FunMemberAbstract -> raise_typing_error "Cannot access super inside an abstract function" p
 		| FunStatic -> raise_typing_error "Cannot access super inside a static function" p;
@@ -396,9 +396,9 @@ let rec type_ident_raise ctx i p mode with_type =
 		let acc =
 			(* Hack for #10787 *)
 			if ctx.com.platform = Cs then
-				AKExpr (null (spawn_monomorph ctx p) p)
+				AKExpr (null (spawn_monomorph ctx.e p) p)
 			else begin
-				let tnull () = ctx.t.tnull (spawn_monomorph ctx p) in
+				let tnull () = ctx.t.tnull (spawn_monomorph ctx.e p) in
 				let t = match with_type with
 					| WithType.WithType(t,_) ->
 						begin match follow t with
@@ -421,7 +421,7 @@ let rec type_ident_raise ctx i p mode with_type =
 		if mode = MGet then acc else AKNo(acc,p)
 	| _ ->
 	try
-		let v = PMap.find i ctx.locals in
+		let v = PMap.find i ctx.f.locals in
 		add_var_flag v VUsedByTyper;
 		(match v.v_extra with
 		| Some ve ->
@@ -447,25 +447,25 @@ let rec type_ident_raise ctx i p mode with_type =
 			AKExpr (mk (TLocal v) v.v_type p))
 	with Not_found -> try
 		(* member variable lookup *)
-		if ctx.curfun = FunStatic then raise Not_found;
-		let c , t , f = class_field ctx ctx.curclass (extract_param_types ctx.curclass.cl_params) i p in
+		if ctx.e.curfun = FunStatic then raise Not_found;
+		let c , t , f = class_field ctx ctx.c.curclass (extract_param_types ctx.c.curclass.cl_params) i p in
 		field_access ctx mode f (match c with None -> FHAnon | Some (c,tl) -> FHInstance (c,tl)) (get_this ctx p) p
 	with Not_found -> try
 		(* static variable lookup *)
-		let f = PMap.find i ctx.curclass.cl_statics in
+		let f = PMap.find i ctx.c.curclass.cl_statics in
 		let is_impl = has_class_field_flag f CfImpl in
 		let is_enum = has_class_field_flag f CfEnum in
-		if is_impl && not (has_class_field_flag ctx.curfield CfImpl) && not is_enum then
+		if is_impl && not (has_class_field_flag ctx.f.curfield CfImpl) && not is_enum then
 			raise_typing_error (Printf.sprintf "Cannot access non-static field %s from static method" f.cf_name) p;
-		let e,fa = match ctx.curclass.cl_kind with
+		let e,fa = match ctx.c.curclass.cl_kind with
 			| KAbstractImpl a when is_impl && not is_enum ->
 				let tl = extract_param_types a.a_params in
 				let e = get_this ctx p in
 				let e = {e with etype = TAbstract(a,tl)} in
-				e,FHAbstract(a,tl,ctx.curclass)
+				e,FHAbstract(a,tl,ctx.c.curclass)
 			| _ ->
-				let e = type_module_type ctx (TClassDecl ctx.curclass) p in
-				e,FHStatic ctx.curclass
+				let e = type_module_type ctx (TClassDecl ctx.c.curclass) p in
+				e,FHStatic ctx.c.curclass
 		in
 		field_access ctx mode f fa e p
 	with Not_found -> try
@@ -500,20 +500,20 @@ and type_ident ctx i p mode with_type =
 			end else
 				raise Not_found
 		with Not_found ->
-			if ctx.untyped then begin
+			if ctx.f.untyped then begin
 				if i = "__this__" then
-					AKExpr (mk (TConst TThis) ctx.tthis p)
+					AKExpr (mk (TConst TThis) ctx.c.tthis p)
 				else
 					let t = mk_mono() in
 					AKExpr ((mk (TIdent i)) t p)
 			end else begin
-				if ctx.curfun = FunStatic && PMap.mem i ctx.curclass.cl_fields then raise_typing_error ("Cannot access " ^ i ^ " in static function") p;
+				if ctx.e.curfun = FunStatic && PMap.mem i ctx.c.curclass.cl_fields then raise_typing_error ("Cannot access " ^ i ^ " in static function") p;
 				if !resolved_to_type_parameter then begin
 					display_error ctx.com ("Only @:const type parameters on @:generic classes can be used as value") p;
 					AKExpr (mk (TConst TNull) t_dynamic p)
 				end else begin
 					let err = Unknown_ident i in
-					if ctx.in_display then begin
+					if ctx.f.in_display then begin
 						raise_error_msg err p
 					end;
 					if Diagnostics.error_in_diagnostics_run ctx.com p then begin
@@ -584,7 +584,7 @@ and handle_efield ctx e p0 mode with_type =
 						end
 					with Not_found ->
 						(* if there was no module name part, last guess is that we're trying to get package completion *)
-						if ctx.in_display then begin
+						if ctx.f.in_display then begin
 							let sl = List.map (fun part -> part.name) path in
 							if is_legacy_completion ctx.com then
 								raise (Parser.TypePath (sl,None,false,p))
@@ -707,15 +707,15 @@ and type_vars ctx vl p =
 	let vl = List.map (fun ev ->
 		let n = fst ev.ev_name
 		and pv = snd ev.ev_name in
-		DeprecationCheck.check_is ctx.com ctx.m.curmod ctx.curclass.cl_meta ctx.curfield.cf_meta n ev.ev_meta pv;
+		DeprecationCheck.check_is ctx.com ctx.m.curmod ctx.c.curclass.cl_meta ctx.f.curfield.cf_meta n ev.ev_meta pv;
 		try
 			let t = Typeload.load_type_hint ctx p ev.ev_type in
 			let e = (match ev.ev_expr with
 				| None -> None
 				| Some e ->
-					let old_in_loop = ctx.in_loop in
-					if ev.ev_static then ctx.in_loop <- false;
-					let e = Std.finally (fun () -> ctx.in_loop <- old_in_loop) (type_expr ctx e) (WithType.with_type t) in
+					let old_in_loop = ctx.e.in_loop in
+					if ev.ev_static then ctx.e.in_loop <- false;
+					let e = Std.finally (fun () -> ctx.e.in_loop <- old_in_loop) (type_expr ctx e) (WithType.with_type t) in
 					let e = AbstractCast.cast_or_unify ctx t e p in
 					Some e
 			) in
@@ -728,7 +728,7 @@ and type_vars ctx vl p =
 			DisplayEmitter.check_display_metadata ctx v.v_meta;
 			if ev.ev_final then add_var_flag v VFinal;
 			if ev.ev_static then add_var_flag v VStatic;
-			if ctx.in_display && DisplayPosition.display_position#enclosed_in pv then
+			if ctx.f.in_display && DisplayPosition.display_position#enclosed_in pv then
 				DisplayEmitter.display_variable ctx v pv;
 			v,e
 		with
@@ -751,7 +751,7 @@ and type_vars ctx vl p =
 
 and format_string ctx s p =
 	FormatString.format_string ctx.com.defines s p (fun enext p ->
-		if ctx.in_display && DisplayPosition.display_position#enclosed_in p then
+		if ctx.f.in_display && DisplayPosition.display_position#enclosed_in p then
 			Display.preprocess_expr ctx.com (enext,p)
 		else
 			enext,p
@@ -823,7 +823,7 @@ and type_object_decl ctx fl with_type p =
 					| None ->
 						let cf = PMap.find n field_map in
 						if (has_class_field_flag cf CfFinal) then is_final := true;
-						if ctx.in_display && DisplayPosition.display_position#enclosed_in pn then DisplayEmitter.display_field ctx Unknown CFSMember cf pn;
+						if ctx.f.in_display && DisplayPosition.display_position#enclosed_in pn then DisplayEmitter.display_field ctx Unknown CFSMember cf pn;
 						cf.cf_type
 				in
 				let e = type_expr ctx e (WithType.with_structure_field t n) in
@@ -844,7 +844,7 @@ and type_object_decl ctx fl with_type p =
 			((n,pn,qs),e)
 		) fl in
 		let t = mk_anon ~fields:!fields (ref Const) in
-		if not ctx.untyped then begin
+		if not ctx.f.untyped then begin
 			(match PMap.foldi (fun n cf acc -> if not (Meta.has Meta.Optional cf.cf_meta) && not (PMap.mem n !fields) then n :: acc else acc) field_map [] with
 				| [] -> ()
 				| [n] -> raise_or_display ctx [Unify_custom ("Object requires field " ^ n)] p
@@ -867,7 +867,7 @@ and type_object_decl ctx fl with_type p =
 			let e = type_expr ctx e (WithType.named_structure_field f) in
 			(match follow e.etype with TAbstract({a_path=[],"Void"},_) -> raise_typing_error "Fields of type Void are not allowed in structures" e.epos | _ -> ());
 			let cf = mk_field f e.etype (punion pf e.epos) pf in
-			if ctx.in_display && DisplayPosition.display_position#enclosed_in pf then DisplayEmitter.display_field ctx Unknown CFSMember cf pf;
+			if ctx.f.in_display && DisplayPosition.display_position#enclosed_in pf then DisplayEmitter.display_field ctx Unknown CFSMember cf pf;
 			(((f,pf,qs),e) :: l, if is_valid then begin
 				if starts_with f '$' then raise_typing_error "Field names starting with a dollar are not allowed" p;
 				PMap.add f cf acc
@@ -875,7 +875,7 @@ and type_object_decl ctx fl with_type p =
 		in
 		let fields , types = List.fold_left loop ([],PMap.empty) fl in
 		let x = ref Const in
-		ctx.opened <- x :: ctx.opened;
+		ctx.e.opened <- x :: ctx.e.opened;
 		mk (TObjectDecl (List.rev fields)) (mk_anon ~fields:types x) p
 	in
 	(match a with
@@ -1017,11 +1017,11 @@ and type_new ctx ptp el with_type force_inline p =
 			tl_or_monos info.build_params
 	in
 	let restore =
-		ctx.call_argument_stack <- el :: ctx.call_argument_stack;
-		ctx.with_type_stack <- with_type :: ctx.with_type_stack;
+		ctx.e.call_argument_stack <- el :: ctx.e.call_argument_stack;
+		ctx.e.with_type_stack <- with_type :: ctx.e.with_type_stack;
 		(fun () ->
-			ctx.with_type_stack <- List.tl ctx.with_type_stack;
-			ctx.call_argument_stack <- List.tl ctx.call_argument_stack
+			ctx.e.with_type_stack <- List.tl ctx.e.with_type_stack;
+			ctx.e.call_argument_stack <- List.tl ctx.e.call_argument_stack
 		)
 	in
 	let t = try
@@ -1122,12 +1122,12 @@ and type_try ctx e1 catches with_type p =
 		check_unreachable acc1 t2 (pos e_ast);
 		let locals = save_locals ctx in
 		let v = add_local_with_origin ctx TVOCatchVariable v t pv in
-		if ctx.is_display_file && DisplayPosition.display_position#enclosed_in pv then
+		if ctx.m.is_display_file && DisplayPosition.display_position#enclosed_in pv then
 			DisplayEmitter.display_variable ctx v pv;
 		let e = type_expr ctx e_ast with_type in
 		(* If the catch position is the display position it means we get completion on the catch keyword or some
 		   punctuation. Otherwise we wouldn't reach this point. *)
-		if ctx.is_display_file && DisplayPosition.display_position#enclosed_in pc then ignore(TyperDisplay.display_expr ctx e_ast e DKMarked MGet with_type pc);
+		if ctx.m.is_display_file && DisplayPosition.display_position#enclosed_in pc then ignore(TyperDisplay.display_expr ctx e_ast e DKMarked MGet with_type pc);
 		v.v_type <- t2;
 		locals();
 		((v,e) :: acc1),(e :: acc2)
@@ -1153,11 +1153,11 @@ and type_map_declaration ctx e1 el with_type p =
 			| TInst({cl_path=["haxe";"ds"],"IntMap"},[tv]) -> ctx.t.tint,tv,true
 			| TInst({cl_path=["haxe";"ds"],"StringMap"},[tv]) -> ctx.t.tstring,tv,true
 			| TInst({cl_path=["haxe";"ds"],("ObjectMap" | "EnumValueMap")},[tk;tv]) -> tk,tv,true
-			| _ -> spawn_monomorph ctx p,spawn_monomorph ctx p,false
+			| _ -> spawn_monomorph ctx.e p,spawn_monomorph ctx.e p,false
 		in
 		match with_type with
 		| WithType.WithType(t,_) -> get_map_params t
-		| _ -> (spawn_monomorph ctx p,spawn_monomorph ctx p,false)
+		| _ -> (spawn_monomorph ctx.e p,spawn_monomorph ctx.e p,false)
 	in
 	let keys = Hashtbl.create 0 in
 	let check_key e_key =
@@ -1227,12 +1227,12 @@ and type_local_function ctx kind f with_type p =
 		| None -> None,p
 		| Some (v,pn) -> Some v,pn
 	) in
-	let old_tp,old_in_loop = ctx.type_params,ctx.in_loop in
+	let old_tp,old_in_loop = ctx.type_params,ctx.e.in_loop in
 	ctx.type_params <- params @ ctx.type_params;
-	if not inline then ctx.in_loop <- false;
+	if not inline then ctx.e.in_loop <- false;
 	let rt = Typeload.load_type_hint ctx p f.f_type in
 	let type_arg _ opt t p = Typeload.load_type_hint ~opt ctx p t in
-	let args = new FunctionArguments.function_arguments ctx type_arg false ctx.in_display None f.f_args in
+	let args = new FunctionArguments.function_arguments ctx type_arg false ctx.f.in_display None f.f_args in
 	let targs = args#for_type in
 	let maybe_unify_arg t1 t2 =
 		match follow t1 with
@@ -1330,15 +1330,15 @@ and type_local_function ctx kind f with_type p =
 			if params <> [] then v.v_extra <- Some (var_extra params None);
 			Some v
 	) in
-	let curfun = match ctx.curfun with
+	let curfun = match ctx.e.curfun with
 		| FunStatic -> FunStatic
 		| FunMemberAbstract
 		| FunMemberAbstractLocal -> FunMemberAbstractLocal
 		| _ -> FunMemberClassLocal
 	in
-	let e = TypeloadFunction.type_function ctx args rt curfun f.f_expr ctx.in_display p in
+	let e = TypeloadFunction.type_function ctx args rt curfun f.f_expr ctx.f.in_display p in
 	ctx.type_params <- old_tp;
-	ctx.in_loop <- old_in_loop;
+	ctx.e.in_loop <- old_in_loop;
 	let tf = {
 		tf_args = args#for_expr;
 		tf_type = rt;
@@ -1351,7 +1351,7 @@ and type_local_function ctx kind f with_type p =
 		Typeload.generate_args_meta ctx.com None (fun m -> v.v_meta <- m :: v.v_meta) f.f_args;
 		let open LocalUsage in
 		if params <> [] || inline then v.v_extra <- Some (var_extra params (if inline then Some e else None));
-		if ctx.in_display && DisplayPosition.display_position#enclosed_in v.v_pos then
+		if ctx.f.in_display && DisplayPosition.display_position#enclosed_in v.v_pos then
 			DisplayEmitter.display_variable ctx v v.v_pos;
 		let rec loop = function
 			| LocalUsage.Block f | LocalUsage.Loop f | LocalUsage.Function f -> f loop
@@ -1369,7 +1369,7 @@ and type_local_function ctx kind f with_type p =
 				(mk (TVar (v,Some (mk (TConst TNull) ft p))) ctx.t.tvoid p) ::
 				(mk (TBinop (OpAssign,mk (TLocal v) ft p,e)) ft p) ::
 				exprs
-			end else if inline && not ctx.is_display_file then
+			end else if inline && not ctx.m.is_display_file then
 				(mk (TBlock []) ctx.t.tvoid p) :: exprs (* do not add variable since it will be inlined *)
 			else
 				(mk (TVar (v,Some e)) ctx.t.tvoid p) :: exprs
@@ -1428,7 +1428,7 @@ and type_array_decl ctx el with_type p =
 		let t = try
 			unify_min_raise ctx el
 		with Error ({ err_message = Unify _ } as err) ->
-			if !allow_array_dynamic || ctx.untyped || ignore_error ctx.com then
+			if !allow_array_dynamic || ctx.f.untyped || ignore_error ctx.com then
 				t_dynamic
 			else begin
 				display_error ctx.com "Arrays of mixed types are only allowed if the type is forced to Array<Dynamic>" err.err_pos;
@@ -1444,7 +1444,7 @@ and type_array_decl ctx el with_type p =
 		mk (TArrayDecl el) (ctx.t.tarray t) p)
 
 and type_array_comprehension ctx e with_type p =
-	let v = gen_local ctx (spawn_monomorph ctx p) p in
+	let v = gen_local ctx (spawn_monomorph ctx.e p) p in
 	let ev = mk (TLocal v) v.v_type p in
 	let e_ref = snd (store_typed_expr ctx.com ev p) in
 	let et = ref (EConst(Ident "null"),p) in
@@ -1480,14 +1480,14 @@ and type_array_comprehension ctx e with_type p =
 	]) v.v_type p
 
 and type_return ?(implicit=false) ctx e with_type p =
-	let is_abstract_ctor = ctx.curfun = FunMemberAbstract && ctx.curfield.cf_name = "_new" in
+	let is_abstract_ctor = ctx.e.curfun = FunMemberAbstract && ctx.f.curfield.cf_name = "_new" in
 	match e with
 	| None when is_abstract_ctor ->
-		let e_cast = mk (TCast(get_this ctx p,None)) ctx.ret p in
+		let e_cast = mk (TCast(get_this ctx p,None)) ctx.e.ret p in
 		mk (TReturn (Some e_cast)) (mono_or_dynamic ctx with_type p) p
 	| None ->
 		let v = ctx.t.tvoid in
-		unify ctx v ctx.ret p;
+		unify ctx v ctx.e.ret p;
 		let expect_void = match with_type with
 			| WithType.WithType(t,_) -> ExtType.is_void (follow t)
 			| WithType.Value (Some ImplicitReturn) -> true
@@ -1502,16 +1502,16 @@ and type_return ?(implicit=false) ctx e with_type p =
 		end;
 		try
 			let with_expected_type =
-				if ExtType.is_void (follow ctx.ret) then WithType.no_value
-				else if implicit then WithType.of_implicit_return ctx.ret
-				else WithType.with_type ctx.ret
+				if ExtType.is_void (follow ctx.e.ret) then WithType.no_value
+				else if implicit then WithType.of_implicit_return ctx.e.ret
+				else WithType.with_type ctx.e.ret
 			in
 			let e = type_expr ctx e with_expected_type in
-			match follow ctx.ret with
+			match follow ctx.e.ret with
 			| TAbstract({a_path=[],"Void"},_) when implicit ->
 				e
 			| _ ->
-				let e = AbstractCast.cast_or_unify ctx ctx.ret e p in
+				let e = AbstractCast.cast_or_unify ctx ctx.e.ret e p in
 				match follow e.etype with
 				| TAbstract({a_path=[],"Void"},_) ->
 					begin match (Texpr.skip e).eexpr with
@@ -1592,9 +1592,9 @@ and type_if ctx e e1 e2 with_type is_ternary p =
 		make_if_then_else ctx e e1 e2 with_type p
 
 and type_meta ?(mode=MGet) ctx m e1 with_type p =
-	if ctx.is_display_file then DisplayEmitter.check_display_metadata ctx [m];
-	let old = ctx.meta in
-	ctx.meta <- m :: ctx.meta;
+	if ctx.m.is_display_file then DisplayEmitter.check_display_metadata ctx [m];
+	let old = ctx.f.meta in
+	ctx.f.meta <- m :: ctx.f.meta;
 	let e () = type_expr ~mode ctx e1 with_type in
 	let e = match m with
 		| (Meta.ToString,_,_) ->
@@ -1617,7 +1617,7 @@ and type_meta ?(mode=MGet) ctx m e1 with_type p =
 		| (Meta.StoredTypedExpr,_,_) ->
 			type_stored_expr ctx e1
 		| (Meta.NoPrivateAccess,_,_) ->
-			ctx.meta <- List.filter (fun(m,_,_) -> m <> Meta.PrivateAccess) ctx.meta;
+			ctx.f.meta <- List.filter (fun(m,_,_) -> m <> Meta.PrivateAccess) ctx.f.meta;
 			e()
 		| (Meta.Fixed,_,_) when ctx.com.platform=Cpp ->
 			let e = e() in
@@ -1626,10 +1626,10 @@ and type_meta ?(mode=MGet) ctx m e1 with_type p =
 			let e = e() in
 			{e with eexpr = TMeta(m,e)}
 		| (Meta.BypassAccessor,_,p) ->
-			let old_counter = ctx.bypass_accessor in
-			ctx.bypass_accessor <- old_counter + 1;
+			let old_counter = ctx.e.bypass_accessor in
+			ctx.e.bypass_accessor <- old_counter + 1;
 			let e = e () in
-			(if ctx.bypass_accessor > old_counter then display_error ctx.com "Field access expression expected after @:bypassAccessor metadata" p);
+			(if ctx.e.bypass_accessor > old_counter then display_error ctx.com "Field access expression expected after @:bypassAccessor metadata" p);
 			e
 		| (Meta.Inline,_,pinline) ->
 			begin match fst e1 with
@@ -1670,7 +1670,7 @@ and type_meta ?(mode=MGet) ctx m e1 with_type p =
 			else
 				e()
 	in
-	ctx.meta <- old;
+	ctx.f.meta <- old;
 	e
 
 and type_call_target ctx e el with_type p_inline =
@@ -1775,8 +1775,8 @@ and type_call_builtin ctx e el mode with_type p =
 	| (EDisplay((EConst (Ident "super"),_ as e1),dk),_),_ ->
 		TyperDisplay.handle_display ctx (ECall(e1,el),p) dk mode with_type
 	| (EConst (Ident "super"),sp) , el ->
-		if ctx.curfun <> FunConstructor then raise_typing_error "Cannot call super constructor outside class constructor" p;
-		let el, t = (match ctx.curclass.cl_super with
+		if ctx.e.curfun <> FunConstructor then raise_typing_error "Cannot call super constructor outside class constructor" p;
+		let el, t = (match ctx.c.curclass.cl_super with
 		| None -> raise_typing_error "Current class does not have a super" p
 		| Some (c,params) ->
 			let fa = FieldAccess.get_constructor_access c params p in
@@ -1801,7 +1801,7 @@ and type_expr ?(mode=MGet) ctx (e,p) (with_type:WithType.t) =
 	| EField(_,n,_) when starts_with n '$' ->
 		raise_typing_error "Field names starting with $ are not allowed" p
 	| EConst (Ident s) ->
-		if s = "super" && with_type <> WithType.NoValue && not ctx.in_display then raise_typing_error "Cannot use super as value" p;
+		if s = "super" && with_type <> WithType.NoValue && not ctx.f.in_display then raise_typing_error "Cannot use super as value" p;
 		let e = maybe_type_against_enum ctx (fun () -> type_ident ctx s p mode with_type) with_type false p in
 		acc_get ctx e
 	| EField _
@@ -1924,18 +1924,18 @@ and type_expr ?(mode=MGet) ctx (e,p) (with_type:WithType.t) =
 	| EIf (e,e1,e2) ->
 		type_if ctx e e1 e2 with_type false p
 	| EWhile (cond,e,NormalWhile) ->
-		let old_loop = ctx.in_loop in
+		let old_loop = ctx.e.in_loop in
 		let cond = type_expr ctx cond WithType.value in
 		let cond = AbstractCast.cast_or_unify ctx ctx.t.tbool cond p in
-		ctx.in_loop <- true;
+		ctx.e.in_loop <- true;
 		let e = type_expr ctx (Expr.ensure_block e) WithType.NoValue in
-		ctx.in_loop <- old_loop;
+		ctx.e.in_loop <- old_loop;
 		mk (TWhile (cond,e,NormalWhile)) ctx.t.tvoid p
 	| EWhile (cond,e,DoWhile) ->
-		let old_loop = ctx.in_loop in
-		ctx.in_loop <- true;
+		let old_loop = ctx.e.in_loop in
+		ctx.e.in_loop <- true;
 		let e = type_expr ctx (Expr.ensure_block e) WithType.NoValue in
-		ctx.in_loop <- old_loop;
+		ctx.e.in_loop <- old_loop;
 		let cond = type_expr ctx cond WithType.value in
 		let cond = AbstractCast.cast_or_unify ctx ctx.t.tbool cond cond.epos in
 		mk (TWhile (cond,e,DoWhile)) ctx.t.tvoid p
@@ -1944,7 +1944,7 @@ and type_expr ?(mode=MGet) ctx (e,p) (with_type:WithType.t) =
 		let e = Matcher.Match.match_expr ctx e1 cases def with_type false p in
 		wrap e
 	| EReturn e ->
-		if not ctx.in_function then begin
+		if not ctx.e.in_function then begin
 			display_error ctx.com "Return outside function" p;
 			match e with
 			| None ->
@@ -1957,10 +1957,10 @@ and type_expr ?(mode=MGet) ctx (e,p) (with_type:WithType.t) =
 		end else
 			type_return ctx e with_type p
 	| EBreak ->
-		if not ctx.in_loop then display_error ctx.com "Break outside loop" p;
+		if not ctx.e.in_loop then display_error ctx.com "Break outside loop" p;
 		mk TBreak (mono_or_dynamic ctx with_type p) p
 	| EContinue ->
-		if not ctx.in_loop then display_error ctx.com "Continue outside loop" p;
+		if not ctx.e.in_loop then display_error ctx.com "Continue outside loop" p;
 		mk TContinue (mono_or_dynamic ctx with_type p) p
 	| ETry (e1,[]) ->
 		type_expr ctx e1 with_type
@@ -1981,11 +1981,11 @@ and type_expr ?(mode=MGet) ctx (e,p) (with_type:WithType.t) =
 	| EFunction (kind,f) ->
 		type_local_function ctx kind f with_type p
 	| EUntyped e ->
-		let old = ctx.untyped in
-		ctx.untyped <- true;
-		if not (Meta.has Meta.HasUntyped ctx.curfield.cf_meta) then ctx.curfield.cf_meta <- (Meta.HasUntyped,[],p) :: ctx.curfield.cf_meta;
+		let old = ctx.f.untyped in
+		ctx.f.untyped <- true;
+		if not (Meta.has Meta.HasUntyped ctx.f.curfield.cf_meta) then ctx.f.curfield.cf_meta <- (Meta.HasUntyped,[],p) :: ctx.f.curfield.cf_meta;
 		let e = type_expr ctx e with_type in
-		ctx.untyped <- old;
+		ctx.f.untyped <- old;
 		{
 			eexpr = e.eexpr;
 			etype = mk_mono();
@@ -1993,7 +1993,7 @@ and type_expr ?(mode=MGet) ctx (e,p) (with_type:WithType.t) =
 		}
 	| ECast (e,None) ->
 		let e = type_expr ctx e WithType.value in
-		mk (TCast (e,None)) (spawn_monomorph ctx p) p
+		mk (TCast (e,None)) (spawn_monomorph ctx.e p) p
 	| ECast (e, Some t) ->
 		type_cast ctx e t p
 	| EDisplay (e,dk) ->
@@ -2011,7 +2011,7 @@ and type_expr ?(mode=MGet) ctx (e,p) (with_type:WithType.t) =
 			if tp.path.tparams <> [] then display_error ctx.com "Type parameters are not supported for the `is` operator" p_t;
 			let e = type_expr ctx e WithType.value in
 			let mt = Typeload.load_type_def ctx p_t tp.path in
-			if ctx.in_display && DisplayPosition.display_position#enclosed_in p_t then
+			if ctx.f.in_display && DisplayPosition.display_position#enclosed_in p_t then
 				DisplayEmitter.display_module_type ctx mt p_t;
 			let e_t = type_module_type ctx mt p_t in
 			Texpr.Builder.resolve_and_make_static_call ctx.com.std "isOfType" [e;e_t] p

+ 15 - 15
src/typing/typerBase.ml

@@ -149,31 +149,31 @@ let is_lower_ident s p =
 	with Invalid_argument msg -> raise_typing_error msg p
 
 let get_this ctx p =
-	match ctx.curfun with
+	match ctx.e.curfun with
 	| FunStatic ->
 		raise_typing_error "Cannot access this from a static function" p
 	| FunMemberClassLocal | FunMemberAbstractLocal ->
-		let v = match ctx.vthis with
+		let v = match ctx.f.vthis with
 			| None ->
-				let v = if ctx.curfun = FunMemberAbstractLocal then begin
-					let v = PMap.find "this" ctx.locals in
+				let v = if ctx.e.curfun = FunMemberAbstractLocal then begin
+					let v = PMap.find "this" ctx.f.locals in
 					add_var_flag v VUsedByTyper;
 					v
 				end else
-					add_local ctx VGenerated (Printf.sprintf "%sthis" gen_local_prefix) ctx.tthis p
+					add_local ctx VGenerated (Printf.sprintf "%sthis" gen_local_prefix) ctx.c.tthis p
 				in
-				ctx.vthis <- Some v;
+				ctx.f.vthis <- Some v;
 				v
 			| Some v ->
-				ctx.locals <- PMap.add v.v_name v ctx.locals;
+				ctx.f.locals <- PMap.add v.v_name v ctx.f.locals;
 				v
 		in
-		mk (TLocal v) ctx.tthis p
+		mk (TLocal v) ctx.c.tthis p
 	| FunMemberAbstract ->
-		let v = (try PMap.find "this" ctx.locals with Not_found -> raise_typing_error "Cannot reference this abstract here" p) in
+		let v = (try PMap.find "this" ctx.f.locals with Not_found -> raise_typing_error "Cannot reference this abstract here" p) in
 		mk (TLocal v) v.v_type p
 	| FunConstructor | FunMember ->
-		mk (TConst TThis) ctx.tthis p
+		mk (TConst TThis) ctx.c.tthis p
 
 let get_stored_typed_expr ctx id =
 	let e = ctx.com.stored_typed_exprs#find id in
@@ -184,11 +184,11 @@ let type_stored_expr ctx e1 =
 	get_stored_typed_expr ctx id
 
 let assign_to_this_is_allowed ctx =
-	match ctx.curclass.cl_kind with
+	match ctx.c.curclass.cl_kind with
 		| KAbstractImpl _ ->
-			(match ctx.curfield.cf_kind with
+			(match ctx.f.curfield.cf_kind with
 				| Method MethInline -> true
-				| Method _ when ctx.curfield.cf_name = "_new" -> true
+				| Method _ when ctx.f.curfield.cf_name = "_new" -> true
 				| _ -> false
 			)
 		| _ -> false
@@ -211,7 +211,7 @@ let type_module_type ctx t p =
 		| TEnumDecl e ->
 			mk (TTypeExpr (TEnumDecl e)) e.e_type p
 		| TTypeDecl s ->
-			let t = apply_typedef s (List.map (fun _ -> spawn_monomorph ctx p) s.t_params) in
+			let t = apply_typedef s (List.map (fun _ -> spawn_monomorph ctx.e p) s.t_params) in
 			DeprecationCheck.check_typedef (create_deprecation_context ctx) s p;
 			(match follow t with
 			| TEnum (e,params) ->
@@ -334,7 +334,7 @@ let get_abstract_froms ctx a pl =
 	let l = List.map (apply_params a.a_params pl) a.a_from in
 	List.fold_left (fun acc (t,f) ->
 		(* We never want to use the @:from we're currently in because that's recursive (see #10604) *)
-		if f == ctx.curfield then
+		if f == ctx.f.curfield then
 			acc
 		else if (AbstractFromConfig.update_config_from_meta (AbstractFromConfig.make ()) f.cf_meta).ignored_by_inference then
 			acc

+ 16 - 16
src/typing/typerDisplay.ml

@@ -178,7 +178,7 @@ let raise_toplevel ctx dk with_type (subject,psubject) =
 	DisplayToplevel.collect_and_raise ctx (match dk with DKPattern _ -> TKPattern psubject | _ -> TKExpr psubject) with_type (CRToplevel expected_type) (subject,psubject) psubject
 
 let display_dollar_type ctx p make_type =
-	let mono = spawn_monomorph ctx p in
+	let mono = spawn_monomorph ctx.e p in
 	let doc = doc_from_string "Outputs type of argument as a warning and uses argument as value" in
 	let arg = ["expression",false,mono] in
 	begin match ctx.com.display.dms_kind with
@@ -194,7 +194,7 @@ let display_dollar_type ctx p make_type =
 	end
 
 let rec handle_signature_display ctx e_ast with_type =
-	ctx.in_display <- true;
+	ctx.f.in_display <- true;
 	let p = pos e_ast in
 	let handle_call tl el p0 =
 		let rec follow_with_callable (t,doc,values) = match follow t with
@@ -340,7 +340,7 @@ let rec handle_signature_display ctx e_ast with_type =
 		| _ -> raise_typing_error "Call expected" p
 
 and display_expr ctx e_ast e dk mode with_type p =
-	let get_super_constructor () = match ctx.curclass.cl_super with
+	let get_super_constructor () = match ctx.c.curclass.cl_super with
 		| None -> raise_typing_error "Current class does not have a super" p
 		| Some (c,params) ->
 			let fa = get_constructor_access c params p in
@@ -419,7 +419,7 @@ and display_expr ctx e_ast e dk mode with_type p =
 				()
 			end
 		| TConst TSuper ->
-			begin match ctx.curclass.cl_super with
+			begin match ctx.c.curclass.cl_super with
 				| None -> ()
 				| Some (c,_) -> Display.ReferencePosition.set (snd c.cl_path,c.cl_name_pos,SKClass c);
 			end
@@ -476,7 +476,7 @@ and display_expr ctx e_ast e dk mode with_type p =
 				[]
 			end
 		| TConst TSuper ->
-			begin match ctx.curclass.cl_super with
+			begin match ctx.c.curclass.cl_super with
 				| None -> []
 				| Some (c,_) -> [c.cl_name_pos]
 			end
@@ -541,9 +541,9 @@ and display_expr ctx e_ast e dk mode with_type p =
 		raise_fields fields (CRField(item,e.epos,iterator,keyValueIterator)) (make_subject None (DisplayPosition.display_position#with_pos p))
 
 let handle_display ctx e_ast dk mode with_type =
-	let old = ctx.in_display,ctx.in_call_args in
-	ctx.in_display <- true;
-	ctx.in_call_args <- false;
+	let old = ctx.f.in_display,ctx.f.in_call_args in
+	ctx.f.in_display <- true;
+	ctx.f.in_call_args <- false;
 	let tpair t =
 		let ct = CompletionType.from_type (get_import_status ctx) t in
 		(t,ct)
@@ -595,10 +595,10 @@ let handle_display ctx e_ast dk mode with_type =
 				begin match mt.has_constructor with
 				| Yes -> true
 				| YesButPrivate ->
-					if (Meta.has Meta.PrivateAccess ctx.meta) then true
+					if (Meta.has Meta.PrivateAccess ctx.f.meta) then true
 					else
 						begin
-							match ctx.curclass.cl_kind with
+							match ctx.c.curclass.cl_kind with
 							| KAbstractImpl { a_path = (pack, name) } -> pack = mt.pack && name = mt.name
 							| _ -> false
 						end
@@ -610,7 +610,7 @@ let handle_display ctx e_ast dk mode with_type =
 									| Some(c,_) -> loop c
 									| None -> false
 							in
-							loop ctx.curclass
+							loop ctx.c.curclass
 						end
 				| No -> false
 				| Maybe ->
@@ -640,7 +640,7 @@ let handle_display ctx e_ast dk mode with_type =
 		| (EField(_,"new",_),_), TFunction { tf_expr = { eexpr = TReturn (Some ({ eexpr = TNew _ } as e1))} } -> e1
 		| _ -> e
 	in
-	let is_display_debug = Meta.has (Meta.Custom ":debug.display") ctx.curfield.cf_meta in
+	let is_display_debug = Meta.has (Meta.Custom ":debug.display") ctx.f.curfield.cf_meta in
 	if is_display_debug then begin
 		print_endline (Printf.sprintf "expected type: %s" (WithType.to_string with_type));
 		print_endline (Printf.sprintf "typed expr:\n%s" (s_expr_ast true "" (s_type (print_context())) e));
@@ -657,14 +657,14 @@ let handle_display ctx e_ast dk mode with_type =
 	if is_display_debug then begin
 		print_endline (Printf.sprintf "cast expr:\n%s" (s_expr_ast true "" (s_type (print_context())) e));
 	end;
-	ctx.in_display <- fst old;
-	ctx.in_call_args <- snd old;
+	ctx.f.in_display <- fst old;
+	ctx.f.in_call_args <- snd old;
 	let f () = display_expr ctx e_ast e dk mode with_type p in
-	if ctx.in_overload_call_args then begin
+	if ctx.f.in_overload_call_args then begin
 		try
 			f()
 		with DisplayException de ->
-			ctx.delayed_display <- Some de;
+			ctx.g.delayed_display <- Some de;
 			e
 	end else
 		f()

+ 9 - 25
src/typing/typerEntry.ml

@@ -36,6 +36,7 @@ let create com macros =
 			get_build_info = InstanceBuilder.get_build_info;
 			do_format_string = format_string;
 			do_load_core_class = Typeload.load_core_class;
+			delayed_display = None;
 		};
 		m = {
 			curmod = null_module;
@@ -44,36 +45,19 @@ let create com macros =
 			enum_with_type = None;
 			module_using = [];
 			import_statements = [];
+			is_display_file = false;
 		};
-		is_display_file = false;
-		bypass_accessor = 0;
-		meta = [];
-		with_type_stack = [];
-		call_argument_stack = [];
+		c = {
+			curclass = null_class;
+			tthis = t_dynamic;
+			get_build_infos = (fun() -> None);
+		};
+		f = TyperManager.create_ctx_f null_field;
+		e = TyperManager.create_ctx_e ();
 		pass = PBuildModule;
-		macro_depth = 0;
-		untyped = false;
-		curfun = FunStatic;
-		in_function = false;
-		in_loop = false;
-		in_display = false;
 		allow_inline = true;
 		allow_transform = true;
-		get_build_infos = (fun() -> None);
-		ret = mk_mono();
-		locals = PMap.empty;
 		type_params = [];
-		curclass = null_class;
-		curfield = null_field;
-		tthis = mk_mono();
-		opened = [];
-		vthis = None;
-		in_call_args = false;
-		in_overload_call_args = false;
-		delayed_display = None;
-		monomorphs = {
-			perfunction = [];
-		};
 		memory_marker = Typecore.memory_marker;
 	} in
 	ctx.g.std_types <- (try