Prechádzať zdrojové kódy

added native carray access with hl 1.14 (#11299)

Nicolas Cannasse 2 rokov pred
rodič
commit
acce4e0676

+ 22 - 4
src/generators/genhl.ml

@@ -130,6 +130,7 @@ type access =
 	| AInstanceProto of texpr * field index
 	| AInstanceField of texpr * field index
 	| AArray of reg * (ttype * ttype) * reg
+	| ACArray of reg * ttype * reg
 	| AVirtualMethod of texpr * field index
 	| ADynamic of texpr * string index
 	| AEnum of tenum * field index
@@ -1376,6 +1377,13 @@ and get_access ctx e =
 				free ctx a;
 				let t = to_type ctx t in
 				AArray (a,(t,t),i)
+			| TInst ({ cl_path = ["hl"],"Abstract" },[TInst({ cl_kind = KExpr (EConst (String("hl_carray",_)),_) },_)]) ->
+				let a = eval_null_check ctx a in
+				hold ctx a;
+				let i = eval_to ctx i HI32 in
+				free ctx a;
+				let t = to_type ctx e.etype in
+				ACArray (a,t,i)
 			| TAbstract (a,pl) ->
 				loop (Abstract.get_underlying_type a pl)
 			| _ ->
@@ -1893,7 +1901,13 @@ and eval_expr ctx e =
 			r
 		| "$asize", [e] ->
 			let r = alloc_tmp ctx HI32 in
-			op ctx (OArraySize (r, eval_to ctx e HArray));
+			(match follow e.etype with
+			| TInst ({cl_path=["hl"],"Abstract"},[TInst({ cl_kind = KExpr (EConst (String("hl_carray",_)),_) },_)]) ->
+				let arr = eval_expr ctx e in
+				op ctx (ONullCheck arr);
+				op ctx (OArraySize (r, arr))
+			| _ ->
+				op ctx (OArraySize (r, eval_to ctx e HArray)));
 			r
 		| "$aalloc", [esize] ->
 			let et = (match follow e.etype with TAbstract ({ a_path = ["hl"],"NativeArray" },[t]) -> to_type ctx t | _ -> invalid()) in
@@ -2207,7 +2221,7 @@ and eval_expr ctx e =
 				ignore(make_fun ctx ("","") fid f None None);
 			end;
 			op ctx (OStaticClosure (r,fid));
-		| ANone | ALocal _ | AArray _ | ACaptured _ ->
+		| ANone | ALocal _ | AArray _ | ACaptured _ | ACArray _ ->
 			abort "Invalid access" e.epos);
 		let to_t = to_type ctx e.etype in
 		(match to_t with
@@ -2451,7 +2465,7 @@ and eval_expr ctx e =
 				let r = value() in
 				op ctx (OSetEnumField (ctx.m.mcaptreg,index,r));
 				r
-			| AEnum _ | ANone | AInstanceFun _ | AInstanceProto _ | AStaticFun _ | AVirtualMethod _ ->
+			| AEnum _ | ANone | AInstanceFun _ | AInstanceProto _ | AStaticFun _ | AVirtualMethod _ | ACArray _ ->
 				die "" __LOC__)
 		| OpBoolOr ->
 			let r = alloc_tmp ctx HBool in
@@ -2726,6 +2740,10 @@ and eval_expr ctx e =
 		(match get_access ctx e with
 		| AArray (a,at,idx) ->
 			array_read ctx a at idx e.epos
+		| ACArray (a,t,idx) ->
+			let tmp = alloc_tmp ctx t in
+			op ctx (OGetArray (tmp,a,idx));
+			tmp
 		| _ ->
 			die "" __LOC__)
 	| TMeta (_,e) ->
@@ -3045,7 +3063,7 @@ and gen_assign_op ctx acc e1 f =
 		free ctx robj;
 		op ctx (ODynSet (robj,fid,r));
 		r
-	| ANone | ALocal _ | AStaticFun _ | AInstanceFun _ | AInstanceProto _ | AVirtualMethod _ | AEnum _ ->
+	| ANone | ALocal _ | AStaticFun _ | AInstanceFun _ | AInstanceProto _ | AVirtualMethod _ | AEnum _ | ACArray _ ->
 		die "" __LOC__
 
 and build_capture_vars ctx f =

+ 2 - 2
src/generators/hlinterp.ml

@@ -2436,7 +2436,7 @@ let check code macros =
 			| ORethrow r ->
 				reg r HDyn
 			| OGetArray (v,a,i) ->
-				reg a HArray;
+				(match rtype a with HAbstract ("hl_carray",_) -> () | _ -> reg a HArray);
 				reg i HI32;
 				ignore(rtype v);
 			| OGetUI8 (r,b,p) | OGetUI16(r,b,p) ->
@@ -2466,7 +2466,7 @@ let check code macros =
 				ignore(rtype a);
 				ignore(rtype b);
 			| OArraySize (r,a) ->
-				reg a HArray;
+				(match rtype a with HAbstract ("hl_carray",_) -> () | _ -> reg a HArray);
 				reg r HI32
 			| OType (r,_) ->
 				reg r HType

+ 5 - 0
src/generators/hlopt.ml

@@ -875,6 +875,11 @@ let _optimize (f:fundecl) =
 			| OGetThis (r,fid) when (match f.regs.(r) with HStruct _ -> true | _ -> false) ->
 				do_write r;
 				if is_packed_field 0 fid then state.(r).rnullcheck <- true;
+			| OGetArray (r,arr,idx) ->
+				do_read arr;
+				do_read idx;
+				do_write r;
+				(match f.regs.(arr) with HAbstract _ -> state.(r).rnullcheck <- true | _ -> ());
 			| _ ->
 				opcode_fx (fun r read ->
 					if read then do_read r else do_write r

+ 6 - 1
std/hl/CArray.hx

@@ -9,9 +9,14 @@ abstract CArray<T>(Abstract<"hl_carray">) {
 
 	public var length(get,never) : Int;
 
-	inline function get_length() return getLen(cast this);
 
+	#if (hl_ver >= version("1.14.0"))
+	inline function get_length() return untyped $asize(this);
+	@:arrayAccess inline function get( index : Int ) : T return untyped this[index];
+	#else
+	inline function get_length() return getLen(cast this);
 	@:arrayAccess inline function get( index : Int ) : T return getIndex(cast this, index);
+	#end
 
 	public static function alloc<T>( cl : Class<T>, size : Int ) : CArray<T> {
 		return cast alloc_carray( (cast cl:BaseType).__type__ , size );