Revision: 7979
Author: sp...@google.com
Date: Mon Apr 26 12:07:45 2010
Log: The gflow constant analyzer assumes that parameters
could initially hold anything, rather than assuming
they haven't been initialized. This caused problems
for code like:
foo(String param) {
if (something) {
param = null;
}
// at this point, analyzer thinks param==null
}
Review at http://gwt-code-reviews.appspot.com/405801
http://code.google.com/p/google-web-toolkit/source/detail?r=7979
Modified:
/trunk/dev/core/src/com/google/gwt/dev/jjs/impl/gflow/constants/ConstantsAnalysis.java
/trunk/dev/core/test/com/google/gwt/dev/jjs/impl/OptimizerTestBase.java
/trunk/dev/core/test/com/google/gwt/dev/jjs/impl/gflow/CfgAnalysisTestBase.java
/trunk/dev/core/test/com/google/gwt/dev/jjs/impl/gflow/constants/ConstantsAnalysisTest.java
=======================================
---
/trunk/dev/core/src/com/google/gwt/dev/jjs/impl/gflow/constants/ConstantsAnalysis.java
Fri Apr 2 14:35:01 2010
+++
/trunk/dev/core/src/com/google/gwt/dev/jjs/impl/gflow/constants/ConstantsAnalysis.java
Mon Apr 26 12:07:45 2010
@@ -15,8 +15,10 @@
*/
package com.google.gwt.dev.jjs.impl.gflow.constants;
+import com.google.gwt.dev.jjs.ast.JParameterRef;
import com.google.gwt.dev.jjs.impl.gflow.Analysis;
import com.google.gwt.dev.jjs.impl.gflow.AssumptionMap;
+import com.google.gwt.dev.jjs.impl.gflow.AssumptionUtil;
import com.google.gwt.dev.jjs.impl.gflow.IntegratedAnalysis;
import com.google.gwt.dev.jjs.impl.gflow.cfg.Cfg;
import com.google.gwt.dev.jjs.impl.gflow.cfg.CfgEdge;
@@ -44,6 +46,18 @@
public void setInitialGraphAssumptions(Cfg graph,
AssumptionMap<CfgEdge, ConstantsAssumption> assumptionMap) {
- // bottom assumptions.
+ // Set all parameter assumptions to T
+
+ ConstantsAssumption.Updater updater = new
ConstantsAssumption.Updater(null);
+ for (CfgNode<?> node : graph.getNodes()) {
+ Object jnode = node.getJNode();
+ if (jnode instanceof JParameterRef) {
+ updater.set(((JParameterRef) jnode).getParameter(), null);
+ }
+ }
+ ConstantsAssumption assumptions = updater.unwrap();
+
+ AssumptionUtil.setAssumptions(graph.getGraphInEdges(), assumptions,
+ assumptionMap);
}
}
=======================================
--- /trunk/dev/core/test/com/google/gwt/dev/jjs/impl/OptimizerTestBase.java
Fri Mar 12 08:11:14 2010
+++ /trunk/dev/core/test/com/google/gwt/dev/jjs/impl/OptimizerTestBase.java
Mon Apr 26 12:07:45 2010
@@ -188,6 +188,21 @@
*/
protected JProgram compileSnippet(final String returnType,
final String codeSnippet) throws UnableToCompleteException {
+ return compileSnippet(returnType, "", codeSnippet);
+ }
+
+ /**
+ * Returns the program that results from compiling the specified code
snippet
+ * as the body of an entry point method.
+ *
+ * @param returnType the return type of the method to compile;
use "void" if
+ * the code snippet has no return statement
+ * @param params the parameter list of the method to compile
+ * @param codeSnippet the body of the entry method
+ */
+ protected JProgram compileSnippet(final String returnType,
+ final String params, final String codeSnippet)
+ throws UnableToCompleteException {
sourceOracle.addOrReplace(new MockJavaResource("test.EntryPoint") {
@Override
protected CharSequence getContent() {
@@ -200,7 +215,8 @@
for (String snippetClassDecl : snippetClassDecls) {
code.append(snippetClassDecl + ";\n");
}
- code.append(" public static " + returnType + " onModuleLoad()
{\n");
+ code.append(" public static " + returnType + " onModuleLoad(" +
params
+ + ") {\n");
code.append(codeSnippet);
code.append(" }\n");
code.append("}\n");
=======================================
---
/trunk/dev/core/test/com/google/gwt/dev/jjs/impl/gflow/CfgAnalysisTestBase.java
Fri Apr 2 14:35:01 2010
+++
/trunk/dev/core/test/com/google/gwt/dev/jjs/impl/gflow/CfgAnalysisTestBase.java
Mon Apr 26 12:07:45 2010
@@ -16,11 +16,16 @@
public abstract class CfgAnalysisTestBase<A extends Assumption<A>>
extends OptimizerTestBase {
protected boolean forward = true;
-
+
protected AnalysisResult analyze(String returnType, String...
codeSnippet)
throws UnableToCompleteException {
- JProgram program = compileSnippet(returnType, Strings.join(codeSnippet,
- "\n"));
+ return analyzeWithParams(returnType, "", codeSnippet);
+ }
+
+ protected AnalysisResult analyzeWithParams(String returnType, String
params,
+ String... codeSnippet) throws UnableToCompleteException {
+ JProgram program = compileSnippet(returnType, params, Strings.join(
+ codeSnippet, "\n"));
JMethodBody body = (JMethodBody) findMainMethod(program).getBody();
Cfg cfgGraph = CfgBuilder.build(program, body.getBlock());
=======================================
---
/trunk/dev/core/test/com/google/gwt/dev/jjs/impl/gflow/constants/ConstantsAnalysisTest.java
Fri Apr 2 14:35:01 2010
+++
/trunk/dev/core/test/com/google/gwt/dev/jjs/impl/gflow/constants/ConstantsAnalysisTest.java
Mon Apr 26 12:07:45 2010
@@ -210,6 +210,27 @@
"2: END"
);
}
+
+ /**
+ * Parameters should have an initial assumption of non-constant.
+ */
+ public void testParamNonConstant() throws Exception {
+ analyzeWithParams("void", "int i, int j", "if (j == 0) { i = 0; } j=i;
j=0;").into(
+ "BLOCK -> [* {i = T, j = T}]",
+ "STMT -> [* {i = T, j = T}]",
+ "READ(j) -> [* {i = T, j = T}]",
+ "COND (j == 0) -> [THEN=* {i = T, j = 0}, ELSE=1 {i = T, j = T}]",
+ "BLOCK -> [* {i = T, j = 0}]",
+ "STMT -> [* {i = T, j = 0}]",
+ "WRITE(i, 0) -> [* {i = 0, j = 0}]",
+ "1: STMT -> [* {i = T, j = T}]",
+ "READ(i) -> [* {i = T, j = T}]",
+ "WRITE(j, i) -> [* {i = T, j = T}]",
+ "STMT -> [* {i = T, j = T}]",
+ "WRITE(j, 0) -> [* {i = T, j = 0}]",
+ "END"
+ );
+ }
@Override
protected Analysis<CfgNode<?>, CfgEdge, Cfg, ConstantsAssumption>
createAnalysis() {
--
http://groups.google.com/group/Google-Web-Toolkit-Contributors