X-Git-Url: https://gerrit.simantics.org/r/gitweb?p=simantics%2Fplatform.git;a=blobdiff_plain;f=bundles%2Forg.simantics.scl.compiler%2Fsrc%2Forg%2Fsimantics%2Fscl%2Fcompiler%2Finternal%2Fcodegen%2Fssa%2FSSABlock.java;h=ba9d62d27ce730bffc2b99772321406736125e07;hp=c9f33ec50c7727e8a9c789858de926bfce31a282;hb=fad36d463b75c3a9944d875fc627c3533f6da74d;hpb=0ae2b770234dfc3cbb18bd38f324125cf0faca07 diff --git a/bundles/org.simantics.scl.compiler/src/org/simantics/scl/compiler/internal/codegen/ssa/SSABlock.java b/bundles/org.simantics.scl.compiler/src/org/simantics/scl/compiler/internal/codegen/ssa/SSABlock.java index c9f33ec50..ba9d62d27 100644 --- a/bundles/org.simantics.scl.compiler/src/org/simantics/scl/compiler/internal/codegen/ssa/SSABlock.java +++ b/bundles/org.simantics.scl.compiler/src/org/simantics/scl/compiler/internal/codegen/ssa/SSABlock.java @@ -4,6 +4,7 @@ import java.util.ArrayList; import org.simantics.scl.compiler.common.exceptions.InternalCompilerError; import org.simantics.scl.compiler.constants.Constant; +import org.simantics.scl.compiler.constants.NoRepConstant; import org.simantics.scl.compiler.constants.SCLConstant; import org.simantics.scl.compiler.internal.codegen.continuations.BranchRef; import org.simantics.scl.compiler.internal.codegen.continuations.Cont; @@ -21,6 +22,7 @@ import org.simantics.scl.compiler.internal.codegen.utils.Printable; import org.simantics.scl.compiler.internal.codegen.utils.PrintingContext; import org.simantics.scl.compiler.internal.codegen.utils.SSALambdaLiftingContext; import org.simantics.scl.compiler.internal.codegen.utils.SSASimplificationContext; +import org.simantics.scl.compiler.internal.codegen.utils.SSAUtils; import org.simantics.scl.compiler.internal.codegen.utils.SSAValidationContext; import org.simantics.scl.compiler.internal.codegen.utils.ValRefVisitor; import org.simantics.scl.compiler.top.SCLCompilerConfiguration; @@ -281,27 +283,42 @@ public final class SSABlock extends Cont implements Printable, BoundVarBinder { context.markModified("improve-parameters"); } + private static Constant getOnlyPossibleValue(Type type) { + type = Types.canonical(type); + if(type == Types.UNIT) + return NoRepConstant.UNIT; + else if(type == Types.PUNIT) + return NoRepConstant.PUNIT; + return null; + } + private boolean tryToImproveParameter(int position) { BoundVar parameter = parameters[position]; - Val constant = null; - ValRef constantRef = null; - for(ContRef ref = getOccurrence(); ref != null; ref = ref.getNext()) { - Jump jump = (Jump)ref.getParent(); - ValRef valRef = jump.getParameters()[position]; - Val val = valRef.getBinding(); - if(val == parameter) - continue; - if(constant == null) { - constant = val; - constantRef = valRef; - continue; + Constant onlyPossibleValue = getOnlyPossibleValue(parameter.getType()); + if(onlyPossibleValue == null) { + Val constant = null; + ValRef constantRef = null; + for(ContRef ref = getOccurrence(); ref != null; ref = ref.getNext()) { + Jump jump = (Jump)ref.getParent(); + ValRef valRef = jump.getParameters()[position]; + Val val = valRef.getBinding(); + if(val == parameter) + continue; + if(constant == null) { + constant = val; + constantRef = valRef; + continue; + } + if(val != constant) + return false; } - if(val != constant) - return false; + if(constant == null) + return false; // This is a strange case, because we cannot get the parameter anywhere + parameter.replaceBy(constantRef); + } + else { + parameter.replaceBy(onlyPossibleValue); } - if(constant == null) - return false; // This is a strange case, because we cannot get the parameter anywhere - parameter.replaceBy(constantRef); for(ContRef ref = getOccurrence(); ref != null; ref = ref.getNext()) { Jump jump = (Jump)ref.getParent(); @@ -331,32 +348,72 @@ public final class SSABlock extends Cont implements Printable, BoundVarBinder { return result; } + /* + * This method assumes that the exit of the block is Jump. + */ private boolean optimizeTailSelfCall() { - Jump jump = (Jump)exit; - if(jump.getTarget().getBinding() != parent.returnCont) - return false; - if(jump.getParameters().length != 1) - return false; + // The last statement of the block is LetApply that calls the parent function with right number of parameters if(lastStatement == null || !(lastStatement instanceof LetApply)) return false; LetApply apply = (LetApply)lastStatement; - SSABlock initialBlock = parent.firstBlock; - if(initialBlock.parameters.length != apply.getParameters().length) - return false; Val function = apply.getFunction().getBinding(); if(function != parent.target) return false; + SSABlock initialBlock = parent.firstBlock; + if(initialBlock.parameters.length != apply.getParameters().length) + return false; + + // The jump is a return (with one parameter) + // The parameter of the jump is the target of LetApply + Jump jump = (Jump)exit; + Cont targetCont = jump.getTarget().getBinding(); + if(targetCont != parent.returnCont) { + SSABlock targetBlock = (SSABlock)targetCont; + if(targetBlock.firstStatement != null) + return false; + if(!(targetBlock.exit instanceof Jump)) + return false; + Jump targetJump = (Jump)targetBlock.exit; + if(targetJump.getTarget().getBinding() != parent.returnCont) + return false; + if(targetJump.getParameters().length != 1) + return false; + + BoundVar applyTarget = apply.getTarget(); + ValRef targetJumpParameter = targetJump.getParameter(0); + isSameParam: if(!SSAUtils.representSameValue(applyTarget, targetJumpParameter)) { + BoundVar[] targetBlockParameters = targetBlock.getParameters(); + for(int i=0;i> AFTER INLINE >>"); System.out.println(getParent()); @@ -473,7 +530,7 @@ public final class SSABlock extends Cont implements Printable, BoundVarBinder { public void markGenerateOnFly() { for(SSAStatement stat = firstStatement; stat != null; stat = stat.next) - stat.markGenerateOnFly(); + stat.markGenerateOnFly(); } public SSABlock copy(CopyContext context) {