فهرست منبع

[php] fix more stupid shit for PHP's (p)arse(r)

Simon Krajewski 9 سال پیش
والد
کامیت
3ee9295cf9
2فایلهای تغییر یافته به همراه31 افزوده شده و 4 حذف شده
  1. 9 4
      src/optimization/analyzerTexpr.ml
  2. 22 0
      tests/unit/src/unit/TestPhp.hx

+ 9 - 4
src/optimization/analyzerTexpr.ml

@@ -675,11 +675,16 @@ module Fusion = struct
 							let e2 = replace e2 in
 							e2,el
 						| Php | Cpp  when not (Common.defined com Define.Cppia) ->
-							let e2 = match e1.eexpr with
-								(* PHP doesn't like call()() expressions. *)
-								| TCall _ when com.platform = Php -> explore e2
-								| _ -> replace e2
+							let is_php_safe e1 =
+								let rec loop e = match e.eexpr with
+									| TCall _ -> raise Exit
+									| TCast(e1,_) | TParenthesis e1 | TMeta(_,e1) -> loop e1
+									| _ -> ()
+								in
+								try loop e1; true with Exit -> false
 							in
+							(* PHP doesn't like call()() expressions. *)
+							let e2 = if com.platform = Php && not (is_php_safe e1) then explore e2 else replace e2 in
 							let el = handle_el el in
 							e2,el
 						| _ ->

+ 22 - 0
tests/unit/src/unit/TestPhp.hx

@@ -58,6 +58,17 @@ class TestPhp extends Test
 	{
 		f(Class2146.test());
 	}
+
+	function testStupidShit9000() {
+		var f = make();
+		f.handle( function() {
+			eq("ok", "ok");
+		});
+	}
+
+	inline static function make():FunctionCallerWrapper {
+		return new FunctionCaller(function(f) f());
+	}
 }
 
 class Class2146 {
@@ -80,4 +91,15 @@ class Class2146 {
 enum Annotation {
 	Abstract;
 	Const(i:String);
+}
+
+private typedef Func = Void->Void;
+
+private abstract FunctionCaller(Func->Void) to Func->Void {
+	public function new(f:Func->Void) this = f;
+}
+
+private abstract FunctionCallerWrapper( FunctionCaller ) from FunctionCaller to FunctionCaller {
+	public inline function handle(callback:Func):Void
+		return (this:Func->Void)(callback);
 }