package jetbrains.mps.baseLanguage.util.plugin.refactorings; /*Generated by MPS */ import org.jetbrains.mps.openapi.model.SNode; import jetbrains.mps.lang.smodel.generator.smodelAdapter.SNodeOperations; import jetbrains.mps.smodel.adapter.structure.MetaAdapterFactory; import jetbrains.mps.smodel.behaviour.BHReflection; import jetbrains.mps.core.aspects.behaviour.SMethodTrimmedId; import jetbrains.mps.lang.smodel.generator.smodelAdapter.SLinkOperations; import jetbrains.mps.internal.collections.runtime.ListSequence; import org.jetbrains.mps.openapi.language.SAbstractConcept; import jetbrains.mps.lang.dataFlow.framework.Program; import jetbrains.mps.lang.dataFlow.MPSProgramBuilder; import jetbrains.mps.lang.dataFlow.framework.instructions.Instruction; import jetbrains.mps.lang.dataFlow.framework.instructions.RetInstruction; import jetbrains.mps.lang.dataFlow.framework.instructions.NopInstruction; import java.util.Set; import jetbrains.mps.internal.collections.runtime.SetSequence; public class InlineMethodModel { private SNode myMethod; private MethodCallAdapter myCall; private boolean myIsContainsSelfCalls; private String myMethodPresentation; public InlineMethodModel(SNode node) { if (SNodeOperations.isInstanceOf(node, MetaAdapterFactory.getConcept(0xf3061a5392264cc5L, 0xa443f952ceaf5816L, 0xf8cc56b1fcL, "jetbrains.mps.baseLanguage.structure.BaseMethodDeclaration"))) { myMethod = SNodeOperations.cast(node, MetaAdapterFactory.getConcept(0xf3061a5392264cc5L, 0xa443f952ceaf5816L, 0xf8cc56b1fcL, "jetbrains.mps.baseLanguage.structure.BaseMethodDeclaration")); } else { myCall = new MethodCallAdapter(node); myMethod = myCall.getMethodDeclaration(); } myMethodPresentation = ((String) BHReflection.invoke(myMethod, SMethodTrimmedId.create("getPresentation", null, "hEwIMiw"))); myIsContainsSelfCalls = isContainsSelfCalls(); } public boolean isRecusive() { return myIsContainsSelfCalls; } public String getMethodPresentation() { return myMethodPresentation; } public MethodCallAdapter getMethodCall() { return myCall; } public SNode getMethod() { return myMethod; } public String getErrors() { if ((SLinkOperations.getTarget(getMethod(), MetaAdapterFactory.getContainmentLink(0xf3061a5392264cc5L, 0xa443f952ceaf5816L, 0xf8cc56b1fcL, 0xf8cc56b1ffL, "body")) == null) || SNodeOperations.isInstanceOf(SLinkOperations.getTarget(getMethod(), MetaAdapterFactory.getContainmentLink(0xf3061a5392264cc5L, 0xa443f952ceaf5816L, 0xf8cc56b1fcL, 0xf8cc56b1ffL, "body")), MetaAdapterFactory.getConcept(0xf3061a5392264cc5L, 0xa443f952ceaf5816L, 0x4975dc2bdcfa0c49L, "jetbrains.mps.baseLanguage.structure.StubStatementList"))) { return "No sources attached"; } if (myCall == null && isRecusive()) { return "Method is recursive"; } if (isReturnBreaksExecitionFlow()) { return "Return breaks execution flow"; } return null; } private boolean isContainsSelfCalls() { for (SNode call : ListSequence.fromList(SNodeOperations.getNodeDescendants(getMethod(), null, false, new SAbstractConcept[]{}))) { if (MethodCallAdapter.isMethodCall(call)) { if (new MethodCallAdapter(call).getMethodDeclaration() == getMethod()) { return true; } } } return false; } private boolean isReturnBreaksExecitionFlow() { Program program = new MPSProgramBuilder().buildProgram(SLinkOperations.getTarget(getMethod(), MetaAdapterFactory.getContainmentLink(0xf3061a5392264cc5L, 0xa443f952ceaf5816L, 0xf8cc56b1fcL, 0xf8cc56b1ffL, "body"))); for (Instruction instruction : ListSequence.fromList(program.getInstructions())) { if (instruction instanceof RetInstruction) { Instruction next = program.get(instruction.getIndex() + 1); while (!(next.equals(program.getEnd()))) { if (next instanceof NopInstruction) { return true; } Set<Instruction> succ = next.succ(); if (SetSequence.fromSet(succ).count() != 1) { return true; } next = SetSequence.fromSet(succ).first(); } } } return false; } }