mirror of
https://github.com/eclipse-cdt/cdt
synced 2025-07-29 11:55:40 +02:00
Added try block support in control flow graph
This commit is contained in:
parent
3ec7ac60fa
commit
b632454589
2 changed files with 58 additions and 0 deletions
|
@ -48,6 +48,8 @@ import org.eclipse.cdt.core.dom.ast.IASTStatement;
|
||||||
import org.eclipse.cdt.core.dom.ast.IASTSwitchStatement;
|
import org.eclipse.cdt.core.dom.ast.IASTSwitchStatement;
|
||||||
import org.eclipse.cdt.core.dom.ast.IASTUnaryExpression;
|
import org.eclipse.cdt.core.dom.ast.IASTUnaryExpression;
|
||||||
import org.eclipse.cdt.core.dom.ast.IASTWhileStatement;
|
import org.eclipse.cdt.core.dom.ast.IASTWhileStatement;
|
||||||
|
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTCatchHandler;
|
||||||
|
import org.eclipse.cdt.core.dom.ast.cpp.ICPPASTTryBlockStatement;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This class creates C control flow graph
|
* This class creates C control flow graph
|
||||||
|
@ -163,12 +165,41 @@ public class ControlFlowGraphBuilder {
|
||||||
return node;
|
return node;
|
||||||
} else if (body == null) {
|
} else if (body == null) {
|
||||||
// skip - sometimes body is empty such as no else
|
// skip - sometimes body is empty such as no else
|
||||||
|
} else if (body instanceof ICPPASTTryBlockStatement) {
|
||||||
|
return createTry(prev, (ICPPASTTryBlockStatement) body);
|
||||||
} else {
|
} else {
|
||||||
System.err.println("unknown statement for cfg: " + body); //$NON-NLS-1$
|
System.err.println("unknown statement for cfg: " + body); //$NON-NLS-1$
|
||||||
}
|
}
|
||||||
return prev;
|
return prev;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param prev
|
||||||
|
* @param body
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
private IBasicBlock createTry(IBasicBlock prev,
|
||||||
|
ICPPASTTryBlockStatement body) {
|
||||||
|
DecisionNode ifNode = factory.createDecisionNode(body);
|
||||||
|
addOutgoing(prev, ifNode);
|
||||||
|
IConnectorNode mergeNode = factory.createConnectorNode();
|
||||||
|
ifNode.setMergeNode(mergeNode);
|
||||||
|
IBranchNode thenNode = factory.createBranchNode(IBranchNode.THEN);
|
||||||
|
addOutgoing(ifNode, thenNode);
|
||||||
|
IBasicBlock then = createSubGraph(thenNode, body.getTryBody());
|
||||||
|
addJump(then, mergeNode);
|
||||||
|
ICPPASTCatchHandler[] catchHandlers = body.getCatchHandlers();
|
||||||
|
for (int i = 0; i < catchHandlers.length; i++) {
|
||||||
|
ICPPASTCatchHandler handler = catchHandlers[i];
|
||||||
|
IBranchNode handlerNode = factory
|
||||||
|
.createBranchNode(handler.getDeclaration());
|
||||||
|
addOutgoing(ifNode, handlerNode);
|
||||||
|
IBasicBlock els = createSubGraph(handlerNode, handler.getCatchBody());
|
||||||
|
addJump(els, mergeNode);
|
||||||
|
}
|
||||||
|
return mergeNode;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @param body
|
* @param body
|
||||||
* @return
|
* @return
|
||||||
|
|
|
@ -333,4 +333,31 @@ public class ControlFlowGraphTest extends CodanFastCxxAstTestCase {
|
||||||
public IChecker getChecker() {
|
public IChecker getChecker() {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// int foo() {
|
||||||
|
// void * p;
|
||||||
|
// try {
|
||||||
|
// *p = 1;
|
||||||
|
// } catch (int e) {
|
||||||
|
// };
|
||||||
|
// }
|
||||||
|
public void test_try() {
|
||||||
|
buildAndCheck_cpp(getAboveComment());
|
||||||
|
IStartNode startNode = graph.getStartNode();
|
||||||
|
IPlainNode decl = (IPlainNode) startNode.getOutgoing();
|
||||||
|
IDecisionNode des = (IDecisionNode) decl.getOutgoing();
|
||||||
|
//assertEquals("", data(des));
|
||||||
|
IPlainNode bThen = (IPlainNode) branchEnd(des, IBranchNode.THEN);
|
||||||
|
assertEquals("*p = 1;", data(bThen));
|
||||||
|
IBasicBlock bElse = null;
|
||||||
|
IBasicBlock[] outgoingNodes = des.getOutgoingNodes();
|
||||||
|
for (int i = 1; i < outgoingNodes.length; i++) {
|
||||||
|
IBasicBlock iBasicBlock = outgoingNodes[i];
|
||||||
|
IBranchNode bn = (IBranchNode) iBasicBlock;
|
||||||
|
bElse = bn;
|
||||||
|
}
|
||||||
|
IBasicBlock m2 = jumpEnd(bThen);
|
||||||
|
IBasicBlock m1 = jumpEnd(bElse);
|
||||||
|
assertSame(m1, m2);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Reference in a new issue