use of com.jopdesign.common.code.ControlFlowGraph.BasicBlockNode in project jop by jop-devel.
the class WCAInvoker method updateWCEP.
private void updateWCEP() {
if (!provideWCAExecCount)
return;
execCounts.clear();
for (MethodInfo root : getWcaTargets()) {
execCounts.put(root, 1L);
}
NodeVisitor<ExecutionContext> visitor = new NodeVisitor<ExecutionContext>() {
@Override
public boolean visitNode(ExecutionContext context) {
MethodInfo method = context.getMethodInfo();
MethodCode code = method.getCode();
long ec = getExecCount(method);
// skip methods which are not on the WCET path.. we can ship iterating over the childs too..
if (ec == 0)
return false;
// iterate over all blocks in the CFG, find all invokes and add block execution counts to invokees
ControlFlowGraph cfg = method.getCode().getControlFlowGraph(false);
for (CFGNode node : cfg.getGraph().vertexSet()) {
if (node instanceof InvokeNode) {
InvokeNode inv = (InvokeNode) node;
long ef = getExecFrequency(method, node);
for (MethodInfo invokee : inv.getImplementingMethods()) {
addExecCount(invokee, ec * ef);
}
} else if (node instanceof BasicBlockNode) {
// check if we have a JVM invoke here (or an invoke not in a dedicated node..)
for (InstructionHandle ih : node.getBasicBlock().getInstructions()) {
if (!code.isInvokeSite(ih))
continue;
long ef = getExecFrequency(method, node);
for (MethodInfo invokee : method.getAppInfo().findImplementations(code.getInvokeSite(ih))) {
addExecCount(invokee, ec * ef);
}
}
}
}
return true;
}
};
TopologicalTraverser<ExecutionContext, ContextEdge> topOrder = new TopologicalTraverser<ExecutionContext, ContextEdge>(wcetTool.getCallGraph().getGraph(), visitor);
topOrder.traverse();
}
use of com.jopdesign.common.code.ControlFlowGraph.BasicBlockNode in project jop by jop-devel.
the class WCAInvoker method getExecFrequency.
@Override
public long getExecFrequency(MethodInfo method, InstructionHandle ih) {
ControlFlowGraph cfg = method.getCode().getControlFlowGraph(false);
BasicBlockNode block = cfg.getHandleNode(ih);
return getExecFrequency(method, block);
}
use of com.jopdesign.common.code.ControlFlowGraph.BasicBlockNode in project jop by jop-devel.
the class WCAInvoker method isOnLocalWCETPath.
public boolean isOnLocalWCETPath(MethodInfo method, InstructionHandle ih) {
ControlFlowGraph cfg = method.getCode().getControlFlowGraph(false);
BasicBlockNode block = cfg.getHandleNode(ih, true);
// we do not have a block.. this is some exception handling path (hopefully..)
if (block == null) {
return false;
}
for (ExecutionContext node : wcetTool.getCallGraph().getNodes(method)) {
Long flow = wcaNodeFlow.get(node).get(block);
if (flow > 0)
return true;
}
return false;
}
use of com.jopdesign.common.code.ControlFlowGraph.BasicBlockNode in project jop by jop-devel.
the class ExecFrequencyAnalysis method getExecFrequency.
public long getExecFrequency(ExecutionContext context, InstructionHandle ih) {
MethodInfo method = context.getMethodInfo();
// By loading the CFG, loopbounds are attached to the blocks if the WCA tool is loaded
ControlFlowGraph cfg = method.getCode().getControlFlowGraph(false);
LoopColoring<CFGNode, CFGEdge> lc = cfg.getLoopColoring();
BasicBlockNode node = cfg.getHandleNode(ih, true);
if (node == null) {
// THIS IS UNSAFE! but what can you do ...
return 1;
}
long ef = 1;
for (CFGNode hol : lc.getLoopColor(node)) {
LoopBound lb = hol.getLoopBound();
if (lb != null) {
if (lb.isDefaultBound() && !analyses.isWCAMethod(method)) {
ef *= DEFAULT_ACET_LOOP_BOUND;
} else {
ef *= lb.getUpperBound(context);
}
} else {
ef *= DEFAULT_ACET_LOOP_BOUND;
}
}
return ef;
}
use of com.jopdesign.common.code.ControlFlowGraph.BasicBlockNode in project jop by jop-devel.
the class WCETEventHandler method loadLoopAnnotations.
/**
* load annotations for the flow graph.
*
* @param cfg the control flow graph of the method
* @throws BadAnnotationException if an annotations is missing
*/
public void loadLoopAnnotations(ControlFlowGraph cfg) throws BadAnnotationException {
SourceAnnotations wcaMap;
MethodInfo method = cfg.getMethodInfo();
MethodCode code = method.getCode();
ExecutionContext eCtx = new ExecutionContext(cfg.getMethodInfo());
for (CFGNode n : cfg.getLoopColoring().getHeadOfLoops()) {
BasicBlockNode headOfLoop = (BasicBlockNode) n;
BasicBlock block = headOfLoop.getBasicBlock();
// check if loopbound has already been loaded
if (block.getLoopBound() != null) {
// or at least check if the source-annotation is tighter than what is currently set?
continue;
}
Set<LoopBound> bounds = new HashSet<LoopBound>(2);
InstructionHandle first = block.getFirstInstruction();
InstructionHandle last = first;
ClassInfo sourceInfo = method.getCode().getSourceClassInfo(block.getFirstInstruction());
for (InstructionHandle ih : block.getInstructions()) {
ClassInfo cls = method.getCode().getSourceClassInfo(ih);
boolean isLast = ih.equals(block.getLastInstruction());
if (!cls.equals(sourceInfo) || isLast) {
try {
wcaMap = getAnnotations(method.getCode().getSourceClassInfo(block.getFirstInstruction()));
} catch (IOException e) {
throw new BadAnnotationException("IO Error reading annotation: " + e.getMessage(), e);
}
if (isLast) {
last = ih;
}
// search for loop annotation in range
int sourceRangeStart = code.getLineNumber(first);
int sourceRangeStop = code.getLineNumber(last);
bounds.addAll(wcaMap.annotationsForLineRange(sourceRangeStart, sourceRangeStop + 1));
first = ih;
}
last = ih;
}
if (bounds.size() > 1) {
String reason = "Ambiguous Annotation [" + bounds + "]";
throw new BadAnnotationException(reason, code, block);
}
LoopBound loopAnnot = null;
if (bounds.size() == 1) {
loopAnnot = bounds.iterator().next();
}
// if we have loop bounds from DFA analysis, use them
loopAnnot = dfaLoopBound(block, eCtx, loopAnnot);
if (loopAnnot == null) {
// Bit of a hack: if we load CFGs before the callgraph is constructed, this will log errors anyway
if (ignoreMissingLoopBounds) {
logger.trace("No loop bound annotation: " + method + ":" + n + " " + getLineRangeText(code, block) + ".\nApproximating with " + DEFAULT_LOOP_BOUND + ", but result is not safe anymore.");
} else if (project.getCallGraph() != null && !project.getCallGraph().containsMethod(method)) {
logger.debug("No loop bound annotation for non-WCET method: " + method + ":" + n + " " + getLineRangeText(code, block) + ".\nApproximating with " + DEFAULT_LOOP_BOUND);
} else {
logger.error("No loop bound annotation: " + method + ":" + n + " " + getLineRangeText(code, block) + ".\nApproximating with " + DEFAULT_LOOP_BOUND + ", but result is not safe anymore.");
}
loopAnnot = LoopBound.defaultBound(DEFAULT_LOOP_BOUND);
}
block.setLoopBound(loopAnnot);
}
}
Aggregations