Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[cs/java] use native arrays for dynamic function invokation #6125

Merged
merged 1 commit into from
Mar 24, 2017
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 12 additions & 10 deletions src/generators/gencommon/closuresToClass.ml
Original file line number Diff line number Diff line change
Expand Up @@ -615,7 +615,7 @@ struct
let args_real_to_func args =
let arity = List.length args in
if arity >= max_arity then
[ alloc_var (mk_internal_name "fn" "dynargs") (basic.tarray t_dynamic), None ]
[ alloc_var (mk_internal_name "fn" "dynargs") (gen.gclasses.nativearray t_dynamic), None ]
else func_args_i arity
in

Expand All @@ -634,7 +634,7 @@ struct
let args_real_to_func_sig args =
let arity = List.length args in
if arity >= max_arity then
[mk_internal_name "fn" "dynargs", false, basic.tarray t_dynamic]
[mk_internal_name "fn" "dynargs", false, gen.gclasses.nativearray t_dynamic]
else begin
func_sig_i arity
end
Expand All @@ -651,7 +651,7 @@ struct

let args_real_to_func_call el (pos:pos) =
if List.length el >= max_arity then
[{ eexpr = TArrayDecl el; etype = basic.tarray t_dynamic; epos = pos }]
[mk_nativearray_decl gen t_dynamic el pos]
else begin
List.fold_left (fun acc e ->
if like_float (gen.greal_type e.etype) && not (like_i64 (gen.greal_type e.etype)) then
Expand Down Expand Up @@ -679,11 +679,13 @@ struct
if arity >= max_arity then begin
let varray = match changed_args with | [v,_] -> v | _ -> assert false in
let varray_local = mk_local varray pos in
let mk_varray i = { eexpr = TArray(varray_local, { eexpr = TConst(TInt(Int32.of_int i)); etype = basic.tint; epos = pos }); etype = t_dynamic; epos = pos } in

snd (List.fold_left (fun (count,acc) (v,const) ->
(count + 1, (mk (TVar(v, Some(mk_const const (mk_varray count) v.v_type))) basic.tvoid pos) :: acc)
) (0,[]) args)
let mk_varray i = { eexpr = TArray(varray_local, ExprBuilder.make_int gen.gcon i pos); etype = t_dynamic; epos = pos } in
let el =
snd (List.fold_left (fun (count,acc) (v,const) ->
(count + 1, (mk (TVar(v, Some(mk_const const (mk_varray count) v.v_type))) basic.tvoid pos) :: acc)
) (0, []) args)
in
List.rev el
end else begin
let _, dyn_args, float_args = List.fold_left (fun (count,fargs, dargs) arg ->
if count land 1 = 0 then
Expand Down Expand Up @@ -844,7 +846,7 @@ struct
in

let type_name = mk_internal_name "fn" "type" in
let dynamic_arg = alloc_var (mk_internal_name "fn" "dynargs") (basic.tarray t_dynamic) in
let dynamic_arg = alloc_var (mk_internal_name "fn" "dynargs") (gen.gclasses.nativearray t_dynamic) in

let mk_invoke_complete_i i is_float =

Expand Down Expand Up @@ -1076,7 +1078,7 @@ struct
eexpr = TIf(
mk (TBinop (OpEq, dynargs, null dynargs.etype pos)) basic.tbool pos,
mk (TConst (TInt Int32.zero)) basic.tint pos,
Some (mk_field_access gen dynargs "length" pos));
Some (gen.gclasses.nativearray_len dynargs pos));
etype = basic.tint;
epos = pos;
} in
Expand Down
12 changes: 6 additions & 6 deletions src/generators/gencommon/reflectionCFs.ml
Original file line number Diff line number Diff line change
Expand Up @@ -1297,7 +1297,7 @@ let implement_invokeField ctx slow_invoke cl =
let field_args, switch_var = field_type_args ctx cl.cl_pos in
let field_args_exprs = List.map (fun (v,_) -> mk_local v pos) field_args in

let dynamic_arg = alloc_var "dynargs" (basic.tarray t_dynamic) in
let dynamic_arg = alloc_var "dynargs" (gen.gclasses.nativearray t_dynamic) in
let all_args = field_args @ [ dynamic_arg, None ] in
let fun_t = TFun(fun_args all_args, t_dynamic) in

Expand Down Expand Up @@ -1434,7 +1434,7 @@ let implement_varargs_cl ctx cl =
let mk_this field t = { (mk_field_access gen this field pos) with etype = t } in

let invokedyn = mk_internal_name "hx" "invokeDynamic" in
let idyn_t = TFun([mk_internal_name "fn" "dynargs", false, basic.tarray t_dynamic], t_dynamic) in
let idyn_t = TFun([mk_internal_name "fn" "dynargs", false, gen.gclasses.nativearray t_dynamic], t_dynamic) in
let this_idyn = mk_this invokedyn idyn_t in

let map_fn arity ret vars api =
Expand All @@ -1450,9 +1450,9 @@ let implement_varargs_cl ctx cl =
let call_arg = if arity = (-1) then
api (-1) t_dynamic None
else if arity = 0 then
null (basic.tarray t_empty) pos
null (gen.gclasses.nativearray t_empty) pos
else
{ eexpr = TArrayDecl(loop (arity - 1) []); etype = basic.tarray t_empty; epos = pos }
mk_nativearray_decl gen t_empty (loop (arity - 1) []) pos
in

let expr = {
Expand Down Expand Up @@ -1513,9 +1513,9 @@ let implement_closure_cl ctx cl =
let call_arg = if arity = (-1) then
api (-1) t_dynamic None
else if arity = 0 then
null (basic.tarray t_empty) pos
null (gen.gclasses.nativearray t_empty) pos
else
{ eexpr = TArrayDecl(loop (arity - 1) []); etype = basic.tarray t_empty; epos = pos }
mk_nativearray_decl gen t_empty (loop (arity - 1) []) pos
in

let expr = {
Expand Down
4 changes: 2 additions & 2 deletions src/generators/gencs.ml
Original file line number Diff line number Diff line change
Expand Up @@ -2797,9 +2797,9 @@ let generate con =
in

let arr_call = if args <> [] then
{ eexpr = TArrayDecl args; etype = basic.tarray t_dynamic; epos = ecall.epos }
mk_nativearray_decl gen t_dynamic args ecall.epos
else
null (basic.tarray t_dynamic) ecall.epos
null (gen.gclasses.nativearray t_dynamic) ecall.epos
in

let call_args =
Expand Down
4 changes: 2 additions & 2 deletions src/generators/genjava.ml
Original file line number Diff line number Diff line change
Expand Up @@ -2167,9 +2167,9 @@ let generate con =
in

let arr_call = if args <> [] then
{ eexpr = TArrayDecl args; etype = basic.tarray t_dynamic; epos = ecall.epos }
mk_nativearray_decl gen t_dynamic args ecall.epos
else
null (basic.tarray t_dynamic) ecall.epos
null (gen.gclasses.nativearray t_dynamic) ecall.epos
in


Expand Down
3 changes: 2 additions & 1 deletion std/cs/_std/Reflect.hx
Original file line number Diff line number Diff line change
Expand Up @@ -76,13 +76,14 @@ import cs.system.reflection.*;
if (ihx != null)
untyped ihx.__hx_setField(field, FieldLookup.hash(field), value, true);
else if (Runtime.slowHasField(o, 'set_$field'))
Runtime.slowCallField(o, 'set_$field', [value]);
Runtime.slowCallField(o, 'set_$field', cs.NativeArray.make(value));
else
Runtime.slowSetField(o,field,value);
}

public static function callMethod( o : Dynamic, func : haxe.Constraints.Function, args : Array<Dynamic> ) : Dynamic
{
var args = cs.Lib.nativeArray(args,true);
return untyped cast(func, Function).__hx_invokeDynamic(args);
}

Expand Down
4 changes: 2 additions & 2 deletions std/cs/_std/Type.hx
Original file line number Diff line number Diff line change
Expand Up @@ -165,7 +165,7 @@ enum ValueType {
t = Lib.toNativeType(resolveClass(getClassName(cl)));
}
var ctors = t.GetConstructors();
return Runtime.callMethod(null, cast ctors, ctors.Length, args);
return Runtime.callMethod(null, cast ctors, ctors.Length, cs.Lib.nativeArray(args,true));
}

// cache empty constructor arguments so we don't allocate it on each createEmptyInstance call
Expand Down Expand Up @@ -202,7 +202,7 @@ enum ValueType {
throw 'Constructor $constr needs parameters';
return ret;
} else {
return cs.internal.Runtime.slowCallField(e,constr,params);
return cs.internal.Runtime.slowCallField(e,constr,cs.Lib.nativeArray(params,true));
}
}

Expand Down
8 changes: 4 additions & 4 deletions std/cs/internal/Function.hx
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ package cs.internal;

@:keep @:nativeGen @:native("haxe.lang.VarArgsBase") private class VarArgsBase extends Function
{
public function __hx_invokeDynamic(dynArgs:Array<Dynamic>):Dynamic
public function __hx_invokeDynamic(dynArgs:cs.NativeArray<Dynamic>):Dynamic
{
throw "Abstract implementation";
}
Expand All @@ -53,9 +53,9 @@ package cs.internal;
this.fun = fun;
}

override public function __hx_invokeDynamic(dynArgs:Array<Dynamic>):Dynamic
override public function __hx_invokeDynamic(dynArgs:cs.NativeArray<Dynamic>):Dynamic
{
return fun(dynArgs);
return fun(cs.Lib.array(dynArgs));
}
}

Expand All @@ -73,7 +73,7 @@ package cs.internal;
this.hash = hash;
}

override public function __hx_invokeDynamic(dynArgs:Array<Dynamic>):Dynamic
override public function __hx_invokeDynamic(dynArgs:cs.NativeArray<Dynamic>):Dynamic
{
return Runtime.callField(obj, field, hash, dynArgs);
}
Expand Down
19 changes: 6 additions & 13 deletions std/cs/internal/Runtime.hx
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,7 @@ import cs.system.Object;
return obj.__hx_setField_f(field, (fieldHash == 0) ? haxe.lang.FieldLookup.hash(field) : fieldHash, value, false);
}

public static object callField(haxe.lang.HxObject obj, string field, int fieldHash, Array args)
public static object callField(haxe.lang.HxObject obj, string field, int fieldHash, object[] args)
{
return obj.__hx_invokeField(field, (fieldHash == 0) ? haxe.lang.FieldLookup.hash(field) : fieldHash, args);
}
Expand Down Expand Up @@ -429,7 +429,7 @@ import cs.system.Object;
}
}

public static function callMethod(obj:Dynamic, methods:NativeArray<MethodBase>, methodLength:Int, args:Array<Dynamic>):Dynamic
public static function callMethod(obj:Dynamic, methods:NativeArray<MethodBase>, methodLength:Int, args:cs.NativeArray<Dynamic>):Dynamic
{
if (methodLength == 0) throw "No available methods";
var length = args.length;
Expand Down Expand Up @@ -578,13 +578,13 @@ import cs.system.Object;
}
#end

public static function slowCallField(obj:Dynamic, field:String, args:Array<Dynamic>):Dynamic
public static function slowCallField(obj:Dynamic, field:String, args:cs.NativeArray<Dynamic>):Dynamic
{
if (field == "toString" && (args == null || args.length == 0))
{
return obj.ToString();
}
if (args == null) args = [];
if (args == null) args = new cs.NativeArray(0);

var bf:BindingFlags;
var t = Lib.as(obj,cs.system.Type);
Expand Down Expand Up @@ -625,14 +625,7 @@ import cs.system.Object;
}

if (last == 0 && t.IsCOMObject)
{
var oargs = new NativeArray(args.length);
for (i in 0...oargs.Length)
{
oargs[i] = args[i];
}
return t.InvokeMember(field, BindingFlags.InvokeMethod, null, obj, oargs);
}
return t.InvokeMember(field, BindingFlags.InvokeMethod, null, obj, args);

if (last == 0)
{
Expand All @@ -642,7 +635,7 @@ import cs.system.Object;
return Runtime.callMethod(obj, mis, last, args);
}

public static function callField(obj:Dynamic, field:String, fieldHash:Int, args:Array<Dynamic>):Dynamic
public static function callField(obj:Dynamic, field:String, fieldHash:Int, args:cs.NativeArray<Dynamic>):Dynamic
{
var hxObj = Lib.as(obj, HxObject);
if (hxObj != null)
Expand Down
19 changes: 11 additions & 8 deletions std/cs/internal/StringExt.hx
Original file line number Diff line number Diff line change
Expand Up @@ -205,14 +205,17 @@ private typedef NativeString = cs.system.String;
}
}

public static function handleCallField(str:NativeString, f:String, args:Array<Dynamic>):Dynamic
public static function handleCallField(str:NativeString, f:String, args:cs.NativeArray<Dynamic>):Dynamic
{
var _args:Array<Dynamic> = [str];
if (args == null)
args = _args;
else
args = _args.concat(args);

return Runtime.slowCallField(StringExt, f, args);
var _args:cs.NativeArray<Dynamic>;
if (args == null) {
_args = cs.NativeArray.make(str);
} else {
_args = new cs.NativeArray(args.length + 1);
for (i in 0...args.length)
_args[i + 1] = args[i];
_args[0] = str;
}
return Runtime.slowCallField(StringExt, f, _args);
}
}
3 changes: 2 additions & 1 deletion std/java/_std/Reflect.hx
Original file line number Diff line number Diff line change
Expand Up @@ -70,14 +70,15 @@ import java.Boot;
if (Std.is(o, IHxObject)) {
untyped (o : IHxObject).__hx_setField(field, value, true);
} else if (Runtime.slowHasField(o, "set_" + field)) {
Runtime.slowCallField(o, "set_" + field, [value]);
Runtime.slowCallField(o, "set_" + field, java.NativeArray.make(value));
} else {
Runtime.slowSetField(o, field, value);
}
}

public static function callMethod( o : Dynamic, func : haxe.Constraints.Function, args : Array<Dynamic> ) : Dynamic
{
var args = java.Lib.nativeArray(args, true);
return untyped (func : Function).__hx_invokeDynamic(args);
}

Expand Down
21 changes: 9 additions & 12 deletions std/java/_std/Type.hx
Original file line number Diff line number Diff line change
Expand Up @@ -257,20 +257,17 @@ enum ValueType {
}
}

@:functionCode('
if (params == null || params.length == 0)
{
java.lang.Object ret = haxe.lang.Runtime.slowGetField(e, constr, true);
if (ret instanceof haxe.lang.Function)
throw haxe.lang.HaxeException.wrap("Constructor " + constr + " needs parameters");
return (T) ret;
public static function createEnum<T>( e : Enum<T>, constr : String, ?params : Array<Dynamic> ) : T {
if (params == null || params.length == 0) {
var ret:Dynamic = java.internal.Runtime.slowGetField(e, constr, true);
if (Std.is(ret, java.internal.Function)) {
throw "Constructor " + constr + " needs parameters";
}
return ret;
} else {
return (T) haxe.lang.Runtime.slowCallField(e, constr, params);
var params = java.Lib.nativeArray(params, true);
return java.internal.Runtime.slowCallField(e, constr, params);
}
')
public static function createEnum<T>( e : Enum<T>, constr : String, ?params : Array<Dynamic> ) : T
{
return null;
}

public static function createEnumIndex<T>( e : Enum<T>, index : Int, ?params : Array<Dynamic> ) : T {
Expand Down
8 changes: 4 additions & 4 deletions std/java/internal/Function.hx
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ import java.internal.Runtime;

@:nativeGen @:native("haxe.lang.VarArgsBase") @:keep private class VarArgsBase extends Function
{
public function __hx_invokeDynamic(dynArgs:Array<Dynamic>):Dynamic
public function __hx_invokeDynamic(dynArgs:java.NativeArray<Dynamic>):Dynamic
{
throw "Abstract implementation";
}
Expand All @@ -55,9 +55,9 @@ import java.internal.Runtime;
this.fun = fun;
}

override public function __hx_invokeDynamic(dynArgs:Array<Dynamic>):Dynamic
override public function __hx_invokeDynamic(dynArgs:java.NativeArray<Dynamic>):Dynamic
{
return fun(dynArgs);
return fun(@:privateAccess Array.ofNative(dynArgs));
}
}

Expand All @@ -73,7 +73,7 @@ import java.internal.Runtime;
this.field = field;
}

override public function __hx_invokeDynamic(dynArgs:Array<Dynamic>):Dynamic
override public function __hx_invokeDynamic(dynArgs:java.NativeArray<Dynamic>):Dynamic
{
return Runtime.callField(obj, field, dynArgs);
}
Expand Down
Loading