all traverse pseudocode methods made static
This commit is contained in:
@@ -38,6 +38,7 @@ import org.jetbrains.jet.lexer.JetTokens;
|
|||||||
import org.jetbrains.jet.plugin.JetMainDetector;
|
import org.jetbrains.jet.plugin.JetMainDetector;
|
||||||
|
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
|
import java.util.Collections;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
|
|
||||||
@@ -62,7 +63,7 @@ public class JetFlowInformationProvider {
|
|||||||
subroutine = declaration;
|
subroutine = declaration;
|
||||||
this.trace = trace;
|
this.trace = trace;
|
||||||
pseudocode = new JetControlFlowProcessor(trace).generatePseudocode(declaration);
|
pseudocode = new JetControlFlowProcessor(trace).generatePseudocode(declaration);
|
||||||
pseudocodeData = new PseudocodeData(pseudocode, trace);
|
pseudocodeData = new PseudocodeData(pseudocode, trace.getBindingContext());
|
||||||
}
|
}
|
||||||
|
|
||||||
private void collectReturnExpressions(@NotNull final Collection<JetElement> returnedExpressions) {
|
private void collectReturnExpressions(@NotNull final Collection<JetElement> returnedExpressions) {
|
||||||
@@ -195,7 +196,7 @@ public class JetFlowInformationProvider {
|
|||||||
VariableDescriptor variableDescriptor = pseudocodeData.extractVariableDescriptorIfAny(instruction, true);
|
VariableDescriptor variableDescriptor = pseudocodeData.extractVariableDescriptorIfAny(instruction, true);
|
||||||
if (variableDescriptor == null) return;
|
if (variableDescriptor == null) return;
|
||||||
if (!(instruction instanceof ReadValueInstruction) && !(instruction instanceof WriteValueInstruction)) return;
|
if (!(instruction instanceof ReadValueInstruction) && !(instruction instanceof WriteValueInstruction)) return;
|
||||||
InstructionData.EdgesData<VariableInitializers> variableInitializers = instructionData.getInitializersMap().get(
|
Edges<VariableInitializers> variableInitializers = instructionData.getInitializersMap().get(
|
||||||
variableDescriptor);
|
variableDescriptor);
|
||||||
if (variableInitializers == null) return;
|
if (variableInitializers == null) return;
|
||||||
if (instruction instanceof ReadValueInstruction) {
|
if (instruction instanceof ReadValueInstruction) {
|
||||||
@@ -394,7 +395,7 @@ public class JetFlowInformationProvider {
|
|||||||
private void recordInitializedVariables(DeclarationData declarationData, InstructionData instructionData) {
|
private void recordInitializedVariables(DeclarationData declarationData, InstructionData instructionData) {
|
||||||
for (VariableDescriptor variable : declarationData.usedVariables) {
|
for (VariableDescriptor variable : declarationData.usedVariables) {
|
||||||
if (variable instanceof PropertyDescriptor && declarationData.declaredVariables.contains(variable)) {
|
if (variable instanceof PropertyDescriptor && declarationData.declaredVariables.contains(variable)) {
|
||||||
InstructionData.EdgesData<VariableInitializers> variableInitializers = instructionData.getInitializersMap().get(variable);
|
Edges<VariableInitializers> variableInitializers = instructionData.getInitializersMap().get(variable);
|
||||||
if (variableInitializers == null) return;
|
if (variableInitializers == null) return;
|
||||||
trace.record(BindingContext.IS_INITIALIZED, (PropertyDescriptor) variable, variableInitializers.getIn().isInitialized());
|
trace.record(BindingContext.IS_INITIALIZED, (PropertyDescriptor) variable, variableInitializers.getIn().isInitialized());
|
||||||
}
|
}
|
||||||
@@ -411,7 +412,7 @@ public class JetFlowInformationProvider {
|
|||||||
VariableDescriptor variableDescriptor = pseudocodeData.extractVariableDescriptorIfAny(instruction, false);
|
VariableDescriptor variableDescriptor = pseudocodeData.extractVariableDescriptorIfAny(instruction, false);
|
||||||
if (variableDescriptor == null || !declarationData.declaredVariables.contains(variableDescriptor) ||
|
if (variableDescriptor == null || !declarationData.declaredVariables.contains(variableDescriptor) ||
|
||||||
!DescriptorUtils.isLocal(variableDescriptor.getContainingDeclaration(), variableDescriptor)) return;
|
!DescriptorUtils.isLocal(variableDescriptor.getContainingDeclaration(), variableDescriptor)) return;
|
||||||
InstructionData.EdgesData<VariableUseStatus> statusEdgesData = instructionData.getUseStatusMap().get(variableDescriptor);
|
Edges<VariableUseStatus> statusEdgesData = instructionData.getUseStatusMap().get(variableDescriptor);
|
||||||
VariableUseStatus variableUseStatus = statusEdgesData != null ? statusEdgesData.getIn() : null;
|
VariableUseStatus variableUseStatus = statusEdgesData != null ? statusEdgesData.getIn() : null;
|
||||||
if (instruction instanceof WriteValueInstruction) {
|
if (instruction instanceof WriteValueInstruction) {
|
||||||
if (trace.get(CAPTURED_IN_CLOSURE, variableDescriptor)) return;
|
if (trace.get(CAPTURED_IN_CLOSURE, variableDescriptor)) return;
|
||||||
@@ -487,10 +488,9 @@ public class JetFlowInformationProvider {
|
|||||||
|
|
||||||
public void markUnusedLiteralsInBlock() {
|
public void markUnusedLiteralsInBlock() {
|
||||||
assert pseudocode != null;
|
assert pseudocode != null;
|
||||||
JetControlFlowGraphTraverser<Void> traverser = JetControlFlowGraphTraverser.create(pseudocode, true, true);
|
PseudocodeTraverser.traverseAndAnalyzeInstructionGraph(pseudocode, true, new PseudocodeTraverser.SimpleInstructionDataAnalyzeStrategy() {
|
||||||
traverser.traverseAndAnalyzeInstructionGraph(new JetControlFlowGraphTraverser.InstructionDataAnalyzeStrategy<Void>() {
|
|
||||||
@Override
|
@Override
|
||||||
public void execute(@NotNull Instruction instruction, @Nullable Void enterData, @Nullable Void exitData) {
|
public void execute(@NotNull Instruction instruction) {
|
||||||
if (!(instruction instanceof ReadValueInstruction)) return;
|
if (!(instruction instanceof ReadValueInstruction)) return;
|
||||||
JetElement element = ((ReadValueInstruction) instruction).getElement();
|
JetElement element = ((ReadValueInstruction) instruction).getElement();
|
||||||
if (!(element instanceof JetFunctionLiteralExpression
|
if (!(element instanceof JetFunctionLiteralExpression
|
||||||
|
|||||||
+62
-57
@@ -19,79 +19,71 @@ package org.jetbrains.jet.lang.cfg;
|
|||||||
import com.google.common.collect.Lists;
|
import com.google.common.collect.Lists;
|
||||||
import com.google.common.collect.Maps;
|
import com.google.common.collect.Maps;
|
||||||
import com.google.common.collect.Sets;
|
import com.google.common.collect.Sets;
|
||||||
import com.intellij.openapi.util.Pair;
|
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
|
import org.jetbrains.jet.lang.cfg.data.Edges;
|
||||||
import org.jetbrains.jet.lang.cfg.pseudocode.*;
|
import org.jetbrains.jet.lang.cfg.pseudocode.*;
|
||||||
|
|
||||||
import java.util.*;
|
import java.util.Collection;
|
||||||
|
import java.util.Collections;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author svtk
|
* @author svtk
|
||||||
*/
|
*/
|
||||||
public class JetControlFlowGraphTraverser<D> {
|
public class PseudocodeTraverser {
|
||||||
private final Pseudocode pseudocode;
|
|
||||||
private final boolean lookInside;
|
|
||||||
private final boolean directOrder;
|
|
||||||
private final Map<Instruction, Pair<D, D>> dataMap = Maps.newLinkedHashMap();
|
|
||||||
|
|
||||||
public static <D> JetControlFlowGraphTraverser<D> create(@NotNull Pseudocode pseudocode, boolean lookInside, boolean straightDirection) {
|
|
||||||
return new JetControlFlowGraphTraverser<D>(pseudocode, lookInside, straightDirection);
|
|
||||||
}
|
|
||||||
|
|
||||||
private JetControlFlowGraphTraverser(@NotNull Pseudocode pseudocode, boolean lookInside, boolean directOrder) {
|
|
||||||
this.pseudocode = pseudocode;
|
|
||||||
this.lookInside = lookInside;
|
|
||||||
this.directOrder = directOrder;
|
|
||||||
}
|
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
private Instruction getStartInstruction(@NotNull Pseudocode pseudocode) {
|
private static Instruction getStartInstruction(@NotNull Pseudocode pseudocode, boolean directOrder) {
|
||||||
return directOrder ? pseudocode.getEnterInstruction() : pseudocode.getSinkInstruction();
|
return directOrder ? pseudocode.getEnterInstruction() : pseudocode.getSinkInstruction();
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
public static <D> Map<Instruction, Edges<D>> collectInformationFromInstructionGraph(
|
||||||
public Map<Instruction, Pair<D, D>> getDataMap() {
|
boolean lookInside,
|
||||||
return dataMap;
|
boolean directOrder,
|
||||||
}
|
@NotNull Pseudocode pseudocode,
|
||||||
|
|
||||||
public void collectInformationFromInstructionGraph(
|
|
||||||
@NotNull D initialDataValue,
|
@NotNull D initialDataValue,
|
||||||
@NotNull D initialDataValueForEnterInstruction,
|
@NotNull D initialDataValueForEnterInstruction,
|
||||||
@NotNull InstructionDataMergeStrategy<D> instructionDataMergeStrategy) {
|
@NotNull InstructionDataMergeStrategy<D> instructionDataMergeStrategy) {
|
||||||
initializeDataMap(pseudocode, initialDataValue);
|
Map<Instruction, Edges<D>> dataMap = Maps.newLinkedHashMap();
|
||||||
dataMap.put(getStartInstruction(pseudocode),
|
initializeDataMap(lookInside, dataMap, pseudocode, initialDataValue);
|
||||||
Pair.create(initialDataValueForEnterInstruction, initialDataValueForEnterInstruction));
|
dataMap.put(getStartInstruction(pseudocode, directOrder),
|
||||||
|
Edges.create(initialDataValueForEnterInstruction, initialDataValueForEnterInstruction));
|
||||||
|
|
||||||
boolean[] changed = new boolean[1];
|
boolean[] changed = new boolean[1];
|
||||||
changed[0] = true;
|
changed[0] = true;
|
||||||
while (changed[0]) {
|
while (changed[0]) {
|
||||||
changed[0] = false;
|
changed[0] = false;
|
||||||
traverseSubGraph(pseudocode, instructionDataMergeStrategy, Collections.<Instruction>emptyList(), changed, false);
|
traverseSubGraph(lookInside, pseudocode, dataMap, instructionDataMergeStrategy, Collections.<Instruction>emptyList(), directOrder, changed, false);
|
||||||
}
|
}
|
||||||
|
return dataMap;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void initializeDataMap(
|
private static <D> void initializeDataMap(
|
||||||
@NotNull Pseudocode pseudocode,
|
boolean lookInside,
|
||||||
|
@NotNull Map<Instruction, Edges<D>> dataMap, @NotNull Pseudocode pseudocode,
|
||||||
@NotNull D initialDataValue) {
|
@NotNull D initialDataValue) {
|
||||||
List<Instruction> instructions = pseudocode.getInstructions();
|
List<Instruction> instructions = pseudocode.getInstructions();
|
||||||
Pair<D, D> initialPair = Pair.create(initialDataValue, initialDataValue);
|
Edges<D> initialEdge = Edges.create(initialDataValue, initialDataValue);
|
||||||
for (Instruction instruction : instructions) {
|
for (Instruction instruction : instructions) {
|
||||||
dataMap.put(instruction, initialPair);
|
dataMap.put(instruction, initialEdge);
|
||||||
if (lookInside && instruction instanceof LocalDeclarationInstruction) {
|
if (lookInside && instruction instanceof LocalDeclarationInstruction) {
|
||||||
initializeDataMap(((LocalDeclarationInstruction) instruction).getBody(), initialDataValue);
|
initializeDataMap(lookInside, dataMap, ((LocalDeclarationInstruction) instruction).getBody(), initialDataValue);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void traverseSubGraph(
|
private static <D> void traverseSubGraph(
|
||||||
|
boolean lookInside,
|
||||||
@NotNull Pseudocode pseudocode,
|
@NotNull Pseudocode pseudocode,
|
||||||
|
@NotNull Map<Instruction, Edges<D>> dataMap,
|
||||||
@NotNull InstructionDataMergeStrategy<D> instructionDataMergeStrategy,
|
@NotNull InstructionDataMergeStrategy<D> instructionDataMergeStrategy,
|
||||||
@NotNull Collection<Instruction> previousSubGraphInstructions,
|
@NotNull Collection<Instruction> previousSubGraphInstructions,
|
||||||
|
boolean directOrder,
|
||||||
boolean[] changed,
|
boolean[] changed,
|
||||||
boolean isLocal) {
|
boolean isLocal) {
|
||||||
List<Instruction> instructions = directOrder ? pseudocode.getInstructions() : pseudocode.getReversedInstructions();
|
List<Instruction> instructions = directOrder ? pseudocode.getInstructions() : pseudocode.getReversedInstructions();
|
||||||
Instruction startInstruction = getStartInstruction(pseudocode);
|
Instruction startInstruction = getStartInstruction(pseudocode, directOrder);
|
||||||
|
|
||||||
for (Instruction instruction : instructions) {
|
for (Instruction instruction : instructions) {
|
||||||
boolean isStart = directOrder ? instruction instanceof SubroutineEnterInstruction : instruction instanceof SubroutineSinkInstruction;
|
boolean isStart = directOrder ? instruction instanceof SubroutineEnterInstruction : instruction instanceof SubroutineSinkInstruction;
|
||||||
@@ -110,27 +102,27 @@ public class JetControlFlowGraphTraverser<D> {
|
|||||||
|
|
||||||
if (lookInside && instruction instanceof LocalDeclarationInstruction) {
|
if (lookInside && instruction instanceof LocalDeclarationInstruction) {
|
||||||
Pseudocode subroutinePseudocode = ((LocalDeclarationInstruction) instruction).getBody();
|
Pseudocode subroutinePseudocode = ((LocalDeclarationInstruction) instruction).getBody();
|
||||||
traverseSubGraph(subroutinePseudocode, instructionDataMergeStrategy, previousInstructions, changed, true);
|
traverseSubGraph(lookInside, subroutinePseudocode, dataMap ,instructionDataMergeStrategy, previousInstructions, directOrder, changed, true);
|
||||||
Instruction lastInstruction = directOrder ? subroutinePseudocode.getSinkInstruction() : subroutinePseudocode.getEnterInstruction();
|
Instruction lastInstruction = directOrder ? subroutinePseudocode.getSinkInstruction() : subroutinePseudocode.getEnterInstruction();
|
||||||
Pair<D, D> previousValue = dataMap.get(instruction);
|
Edges<D> previousValue = dataMap.get(instruction);
|
||||||
Pair<D, D> newValue = dataMap.get(lastInstruction);
|
Edges<D> newValue = dataMap.get(lastInstruction);
|
||||||
if (!previousValue.equals(newValue)) {
|
if (!previousValue.equals(newValue)) {
|
||||||
changed[0] = true;
|
changed[0] = true;
|
||||||
dataMap.put(instruction, newValue);
|
dataMap.put(instruction, newValue);
|
||||||
}
|
}
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
Pair<D, D> previousDataValue = dataMap.get(instruction);
|
Edges<D> previousDataValue = dataMap.get(instruction);
|
||||||
|
|
||||||
Collection<D> incomingEdgesData = Sets.newHashSet();
|
Collection<D> incomingEdgesData = Sets.newHashSet();
|
||||||
|
|
||||||
for (Instruction previousInstruction : allPreviousInstructions) {
|
for (Instruction previousInstruction : allPreviousInstructions) {
|
||||||
Pair<D, D> previousData = dataMap.get(previousInstruction);
|
Edges<D> previousData = dataMap.get(previousInstruction);
|
||||||
if (previousData != null) {
|
if (previousData != null) {
|
||||||
incomingEdgesData.add(previousData.getSecond());
|
incomingEdgesData.add(previousData.out);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Pair<D, D> mergedData = instructionDataMergeStrategy.execute(instruction, incomingEdgesData);
|
Edges<D> mergedData = instructionDataMergeStrategy.execute(instruction, incomingEdgesData);
|
||||||
if (!mergedData.equals(previousDataValue)) {
|
if (!mergedData.equals(previousDataValue)) {
|
||||||
changed[0] = true;
|
changed[0] = true;
|
||||||
dataMap.put(instruction, mergedData);
|
dataMap.put(instruction, mergedData);
|
||||||
@@ -138,13 +130,28 @@ public class JetControlFlowGraphTraverser<D> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void traverseAndAnalyzeInstructionGraph(
|
public static void traverseAndAnalyzeInstructionGraph(
|
||||||
@NotNull InstructionDataAnalyzeStrategy<D> instructionDataAnalyzeStrategy) {
|
@NotNull Pseudocode pseudocode,
|
||||||
traverseAndAnalyzeInstructionGraph(pseudocode, instructionDataAnalyzeStrategy);
|
boolean directOrder,
|
||||||
|
SimpleInstructionDataAnalyzeStrategy instructionDataAnalyzeStrategy) {
|
||||||
|
List<Instruction> instructions = pseudocode.getInstructions();
|
||||||
|
if (!directOrder) {
|
||||||
|
instructions = Lists.newArrayList(instructions);
|
||||||
|
Collections.reverse(instructions);
|
||||||
|
}
|
||||||
|
for (Instruction instruction : instructions) {
|
||||||
|
if (instruction instanceof LocalDeclarationInstruction) {
|
||||||
|
traverseAndAnalyzeInstructionGraph(((LocalDeclarationInstruction) instruction).getBody(), directOrder, instructionDataAnalyzeStrategy);
|
||||||
|
}
|
||||||
|
instructionDataAnalyzeStrategy.execute(instruction);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void traverseAndAnalyzeInstructionGraph(
|
public static <D> void traverseAndAnalyzeInstructionGraph(
|
||||||
|
boolean lookInside,
|
||||||
@NotNull Pseudocode pseudocode,
|
@NotNull Pseudocode pseudocode,
|
||||||
|
@NotNull Map<Instruction, Edges<D>> dataMap,
|
||||||
|
boolean directOrder,
|
||||||
@NotNull InstructionDataAnalyzeStrategy<D> instructionDataAnalyzeStrategy) {
|
@NotNull InstructionDataAnalyzeStrategy<D> instructionDataAnalyzeStrategy) {
|
||||||
List<Instruction> instructions = pseudocode.getInstructions();
|
List<Instruction> instructions = pseudocode.getInstructions();
|
||||||
if (!directOrder) {
|
if (!directOrder) {
|
||||||
@@ -153,24 +160,22 @@ public class JetControlFlowGraphTraverser<D> {
|
|||||||
}
|
}
|
||||||
for (Instruction instruction : instructions) {
|
for (Instruction instruction : instructions) {
|
||||||
if (lookInside && instruction instanceof LocalDeclarationInstruction) {
|
if (lookInside && instruction instanceof LocalDeclarationInstruction) {
|
||||||
traverseAndAnalyzeInstructionGraph(((LocalDeclarationInstruction) instruction).getBody(), instructionDataAnalyzeStrategy);
|
traverseAndAnalyzeInstructionGraph(lookInside, ((LocalDeclarationInstruction) instruction).getBody(), dataMap, directOrder, instructionDataAnalyzeStrategy);
|
||||||
}
|
}
|
||||||
Pair<D, D> pair = dataMap.get(instruction);
|
Edges<D> edges = dataMap.get(instruction);
|
||||||
instructionDataAnalyzeStrategy.execute(instruction,
|
instructionDataAnalyzeStrategy.execute(instruction, edges != null ? edges.in : null, edges != null ? edges.out : null);
|
||||||
pair != null ? pair.getFirst() : null,
|
|
||||||
pair != null ? pair.getSecond() : null);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public D getResultInfo() {
|
|
||||||
return dataMap.get(pseudocode.getExitInstruction()).getFirst();
|
|
||||||
}
|
|
||||||
|
|
||||||
public interface InstructionDataMergeStrategy<D> {
|
public interface InstructionDataMergeStrategy<D> {
|
||||||
Pair<D, D> execute(@NotNull Instruction instruction, @NotNull Collection<D> incomingEdgesData);
|
Edges<D> execute(@NotNull Instruction instruction, @NotNull Collection<D> incomingEdgesData);
|
||||||
}
|
}
|
||||||
|
|
||||||
public interface InstructionDataAnalyzeStrategy<D> {
|
public interface InstructionDataAnalyzeStrategy<D> {
|
||||||
void execute(@NotNull Instruction instruction, @Nullable D enterData, @Nullable D exitData);
|
void execute(@NotNull Instruction instruction, @Nullable D enterData, @Nullable D exitData);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public interface SimpleInstructionDataAnalyzeStrategy {
|
||||||
|
void execute(@NotNull Instruction instruction);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
@@ -0,0 +1,66 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2012 JetBrains s.r.o.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package org.jetbrains.jet.lang.cfg.data;
|
||||||
|
|
||||||
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @author svtk
|
||||||
|
*/
|
||||||
|
public class Edges<T> {
|
||||||
|
public final T in;
|
||||||
|
public final T out;
|
||||||
|
|
||||||
|
Edges(@NotNull T in, @NotNull T out) {
|
||||||
|
this.in = in;
|
||||||
|
this.out = out;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static <T> Edges<T> create(@NotNull T in, @NotNull T out) {
|
||||||
|
return new Edges<T>(in, out);
|
||||||
|
}
|
||||||
|
|
||||||
|
@NotNull
|
||||||
|
public T getIn() {
|
||||||
|
return in;
|
||||||
|
}
|
||||||
|
|
||||||
|
@NotNull
|
||||||
|
public T getOut() {
|
||||||
|
return out;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean equals(Object o) {
|
||||||
|
if (this == o) return true;
|
||||||
|
if (!(o instanceof Edges)) return false;
|
||||||
|
|
||||||
|
Edges edges = (Edges) o;
|
||||||
|
|
||||||
|
if (in != null ? !in.equals(edges.in) : edges.in != null) return false;
|
||||||
|
if (out != null ? !out.equals(edges.out) : edges.out != null) return false;
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int hashCode() {
|
||||||
|
int result = in != null ? in.hashCode() : 0;
|
||||||
|
result = 31 * result + (out != null ? out.hashCode() : 0);
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -31,62 +31,38 @@ public class InstructionData {
|
|||||||
public final Instruction instruction;
|
public final Instruction instruction;
|
||||||
public final PseudocodeData pseudocodeData;
|
public final PseudocodeData pseudocodeData;
|
||||||
|
|
||||||
private final Map<VariableDescriptor, EdgesData<VariableInitializers>> initializersMap = Maps.newHashMap();
|
private final Map<VariableDescriptor, Edges<VariableInitializers>> initializersMap = Maps.newHashMap();
|
||||||
private final Map<VariableDescriptor, EdgesData<VariableUseStatus>> useStatusMap = Maps.newHashMap();
|
private final Map<VariableDescriptor, Edges<VariableUseStatus>> useStatusMap = Maps.newHashMap();
|
||||||
|
|
||||||
public InstructionData(@NotNull PseudocodeData data, @NotNull Instruction instruction,
|
public InstructionData(@NotNull PseudocodeData data, @NotNull Instruction instruction,
|
||||||
@NotNull Pair<Map<VariableDescriptor, VariableInitializers>, Map<VariableDescriptor, VariableInitializers>> pairOfVariableInitializersMap,
|
@NotNull Edges<Map<VariableDescriptor, VariableInitializers>> pairOfVariableInitializersMap,
|
||||||
@NotNull Pair<Map<VariableDescriptor, VariableUseStatus>, Map<VariableDescriptor, VariableUseStatus>> pairOfVariableStatusMap) {
|
@NotNull Edges<Map<VariableDescriptor, VariableUseStatus>> pairOfVariableStatusMap) {
|
||||||
pseudocodeData = data;
|
pseudocodeData = data;
|
||||||
this.instruction = instruction;
|
this.instruction = instruction;
|
||||||
|
|
||||||
for (Map.Entry<VariableDescriptor, VariableInitializers> entry : pairOfVariableInitializersMap.second.entrySet()) {
|
for (Map.Entry<VariableDescriptor, VariableInitializers> entry : pairOfVariableInitializersMap.out.entrySet()) {
|
||||||
VariableDescriptor variableDescriptor = entry.getKey();
|
VariableDescriptor variableDescriptor = entry.getKey();
|
||||||
VariableInitializers in = pairOfVariableInitializersMap.first.get(variableDescriptor);
|
VariableInitializers in = pairOfVariableInitializersMap.in.get(variableDescriptor);
|
||||||
VariableInitializers out = entry.getValue();
|
VariableInitializers out = entry.getValue();
|
||||||
initializersMap.put(variableDescriptor, EdgesData.create(in, out));
|
initializersMap.put(variableDescriptor, Edges.create(in, out));
|
||||||
}
|
}
|
||||||
|
|
||||||
for (Map.Entry<VariableDescriptor, VariableUseStatus> entry : pairOfVariableStatusMap.second.entrySet()) {
|
for (Map.Entry<VariableDescriptor, VariableUseStatus> entry : pairOfVariableStatusMap.out.entrySet()) {
|
||||||
VariableDescriptor variableDescriptor = entry.getKey();
|
VariableDescriptor variableDescriptor = entry.getKey();
|
||||||
VariableUseStatus in = pairOfVariableStatusMap.first.get(variableDescriptor);
|
VariableUseStatus in = pairOfVariableStatusMap.in.get(variableDescriptor);
|
||||||
VariableUseStatus out = entry.getValue();
|
VariableUseStatus out = entry.getValue();
|
||||||
if (in == null || out == null) continue;
|
if (in == null || out == null) continue;
|
||||||
useStatusMap.put(variableDescriptor, EdgesData.create(in, out));
|
useStatusMap.put(variableDescriptor, Edges.create(in, out));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public Map<VariableDescriptor, EdgesData<VariableInitializers>> getInitializersMap() {
|
public Map<VariableDescriptor, Edges<VariableInitializers>> getInitializersMap() {
|
||||||
return initializersMap;
|
return initializersMap;
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public Map<VariableDescriptor, EdgesData<VariableUseStatus>> getUseStatusMap() {
|
public Map<VariableDescriptor, Edges<VariableUseStatus>> getUseStatusMap() {
|
||||||
return useStatusMap;
|
return useStatusMap;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class EdgesData<T> {
|
|
||||||
private final T in;
|
|
||||||
private final T out;
|
|
||||||
|
|
||||||
private EdgesData(@NotNull T in, @NotNull T out) {
|
|
||||||
this.in = in;
|
|
||||||
this.out = out;
|
|
||||||
}
|
|
||||||
|
|
||||||
private static <T> EdgesData<T> create(@NotNull T in, @NotNull T out) {
|
|
||||||
return new EdgesData<T>(in, out);
|
|
||||||
}
|
|
||||||
|
|
||||||
@NotNull
|
|
||||||
public T getIn() {
|
|
||||||
return in;
|
|
||||||
}
|
|
||||||
|
|
||||||
@NotNull
|
|
||||||
public T getOut() {
|
|
||||||
return out;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -19,10 +19,9 @@ package org.jetbrains.jet.lang.cfg.data;
|
|||||||
import com.google.common.collect.Lists;
|
import com.google.common.collect.Lists;
|
||||||
import com.google.common.collect.Maps;
|
import com.google.common.collect.Maps;
|
||||||
import com.google.common.collect.Sets;
|
import com.google.common.collect.Sets;
|
||||||
import com.intellij.openapi.util.Pair;
|
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
import org.jetbrains.jet.lang.cfg.JetControlFlowGraphTraverser;
|
import org.jetbrains.jet.lang.cfg.PseudocodeTraverser;
|
||||||
import org.jetbrains.jet.lang.cfg.pseudocode.*;
|
import org.jetbrains.jet.lang.cfg.pseudocode.*;
|
||||||
import org.jetbrains.jet.lang.descriptors.DeclarationDescriptor;
|
import org.jetbrains.jet.lang.descriptors.DeclarationDescriptor;
|
||||||
import org.jetbrains.jet.lang.descriptors.VariableDescriptor;
|
import org.jetbrains.jet.lang.descriptors.VariableDescriptor;
|
||||||
@@ -31,7 +30,6 @@ import org.jetbrains.jet.lang.psi.JetElement;
|
|||||||
import org.jetbrains.jet.lang.psi.JetProperty;
|
import org.jetbrains.jet.lang.psi.JetProperty;
|
||||||
import org.jetbrains.jet.lang.resolve.BindingContext;
|
import org.jetbrains.jet.lang.resolve.BindingContext;
|
||||||
import org.jetbrains.jet.lang.resolve.BindingContextUtils;
|
import org.jetbrains.jet.lang.resolve.BindingContextUtils;
|
||||||
import org.jetbrains.jet.lang.resolve.BindingTrace;
|
|
||||||
|
|
||||||
import java.util.*;
|
import java.util.*;
|
||||||
|
|
||||||
@@ -42,29 +40,38 @@ public class PseudocodeData {
|
|||||||
private final Pseudocode pseudocode;
|
private final Pseudocode pseudocode;
|
||||||
private final Map<Instruction, InstructionData> instructionDataMap = Maps.newLinkedHashMap();
|
private final Map<Instruction, InstructionData> instructionDataMap = Maps.newLinkedHashMap();
|
||||||
private final Map<Pseudocode, DeclarationData> declarationDataMap = Maps.newLinkedHashMap();
|
private final Map<Pseudocode, DeclarationData> declarationDataMap = Maps.newLinkedHashMap();
|
||||||
private final BindingTrace trace;
|
|
||||||
|
|
||||||
public PseudocodeData(@NotNull Pseudocode pseudocode, @NotNull BindingTrace trace) {
|
//private final Map<Pseudocode, Set<VariableDescriptor>> declaredVariablesInEachDeclaration;
|
||||||
|
//private final Map<Pseudocode, Set<VariableDescriptor>> usedVariablesInEachDeclaration;
|
||||||
|
|
||||||
|
private final BindingContext bindingContext;
|
||||||
|
|
||||||
|
public PseudocodeData(@NotNull Pseudocode pseudocode, @NotNull BindingContext bindingContext) {
|
||||||
this.pseudocode = pseudocode;
|
this.pseudocode = pseudocode;
|
||||||
this.trace = trace;
|
this.bindingContext = bindingContext;
|
||||||
collectDeclarationData(pseudocode);
|
collectDeclarationData(pseudocode);
|
||||||
|
|
||||||
DeclarationData declarationData = declarationDataMap.get(pseudocode);
|
DeclarationData declarationData = declarationDataMap.get(pseudocode);
|
||||||
|
|
||||||
final Map<Instruction, Pair<Map<VariableDescriptor, VariableInitializers>, Map<VariableDescriptor, VariableInitializers>>> variableInitializersMap =
|
final Map<Instruction, Edges<Map<VariableDescriptor, VariableInitializers>>> variableInitializersMap =
|
||||||
collectVariableInitializers(pseudocode, declarationData);
|
collectVariableInitializers(pseudocode, declarationData);
|
||||||
final Map<Instruction, Pair<Map<VariableDescriptor, VariableUseStatus>, Map<VariableDescriptor, VariableUseStatus>>> variableStatusMap =
|
final Map<Instruction, Edges<Map<VariableDescriptor, VariableUseStatus>>> variableStatusMap =
|
||||||
collectVariableStatusData();
|
collectVariableStatusData();
|
||||||
|
|
||||||
JetControlFlowGraphTraverser.<Void>create(pseudocode, true, true).traverseAndAnalyzeInstructionGraph(
|
|
||||||
new JetControlFlowGraphTraverser.InstructionDataAnalyzeStrategy<Void>() {
|
PseudocodeTraverser.traverseAndAnalyzeInstructionGraph(pseudocode, true,
|
||||||
@Override
|
new PseudocodeTraverser.SimpleInstructionDataAnalyzeStrategy() {
|
||||||
public void execute(@NotNull Instruction instruction, Void enterData, Void exitData) {
|
@Override
|
||||||
instructionDataMap.put(instruction,
|
public void execute(@NotNull Instruction instruction) {
|
||||||
new InstructionData(PseudocodeData.this, instruction, variableInitializersMap.get(instruction),
|
instructionDataMap.put(instruction,
|
||||||
variableStatusMap.get(instruction)));
|
new InstructionData(PseudocodeData.this,
|
||||||
}
|
instruction,
|
||||||
});
|
variableInitializersMap
|
||||||
|
.get(instruction),
|
||||||
|
variableStatusMap
|
||||||
|
.get(instruction)));
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
@@ -126,64 +133,59 @@ public class PseudocodeData {
|
|||||||
|
|
||||||
private Set<VariableDescriptor> collectUsedVariables(@NotNull Pseudocode pseudocode) {
|
private Set<VariableDescriptor> collectUsedVariables(@NotNull Pseudocode pseudocode) {
|
||||||
final Set<VariableDescriptor> usedVariables = Sets.newHashSet();
|
final Set<VariableDescriptor> usedVariables = Sets.newHashSet();
|
||||||
JetControlFlowGraphTraverser.<Void>create(pseudocode, true, true).traverseAndAnalyzeInstructionGraph(new JetControlFlowGraphTraverser.InstructionDataAnalyzeStrategy<Void>() {
|
PseudocodeTraverser.traverseAndAnalyzeInstructionGraph(pseudocode, true,
|
||||||
@Override
|
new PseudocodeTraverser.SimpleInstructionDataAnalyzeStrategy() {
|
||||||
public void execute(@NotNull Instruction instruction, @Nullable Void enterData, @Nullable Void exitData) {
|
@Override
|
||||||
VariableDescriptor variableDescriptor = extractVariableDescriptorIfAny(instruction, false);
|
public void execute(@NotNull Instruction instruction) {
|
||||||
if (variableDescriptor != null) {
|
VariableDescriptor variableDescriptor =
|
||||||
usedVariables.add(variableDescriptor);
|
extractVariableDescriptorIfAny(instruction, false);
|
||||||
}
|
if (variableDescriptor != null) {
|
||||||
}
|
usedVariables.add(variableDescriptor);
|
||||||
});
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
return usedVariables;
|
return usedVariables;
|
||||||
}
|
}
|
||||||
|
|
||||||
private Set<VariableDescriptor> collectDeclaredVariables(@NotNull Pseudocode pseudocode) {
|
private Set<VariableDescriptor> collectDeclaredVariables(@NotNull Pseudocode pseudocode) {
|
||||||
final Set<VariableDescriptor> declaredVariables = Sets.newHashSet();
|
final Set<VariableDescriptor> declaredVariables = Sets.newHashSet();
|
||||||
JetControlFlowGraphTraverser.<Void>create(pseudocode, false, true).traverseAndAnalyzeInstructionGraph(new JetControlFlowGraphTraverser.InstructionDataAnalyzeStrategy<Void>() {
|
for (Instruction instruction : pseudocode.getInstructions()) {
|
||||||
@Override
|
if (instruction instanceof VariableDeclarationInstruction) {
|
||||||
public void execute(@NotNull Instruction instruction, @Nullable Void enterData, @Nullable Void exitData) {
|
JetDeclaration variableDeclarationElement = ((VariableDeclarationInstruction) instruction).getVariableDeclarationElement();
|
||||||
if (instruction instanceof VariableDeclarationInstruction) {
|
DeclarationDescriptor descriptor = bindingContext.get(BindingContext.DECLARATION_TO_DESCRIPTOR, variableDeclarationElement);
|
||||||
JetDeclaration variableDeclarationElement = ((VariableDeclarationInstruction) instruction).getVariableDeclarationElement();
|
if (descriptor != null) {
|
||||||
DeclarationDescriptor descriptor = trace.get(BindingContext.DECLARATION_TO_DESCRIPTOR, variableDeclarationElement);
|
assert descriptor instanceof VariableDescriptor;
|
||||||
if (descriptor != null) {
|
declaredVariables.add((VariableDescriptor) descriptor);
|
||||||
assert descriptor instanceof VariableDescriptor;
|
|
||||||
declaredVariables.add((VariableDescriptor) descriptor);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
}
|
||||||
return declaredVariables;
|
return declaredVariables;
|
||||||
}
|
}
|
||||||
|
|
||||||
// variable initializers
|
// variable initializers
|
||||||
|
|
||||||
private Map<Instruction, Pair<Map<VariableDescriptor, VariableInitializers>, Map<VariableDescriptor, VariableInitializers>>> collectVariableInitializers(
|
private Map<Instruction, Edges<Map<VariableDescriptor, VariableInitializers>>> collectVariableInitializers(
|
||||||
Pseudocode pseudocode, DeclarationData data) {
|
Pseudocode pseudocode, DeclarationData data) {
|
||||||
|
|
||||||
JetControlFlowGraphTraverser<Map<VariableDescriptor, VariableInitializers>> traverser = JetControlFlowGraphTraverser.create(pseudocode, false, true);
|
|
||||||
|
|
||||||
final Map<VariableDescriptor, VariableInitializers> initialMapForStartInstruction = prepareInitialMapForStartInstruction(data.usedVariables, data.declaredVariables);
|
final Map<VariableDescriptor, VariableInitializers> initialMapForStartInstruction = prepareInitialMapForStartInstruction(data.usedVariables, data.declaredVariables);
|
||||||
|
|
||||||
traverser.collectInformationFromInstructionGraph(Collections.<VariableDescriptor, VariableInitializers>emptyMap(), initialMapForStartInstruction,
|
Map<Instruction, Edges<Map<VariableDescriptor, VariableInitializers>>> result =
|
||||||
new JetControlFlowGraphTraverser.InstructionDataMergeStrategy<Map<VariableDescriptor, VariableInitializers>>() {
|
PseudocodeTraverser.collectInformationFromInstructionGraph(false, true, pseudocode, Collections.<VariableDescriptor, VariableInitializers>emptyMap(), initialMapForStartInstruction,
|
||||||
|
new PseudocodeTraverser.InstructionDataMergeStrategy<Map<VariableDescriptor, VariableInitializers>>() {
|
||||||
@Override
|
@Override
|
||||||
public Pair<Map<VariableDescriptor, VariableInitializers>, Map<VariableDescriptor, VariableInitializers>> execute(
|
public Edges<Map<VariableDescriptor, VariableInitializers>> execute(
|
||||||
@NotNull Instruction instruction,
|
@NotNull Instruction instruction,
|
||||||
@NotNull Collection<Map<VariableDescriptor, VariableInitializers>> incomingEdgesData) {
|
@NotNull Collection<Map<VariableDescriptor, VariableInitializers>> incomingEdgesData) {
|
||||||
|
|
||||||
Map<VariableDescriptor, VariableInitializers> enterInstructionData = mergeIncomingEdgesData(incomingEdgesData);
|
Map<VariableDescriptor, VariableInitializers> enterInstructionData = mergeIncomingEdgesData(incomingEdgesData);
|
||||||
Map<VariableDescriptor, VariableInitializers> exitInstructionData = addVariableInitializerFromCurrentInstructionIfAny(instruction, enterInstructionData);
|
Map<VariableDescriptor, VariableInitializers> exitInstructionData = addVariableInitializerFromCurrentInstructionIfAny(instruction, enterInstructionData);
|
||||||
return Pair.create(enterInstructionData, exitInstructionData);
|
return Edges.create(enterInstructionData, exitInstructionData);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
Map<Instruction, Pair<Map<VariableDescriptor, VariableInitializers>, Map<VariableDescriptor, VariableInitializers>>> result =
|
|
||||||
traverser.getDataMap();
|
|
||||||
|
|
||||||
for (LocalDeclarationInstruction localDeclarationInstruction : pseudocode.getLocalDeclarations()) {
|
for (LocalDeclarationInstruction localDeclarationInstruction : pseudocode.getLocalDeclarations()) {
|
||||||
Pseudocode localPseudocode = localDeclarationInstruction.getBody();
|
Pseudocode localPseudocode = localDeclarationInstruction.getBody();
|
||||||
Map<Instruction, Pair<Map<VariableDescriptor, VariableInitializers>, Map<VariableDescriptor, VariableInitializers>>> initializersForLocalDeclaration =
|
Map<Instruction, Edges<Map<VariableDescriptor, VariableInitializers>>> initializersForLocalDeclaration =
|
||||||
collectVariableInitializers(localPseudocode, declarationDataMap.get(localPseudocode));
|
collectVariableInitializers(localPseudocode, declarationDataMap.get(localPseudocode));
|
||||||
|
|
||||||
for (Instruction instruction : initializersForLocalDeclaration.keySet()) {
|
for (Instruction instruction : initializersForLocalDeclaration.keySet()) {
|
||||||
@@ -267,17 +269,15 @@ public class PseudocodeData {
|
|||||||
|
|
||||||
// variable use
|
// variable use
|
||||||
|
|
||||||
private Map<Instruction, Pair<Map<VariableDescriptor, VariableUseStatus>, Map<VariableDescriptor, VariableUseStatus>>> collectVariableStatusData() {
|
private Map<Instruction, Edges<Map<VariableDescriptor, VariableUseStatus>>> collectVariableStatusData() {
|
||||||
JetControlFlowGraphTraverser<Map<VariableDescriptor, VariableUseStatus>> traverser =
|
|
||||||
JetControlFlowGraphTraverser.create(pseudocode, true, false);
|
|
||||||
Map<VariableDescriptor, VariableUseStatus> sinkInstructionData = Maps.newHashMap();
|
Map<VariableDescriptor, VariableUseStatus> sinkInstructionData = Maps.newHashMap();
|
||||||
for (VariableDescriptor usedVariable : declarationDataMap.get(pseudocode).usedVariables) {
|
for (VariableDescriptor usedVariable : declarationDataMap.get(pseudocode).usedVariables) {
|
||||||
sinkInstructionData.put(usedVariable, VariableUseStatus.UNUSED);
|
sinkInstructionData.put(usedVariable, VariableUseStatus.UNUSED);
|
||||||
}
|
}
|
||||||
traverser.collectInformationFromInstructionGraph(Collections.<VariableDescriptor, VariableUseStatus>emptyMap(), sinkInstructionData,
|
return PseudocodeTraverser.collectInformationFromInstructionGraph(true, false, pseudocode, Collections.<VariableDescriptor, VariableUseStatus>emptyMap(), sinkInstructionData,
|
||||||
new JetControlFlowGraphTraverser.InstructionDataMergeStrategy<Map<VariableDescriptor, VariableUseStatus>>() {
|
new PseudocodeTraverser.InstructionDataMergeStrategy<Map<VariableDescriptor, VariableUseStatus>>() {
|
||||||
@Override
|
@Override
|
||||||
public Pair<Map<VariableDescriptor, VariableUseStatus>, Map<VariableDescriptor, VariableUseStatus>> execute(@NotNull Instruction instruction, @NotNull Collection<Map<VariableDescriptor, VariableUseStatus>> incomingEdgesData) {
|
public Edges<Map<VariableDescriptor, VariableUseStatus>> execute(@NotNull Instruction instruction, @NotNull Collection<Map<VariableDescriptor, VariableUseStatus>> incomingEdgesData) {
|
||||||
Map<VariableDescriptor, VariableUseStatus> enterResult = Maps.newHashMap();
|
Map<VariableDescriptor, VariableUseStatus> enterResult = Maps.newHashMap();
|
||||||
for (Map<VariableDescriptor, VariableUseStatus> edgeData : incomingEdgesData) {
|
for (Map<VariableDescriptor, VariableUseStatus> edgeData : incomingEdgesData) {
|
||||||
for (Map.Entry<VariableDescriptor, VariableUseStatus> entry : edgeData.entrySet()) {
|
for (Map.Entry<VariableDescriptor, VariableUseStatus> entry : edgeData.entrySet()) {
|
||||||
@@ -288,7 +288,7 @@ public class PseudocodeData {
|
|||||||
}
|
}
|
||||||
VariableDescriptor variableDescriptor = extractVariableDescriptorIfAny(instruction, true);
|
VariableDescriptor variableDescriptor = extractVariableDescriptorIfAny(instruction, true);
|
||||||
if (variableDescriptor == null || (!(instruction instanceof ReadValueInstruction) && !(instruction instanceof WriteValueInstruction))) {
|
if (variableDescriptor == null || (!(instruction instanceof ReadValueInstruction) && !(instruction instanceof WriteValueInstruction))) {
|
||||||
return Pair.create(enterResult, enterResult);
|
return Edges.create(enterResult, enterResult);
|
||||||
}
|
}
|
||||||
Map<VariableDescriptor, VariableUseStatus> exitResult = Maps.newHashMap(enterResult);
|
Map<VariableDescriptor, VariableUseStatus> exitResult = Maps.newHashMap(enterResult);
|
||||||
if (instruction instanceof ReadValueInstruction) {
|
if (instruction instanceof ReadValueInstruction) {
|
||||||
@@ -307,10 +307,9 @@ public class PseudocodeData {
|
|||||||
exitResult.put(variableDescriptor, VariableUseStatus.LAST_WRITTEN);
|
exitResult.put(variableDescriptor, VariableUseStatus.LAST_WRITTEN);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return Pair.create(enterResult, exitResult);
|
return Edges.create(enterResult, exitResult);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
return traverser.getDataMap();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Util methods
|
// Util methods
|
||||||
@@ -327,7 +326,7 @@ public class PseudocodeData {
|
|||||||
else if (instruction instanceof VariableDeclarationInstruction) {
|
else if (instruction instanceof VariableDeclarationInstruction) {
|
||||||
element = ((VariableDeclarationInstruction) instruction).getVariableDeclarationElement();
|
element = ((VariableDeclarationInstruction) instruction).getVariableDeclarationElement();
|
||||||
}
|
}
|
||||||
return BindingContextUtils.extractVariableDescriptorIfAny(trace.getBindingContext(), element, onlyReference);
|
return BindingContextUtils.extractVariableDescriptorIfAny(bindingContext, element, onlyReference);
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -65,5 +65,4 @@ public class PseudocodeUtil {
|
|||||||
return new JetControlFlowProcessor(mockTrace).generatePseudocode(declaration);
|
return new JetControlFlowProcessor(mockTrace).generatePseudocode(declaration);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user