Skip to content

Commit

Permalink
[cs] Only use __hx_cast when the types fail to unify (and are not Dyn…
Browse files Browse the repository at this point in the history
…amic). Old behaviour can still have a fallback with -D cs_safe_casts. Fixed last failing test. Closes HaxeFoundation#2066
  • Loading branch information
waneck committed Mar 3, 2014
1 parent b5bbcc4 commit 7d5d185
Show file tree
Hide file tree
Showing 2 changed files with 28 additions and 8 deletions.
23 changes: 19 additions & 4 deletions gencommon.ml
Original file line number Diff line number Diff line change
Expand Up @@ -4526,9 +4526,20 @@ struct
match e.eexpr with
| TCast(cast_expr, _) ->
(* see if casting to a native generic class *)
let t = follow (gen.greal_type e.etype) in
(match t with
| TInst(cl, p1 :: pl) when is_hxgeneric (TClassDecl cl) ->
let t = gen.greal_type e.etype in
let unifies =
let ctype = gen.greal_type cast_expr.etype in
match follow ctype with
| TInst(cl,_) -> (try
unify ctype t;
true
with | Unify_error el ->
false)
| _ -> false
in
let unifies = unifies && not (PMap.mem "cs_safe_casts" gen.gcon.defines) in
(match follow t with
| TInst(cl, p1 :: pl) when is_hxgeneric (TClassDecl cl) && not unifies ->
let iface = Hashtbl.find ifaces cl.cl_path in
mk_cast e.etype (change_expr (Type.map_expr run cast_expr) cl iface (p1 :: pl))
| _ -> Type.map_expr run e
Expand Down Expand Up @@ -6237,7 +6248,11 @@ struct
| _ -> None
in
(match get_null expr with
| Some enull -> { enull with etype = e.etype }
| Some enull ->
if gen.gcon.platform = Cs then
{ enull with etype = gen.greal_type e.etype }
else
mk_cast (gen.greal_type e.etype) enull
| _ ->
let last_unsafe = gen.gon_unsafe_cast in
gen.gon_unsafe_cast <- (fun t t2 pos -> ());
Expand Down
13 changes: 9 additions & 4 deletions gencs.ml
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ open Printf
open Option
open ExtString

let is_cs_basic_type t =
let rec is_cs_basic_type t =
match follow t with
| TInst( { cl_path = (["haxe"], "Int32") }, [] )
| TInst( { cl_path = (["haxe"], "Int64") }, [] )
Expand All @@ -43,6 +43,8 @@ let is_cs_basic_type t =
true
| TAbstract _ when like_float t ->
true
| TAbstract({ a_impl = Some _ } as a,pl) ->
is_cs_basic_type (Codegen.Abstract.get_underlying_type a pl)
| TEnum(e, _) when not (Meta.has Meta.Class e.e_meta) -> true
| TInst(cl, _) when Meta.has Meta.Struct cl.cl_meta -> true
| _ -> false
Expand Down Expand Up @@ -787,7 +789,9 @@ let configure gen =
*)
change_param_type md tl =
let is_hxgeneric = (TypeParams.RealTypeParams.is_hxgeneric md) in
let ret t = match is_hxgeneric, real_type t with
let ret t =
let t_changed = real_type t in
match is_hxgeneric, t_changed with
| false, _ -> t
(*
Because Null<> types need a special compiler treatment for many operations (e.g. boxing/unboxing),
Expand All @@ -797,9 +801,10 @@ let configure gen =
| true, TInst ( { cl_kind = KTypeParameter _ }, _ ) -> t
| true, TInst _
| true, TEnum _
| true, TAbstract _ when is_cs_basic_type t -> t
| true, TAbstract _ when is_cs_basic_type t_changed -> t
| true, TDynamic _ -> t
| true, _ -> dynamic_anon
| true, x ->
dynamic_anon
in
if is_hxgeneric && List.exists (fun t -> match follow t with | TDynamic _ -> true | _ -> false) tl then
List.map (fun _ -> t_dynamic) tl
Expand Down

0 comments on commit 7d5d185

Please sign in to comment.