Browse Source

[analyzer] remove redundant `local = local` assignmnets (closes #8950)

Aleksandr Kuzmenko 5 years ago
parent
commit
4e6c703282

+ 2 - 0
src/optimization/analyzerTexpr.ml

@@ -640,6 +640,8 @@ module Fusion = struct
 		(* Handles block-level expressions, e.g. by removing side-effect-free ones and recursing into compound constructs like
 		(* Handles block-level expressions, e.g. by removing side-effect-free ones and recursing into compound constructs like
 		   array or object declarations. The resulting element list is reversed. *)
 		   array or object declarations. The resulting element list is reversed. *)
 		let rec block_element acc el = match el with
 		let rec block_element acc el = match el with
+			| {eexpr = TBinop(OpAssign, { eexpr = TLocal v1 }, { eexpr = TLocal v2 })} :: el when v1 == v2 ->
+				block_element acc el
 			| {eexpr = TBinop((OpAssign | OpAssignOp _),_,_) | TUnop((Increment | Decrement),_,_)} as e1 :: el ->
 			| {eexpr = TBinop((OpAssign | OpAssignOp _),_,_) | TUnop((Increment | Decrement),_,_)} as e1 :: el ->
 				block_element (e1 :: acc) el
 				block_element (e1 :: acc) el
 			| {eexpr = TLocal _} as e1 :: el when not config.local_dce ->
 			| {eexpr = TLocal _} as e1 :: el when not config.local_dce ->

+ 11 - 0
tests/optimization/src/TestJs.hx

@@ -563,6 +563,17 @@ class TestJs {
 		return if (Std.isOfType(v, c)) v else null;
 		return if (Std.isOfType(v, c)) v else null;
 	}
 	}
 
 
+	@:js('var f = function(x) {console.log("src/TestJs.hx:572:",x);};f(10);')
+	static function testVarSelfAssignmentRemoved() {
+		inline function g() return 0;
+
+		function f(x:Int) {
+			x = x + g();
+			trace(x);
+		}
+
+		f(10);
+	}
 }
 }
 
 
 extern class Extern {
 extern class Extern {

+ 8 - 2
tests/optimization/src/issues/Issue6302.hx

@@ -1,9 +1,15 @@
 package issues;
 package issues;
 
 
 class Issue6302 {
 class Issue6302 {
-	@:js('a = b && a;')
+	@:js('a = b && c;')
 	@:analyzer(no_local_dce)
 	@:analyzer(no_local_dce)
-	static function f(a, b) {
+	static function f1(a, b, c) {
+		a = b && c;
+	}
+
+	@:js('if(!b) {a = false;}')
+	@:analyzer(no_local_dce)
+	static function f2(a, b) {
 		a = b && a;
 		a = b && a;
 	}
 	}
 }
 }