Browse Source

macro AST changes (added full class field definition)

Nicolas Cannasse 14 years ago
parent
commit
cb88382c0e
11 changed files with 241 additions and 160 deletions
  1. 12 16
      ast.ml
  2. 5 4
      codegen.ml
  3. 4 3
      genswf.ml
  4. 110 65
      interp.ml
  5. 20 22
      parser.ml
  6. 1 1
      std/Reflect.hx
  7. 21 8
      std/haxe/macro/Expr.hx
  8. 5 5
      std/haxe/macro/Type.hx
  9. 1 1
      typecore.ml
  10. 61 34
      typeload.ml
  11. 1 1
      typer.ml

+ 12 - 16
ast.ml

@@ -145,22 +145,18 @@ and type_param_or_const =
 	| TPType of complex_type
 	| TPType of complex_type
 	| TPConst of constant
 	| TPConst of constant
 
 
-and anonymous_field =
-	| AFVar of complex_type
-	| AFProp of complex_type * string * string
-	| AFFun of (string * bool * complex_type) list * complex_type
-
 and complex_type =
 and complex_type =
 	| CTPath of type_path
 	| CTPath of type_path
 	| CTFunction of complex_type list * complex_type
 	| CTFunction of complex_type list * complex_type
-	| CTAnonymous of (string * bool option * anonymous_field * pos) list
+	| CTAnonymous of class_field list
 	| CTParent of complex_type
 	| CTParent of complex_type
-	| CTExtend of type_path * (string * bool option * anonymous_field * pos) list
+	| CTExtend of type_path * class_field list
 
 
-type func = {
+and func = {
+	f_params : type_param list;
 	f_args : (string * bool * complex_type option * expr option) list;
 	f_args : (string * bool * complex_type option * expr option) list;
 	f_type : complex_type option;
 	f_type : complex_type option;
-	f_expr : expr;
+	f_expr : expr option;
 }
 }
 
 
 and expr_def =
 and expr_def =
@@ -195,13 +191,13 @@ and expr_def =
 
 
 and expr = expr_def * pos
 and expr = expr_def * pos
 
 
-type type_param = string * type_path list
+and type_param = string * complex_type list
 
 
-type documentation = string option
+and documentation = string option
 
 
-type metadata = (string * expr list * pos) list
+and metadata = (string * expr list * pos) list
 
 
-type access =
+and access =
 	| APublic
 	| APublic
 	| APrivate
 	| APrivate
 	| AStatic
 	| AStatic
@@ -209,12 +205,12 @@ type access =
 	| ADynamic
 	| ADynamic
 	| AInline
 	| AInline
 
 
-type class_field_kind =
+and class_field_kind =
 	| FVar of complex_type option * expr option
 	| FVar of complex_type option * expr option
-	| FFun of type_param list * func
+	| FFun of func
 	| FProp of string * string * complex_type
 	| FProp of string * string * complex_type
 
 
-type class_field = {
+and class_field = {
 	cff_name : string;
 	cff_name : string;
 	cff_doc : documentation;
 	cff_doc : documentation;
 	cff_pos : pos;
 	cff_pos : pos;

+ 5 - 4
codegen.ml

@@ -109,14 +109,14 @@ let extend_remoting ctx c t p async prot =
 	ctx.com.package_rules <- rules;
 	ctx.com.package_rules <- rules;
 	let base_fields = [
 	let base_fields = [
 		{ cff_name = "__cnx"; cff_pos = p; cff_doc = None; cff_meta = []; cff_access = []; cff_kind = FVar (Some (CTPath { tpackage = ["haxe";"remoting"]; tname = if async then "AsyncConnection" else "Connection"; tparams = []; tsub = None }),None) };
 		{ cff_name = "__cnx"; cff_pos = p; cff_doc = None; cff_meta = []; cff_access = []; cff_kind = FVar (Some (CTPath { tpackage = ["haxe";"remoting"]; tname = if async then "AsyncConnection" else "Connection"; tparams = []; tsub = None }),None) };
-		{ cff_name = "new"; cff_pos = p; cff_doc = None; cff_meta = []; cff_access = [APublic]; cff_kind = FFun ([],{ f_args = ["c",false,None,None]; f_type = None; f_expr = (EBinop (OpAssign,(EConst (Ident "__cnx"),p),(EConst (Ident "c"),p)),p) }) };
+		{ cff_name = "new"; cff_pos = p; cff_doc = None; cff_meta = []; cff_access = [APublic]; cff_kind = FFun { f_args = ["c",false,None,None]; f_type = None; f_expr = Some (EBinop (OpAssign,(EConst (Ident "__cnx"),p),(EConst (Ident "c"),p)),p); f_params = [] } };
 	] in
 	] in
 	let tvoid = CTPath { tpackage = []; tname = "Void"; tparams = []; tsub = None } in
 	let tvoid = CTPath { tpackage = []; tname = "Void"; tparams = []; tsub = None } in
 	let build_field is_public acc f =
 	let build_field is_public acc f =
 		if f.cff_name = "new" then
 		if f.cff_name = "new" then
 			acc
 			acc
 		else match f.cff_kind with
 		else match f.cff_kind with
-		| FFun (pl,fd) when (is_public || List.mem APublic f.cff_access) && not (List.mem AStatic f.cff_access) ->
+		| FFun fd when (is_public || List.mem APublic f.cff_access) && not (List.mem AStatic f.cff_access) ->
 			if List.exists (fun (_,_,t,_) -> t = None) fd.f_args then error ("Field " ^ f.cff_name ^ " type is not complete and cannot be used by RemotingProxy") p;
 			if List.exists (fun (_,_,t,_) -> t = None) fd.f_args then error ("Field " ^ f.cff_name ^ " type is not complete and cannot be used by RemotingProxy") p;
 			let eargs = [EArrayDecl (List.map (fun (a,_,_,_) -> (EConst (Ident a),p)) fd.f_args),p] in
 			let eargs = [EArrayDecl (List.map (fun (a,_,_,_) -> (EConst (Ident a),p)) fd.f_args),p] in
 			let ftype = (match fd.f_type with Some (CTPath { tpackage = []; tname = "Void" }) -> None | _ -> fd.f_type) in
 			let ftype = (match fd.f_type with Some (CTPath { tpackage = []; tname = "Void" }) -> None | _ -> fd.f_type) in
@@ -136,11 +136,12 @@ let extend_remoting ctx c t p async prot =
 			in
 			in
 			let expr = if async || ftype = None then expr else (EReturn (Some expr),p) in
 			let expr = if async || ftype = None then expr else (EReturn (Some expr),p) in
 			let fd = {
 			let fd = {
+				f_params = fd.f_params;
 				f_args = fargs;
 				f_args = fargs;
 				f_type = if async then None else ftype;
 				f_type = if async then None else ftype;
-				f_expr = (EBlock [expr],p);
+				f_expr = Some (EBlock [expr],p);
 			} in
 			} in
-			{ cff_name = f.cff_name; cff_pos = p; cff_doc = None; cff_meta = []; cff_access = [APublic]; cff_kind = FFun (pl,fd) } :: acc
+			{ cff_name = f.cff_name; cff_pos = p; cff_doc = None; cff_meta = []; cff_access = [APublic]; cff_kind = FFun fd } :: acc
 		| _ -> acc
 		| _ -> acc
 	in
 	in
 	let decls = List.map (fun d ->
 	let decls = List.map (fun d ->

+ 4 - 3
genswf.ml

@@ -319,12 +319,13 @@ let build_class com c file =
 					args @ List.map (fun _ -> incr pn; ("p" ^ string_of_int !pn,true,Some (make_type None),None)) [1;2;3;4;5]
 					args @ List.map (fun _ -> incr pn; ("p" ^ string_of_int !pn,true,Some (make_type None),None)) [1;2;3;4;5]
 				else args in
 				else args in
 				let f = {
 				let f = {
+					f_params = [];
 					f_args = args;
 					f_args = args;
 					f_type = Some (make_type t.hlmt_ret);
 					f_type = Some (make_type t.hlmt_ret);
-					f_expr = (EBlock [],pos)
+					f_expr = None;
 				} in
 				} in
 				cf.cff_meta <- mk_meta();
 				cf.cff_meta <- mk_meta();
-				cf.cff_kind <- FFun ([],f);
+				cf.cff_kind <- FFun f;
 				cf :: acc
 				cf :: acc
 			| MK3Getter ->
 			| MK3Getter ->
 				Hashtbl.add getters (name,stat) m.hlm_type.hlmt_ret;
 				Hashtbl.add getters (name,stat) m.hlm_type.hlmt_ret;
@@ -387,7 +388,7 @@ let build_class com c file =
 				| FVar (Some (CTPath { tpackage = []; tname = ("String" | "Int" | "UInt") as tname }),None) when List.mem AStatic f.cff_access ->
 				| FVar (Some (CTPath { tpackage = []; tname = ("String" | "Int" | "UInt") as tname }),None) when List.mem AStatic f.cff_access ->
 					if !real_type = "" then real_type := tname else if !real_type <> tname then raise Exit;
 					if !real_type = "" then real_type := tname else if !real_type <> tname then raise Exit;
 					(f.cff_name,None,[],[],pos) :: loop l
 					(f.cff_name,None,[],[],pos) :: loop l
-				| FFun (_,{ f_args = [] }) when f.cff_name = "new" -> loop l
+				| FFun { f_args = [] } when f.cff_name = "new" -> loop l
 				| _ -> raise Exit
 				| _ -> raise Exit
 		in
 		in
 		(match path.tpackage, path.tname with
 		(match path.tpackage, path.tname with

+ 110 - 65
interp.ml

@@ -2391,6 +2391,7 @@ type enum_index =
 	| IFieldKind
 	| IFieldKind
 	| IMethodKind
 	| IMethodKind
 	| IVarAccess
 	| IVarAccess
+	| IAccess
 
 
 let enum_name = function
 let enum_name = function
 	| IExpr -> "ExprDef"
 	| IExpr -> "ExprDef"
@@ -2404,6 +2405,7 @@ let enum_name = function
 	| IFieldKind -> "FieldKind"
 	| IFieldKind -> "FieldKind"
 	| IMethodKind -> "MethodKind"
 	| IMethodKind -> "MethodKind"
 	| IVarAccess -> "VarAccess"
 	| IVarAccess -> "VarAccess"
+	| IAccess -> "Access"
 
 
 let init ctx =
 let init ctx =
 	let enums = [IExpr;IBinop;IUnop;IConst;ITParam;ICType;IField;IType;IFieldKind;IMethodKind;IVarAccess] in
 	let enums = [IExpr;IBinop;IUnop;IConst;ITParam;ICType;IField;IType;IFieldKind;IMethodKind;IVarAccess] in
@@ -2542,23 +2544,39 @@ and encode_tparam = function
 	| TPType t -> enc_enum ITParam 0 [encode_type t]
 	| TPType t -> enc_enum ITParam 0 [encode_type t]
 	| TPConst c -> enc_enum ITParam 1 [encode_const c]
 	| TPConst c -> enc_enum ITParam 1 [encode_const c]
 
 
-and encode_field (f,pub,field,pos) =
-	let tag, pl = match field with
-		| AFVar t -> 0, [encode_type t]
-		| AFProp (t,get,set) -> 1, [encode_type t; enc_string get; enc_string set]
-		| AFFun (pl,t) -> 2, [enc_array (List.map (fun (n,opt,t) ->
-			enc_obj [
-				"name", enc_string n;
-				"opt", VBool opt;
-				"type", encode_type t
-			]
-		) pl); encode_type t]
+and encode_access a =
+	let tag = match a with
+		| APublic -> 0
+		| APrivate -> 1
+		| AStatic -> 2
+		| AOverride -> 3
+		| ADynamic -> 4
+		| AInline -> 5
+	in
+	enc_enum IAccess tag []
+
+and encode_meta_content m =
+	enc_array (List.map (fun (m,ml,p) ->
+		enc_obj [
+			"name", enc_string m;
+			"params", enc_array (List.map encode_expr ml);
+			"pos", encode_pos p;
+		]
+	) m)
+
+and encode_field (f:class_field) =
+	let tag, pl = match f.cff_kind with
+		| FVar (t,e) -> 0, [null encode_type t; null encode_expr e]
+		| FFun f -> 1, [encode_fun f]
+		| FProp (get,set, t) -> 2, [enc_string get; enc_string set; encode_type t]
 	in
 	in
 	enc_obj [
 	enc_obj [
-		"name",enc_string f;
-		"isPublic",null (fun b -> VBool b) pub;
-		"type", enc_enum IField tag pl;
-		"pos", encode_pos pos;
+		"name",enc_string f.cff_name;
+		"doc", null enc_string f.cff_doc;
+		"pos", encode_pos f.cff_pos;
+		"kind", enc_enum IField tag pl;
+		"meta", encode_meta_content f.cff_meta;
+		"access", enc_array (List.map encode_access f.cff_access);
 	]
 	]
 
 
 and encode_type t =
 and encode_type t =
@@ -2576,7 +2594,27 @@ and encode_type t =
 	in
 	in
 	enc_enum ICType tag pl
 	enc_enum ICType tag pl
 
 
-let encode_expr e =
+and encode_fun f =
+	enc_obj [
+		"params", enc_array (List.map (fun (n,cl) ->
+			enc_obj [
+				"name", enc_string n;
+				"constraints", enc_array (List.map encode_type cl);
+			]
+		) f.f_params);
+		"args", enc_array (List.map (fun (n,opt,t,e) ->
+			enc_obj [
+				"name", enc_string n;
+				"opt", VBool opt;
+				"type", null encode_type t;
+				"value", null encode_expr e;
+			]
+		) f.f_args);
+		"ret", null encode_type f.f_type;
+		"expr", null encode_expr f.f_expr
+	]
+
+and encode_expr e =
 	let rec loop (e,p) =
 	let rec loop (e,p) =
 		let tag, pl = match e with
 		let tag, pl = match e with
 			| EConst c ->
 			| EConst c ->
@@ -2613,19 +2651,7 @@ let encode_expr e =
 					]
 					]
 				) vl)]
 				) vl)]
 			| EFunction (name,f) ->
 			| EFunction (name,f) ->
-				12, [enc_obj [
-					"name", null enc_string name;
-					"args", enc_array (List.map (fun (n,opt,t,e) ->
-						enc_obj [
-							"name", enc_string n;
-							"opt", VBool opt;
-							"type", null encode_type t;
-							"value", null loop e;
-						]
-					) f.f_args);
-					"ret", null encode_type f.f_type;
-					"expr", loop f.f_expr
-				]]
+				12, [null enc_string name; encode_fun f]
 			| EBlock el ->
 			| EBlock el ->
 				13, [enc_array (List.map loop el)]
 				13, [enc_array (List.map loop el)]
 			| EFor (v,e,eloop) ->
 			| EFor (v,e,eloop) ->
@@ -2773,26 +2799,52 @@ and decode_tparam v =
 	| 1,[c] -> TPConst (decode_const c)
 	| 1,[c] -> TPConst (decode_const c)
 	| _ -> raise Invalid_expr
 	| _ -> raise Invalid_expr
 
 
+and decode_fun v =
+	{
+		f_params = List.map (fun v ->
+			(dec_string (field v "name"), List.map decode_ctype (dec_array (field v "constraints")))
+		) (dec_array (field v "params"));
+		f_args = List.map (fun o ->
+			(dec_string (field o "name"),dec_bool (field o "opt"),opt decode_ctype (field o "type"),opt decode_expr (field o "value"))
+		) (dec_array (field v "args"));
+		f_type = opt decode_ctype (field v "ret");
+		f_expr = opt decode_expr (field v "expr");
+	}
+
+and decode_access v =
+	match decode_enum v with
+	| 0, [] -> APublic
+	| 1, [] -> APrivate
+	| 2, [] -> AStatic
+	| 3, [] -> AOverride
+	| 4, [] -> ADynamic
+	| 5, [] -> AInline
+	| _ -> raise Invalid_expr
+
+and decode_meta_content v =
+	List.map (fun v ->
+		(dec_string (field v "name"), List.map decode_expr (dec_array (field v "params")), decode_pos (field v "pos"))
+	) (dec_array v)
+
 and decode_field v =
 and decode_field v =
-	let ftype = match decode_enum (field v "type") with
-		| 0, [t] ->
-			AFVar (decode_ctype t)
-		| 1, [t;get;set] ->
-			AFProp (decode_ctype t, dec_string get, dec_string set)
-		| 2, [pl;t] ->
-			let pl = List.map (fun p ->
-				(dec_string (field p "name"),dec_bool (field p "opt"),decode_ctype (field p "type"))
-			) (dec_array pl) in
-			AFFun (pl, decode_ctype t)
+	let fkind = match decode_enum (field v "kind") with
+		| 0, [t;e] ->
+			FVar (opt decode_ctype t, opt decode_expr e)
+		| 1, [f] ->
+			FFun (decode_fun f)
+		| 2, [get;set; t] ->
+			FProp (dec_string get, dec_string set, decode_ctype t)
 		| _ ->
 		| _ ->
 			raise Invalid_expr
 			raise Invalid_expr
 	in
 	in
-	(
-		dec_string (field v "name"),
-		opt dec_bool (field v "isPublic"),
-		ftype,
-		decode_pos (field v "pos")
-	)
+	{
+		cff_name = dec_string (field v "name");
+		cff_doc = opt dec_string (field v "doc");
+		cff_pos = decode_pos (field v "pos");
+		cff_kind = fkind;
+		cff_access = List.map decode_access (dec_array (field v "access"));
+		cff_meta = decode_meta_content (field v "meta");
+	}
 
 
 and decode_ctype t =
 and decode_ctype t =
 	match decode_enum t with
 	match decode_enum t with
@@ -2842,15 +2894,8 @@ let decode_expr v =
 			EVars (List.map (fun v ->
 			EVars (List.map (fun v ->
 				(dec_string (field v "name"),opt decode_ctype (field v "type"),opt loop (field v "expr"))
 				(dec_string (field v "name"),opt decode_ctype (field v "type"),opt loop (field v "expr"))
 			) (dec_array vl))
 			) (dec_array vl))
-		| 12, [f] ->
-			let ft = {
-				f_args = List.map (fun o ->
-					(dec_string (field o "name"),dec_bool (field o "opt"),opt decode_ctype (field o "type"),opt loop (field o "value"))
-				) (dec_array (field f "args"));
-				f_type = opt decode_ctype (field f "ret");
-				f_expr = loop (field f "expr");
-			} in
-			EFunction (opt dec_string (field f "name"),ft)
+		| 12, [fname;f] ->
+			EFunction (opt dec_string fname,decode_fun f)
 		| 13, [el] ->
 		| 13, [el] ->
 			EBlock (List.map loop (dec_array el))
 			EBlock (List.map loop (dec_array el))
 		| 14, [v;e1;e2] ->
 		| 14, [v;e1;e2] ->
@@ -2925,13 +2970,7 @@ let encode_meta m set =
 	let meta = ref m in
 	let meta = ref m in
 	enc_obj [
 	enc_obj [
 		"get", VFunction (Fun0 (fun() ->
 		"get", VFunction (Fun0 (fun() ->
-			enc_array (List.map (fun (m,ml,p) ->
-				enc_obj [
-					"name", enc_string m;
-					"params", enc_array (List.map encode_expr ml);
-					"pos", encode_pos p;
-				]
-			) (!meta))
+			encode_meta_content (!meta)
 		));
 		));
 		"add", VFunction (Fun3 (fun k vl p ->
 		"add", VFunction (Fun3 (fun k vl p ->
 			(try
 			(try
@@ -3197,14 +3236,20 @@ let rec make_ast e =
 			CTFunction (List.map (fun (_,_,t) -> mk_type t) args, mk_type ret)			
 			CTFunction (List.map (fun (_,_,t) -> mk_type t) args, mk_type ret)			
 		| TAnon a ->
 		| TAnon a ->
 			CTAnonymous (PMap.foldi (fun _ f acc -> 
 			CTAnonymous (PMap.foldi (fun _ f acc -> 
-				(f.cf_name,None,AFVar (mk_type f.cf_type), e.epos) :: acc
+				{
+					cff_name = f.cf_name;
+					cff_kind = FVar (mk_ot f.cf_type,None);
+					cff_pos = e.epos;
+					cff_doc = f.cf_doc;
+					cff_meta = f.cf_meta;
+					cff_access = [];
+				} :: acc
 			) a.a_fields [])
 			) a.a_fields [])
 		| (TDynamic t2) as t ->
 		| (TDynamic t2) as t ->
 			tpath ([],"Dynamic") (if t == t_dynamic then [] else [mk_type t2])
 			tpath ([],"Dynamic") (if t == t_dynamic then [] else [mk_type t2])
 		| TLazy f ->
 		| TLazy f ->
 			mk_type ((!f)())
 			mk_type ((!f)())
-	in
-	let mk_ot t =
+	and mk_ot t =
 		match follow t with
 		match follow t with
 		| TMono _ -> None
 		| TMono _ -> None
 		| _ -> Some (mk_type t)
 		| _ -> Some (mk_type t)
@@ -3227,7 +3272,7 @@ let rec make_ast e =
 	| TUnop (op,p,e) -> EUnop (op,p,make_ast e)
 	| TUnop (op,p,e) -> EUnop (op,p,make_ast e)
 	| TFunction f -> 
 	| TFunction f -> 
 		let arg (n,c,t) = n, false, mk_ot t, (match c with None -> None | Some c -> Some (EConst (mk_const c),e.epos)) in
 		let arg (n,c,t) = n, false, mk_ot t, (match c with None -> None | Some c -> Some (EConst (mk_const c),e.epos)) in
-		EFunction (None,{ f_args = List.map arg f.tf_args; f_type = mk_ot f.tf_type; f_expr = make_ast f.tf_expr })
+		EFunction (None,{ f_params = []; f_args = List.map arg f.tf_args; f_type = mk_ot f.tf_type; f_expr = Some (make_ast f.tf_expr) })
 	| TVars vl ->
 	| TVars vl ->
 		EVars (List.map (fun (n,t,e) -> n, mk_ot t, eopt e) vl)
 		EVars (List.map (fun (n,t,e) -> n, mk_ot t, eopt e) vl)
 	| TBlock el -> EBlock (List.map make_ast el)
 	| TBlock el -> EBlock (List.map make_ast el)

+ 20 - 22
parser.ml

@@ -290,9 +290,9 @@ and parse_complex_type = parser
 			| [< '(Binop OpGt,_); t = parse_type_path; '(Comma,_); s >] ->
 			| [< '(Binop OpGt,_); t = parse_type_path; '(Comma,_); s >] ->
 				(match s with parser
 				(match s with parser
 				| [< name = any_ident; l = parse_type_anonymous_resume name >] -> CTExtend (t,l)
 				| [< name = any_ident; l = parse_type_anonymous_resume name >] -> CTExtend (t,l)
-				| [< l = plist (parse_signature_field None); '(BrClose,_) >] -> CTExtend (t,l)
+				| [< l = parse_class_field_resume; '(BrClose,_) >] -> CTExtend (t,l)
 				| [< >] -> serror())
 				| [< >] -> serror())
-			| [< l = plist (parse_signature_field None); '(BrClose,_) >] -> CTAnonymous l
+			| [< l = parse_class_field_resume; '(BrClose,_) >] -> CTAnonymous l
 			| [< >] -> serror()
 			| [< >] -> serror()
 		) in
 		) in
 		parse_complex_type_next t s
 		parse_complex_type_next t s
@@ -354,7 +354,14 @@ and parse_complex_type_next t = parser
 
 
 and parse_type_anonymous_resume name = parser
 and parse_type_anonymous_resume name = parser
 	| [< '(DblDot,p); t = parse_complex_type; s >] ->
 	| [< '(DblDot,p); t = parse_complex_type; s >] ->
-		(name, None, AFVar t, p) ::
+		{
+			cff_name = name;
+			cff_meta = [];
+			cff_access = [];
+			cff_doc = None;
+			cff_kind = FVar (Some t,None);
+			cff_pos = p;
+		} ::
 		match s with parser
 		match s with parser
 		| [< '(BrClose,_) >] -> []
 		| [< '(BrClose,_) >] -> []
 		| [< '(Comma,_) >] ->
 		| [< '(Comma,_) >] ->
@@ -395,17 +402,18 @@ and parse_class_field s =
 				) in
 				) in
 				name, punion p1 p2, FVar (t,e))
 				name, punion p1 p2, FVar (t,e))
 		| [< '(Kwd Function,p1); name = parse_fun_name; pl = parse_constraint_params; '(POpen,_); al = psep Comma parse_fun_param; '(PClose,_); t = parse_type_opt; s >] ->
 		| [< '(Kwd Function,p1); name = parse_fun_name; pl = parse_constraint_params; '(POpen,_); al = psep Comma parse_fun_param; '(PClose,_); t = parse_type_opt; s >] ->
-			let e = (match s with parser
-				| [< e = toplevel_expr >] -> e
-				| [< '(Semicolon,p) >] -> (EBlock [],p)
+			let e, p2 = (match s with parser
+				| [< e = toplevel_expr >] -> Some e, pos e
+				| [< '(Semicolon,p) >] -> None, p
 				| [< >] -> serror()
 				| [< >] -> serror()
 			) in
 			) in
 			let f = {
 			let f = {
+				f_params = pl;
 				f_args = al;
 				f_args = al;
 				f_type = t;
 				f_type = t;
 				f_expr = e;
 				f_expr = e;
 			} in
 			} in
-			name, punion p1 (pos e), FFun (pl,f)
+			name, punion p1 p2, FFun f
 		| [< >] ->
 		| [< >] ->
 			if al = [] then raise Stream.Failure else serror()
 			if al = [] then raise Stream.Failure else serror()
 		) in
 		) in
@@ -418,17 +426,6 @@ and parse_class_field s =
 			cff_kind = k;
 			cff_kind = k;
 		}
 		}
 
 
-and parse_signature_field flag = parser
-	| [< '(Kwd Var,p1); name = any_ident; s >] ->
-		(match s with parser
-		| [< '(DblDot,_); t = parse_complex_type; p2 = semicolon >] -> (name,flag,AFVar t,punion p1 p2)
-		| [< '(POpen,_); i1 = property_ident; '(Comma,_); i2 = property_ident; '(PClose,_); '(DblDot,_); t = parse_complex_type; p2 = semicolon >] -> (name,flag,AFProp (t,i1,i2),punion p1 p2)
-		| [< >] -> serror())
-	| [< '(Kwd Function,p1); name = any_ident; '(POpen,_); al = psep Comma parse_fun_param_type; '(PClose,_); '(DblDot,_); t = parse_complex_type; p2 = semicolon >] ->
-		(name,flag,AFFun (al,t),punion p1 p2)
-	| [< '(Kwd Private,_) when flag = None; s >] -> parse_signature_field (Some false) s
-	| [< '(Kwd Public,_) when flag = None; s >] -> parse_signature_field (Some true) s
-
 and parse_cf_rights allow_static l = parser
 and parse_cf_rights allow_static l = parser
 	| [< '(Kwd Static,_) when allow_static; l = parse_cf_rights false (AStatic :: l) >] -> l
 	| [< '(Kwd Static,_) when allow_static; l = parse_cf_rights false (AStatic :: l) >] -> l
 	| [< '(Kwd Public,_) when not(List.mem APublic l || List.mem APrivate l); l = parse_cf_rights allow_static (APublic :: l) >] -> l
 	| [< '(Kwd Public,_) when not(List.mem APublic l || List.mem APrivate l); l = parse_cf_rights allow_static (APublic :: l) >] -> l
@@ -464,8 +461,8 @@ and parse_constraint_param = parser
 		match s with parser
 		match s with parser
 		| [< '(DblDot,_); s >] ->
 		| [< '(DblDot,_); s >] ->
 			(match s with parser
 			(match s with parser
-			| [< '(POpen,_); l = psep Comma parse_type_path; '(PClose,_) >] -> (name,l)
-			| [< t = parse_type_path >] -> (name,[t])
+			| [< '(POpen,_); l = psep Comma parse_complex_type; '(PClose,_) >] -> (name,l)
+			| [< t = parse_complex_type >] -> (name,[t])
 			| [< >] -> serror())
 			| [< >] -> serror())
 		| [< >] -> (name,[])
 		| [< >] -> (name,[])
 
 
@@ -557,12 +554,13 @@ and expr = parser
 		| [< >] -> serror())
 		| [< >] -> serror())
 	| [< '(POpen,p1); e = expr; '(PClose,p2); s >] -> expr_next (EParenthesis e, punion p1 p2) s
 	| [< '(POpen,p1); e = expr; '(PClose,p2); s >] -> expr_next (EParenthesis e, punion p1 p2) s
 	| [< '(BkOpen,p1); l = parse_array_decl; '(BkClose,p2); s >] -> expr_next (EArrayDecl l, punion p1 p2) s
 	| [< '(BkOpen,p1); l = parse_array_decl; '(BkClose,p2); s >] -> expr_next (EArrayDecl l, punion p1 p2) s
-	| [< '(Kwd Function,p1); name = popt any_ident; '(POpen,_); al = psep Comma parse_fun_param; '(PClose,_); t = parse_type_opt; s >] ->
+	| [< '(Kwd Function,p1); name = popt any_ident; pl = parse_constraint_params; '(POpen,_); al = psep Comma parse_fun_param; '(PClose,_); t = parse_type_opt; s >] ->
 		let make e =
 		let make e =
 			let f = {
 			let f = {
+				f_params = pl;
 				f_type = t;
 				f_type = t;
 				f_args = al;
 				f_args = al;
-				f_expr = e;
+				f_expr = Some e;
 			} in
 			} in
 			EFunction (name,f), punion p1 (pos e)
 			EFunction (name,f), punion p1 (pos e)
 		in
 		in

+ 1 - 1
std/Reflect.hx

@@ -43,7 +43,7 @@ extern class Reflect {
 	/**
 	/**
 		Set an object field value.
 		Set an object field value.
 	**/
 	**/
-	public inline static function setField( o : Dynamic, field : String, value : Dynamic ) : Void;
+	public static function setField( o : Dynamic, field : String, value : Dynamic ) : Void;
 
 
 	/**
 	/**
 		Call a method with the given object and arguments.
 		Call a method with the given object and arguments.

+ 21 - 8
std/haxe/macro/Expr.hx

@@ -98,7 +98,7 @@ enum ExprDef {
 	ENew( t : TypePath, params : Array<Expr> );
 	ENew( t : TypePath, params : Array<Expr> );
 	EUnop( op : Unop, postFix : Bool, e : Expr );
 	EUnop( op : Unop, postFix : Bool, e : Expr );
 	EVars( vars : Array<{ name : String, type : Null<ComplexType>, expr : Null<Expr> }> );
 	EVars( vars : Array<{ name : String, type : Null<ComplexType>, expr : Null<Expr> }> );
-	EFunction( f : Function );
+	EFunction( name : Null<String>, f : Function );
 	EBlock( exprs : Array<Expr> );
 	EBlock( exprs : Array<Expr> );
 	EFor( v : String, it : Expr, expr : Expr );
 	EFor( v : String, it : Expr, expr : Expr );
 	EIf( econd : Expr, eif : Expr, eelse : Null<Expr> );
 	EIf( econd : Expr, eif : Expr, eelse : Null<Expr> );
@@ -137,10 +137,10 @@ enum TypeParam {
 }
 }
 
 
 typedef Function = {
 typedef Function = {
-	var name : Null<String>;
 	var args : Array<FunctionArg>;
 	var args : Array<FunctionArg>;
 	var ret : Null<ComplexType>;
 	var ret : Null<ComplexType>;
-	var expr : Expr;
+	var expr : Null<Expr>;
+	var params : Array<{ name : String, constraints : Array<ComplexType> }>;
 }
 }
 
 
 typedef FunctionArg = {
 typedef FunctionArg = {
@@ -150,16 +150,29 @@ typedef FunctionArg = {
 	var value : Null<Expr>;
 	var value : Null<Expr>;
 }
 }
 
 
+typedef Metadata = Array<{ name : String, params : Array<Expr>, pos : Position }>;
+
 typedef Field = {
 typedef Field = {
 	var name : String;
 	var name : String;
-	var isPublic : Null<Bool>;
-	var type : FieldType;
+	var doc : Null<String>;
+	var access : Array<Access>;
+	var kind : FieldType;
 	var pos : Position;
 	var pos : Position;
+	var meta : Metadata;
+}
+
+enum Access {
+	APublic;
+	APrivate;
+	AStatic;
+	AOverride;
+	ADynamic;
+	AInline;
 }
 }
 
 
 enum FieldType {
 enum FieldType {
-	FVar( t : ComplexType );
-	FProp( t : ComplexType, get : String, set : String );
-	FFun( args : Array<{ name : String, opt : Bool, type : ComplexType }>, ret : ComplexType );
+	FVar( t : Null<ComplexType>, e : Null<Expr> );
+	FFun( f : Function );
+	FProp( get : String, set : String, t : ComplexType );
 }
 }
 
 

+ 5 - 5
std/haxe/macro/Type.hx

@@ -51,7 +51,7 @@ typedef BaseType = {
 	var isPrivate : Bool;
 	var isPrivate : Bool;
 	var isExtern : Bool;
 	var isExtern : Bool;
 	var params : Array<{ name : String, t : Type }>;
 	var params : Array<{ name : String, t : Type }>;
-	var meta : Metadata;
+	var meta : MetaAccess;
 	function exclude() : Void;
 	function exclude() : Void;
 }
 }
 
 
@@ -60,7 +60,7 @@ typedef ClassField = {
 	var type : Type;
 	var type : Type;
 	var isPublic : Bool;
 	var isPublic : Bool;
 	var params : Array<{ name : String, t : Type }>;
 	var params : Array<{ name : String, t : Type }>;
-	var meta : Metadata;
+	var meta : MetaAccess;
 	var kind : FieldKind;
 	var kind : FieldKind;
 	var expr : Null<TypedExpr>;
 	var expr : Null<TypedExpr>;
 	var pos : Expr.Position;
 	var pos : Expr.Position;
@@ -83,7 +83,7 @@ typedef EnumField = {
 	var name : String;
 	var name : String;
 	var type : Type;
 	var type : Type;
 	var pos : Expr.Position;
 	var pos : Expr.Position;
-	var meta : Metadata;
+	var meta : MetaAccess;
 	var index : Int;
 	var index : Int;
 }
 }
 
 
@@ -96,8 +96,8 @@ typedef DefType = {> BaseType,
 	var type : Type;
 	var type : Type;
 }
 }
 
 
-typedef Metadata = {
-	function get() : Array<{ name : String, params : Array<Expr>, pos : Expr.Position }>;
+typedef MetaAccess = {
+	function get() : Expr.Metadata;
 	function add( name : String, params : Array<Expr>, pos : Expr.Position ) : Void;
 	function add( name : String, params : Array<Expr>, pos : Expr.Position ) : Void;
 	function remove( name : String ) : Void;
 	function remove( name : String ) : Void;
 	function has( name : String ) : Bool;
 	function has( name : String ) : Bool;

+ 1 - 1
typecore.ml

@@ -29,7 +29,7 @@ type typer_globals = {
 	types_module : (path, path) Hashtbl.t;
 	types_module : (path, path) Hashtbl.t;
 	modules : (path , module_def) Hashtbl.t;
 	modules : (path , module_def) Hashtbl.t;
 	mutable delayed : (unit -> unit) list;
 	mutable delayed : (unit -> unit) list;
-	constructs : (path , Ast.access list * Ast.type_param list * Ast.func) Hashtbl.t;
+	constructs : (path , Ast.access list * Ast.func) Hashtbl.t;
 	doinline : bool;
 	doinline : bool;
 	mutable core_api : typer option;
 	mutable core_api : typer option;
 	mutable macros : ((unit -> unit) * typer) option;
 	mutable macros : ((unit -> unit) * typer) option;

+ 61 - 34
typeload.ml

@@ -199,16 +199,37 @@ and load_complex_type ctx p t =
 			loop (load_instance ctx t p false)
 			loop (load_instance ctx t p false)
 		| _ -> assert false)
 		| _ -> assert false)
 	| CTAnonymous l ->
 	| CTAnonymous l ->
-		let rec loop acc (n,pub,f,p) =
+		let rec loop acc f =
+			let n = f.cff_name in
+			let p = f.cff_pos in
 			if PMap.mem n acc then error ("Duplicate field declaration : " ^ n) p;
 			if PMap.mem n acc then error ("Duplicate field declaration : " ^ n) p;
-			let t , access = (match f with
-				| AFVar t ->
-					load_complex_type ctx p t, Var { v_read = AccNormal; v_write = AccNormal }
-				| AFFun (tl,t) ->
-					let t = load_complex_type ctx p t in
-					let args = List.map (fun (name,o,t) -> name , o, load_complex_type ctx p t) tl in
-					TFun (args,t), Method MethNormal
-				| AFProp (t,i1,i2) ->
+			let topt = function
+				| None -> error ("Explicit type required for field " ^ n) p
+				| Some t -> load_complex_type ctx p t
+			in
+			let no_expr = function
+				| None -> ()
+				| Some (_,p) -> error "Expression not allowed here" p
+			in
+			let pub = ref true in
+			let dyn = ref false in
+			List.iter (fun a ->
+				match a with
+				| APublic -> ()
+				| APrivate -> pub := false;
+				| ADynamic when (match f.cff_kind with FFun _ -> true | _ -> false) -> dyn := true
+				| AStatic | AOverride | AInline | ADynamic -> error ("Invalid access " ^ Ast.s_access a) p
+			) f.cff_access;
+			let t , access = (match f.cff_kind with
+				| FVar (t, e) ->
+					no_expr e;
+					topt t, Var { v_read = AccNormal; v_write = AccNormal }
+				| FFun f ->
+					if f.f_params <> [] then error "Type parameters are not allowed in structures" p;
+					no_expr f.f_expr;
+					let args = List.map (fun (name,o,t,e) -> no_expr e; name, o, topt t) f.f_args in
+					TFun (args,topt f.f_type), Method (if !dyn then MethDynamic else MethNormal)
+				| FProp (i1,i2,t) ->
 					let access m get =
 					let access m get =
 						match m with
 						match m with
 						| "null" -> AccNo
 						| "null" -> AccNo
@@ -223,12 +244,12 @@ and load_complex_type ctx p t =
 				cf_name = n;
 				cf_name = n;
 				cf_type = t;
 				cf_type = t;
 				cf_pos = p;
 				cf_pos = p;
-				cf_public = (match pub with None -> true | Some p -> p);
+				cf_public = !pub;
 				cf_kind = access;
 				cf_kind = access;
 				cf_params = [];
 				cf_params = [];
 				cf_expr = None;
 				cf_expr = None;
-				cf_doc = None;
-				cf_meta = no_meta;
+				cf_doc = f.cff_doc;
+				cf_meta = f.cff_meta;
 			} acc
 			} acc
 		in
 		in
 		mk_anon (List.fold_left loop PMap.empty l)
 		mk_anon (List.fold_left loop PMap.empty l)
@@ -491,7 +512,7 @@ let type_type_params ctx path get_params p (n,flags) =
 		let r = exc_protect (fun r ->
 		let r = exc_protect (fun r ->
 			r := (fun _ -> t);
 			r := (fun _ -> t);
 			let ctx = { ctx with type_params = ctx.type_params @ get_params() } in
 			let ctx = { ctx with type_params = ctx.type_params @ get_params() } in
-			set_heritance ctx c (List.map (fun t -> HImplements t) flags) p;
+			set_heritance ctx c (List.map (fun t -> match t with CTPath t -> HImplements t | _ -> error "Unsupported type constraint" p) flags) p;
 			t
 			t
 		) in
 		) in
 		delay ctx (fun () -> ignore(!r()));
 		delay ctx (fun () -> ignore(!r()));
@@ -521,7 +542,7 @@ let type_function ctx args ret static constr f p =
 	ctx.in_constructor <- constr;
 	ctx.in_constructor <- constr;
 	ctx.ret <- ret;
 	ctx.ret <- ret;
 	ctx.opened <- [];
 	ctx.opened <- [];
-	let e = type_expr ctx f.f_expr false in
+	let e = type_expr ctx (match f.f_expr with None -> error "Function body required" p | Some e -> e) false in
 	let rec loop e =
 	let rec loop e =
 		match e.eexpr with
 		match e.eexpr with
 		| TReturn (Some _) -> raise Exit
 		| TReturn (Some _) -> raise Exit
@@ -619,7 +640,7 @@ let patch_class ctx c fields =
 			| f :: l ->
 			| f :: l ->
 				(* patch arguments types *)
 				(* patch arguments types *)
 				(match f.cff_kind with
 				(match f.cff_kind with
-				| FFun (pl,ff) ->
+				| FFun ff ->
 					let param ((n,opt,t,e) as p) =
 					let param ((n,opt,t,e) as p) =
 						try
 						try
 							let t2 = (try Hashtbl.find h (("$" ^ f.cff_name ^ "__" ^ n),false) with Not_found -> Hashtbl.find h (("$" ^ n),false)) in
 							let t2 = (try Hashtbl.find h (("$" ^ f.cff_name ^ "__" ^ n),false) with Not_found -> Hashtbl.find h (("$" ^ n),false)) in
@@ -627,7 +648,7 @@ let patch_class ctx c fields =
 						with Not_found ->
 						with Not_found ->
 							p
 							p
 					in
 					in
-					f.cff_kind <- FFun (pl,{ ff with f_args = List.map param ff.f_args })
+					f.cff_kind <- FFun { ff with f_args = List.map param ff.f_args }
 				| _ -> ());
 				| _ -> ());
 				(* other patches *)
 				(* other patches *)
 				match (try Some (Hashtbl.find h (f.cff_name,List.mem AStatic f.cff_access)) with Not_found -> None) with
 				match (try Some (Hashtbl.find h (f.cff_name,List.mem AStatic f.cff_access)) with Not_found -> None) with
@@ -641,7 +662,7 @@ let patch_class ctx c fields =
 						f.cff_kind <- match f.cff_kind with
 						f.cff_kind <- match f.cff_kind with
 						| FVar (_,e) -> FVar (Some t,e)
 						| FVar (_,e) -> FVar (Some t,e)
 						| FProp (get,set,_) -> FProp (get,set,t)
 						| FProp (get,set,_) -> FProp (get,set,t)
-						| FFun (pl,f) -> FFun (pl,{ f with f_type = Some t }));
+						| FFun f -> FFun { f with f_type = Some t });
 					loop (f :: acc) l
 					loop (f :: acc) l
 		in
 		in
 		List.rev (loop [] fields)
 		List.rev (loop [] fields)
@@ -685,7 +706,7 @@ let init_class ctx c p herits fields =
 			List.map (fun (e,p) ->
 			List.map (fun (e,p) ->
 				let n, k = (match e with
 				let n, k = (match e with
 				| EVars [v,t,e] -> v, FVar (t,e)
 				| EVars [v,t,e] -> v, FVar (t,e)
-				| EFunction (Some n,f) -> (if n = "__new__" then "new" else n), FFun ([],f)
+				| EFunction (Some n,f) -> (if n = "__new__" then "new" else n), FFun f
 				| _ -> error "Class build expression should be a single variable or a named function" p
 				| _ -> error "Class build expression should be a single variable or a named function" p
 				) in
 				) in
 				let accesses = [APublic; APrivate; AStatic; AOverride; ADynamic; AInline] in
 				let accesses = [APublic; APrivate; AStatic; AOverride; ADynamic; AInline] in
@@ -908,14 +929,14 @@ let init_class ctx c p herits fields =
 					bind_type cf r (snd e) false
 					bind_type cf r (snd e) false
 			) in
 			) in
 			f, false, cf, delay
 			f, false, cf, delay
-		| FFun (fparams,fd) ->
+		| FFun fd ->
 			let params = ref [] in
 			let params = ref [] in
 			params := List.map (fun (n,flags) ->
 			params := List.map (fun (n,flags) ->
 				match flags with
 				match flags with
 				| [] ->
 				| [] ->
 					type_type_params ctx ([],name) (fun() -> !params) p (n,[])
 					type_type_params ctx ([],name) (fun() -> !params) p (n,[])
 				| _ -> error "This notation is not allowed because it can't be checked" p
 				| _ -> error "This notation is not allowed because it can't be checked" p
-			) fparams;
+			) fd.f_params;
 			let params = !params in
 			let params = !params in
 			if inline && c.cl_interface then error "You can't declare inline methods in interfaces" p;
 			if inline && c.cl_interface then error "You can't declare inline methods in interfaces" p;
 			let is_macro = (is_macro && stat) || has_meta ":macro" f.cff_meta in
 			let is_macro = (is_macro && stat) || has_meta ":macro" f.cff_meta in
@@ -933,6 +954,7 @@ let init_class ctx c p herits fields =
 			else if ctx.in_macro then
 			else if ctx.in_macro then
 				let texpr = CTPath { tpackage = ["haxe";"macro"]; tname = "Expr"; tparams = []; tsub = None } in
 				let texpr = CTPath { tpackage = ["haxe";"macro"]; tname = "Expr"; tparams = []; tsub = None } in
 				{
 				{
+					f_params = fd.f_params;
 					f_type = (match fd.f_type with None -> Some texpr | t -> t);
 					f_type = (match fd.f_type with None -> Some texpr | t -> t);
 					f_args = List.map (fun (a,o,t,e) -> a,o,(match t with None -> Some texpr | _ -> t),e) fd.f_args;
 					f_args = List.map (fun (a,o,t,e) -> a,o,(match t with None -> Some texpr | _ -> t),e) fd.f_args;
 					f_expr = fd.f_expr;
 					f_expr = fd.f_expr;
@@ -945,9 +967,10 @@ let init_class ctx c p herits fields =
 					| _ -> tdyn
 					| _ -> tdyn
 				in
 				in
 				{
 				{
+					f_params = fd.f_params;
 					f_type = (match fd.f_type with Some (CTPath t) -> to_dyn t | _ -> tdyn);
 					f_type = (match fd.f_type with Some (CTPath t) -> to_dyn t | _ -> tdyn);
 					f_args = List.map (fun (a,o,t,_) -> a,o,(match t with Some (CTPath t) -> to_dyn t | _ -> tdyn),None) fd.f_args;
 					f_args = List.map (fun (a,o,t,_) -> a,o,(match t with Some (CTPath t) -> to_dyn t | _ -> tdyn),None) fd.f_args;
-					f_expr = (EBlock [],p)
+					f_expr = None;
 				}
 				}
 			in
 			in
 			let parent = (if not stat then get_parent c name else None) in
 			let parent = (if not stat then get_parent c name else None) in
@@ -967,7 +990,7 @@ let init_class ctx c p herits fields =
 			let t = TFun (fun_args args,ret) in
 			let t = TFun (fun_args args,ret) in
 			let constr = (name = "new") in
 			let constr = (name = "new") in
 			if constr && c.cl_interface then error "An interface cannot have a constructor" p;
 			if constr && c.cl_interface then error "An interface cannot have a constructor" p;
-			if c.cl_interface && not stat && (match fd.f_expr with EBlock [] , _ -> false | _ -> true) then error "An interface method cannot have a body" p;
+			if c.cl_interface && not stat && fd.f_expr <> None then error "An interface method cannot have a body" p;
 			if constr then (match fd.f_type with
 			if constr then (match fd.f_type with
 				| None | Some (CTPath { tpackage = []; tname = "Void" }) -> ()
 				| None | Some (CTPath { tpackage = []; tname = "Void" }) -> ()
 				| _ -> error "A class constructor can't have a return value" p
 				| _ -> error "A class constructor can't have a return value" p
@@ -1014,7 +1037,7 @@ let init_class ctx c p herits fields =
 			end else if ((c.cl_extern && not inline) || c.cl_interface) && cf.cf_name <> "__init__" then
 			end else if ((c.cl_extern && not inline) || c.cl_interface) && cf.cf_name <> "__init__" then
 				(fun() -> ())
 				(fun() -> ())
 			else
 			else
-				bind_type cf r (snd fd.f_expr) is_macro
+				bind_type cf r (match fd.f_expr with Some e -> snd e | None -> f.cff_pos) is_macro
 			in
 			in
 			f, constr, cf, delay
 			f, constr, cf, delay
 		| FProp (get,set,t) ->
 		| FProp (get,set,t) ->
@@ -1127,11 +1150,11 @@ let init_class ctx c p herits fields =
 			| Some (csuper,_) ->
 			| Some (csuper,_) ->
 				match define_constructor ctx csuper with
 				match define_constructor ctx csuper with
 				| None -> None
 				| None -> None
-				| Some (acc,pl,f) as infos ->
+				| Some (acc,f) as infos ->
 					let p = c.cl_pos in
 					let p = c.cl_pos in
 					let esuper = (ECall ((EConst (Ident "super"),p),List.map (fun (n,_,_,_) -> (EConst (Ident n),p)) f.f_args),p) in
 					let esuper = (ECall ((EConst (Ident "super"),p),List.map (fun (n,_,_,_) -> (EConst (Ident n),p)) f.f_args),p) in
 					let acc = (if csuper.cl_extern && acc = [] then [APublic] else acc) in
 					let acc = (if csuper.cl_extern && acc = [] then [APublic] else acc) in
-					let fnew = { f with f_expr = esuper; f_args = List.map (fun (a,opt,t,def) ->
+					let fnew = { f with f_expr = Some esuper; f_args = List.map (fun (a,opt,t,def) ->
 						(*
 						(*
 							we are removing the type and letting the type inference
 							we are removing the type and letting the type inference
 							work because the current package is not the same as the superclass one
 							work because the current package is not the same as the superclass one
@@ -1145,12 +1168,16 @@ let init_class ctx c p herits fields =
 							| CTPath t -> is_qual_name t
 							| CTPath t -> is_qual_name t
 							| CTParent t -> is_qualified t
 							| CTParent t -> is_qualified t
 							| CTFunction (tl,t) -> List.for_all is_qualified tl && is_qualified t
 							| CTFunction (tl,t) -> List.for_all is_qualified tl && is_qualified t
-							| CTAnonymous fl -> List.for_all (fun (_,_,f,_) -> is_qual_field f) fl
-							| CTExtend (t,fl) -> is_qual_name t && List.for_all (fun (_,_,f,_) -> is_qual_field f) fl
-						and is_qual_field = function
-							| AFVar t -> is_qualified t
-							| AFProp (t,_,_) -> is_qualified t
-							| AFFun (pl,t) -> List.for_all (fun (_,_,t) -> is_qualified t) pl && is_qualified t
+							| CTAnonymous fl -> List.for_all is_qual_field fl
+							| CTExtend (t,fl) -> is_qual_name t && List.for_all is_qual_field fl
+						and is_qual_field f =
+							match f.cff_kind with
+							| FVar (t,_) -> is_qual_opt t
+							| FProp (_,_,t) -> is_qualified t
+							| FFun f -> List.for_all (fun (_,_,t,_) -> is_qual_opt t) f.f_args && is_qual_opt f.f_type
+						and is_qual_opt = function
+							| None -> true
+							| Some t -> is_qualified t
 						and is_qual_name t =
 						and is_qual_name t =
 							match t.tpackage with
 							match t.tpackage with
 							| [] -> t.tname = "Dynamic" && List.for_all is_qual_param t.tparams
 							| [] -> t.tname = "Dynamic" && List.for_all is_qual_param t.tparams
@@ -1165,9 +1192,9 @@ let init_class ctx c p herits fields =
 						) in
 						) in
 						a,opt,t,def
 						a,opt,t,def
 					) f.f_args } in
 					) f.f_args } in
-					let _, _, cf, delayed = loop_cf { cff_name = "new"; cff_pos = p; cff_doc = None; cff_meta = []; cff_access = acc; cff_kind = FFun (pl,fnew) } in
+					let _, _, cf, delayed = loop_cf { cff_name = "new"; cff_pos = p; cff_doc = None; cff_meta = []; cff_access = acc; cff_kind = FFun fnew } in
 					c.cl_constructor <- Some cf;
 					c.cl_constructor <- Some cf;
-					Hashtbl.add ctx.g.constructs c.cl_path (acc,pl,f);
+					Hashtbl.add ctx.g.constructs c.cl_path (acc,f);
 					delay ctx delayed;
 					delay ctx delayed;
 					infos
 					infos
 	in
 	in
@@ -1214,7 +1241,7 @@ let type_module ctx m tdecls loadp =
 			(* store the constructor for later usage *)
 			(* store the constructor for later usage *)
 			List.iter (fun cf ->
 			List.iter (fun cf ->
 				match cf with
 				match cf with
-				| { cff_name = "new"; cff_kind = FFun (pl,f) } -> Hashtbl.add ctx.g.constructs path (cf.cff_access,pl,f)
+				| { cff_name = "new"; cff_kind = FFun f } -> Hashtbl.add ctx.g.constructs path (cf.cff_access,f)
 				| _ -> ()
 				| _ -> ()
 			) d.d_data;
 			) d.d_data;
 			decls := TClassDecl c :: !decls
 			decls := TClassDecl c :: !decls

+ 1 - 1
typer.ml

@@ -1966,7 +1966,7 @@ let make_macro_api ctx p =
 			let head = "class X{static function main() " in
 			let head = "class X{static function main() " in
 			let head = (if p.pmin > String.length head then head ^ String.make (p.pmin - String.length head) ' ' else head) in
 			let head = (if p.pmin > String.length head then head ^ String.make (p.pmin - String.length head) ' ' else head) in
 			match parse_string ctx (head ^ s ^ "}") p with
 			match parse_string ctx (head ^ s ^ "}") p with
-			| EClass { d_data = [{ cff_name = "main"; cff_kind = FFun (_,{ f_expr = e }) }]} -> e
+			| EClass { d_data = [{ cff_name = "main"; cff_kind = FFun { f_expr = Some e } }]} -> e
 			| _ -> assert false
 			| _ -> assert false
 		);
 		);
 		Interp.typeof = (fun e ->
 		Interp.typeof = (fun e ->