]> git.uio.no Git - ifi-stolz-refaktor.git/blob - software/no.uio.ifi.refaktor/src/no/uio/ifi/refaktor/analyze/checkers/IllegalStatementsChecker.java
853d0adb13637fd4ca78c6580bead02bf212a5ce
[ifi-stolz-refaktor.git] / software / no.uio.ifi.refaktor / src / no / uio / ifi / refaktor / analyze / checkers / IllegalStatementsChecker.java
1 package no.uio.ifi.refaktor.analyze.checkers;
2
3 import no.uio.ifi.refaktor.analyze.CollectorManager;
4 import no.uio.ifi.refaktor.analyze.collectors.PropertyCollector;
5 import no.uio.ifi.refaktor.analyze.exceptions.IllegalExpressionFoundException;
6 import no.uio.ifi.refaktor.analyze.exceptions.IllegalStatementFoundException;
7 import no.uio.ifi.refaktor.analyze.matchers.InstanceOfMatcher;
8 import no.uio.ifi.refaktor.analyze.matchers.LoopStatementMatcher;
9 import no.uio.ifi.refaktor.analyze.matchers.OrInstanceOfMatcher;
10 import no.uio.ifi.refaktor.analyze.matchers.SwitchStatementMatcher;
11 import no.uio.ifi.refaktor.utils.CompilationUnitTextSelection;
12
13 import org.eclipse.jdt.core.dom.ASTNode;
14 import org.eclipse.jdt.core.dom.ArrayAccess;
15 import org.eclipse.jdt.core.dom.Assignment;
16 import org.eclipse.jdt.core.dom.BreakStatement;
17 import org.eclipse.jdt.core.dom.ContinueStatement;
18 import org.eclipse.jdt.core.dom.Expression;
19 import org.eclipse.jdt.core.dom.IBinding;
20 import org.eclipse.jdt.core.dom.LabeledStatement;
21 import org.eclipse.jdt.core.dom.Modifier;
22 import org.eclipse.jdt.core.dom.QualifiedName;
23 import org.eclipse.jdt.core.dom.SimpleName;
24 import org.eclipse.jdt.core.dom.Statement;
25 import org.eclipse.jdt.core.dom.SuperConstructorInvocation;
26 import org.eclipse.jdt.core.dom.SuperFieldAccess;
27 import org.eclipse.jdt.core.dom.SuperMethodInvocation;
28
29 public class IllegalStatementsChecker extends PropertyCollector implements Checker {
30
31         public IllegalStatementsChecker(CompilationUnitTextSelection selection) {
32                 super(selection);
33         }
34
35         @Override
36         public void check() throws IllegalStatementFoundException, IllegalExpressionFoundException {
37                 CollectorManager.collectProperties(selection, this);
38         }
39
40         @Override
41         public void clearData() {
42         }
43
44         @Override
45         public boolean visit(SuperConstructorInvocation node) {
46                 if (!nodeInSelection(node))
47                         return false;
48
49                 throw new IllegalStatementFoundException(node);
50         }
51
52         @Override
53         public boolean visit(SuperMethodInvocation node) {
54                 if (!nodeInSelection(node))
55                         return false;
56
57                 throw new IllegalExpressionFoundException(node);
58         }
59
60         @Override
61         public boolean visit(SuperFieldAccess node) {
62                 if (!nodeInSelection(node))
63                         return false;
64
65                 throw new IllegalExpressionFoundException(node);
66         }
67
68         @Override
69         public boolean visit(BreakStatement node) {
70                 if (!nodeInSelection(node))
71                         return false;
72
73                 if (node.getLabel() != null) {
74                         checkThatCorrespondingLabelStatementIsInSelection(node, node.getLabel());
75                 } else {
76                         checkThatInnermostMatchingStatementIsInSelection(node, new OrInstanceOfMatcher(new LoopStatementMatcher(), new SwitchStatementMatcher()));
77                 }
78
79                 return true;
80         }
81
82         @Override
83         public boolean visit(ContinueStatement node) {
84                 if (!nodeInSelection(node))
85                         return false;
86
87                 if (node.getLabel() != null) {
88                         checkThatCorrespondingLabelStatementIsInSelection(node, node.getLabel());
89                 } else {
90                         checkThatInnermostMatchingStatementIsInSelection(node, new LoopStatementMatcher());
91                 }
92
93                 return true;
94         }
95
96         private void checkThatCorrespondingLabelStatementIsInSelection(ASTNode node, SimpleName nodeLabel) {
97                 ASTNode parent = node.getParent();
98
99                 while (!parentMatchesLabel(parent, nodeLabel) && parent != node.getRoot())
100                         parent = parent.getParent();
101
102                 if (parent == node.getRoot() || !nodeInSelection(parent))
103                         throw new IllegalStatementFoundException(node);
104         }
105
106         private boolean parentMatchesLabel(ASTNode parent, SimpleName nodeLabel) {
107                 return parent instanceof LabeledStatement && labelsMatches((LabeledStatement) parent, nodeLabel);
108         }
109
110         private boolean labelsMatches(LabeledStatement parentLabelStatement, SimpleName nodeLabel) {
111                 return parentLabelStatement.getLabel().getIdentifier().equals(nodeLabel.getIdentifier());
112         }
113
114         private void checkThatInnermostMatchingStatementIsInSelection(ASTNode node, InstanceOfMatcher matcher) {
115                 ASTNode parent = node.getParent();
116
117                 while (!matcher.matches(parent) && parent != node.getRoot())
118                         parent = parent.getParent();
119
120                 if (parent == node.getRoot())
121                         throw new IllegalStatementFoundException(node);
122
123                 assert parent instanceof Statement;
124
125                 if (!nodeInSelection(parent))
126                         throw new IllegalStatementFoundException(node);
127         }
128         
129         @Override
130         public boolean visit(Assignment node) {
131                 if (!nodeInSelection(node))
132                         return false;
133
134                 if (assignmentIsLegal(node))
135                         return true;
136                 
137                 throw new IllegalStatementFoundException(node);
138         }
139
140         private boolean assignmentIsLegal(Assignment node) {
141                 Expression lhs = node.getLeftHandSide();
142                 if (lhs instanceof SimpleName) {
143                         SimpleName simpleName = (SimpleName) lhs;
144                         IBinding binding = simpleName.resolveBinding();
145                         assert binding != null;
146                         // TODO: refine
147                         return !Modifier.isFinal(binding.getModifiers());
148                 } else if (lhs instanceof QualifiedName || lhs instanceof ArrayAccess) {
149                         return true;
150                 }
151                 return false;
152         }
153 }