/** * Returns LiveVariables object with information concerning local variables and parameters */ public static LiveVariables analyze(CFG cfg) { return analyze(cfg, false); }
/** * Returns LiveVariables object with information concerning local variables, parameters and fields */ public static LiveVariables analyzeWithFields(CFG cfg) { return analyze(cfg, true); }
/** * Returns LiveVariables object with information concerning local variables and parameters */ public static LiveVariables analyze(CFG cfg) { return analyze(cfg, false); }
/** * Returns LiveVariables object with information concerning local variables, parameters and fields */ public static LiveVariables analyzeWithFields(CFG cfg) { return analyze(cfg, true); }
@Override public void visitForEachStatement(ForEachStatement tree) { CFG cfg = CFG.buildCFG(Collections.singletonList(tree), true); Symbol var = tree.variable().symbol(); boolean liveVar = true; if(var.owner().isMethodSymbol()) { cfg.setMethodSymbol((Symbol.MethodSymbol) var.owner()); LiveVariables analyze = LiveVariables.analyze(cfg); Set<Symbol> live = analyze.getOut(cfg.reversedBlocks().get(1)); liveVar = live.contains(var); } if(!liveVar) { variables.add(var); } super.visitForEachStatement(tree); if(!liveVar) { variables.remove(var); } }
@Override public void visitForEachStatement(ForEachStatement tree) { CFG cfg = CFG.buildCFG(Collections.singletonList(tree), true); Symbol var = tree.variable().symbol(); boolean liveVar = true; if(var.owner().isMethodSymbol()) { cfg.setMethodSymbol((Symbol.MethodSymbol) var.owner()); LiveVariables analyze = LiveVariables.analyze(cfg); Set<Symbol> live = analyze.getOut(cfg.reversedBlocks().get(1)); liveVar = live.contains(var); } if(!liveVar) { variables.add(var); } super.visitForEachStatement(tree); if(!liveVar) { variables.remove(var); } }
@Override public void visitMethod(MethodTree tree) { BlockTree block = tree.block(); if(block == null) { return; } CFG cfg = CFG.build(tree); LiveVariables analyze = LiveVariables.analyze(cfg); Set<Symbol> live = analyze.getIn(cfg.entryBlock()); for (VariableTree parameterTree : tree.parameters()) { if(!live.contains(parameterTree.symbol())) { variables.add(parameterTree.symbol()); } } super.visitMethod(tree); for (VariableTree parameterTree : tree.parameters()) { if(!live.contains(parameterTree.symbol())) { variables.remove(parameterTree.symbol()); } } }
@Override public void visitMethod(MethodTree tree) { BlockTree block = tree.block(); if(block == null) { return; } CFG cfg = CFG.build(tree); LiveVariables analyze = LiveVariables.analyze(cfg); Set<Symbol> live = analyze.getIn(cfg.entryBlock()); for (VariableTree parameterTree : tree.parameters()) { if(!live.contains(parameterTree.symbol())) { variables.add(parameterTree.symbol()); } } super.visitMethod(tree); for (VariableTree parameterTree : tree.parameters()) { if(!live.contains(parameterTree.symbol())) { variables.remove(parameterTree.symbol()); } } }
@Override public void visitCatch(CatchTree tree) { CFG cfg = CFG.buildCFG(tree.block().body(), true); Symbol var = tree.parameter().symbol(); boolean liveVar = true; if(var.owner().isMethodSymbol()) { cfg.setMethodSymbol((Symbol.MethodSymbol) var.owner()); LiveVariables analyze = LiveVariables.analyze(cfg); Set<Symbol> live = analyze.getIn(cfg.entryBlock()); liveVar = live.contains(var); } if(!liveVar) { variables.add(var); } super.visitCatch(tree); if(!liveVar) { variables.remove(var); } }
@Override public void visitCatch(CatchTree tree) { CFG cfg = CFG.buildCFG(tree.block().body(), true); Symbol var = tree.parameter().symbol(); boolean liveVar = true; if(var.owner().isMethodSymbol()) { cfg.setMethodSymbol((Symbol.MethodSymbol) var.owner()); LiveVariables analyze = LiveVariables.analyze(cfg); Set<Symbol> live = analyze.getIn(cfg.entryBlock()); liveVar = live.contains(var); } if(!liveVar) { variables.add(var); } super.visitCatch(tree); if(!liveVar) { variables.remove(var); } }
exitBlock = cfg.exitBlock(); checkerDispatcher.init(tree, cfg); liveVariables = LiveVariables.analyze(cfg); explodedGraph = new ExplodedGraph(); methodTree = tree;
exitBlock = cfg.exitBlock(); checkerDispatcher.init(tree, cfg); liveVariables = LiveVariables.analyze(cfg); explodedGraph = new ExplodedGraph(); methodTree = tree;
@Override public void visitNode(Tree tree) { if (!hasSemantic()) { return; } MethodTree methodTree = (MethodTree) tree; if (methodTree.block() == null) { return; } // TODO(npe) Exclude try statements with finally as CFG is incorrect for those and lead to false positive if (hasTryFinallyWithLocalVar(methodTree.block(), methodTree.symbol())) { return; } Symbol.MethodSymbol methodSymbol = methodTree.symbol(); CFG cfg = CFG.build(methodTree); LiveVariables liveVariables = LiveVariables.analyze(cfg); // Liveness analysis provides information only for block boundaries, so we should do analysis between elements within blocks for (CFG.Block block : cfg.blocks()) { checkElements(block, liveVariables.getOut(block), methodSymbol); } }
@Override public void visitNode(Tree tree) { if (!hasSemantic()) { return; } MethodTree methodTree = (MethodTree) tree; if (methodTree.block() == null) { return; } // TODO(npe) Exclude try statements with finally as CFG is incorrect for those and lead to false positive if (hasTryFinallyWithLocalVar(methodTree.block(), methodTree.symbol())) { return; } Symbol.MethodSymbol methodSymbol = methodTree.symbol(); CFG cfg = CFG.build(methodTree); LiveVariables liveVariables = LiveVariables.analyze(cfg); // Liveness analysis provides information only for block boundaries, so we should do analysis between elements within blocks for (CFG.Block block : cfg.blocks()) { checkElements(block, liveVariables.getOut(block), methodSymbol); } }
private void execute(MethodTree tree) { checkerDispatcher.init(); CFG cfg = CFG.build(tree); liveVariables = LiveVariables.analyze(cfg); explodedGraph = new ExplodedGraph(); methodTree = tree;