mirror of
https://github.com/github/codeql.git
synced 2026-05-23 23:57:06 +02:00
C++: remove some side-effect instructions
This leverages the existing alias analysis to identify functions which have no reads or writes of the AllAliasedMemory virtual variable, and therefore have no global side effects. A recursion over the call graph identifies functions which have no indirect global side effects, and calls to those functions have their global side effect instructions removed.
This commit is contained in:
@@ -11,8 +11,11 @@ private import NewIR
|
||||
|
||||
private class OldBlock = Reachability::ReachableBlock;
|
||||
|
||||
private class OldInstruction = Reachability::ReachableInstruction;
|
||||
private class OldInstruction extends Reachability::ReachableInstruction {
|
||||
OldInstruction() { not Elim::removeableSideEffect(this)}
|
||||
}
|
||||
|
||||
private import SideEffectElimination as Elim
|
||||
import Cached
|
||||
|
||||
cached
|
||||
@@ -58,7 +61,9 @@ private module Cached {
|
||||
|
||||
cached
|
||||
predicate hasInstruction(TStageInstruction instr) {
|
||||
instr instanceof TRawInstruction and instr instanceof OldInstruction
|
||||
instr instanceof TRawInstruction and
|
||||
instr instanceof OldInstruction and
|
||||
not Elim::removeableSideEffect(instr)
|
||||
or
|
||||
instr = phiInstruction(_, _)
|
||||
or
|
||||
@@ -382,7 +387,14 @@ private module Cached {
|
||||
(
|
||||
if Reachability::isInfeasibleInstructionSuccessor(oldInstruction, kind)
|
||||
then result = unreachedInstruction(instruction.getEnclosingIRFunction())
|
||||
else result = getNewInstruction(oldInstruction.getSuccessor(kind))
|
||||
else
|
||||
if Elim::removeableSideEffect(oldInstruction.getSuccessor(kind))
|
||||
then
|
||||
// the only removed nodes are side-effect writes, but those may have Chi nodes
|
||||
// skip to the following instruction in the old IR, which won't be removed
|
||||
// if we start skipping specific side effects, this may no longer hold
|
||||
result = getNewInstruction(oldInstruction.getSuccessor(kind).getSuccessor(kind))
|
||||
else result = getNewInstruction(oldInstruction.getSuccessor(kind))
|
||||
)
|
||||
)
|
||||
or
|
||||
|
||||
@@ -34,6 +34,7 @@ newtype TInstruction =
|
||||
AliasedSSA::SSA::hasPhiInstruction(blockStartInstr, memoryLocation)
|
||||
} or
|
||||
TAliasedSsaChiInstruction(TRawInstruction primaryInstruction) {
|
||||
not Elim::removeableSideEffect(primaryInstruction) and
|
||||
AliasedSSA::SSA::hasChiInstruction(primaryInstruction)
|
||||
} or
|
||||
TAliasedSsaUnreachedInstruction(IRFunctionBase irFunc) {
|
||||
|
||||
@@ -2,3 +2,4 @@ import semmle.code.cpp.ir.internal.IRCppLanguage as Language
|
||||
import semmle.code.cpp.ir.implementation.raw.internal.IRConstruction as IRConstruction
|
||||
import semmle.code.cpp.ir.implementation.unaliased_ssa.internal.SSAConstruction as UnaliasedSsa
|
||||
import semmle.code.cpp.ir.implementation.aliased_ssa.internal.SSAConstruction as AliasedSSA
|
||||
import semmle.code.cpp.ir.implementation.aliased_ssa.internal.SideEffectElimination as Elim
|
||||
|
||||
Reference in New Issue
Block a user