diff --git a/clambcc/clambc-compiler.py b/clambcc/clambc-compiler.py index 948c37fee6..3fbca66e33 100755 --- a/clambcc/clambc-compiler.py +++ b/clambcc/clambc-compiler.py @@ -435,72 +435,92 @@ def optimize(inFile, outFile, sigFile, inputSourceFile, standardCompiler): internalizeAPIList += ",main" #TODO: Modify ClamBCRemoveUndefs to not require mem2reg to be run before it. - cmd = f'opt-{CLANG_VERSION} \ - -S \ - -verify-each \ - -load "{SHARED_OBJ_FILE}" \ - {inFile} \ - -o {outFile} \ - -mem2reg \ - -clambc-remove-undefs \ - -O3 \ - -clambc-remove-pointer-phis \ - -dce \ - -disable-loop-vectorization \ - -disable-slp-vectorization \ - -globaldce \ - -strip-dead-prototypes \ - -constmerge \ - -mem2reg \ - -always-inline \ - -globalopt \ - -lowerswitch \ - -lowerinvoke \ - -globalopt \ - -simplifycfg \ - -indvars \ - -constprop \ - -clambc-lowering-notfinal \ - -lowerswitch \ - -clambc-verifier \ - -clambc-lowering-notfinal \ - -dce \ - -simplifycfg \ - -mem2reg \ - -clambc-lcompiler \ - -internalize -internalize-public-api-list="{internalizeAPIList}" \ - -globaldce \ - -instcombine \ - -clambc-rebuild \ - -verify \ - -simplifycfg \ - -dce \ - -lowerswitch \ - -clambc-verifier \ - -verify \ - -strip-debug-declare \ - -clambc-gepsplitter-placeholder \ - -clambc-lowering-final \ - -clambc-trace \ - -dce \ - -clambc-module \ - -verify \ - -globalopt \ - -remove-selects \ - -clambc-outline-endianness-calls \ - -clambc-change-malloc-arg-size \ - -globalopt \ - -clambc-prepare-geps-for-writer \ - -globalopt \ - -clambc-convert-intrinsics \ - -clambc-writer \ - -clambc-writer-input-source={inputSourceFile} \ - -clambc-sigfile={sigFile} \ - ' + cmd = (f'opt-{CLANG_VERSION}' + f' -S' + f' -verify-each' + f' -load "{SHARED_OBJ_FILE}"' + f' {inFile}' + f' -o {outFile}' + f' -mem2reg' + f' -clambc-remove-undefs' #add pointer bounds checking. + f' -clambc-preserve-abis' #add fake function calls that use all of + #the arguments so that O3 doesn't change + #the argument lists + f' -O3' + f' -clambc-preserve-abis' #remove fake function calls because O3 has already run + f' -clambc-remove-pointer-phis' + f' -dce' + f' -disable-loop-vectorization' + f' -disable-slp-vectorization' + f' -globaldce' + f' -strip-dead-prototypes' + f' -constmerge' + f' -mem2reg' + f' -always-inline' + f' -globalopt' + f' -lowerswitch' + f' -lowerinvoke' + f' -globalopt' + f' -simplifycfg' + f' -indvars' + f' -constprop' + f' -clambc-lowering-notfinal' # perform lowering pass + f' -lowerswitch' + f' -clambc-verifier' + f' -clambc-lowering-notfinal' # perform lowering pass + f' -dce' + f' -simplifycfg' + f' -mem2reg' + f' -clambc-lcompiler' #compile the logical_trigger function to a + #logical signature. + f' -internalize -internalize-public-api-list="{internalizeAPIList}"' + f' -globaldce' + f' -instcombine' + f' -clambc-rebuild' + f' -verify' + f' -simplifycfg' + f' -dce' + f' -lowerswitch' + f' -clambc-verifier' + f' -verify' + f' -strip-debug-declare' + f' -clambc-gepsplitter-placeholder' + f' -clambc-lowering-final' + f' -clambc-trace' + f' -dce' + f' -clambc-module' + f' -verify' + f' -globalopt' + f' -remove-selects' + f' -clambc-outline-endianness-calls' #outline the endianness calls + #because otherwise the call + #is replaced with a constant + #that is based on where the + #signature was compiled, and + #won't always be accurate. + f' -clambc-change-malloc-arg-size' #make sure we always use the + #64-bit malloc. + f' -globalopt' + f' -clambc-extend-phis-to-64bit' #make all integer phi nodes 64-bit + #because the llvm runtime inserts a + #cast after phi nodes without + #verifying that there is not + #another phi node after it. + f' -clambc-prepare-geps-for-writer' #format gep indexes to not not + #have more than 2, because + #otherwise the writer gets + #unhappy. + f' -globalopt' + f' -clambc-convert-intrinsics' #convert all memset intrinsics to + #the 32-bit instead of the 64-bit + #intrinsic + f' -clambc-writer' #write the bytecode + f' -clambc-writer-input-source={inputSourceFile}' + f' -clambc-sigfile={sigFile}' + ) if standardCompiler: - cmd += f"-clambc-standard-compiler \ - " + cmd += f" -clambc-standard-compiler" return run(cmd) diff --git a/libclambcc/CMakeLists.txt b/libclambcc/CMakeLists.txt index 2c1ce89e3c..5db43e92a4 100644 --- a/libclambcc/CMakeLists.txt +++ b/libclambcc/CMakeLists.txt @@ -27,6 +27,8 @@ target_sources(clambcc_obj ClamBCRemovePointerPHIs/ClamBCRemovePointerPHIs.cpp ClamBCConvertIntrinsics/ClamBCConvertIntrinsics.cpp ClamBCRemoveUndefs/ClamBCRemoveUndefs.cpp + ClamBCPreserveABIs/ClamBCPreserveABIs.cpp + ClamBCExtendPHIsTo64Bit/ClamBCExtendPHIsTo64Bit.cpp ) target_include_directories(clambcc_obj diff --git a/libclambcc/ClamBCExtendPHIsTo64Bit/ClamBCExtendPHIsTo64Bit.cpp b/libclambcc/ClamBCExtendPHIsTo64Bit/ClamBCExtendPHIsTo64Bit.cpp new file mode 100644 index 0000000000..96566027b8 --- /dev/null +++ b/libclambcc/ClamBCExtendPHIsTo64Bit/ClamBCExtendPHIsTo64Bit.cpp @@ -0,0 +1,150 @@ +/* + * Compile LLVM bytecode to ClamAV bytecode. + * + * Copyright (C) 2009-2010 Sourcefire, Inc. + * + * Authors: Andy Ragusa + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, + * MA 02110-1301, USA. + */ +#include "../Common/bytecode_api.h" +#include "clambc.h" +#include "ClamBCModule.h" +#include "ClamBCAnalyzer/ClamBCAnalyzer.h" +#include "Common/ClamBCUtilities.h" + +#include +//#include "ClamBCTargetMachine.h" +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +//#include "llvm/Config/config.h" +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include + +using namespace llvm; + +class ClamBCExtendPHIsTo64Bit : public ModulePass +{ + protected: + llvm::Module *pMod = nullptr; + + virtual void convertPHIs(Function *pFunc) + { + std::vector phis; + for (auto i = pFunc->begin(), e = pFunc->end(); i != e; i++) { + BasicBlock *bb = llvm::cast(i); + for (auto bi = bb->begin(), be = bb->end(); bi != be; bi++) { + if (PHINode *phi = llvm::dyn_cast(bi)) { + phis.push_back(phi); + } + } + } + + for (size_t i = 0; i < phis.size(); i++) { + convertPHI(phis[i]); + } + } + + virtual void convertPHI(PHINode *pn) + { + IntegerType *dstType = IntegerType::get(pMod->getContext(), 64); + IntegerType *origType = llvm::dyn_cast(pn->getType()); + if ((dstType == origType) || (nullptr == origType)) { + return; + } + + PHINode *newNode = PHINode::Create(dstType, pn->getNumIncomingValues(), "ClamBCConvertPHINodes_", pn); + for (size_t i = 0; i < pn->getNumIncomingValues(); i++) { + Value *incomingValue = pn->getIncomingValue(i); + BasicBlock *incomingBlock = pn->getIncomingBlock(i); + + if (ConstantInt *ci = llvm::dyn_cast(incomingValue)) { + Constant *newCi = ConstantInt::get(dstType, ci->getLimitedValue()); + newNode->addIncoming(newCi, incomingBlock); + } else { + Instruction *insPt = llvm::cast(--(incomingBlock->end())); + Instruction *inst = CastInst::CreateIntegerCast(pn->getIncomingValue(i), dstType, true, "ClamBCConvertPHINodes_", insPt); + + newNode->addIncoming(inst, incomingBlock); + } + } + Instruction *insPt = nullptr; + for (auto i = pn->getParent()->begin(), e = pn->getParent()->end(); i != e; i++) { + if (llvm::isa(i)) { + continue; + } + + //Not allowed in bytecode sigs, but no reason not to support it. + if (llvm::isa(i)) { + continue; + } + + insPt = llvm::cast(i); + break; + } + + Instruction *cast = CastInst::CreateIntegerCast(newNode, origType, true, "ClamBCConvertPHINodes_", insPt); + pn->replaceAllUsesWith(cast); + pn->eraseFromParent(); + } + + public: + static char ID; + + explicit ClamBCExtendPHIsTo64Bit() + : ModulePass(ID) {} + + virtual ~ClamBCExtendPHIsTo64Bit() {} + + virtual bool runOnModule(Module &m) + { + + pMod = &m; + + for (auto i = pMod->begin(), e = pMod->end(); i != e; i++) { + Function *pFunc = llvm::cast(i); + convertPHIs(pFunc); + } + + return true; + } +}; + +char ClamBCExtendPHIsTo64Bit::ID = 0; +static RegisterPass X("clambc-extend-phis-to-64bit", "ClamBCExtendPHIsTo64Bit Pass", + false /* Only looks at CFG */, + false /* Analysis Pass */); + +llvm::ModulePass *createClamBCExtendPHIsTo64Bit() +{ + return new ClamBCExtendPHIsTo64Bit(); +} diff --git a/libclambcc/ClamBCLogicalCompiler/ClamBCLogicalCompiler.cpp b/libclambcc/ClamBCLogicalCompiler/ClamBCLogicalCompiler.cpp index 56d748f0f3..18adfb04ae 100644 --- a/libclambcc/ClamBCLogicalCompiler/ClamBCLogicalCompiler.cpp +++ b/libclambcc/ClamBCLogicalCompiler/ClamBCLogicalCompiler.cpp @@ -688,72 +688,80 @@ class LogicalCompiler return true; } - - class LogicalPHIHelper { - public: - - LogicalPHIHelper (BranchInst * bi, bool isTrue) { - pBranchInst = bi; - pBasicBlock = bi->getParent(); + class LogicalPHIHelper + { + public: + LogicalPHIHelper(BranchInst *bi, bool isTrue) + { + pBranchInst = bi; + pBasicBlock = bi->getParent(); this->isTrue = isTrue; } - LogicalPHIHelper(LogicalPHIHelper * lph){ + LogicalPHIHelper(LogicalPHIHelper *lph) + { this->pBasicBlock = lph->pBasicBlock; this->pBranchInst = lph->pBranchInst; - this->isTrue = lph->isTrue; + this->isTrue = lph->isTrue; } - virtual ~LogicalPHIHelper(){} + virtual ~LogicalPHIHelper() {} - BranchInst * getBranchInst() { return pBranchInst; } + BranchInst *getBranchInst() + { + return pBranchInst; + } - BasicBlock * getBasicBlock() { return pBasicBlock; } + BasicBlock *getBasicBlock() + { + return pBasicBlock; + } - bool getIsTrue() { + bool getIsTrue() + { return isTrue; } - Value * getCondition(){ - if (pBranchInst->isConditional()){ + Value *getCondition() + { + if (pBranchInst->isConditional()) { return pBranchInst->getCondition(); } return nullptr; } - protected: - BasicBlock * pBasicBlock; + protected: + BasicBlock *pBasicBlock; - BranchInst * pBranchInst; + BranchInst *pBranchInst; bool isTrue; - }; - /*Generate all paths from the 'curr' to 'end' and store them in routes.*/ - void populateRoutes(BasicBlock * curr, BasicBlock * end, std::vector> & routes, size_t idx){ + void populateRoutes(BasicBlock *curr, BasicBlock *end, std::vector> &routes, size_t idx) + { - if (curr == end){ + if (curr == end) { return; } - for (size_t i = 0; i < routes[idx].size(); i++){ - if (routes[idx][i]->getBranchInst() == curr->getTerminator()){ - return ; + for (size_t i = 0; i < routes[idx].size(); i++) { + if (routes[idx][i]->getBranchInst() == curr->getTerminator()) { + return; } } - if (BranchInst * bi = llvm::dyn_cast(curr->getTerminator())){ - if (bi->isConditional()){ + if (BranchInst *bi = llvm::dyn_cast(curr->getTerminator())) { + if (bi->isConditional()) { //copy the route, so that there are separate paths for the true //and false condition. - std::vector route; - for (size_t i = 0; i < routes[idx].size(); i++){ + std::vector route; + for (size_t i = 0; i < routes[idx].size(); i++) { route.push_back(new LogicalPHIHelper(routes[idx][i])); } routes.push_back(route); - size_t falseIdx = routes.size()-1; + size_t falseIdx = routes.size() - 1; routes[idx].push_back(new LogicalPHIHelper(bi, true)); routes[falseIdx].push_back(new LogicalPHIHelper(bi, false)); @@ -765,36 +773,35 @@ class LogicalCompiler routes[idx].push_back(new LogicalPHIHelper(bi, true)); populateRoutes(bi->getSuccessor(0), end, routes, idx); } - } - } - /* Find all routes from the entry BasicBlock that end with 'pBasicBlock' */ - std::vector findRoute(BasicBlock * pBasicBlock, std::vector> & routes){ + std::vector findRoute(BasicBlock *pBasicBlock, std::vector> &routes) + { std::vector ret; - for (size_t i = 0; i < routes.size(); i++){ - size_t lastIdx = routes[i].size()-1; - if (routes[i][lastIdx]->getBasicBlock() == pBasicBlock){ + for (size_t i = 0; i < routes.size(); i++) { + size_t lastIdx = routes[i].size() - 1; + if (routes[i][lastIdx]->getBasicBlock() == pBasicBlock) { ret.push_back(i); } } return ret; } - LogicalNode * getLogicalNode(std::vector & route){ - LogicalNode * ret = nullptr; + LogicalNode *getLogicalNode(std::vector &route) + { + LogicalNode *ret = nullptr; - for (size_t i = 0; i < route.size(); i++){ - Value * vCond = route[i]->getCondition(); - if (vCond){ - LogicalNode * ln = Map.find(vCond)->second; - if (not route[i]->getIsTrue()){ + for (size_t i = 0; i < route.size(); i++) { + Value *vCond = route[i]->getCondition(); + if (vCond) { + LogicalNode *ln = Map.find(vCond)->second; + if (not route[i]->getIsTrue()) { ln = LogicalNode::getNot(ln); } - if (nullptr == ret){ + if (nullptr == ret) { ret = ln; } else { ret = LogicalNode::getAnd(ret, ln); @@ -803,7 +810,6 @@ class LogicalCompiler } return ret; - } /* @@ -864,35 +870,35 @@ class LogicalCompiler (%or.cond1 AND (NOT %cmp.i35) AND %cmp.i47 AND (NOT %or.cond)) OR (%cmp.i41 AND (NOT %cmp.i47) AND (NOT %or.cond)) * */ - void processPHI(PHINode * pn){ - BasicBlock * phiBlock = pn->getParent(); - BasicBlock * startBlock = llvm::cast(pn->getParent()->getParent()->begin()); + void processPHI(PHINode *pn) + { + BasicBlock *phiBlock = pn->getParent(); + BasicBlock *startBlock = llvm::cast(pn->getParent()->getParent()->begin()); - std::vector> routes; + std::vector> routes; std::vector route; routes.push_back(route); populateRoutes(startBlock, phiBlock, routes, 0); - LogicalNode * ln = nullptr; + LogicalNode *ln = nullptr; - for (size_t i = 0; i < pn->getNumIncomingValues(); i++){ - Value * vIncoming = pn->getIncomingValue(i); - ConstantInt * pci = llvm::dyn_cast(vIncoming); - if (pci){ - if (pci->isZero()){ + for (size_t i = 0; i < pn->getNumIncomingValues(); i++) { + Value *vIncoming = pn->getIncomingValue(i); + ConstantInt *pci = llvm::dyn_cast(vIncoming); + if (pci) { + if (pci->isZero()) { continue; } - } std::vector idxs = findRoute(pn->getIncomingBlock(i), routes); for (size_t j = 0; j < idxs.size(); j++) { - size_t idx = idxs[j]; - LogicalNode * tmp = getLogicalNode(routes[idx]); - if (nullptr == pci){ //Then this isn't a constant - LogicalNode * l = Map.find(vIncoming)->second; - tmp = LogicalNode::getAnd(tmp, l); + size_t idx = idxs[j]; + LogicalNode *tmp = getLogicalNode(routes[idx]); + if (nullptr == pci) { //Then this isn't a constant + LogicalNode *l = Map.find(vIncoming)->second; + tmp = LogicalNode::getAnd(tmp, l); } - if (nullptr == ln){ + if (nullptr == ln) { ln = tmp; } else { ln = LogicalNode::getOr(ln, tmp); @@ -901,9 +907,9 @@ class LogicalCompiler } Map[pn] = ln; - for (size_t i = 0; i < routes.size(); i++){ - for (size_t j = 0; j < routes[i].size(); j++){ - delete(routes[i][j]); + for (size_t i = 0; i < routes.size(); i++) { + for (size_t j = 0; j < routes[i].size(); j++) { + delete (routes[i][j]); } } } @@ -1672,7 +1678,6 @@ bool ClamBCLogicalCompiler::compileVirusNames(Module &M, unsigned kind) return Valid; } - bool ClamBCLogicalCompiler::runOnModule(Module &M) { bool Valid = true; @@ -1680,11 +1685,8 @@ bool ClamBCLogicalCompiler::runOnModule(Module &M) virusnames = ""; pMod = &M; - //dumpPHIGraphs(); - - // Handle virusname unsigned kind = 0; GlobalVariable *GVKind = M.getGlobalVariable("__clambc_kind"); diff --git a/libclambcc/ClamBCPrepareGEPsForWriter/ClamBCPrepareGEPsForWriter.cpp b/libclambcc/ClamBCPrepareGEPsForWriter/ClamBCPrepareGEPsForWriter.cpp index 468d9075ad..7ed4f99950 100644 --- a/libclambcc/ClamBCPrepareGEPsForWriter/ClamBCPrepareGEPsForWriter.cpp +++ b/libclambcc/ClamBCPrepareGEPsForWriter/ClamBCPrepareGEPsForWriter.cpp @@ -50,380 +50,367 @@ #include -//#define USE_ANALYZER - using namespace llvm; class ClamBCPrepareGEPsForWriter : public ModulePass { - protected: - llvm::Module *pMod = nullptr; - ClamBCAnalyzer *pAnalyzer = nullptr; + protected: + llvm::Module *pMod = nullptr; - public: - static char ID; + public: + static char ID; - explicit ClamBCPrepareGEPsForWriter() - : ModulePass(ID) {} + explicit ClamBCPrepareGEPsForWriter() + : ModulePass(ID) {} - virtual ~ClamBCPrepareGEPsForWriter() {} + virtual ~ClamBCPrepareGEPsForWriter() {} - void getAnalysisUsage(AnalysisUsage &AU) const - { -#ifdef USE_ANALYZER - AU.addRequired(); -#endif - } + virtual bool ignoreGEPI(GetElementPtrInst *pgepi) + { + Type *ignType = Type::getInt8Ty(pMod->getContext()); - virtual bool ignoreGEPI(GetElementPtrInst * pgepi){ - Type *ignType = Type::getInt8Ty(pMod->getContext()); + Type *ptrTy = pgepi->getPointerOperand()->getType()->getPointerElementType(); - Type * ptrTy = pgepi->getPointerOperand()->getType()->getPointerElementType(); + if (ptrTy == ignType) { + return true; + } - if (ptrTy == ignType){ + if (ptrTy->isArrayTy()) { + ptrTy = ptrTy->getArrayElementType(); + if (ptrTy == Type::getInt8Ty(pMod->getContext())) { return true; } + } - if (ptrTy->isArrayTy()){ - ptrTy = ptrTy->getArrayElementType(); - if (ptrTy == Type::getInt8Ty(pMod->getContext())){ - return true; - } - - } + return false; + } - return false; + virtual int64_t getTypeSize(Type *pt) + { + int64_t size = pt->getScalarSizeInBits(); + if (size) { + return size; } - virtual int64_t getTypeSize(Type *pt) - { - int64_t size = pt->getScalarSizeInBits(); + if (ArrayType *pat = llvm::dyn_cast(pt)) { + size = pat->getNumElements() * (getTypeSize(pat->getElementType())); if (size) { return size; } + } - if (ArrayType *pat = llvm::dyn_cast(pt)) { - size = pat->getNumElements() * (getTypeSize(pat->getElementType())); - if (size) { - return size; - } - } - - if (StructType *pst = llvm::dyn_cast(pt)) { - const StructLayout * psl = pMod->getDataLayout().getStructLayout(pst); - return psl->getSizeInBits(); - } - - assert(0 && "Size has not been computed"); - return -1; - } + if (StructType *pst = llvm::dyn_cast(pt)) { + const StructLayout *psl = pMod->getDataLayout().getStructLayout(pst); + return psl->getSizeInBits(); + } - virtual int64_t getTypeSizeInBytes(Type *pt) - { - return getTypeSize(pt) / 8; - } + assert(0 && "Size has not been computed"); + return -1; + } - virtual int64_t computeOffsetInBytes(Type *pt, uint64_t idx) { + virtual int64_t getTypeSizeInBytes(Type *pt) + { + return getTypeSize(pt) / 8; + } - int64_t cnt = 0; + virtual int64_t computeOffsetInBytes(Type *pt, uint64_t idx) + { - assert ((llvm::isa(pt) || llvm::isa(pt)) && "pt must be a complex type"); + int64_t cnt = 0; - if (StructType * pst = llvm::dyn_cast(pt)){ - assert((idx <= pst->getNumElements()) && "Idx too high"); + assert((llvm::isa(pt) || llvm::isa(pt)) && "pt must be a complex type"); - const StructLayout * psl = pMod->getDataLayout().getStructLayout(pst); - assert (psl && "Could not get layout"); + if (StructType *pst = llvm::dyn_cast(pt)) { + assert((idx <= pst->getNumElements()) && "Idx too high"); - cnt = psl->getElementOffsetInBits(idx)/8; + const StructLayout *psl = pMod->getDataLayout().getStructLayout(pst); + assert(psl && "Could not get layout"); - } else if (ArrayType * pat = llvm::dyn_cast(pt)){ - assert((idx <= pat->getNumElements()) && "Idx too high"); - cnt = idx * getTypeSizeInBytes(pat->getElementType()); - } + cnt = psl->getElementOffsetInBits(idx) / 8; - return cnt; + } else if (ArrayType *pat = llvm::dyn_cast(pt)) { + assert((idx <= pat->getNumElements()) && "Idx too high"); + cnt = idx * getTypeSizeInBytes(pat->getElementType()); } - virtual int64_t computeOffsetInBytes(Type *pst, ConstantInt *pIdx) - { - int64_t idx = pIdx->getLimitedValue(); - return computeOffsetInBytes(pst, idx); - } - - virtual int64_t computeOffsetInBytes(Type *pst) - { - if (llvm::isa(pst)){ - return computeOffsetInBytes(pst, pst->getStructNumElements()); - } else if (llvm::isa(pst)){ - return computeOffsetInBytes(pst, pst->getArrayNumElements()); - } else { - assert (0 && "pt must be a complex type"); - } - - return 0; - } - - virtual Type * findTypeAtIndex(Type * pst, ConstantInt * ciIdx){ - Type * ret = nullptr; - if (StructType * st = llvm::dyn_cast(pst)){ - uint64_t idx = ciIdx->getLimitedValue(); + return cnt; + } + + virtual int64_t computeOffsetInBytes(Type *pst, ConstantInt *pIdx) + { + int64_t idx = pIdx->getLimitedValue(); + return computeOffsetInBytes(pst, idx); + } + + virtual int64_t computeOffsetInBytes(Type *pst) + { + if (llvm::isa(pst)) { + return computeOffsetInBytes(pst, pst->getStructNumElements()); + } else if (llvm::isa(pst)) { + return computeOffsetInBytes(pst, pst->getArrayNumElements()); + } else { + assert(0 && "pt must be a complex type"); + } - assert (idx < st->getNumElements() && "Something went wrong"); - return st->getTypeAtIndex(idx); - } + return 0; + } - if (ArrayType * at = llvm::dyn_cast(pst)){ - return at->getArrayElementType(); - } - return ret; + virtual Type *findTypeAtIndex(Type *pst, ConstantInt *ciIdx) + { + Type *ret = nullptr; + if (StructType *st = llvm::dyn_cast(pst)) { + uint64_t idx = ciIdx->getLimitedValue(); + assert(idx < st->getNumElements() && "Something went wrong"); + return st->getTypeAtIndex(idx); } - virtual void processGEPI(GetElementPtrInst * pgepi, BitCastInst * pbci, Value * underlyingObject, StructType * gepiDstType){ + if (ArrayType *at = llvm::dyn_cast(pst)) { + return at->getArrayElementType(); + } + return ret; + } - uint64_t size = getTypeSizeInBytes(gepiDstType); - assert (size && "size not computed"); + virtual void processGEPI(GetElementPtrInst *pgepi, BitCastInst *pbci, Value *underlyingObject, StructType *gepiDstType) + { - Value * vCnt = nullptr; + uint64_t size = getTypeSizeInBytes(gepiDstType); + assert(size && "size not computed"); - auto i = pgepi->idx_begin(); - Value * vIdx = llvm::cast(i); - vCnt = ConstantInt::get(vIdx->getType(), size); - vCnt = BinaryOperator::Create(Instruction::Mul, vCnt, vIdx, "processGEPI_", pgepi); - i++; + Value *vCnt = nullptr; - Type * currType = gepiDstType; + auto i = pgepi->idx_begin(); + Value *vIdx = llvm::cast(i); + vCnt = ConstantInt::get(vIdx->getType(), size); + vCnt = BinaryOperator::Create(Instruction::Mul, vCnt, vIdx, "processGEPI_", pgepi); + i++; - for (auto e = pgepi->idx_end(); i != e; i++){ - Value * vIdx = llvm::cast(i); + Type *currType = gepiDstType; - Value * ciAddend = nullptr; - if ( ConstantInt * ciIdx = llvm::dyn_cast(vIdx)){ + for (auto e = pgepi->idx_end(); i != e; i++) { + Value *vIdx = llvm::cast(i); - uint64_t val = computeOffsetInBytes(currType, ciIdx); - ciAddend = ConstantInt::get(ciIdx->getType(), val); + Value *ciAddend = nullptr; + if (ConstantInt *ciIdx = llvm::dyn_cast(vIdx)) { - Type * tmp = findTypeAtIndex(currType, ciIdx); - assert (tmp && "Should always be defined"); + uint64_t val = computeOffsetInBytes(currType, ciIdx); + ciAddend = ConstantInt::get(ciIdx->getType(), val); - if (llvm::isa(tmp)){ - currType = llvm::cast(tmp); - } else if (llvm::isa(tmp)){ - currType = tmp; - } - } else if (ArrayType * pat = llvm::dyn_cast(currType)){ + Type *tmp = findTypeAtIndex(currType, ciIdx); + assert(tmp && "Should always be defined"); - uint64_t size = getTypeSizeInBytes(pat->getArrayElementType()); - Constant * pci = ConstantInt::get(vIdx->getType(), size); - ciAddend = BinaryOperator::Create(Instruction::Mul, pci, vIdx, "processGEPI_", pgepi); - } else { - assert (0 && "Figure out what to do here"); + if (llvm::isa(tmp)) { + currType = llvm::cast(tmp); + } else if (llvm::isa(tmp)) { + currType = tmp; } + } else if (ArrayType *pat = llvm::dyn_cast(currType)) { - vCnt = BinaryOperator::Create(Instruction::Add, vCnt, ciAddend, "processGEPI_", pgepi); + uint64_t size = getTypeSizeInBytes(pat->getArrayElementType()); + Constant *pci = ConstantInt::get(vIdx->getType(), size); + ciAddend = BinaryOperator::Create(Instruction::Mul, pci, vIdx, "processGEPI_", pgepi); + } else { + assert(0 && "Figure out what to do here"); } - Constant * Zero = ConstantInt::get(vIdx->getType(), 0); - llvm::ArrayRef Idxs = {Zero, Zero}; + vCnt = BinaryOperator::Create(Instruction::Add, vCnt, ciAddend, "processGEPI_", pgepi); + } - Value * gepiNew = underlyingObject; - if (gepiNew->getType()->getPointerElementType()->isArrayTy()){ - gepiNew = GetElementPtrInst::Create(nullptr, gepiNew, Idxs, "processGEPI_2_", pgepi); - } + Constant *Zero = ConstantInt::get(vIdx->getType(), 0); + llvm::ArrayRef Idxs = {Zero, Zero}; - gepiNew = GetElementPtrInst::Create(nullptr, gepiNew, vCnt, "processGEPI_3_", pgepi); + Value *gepiNew = underlyingObject; + if (gepiNew->getType()->getPointerElementType()->isArrayTy()) { + gepiNew = GetElementPtrInst::Create(nullptr, gepiNew, Idxs, "processGEPI_2_", pgepi); + } - CastInst *ciNew = CastInst::CreatePointerCast(gepiNew, pgepi->getType(), "processGEPI_", pgepi); + gepiNew = GetElementPtrInst::Create(nullptr, gepiNew, vCnt, "processGEPI_3_", pgepi); - pgepi->replaceAllUsesWith(ciNew); - pgepi->eraseFromParent(); + CastInst *ciNew = CastInst::CreatePointerCast(gepiNew, pgepi->getType(), "processGEPI_", pgepi); - } + pgepi->replaceAllUsesWith(ciNew); + pgepi->eraseFromParent(); + } - virtual void processGEPI(GetElementPtrInst * pgepi, BitCastInst * pbci, Value * underlyingObject, ArrayType * gepiDstType){ + virtual void processGEPI(GetElementPtrInst *pgepi, BitCastInst *pbci, Value *underlyingObject, ArrayType *gepiDstType) + { - Type * currType = gepiDstType->getArrayElementType(); + Type *currType = gepiDstType->getArrayElementType(); - uint64_t size = getTypeSizeInBytes(currType); - assert (size && "size not computed"); + uint64_t size = getTypeSizeInBytes(currType); + assert(size && "size not computed"); - Value * vCnt = nullptr; + Value *vCnt = nullptr; - auto i = pgepi->idx_begin(); - Value * vIdx = llvm::cast(i); - vCnt = ConstantInt::get(vIdx->getType(), size); - vCnt = BinaryOperator::Create(Instruction::Mul, vCnt, vIdx, "processGEPI_", pgepi); - i++; + auto i = pgepi->idx_begin(); + Value *vIdx = llvm::cast(i); + vCnt = ConstantInt::get(vIdx->getType(), size); + vCnt = BinaryOperator::Create(Instruction::Mul, vCnt, vIdx, "processGEPI_", pgepi); + i++; - StructType * pCurrStruct = nullptr; + StructType *pCurrStruct = nullptr; - for (auto e = pgepi->idx_end(); i != e; i++){ - Value * vIdx = llvm::cast(i); + for (auto e = pgepi->idx_end(); i != e; i++) { + Value *vIdx = llvm::cast(i); - if (nullptr == pCurrStruct){ - if (StructType * st = llvm::dyn_cast(currType)){ - pCurrStruct = st; - } + if (nullptr == pCurrStruct) { + if (StructType *st = llvm::dyn_cast(currType)) { + pCurrStruct = st; } + } - ConstantInt* pc = llvm::dyn_cast(vIdx); - if (pc){ - Type * pt = findTypeAtIndex(currType, pc); - if (pt){ - currType = pt; - ConstantInt * ciAddend = nullptr; - if (StructType * pst = llvm::dyn_cast(pt)){ - uint64_t val = computeOffsetInBytes(pst, pc); - ciAddend = ConstantInt::get(pc->getType(), val); - pCurrStruct = pst; - - } else { - uint64_t val = computeOffsetInBytes(pCurrStruct, pc); - ciAddend = ConstantInt::get(pc->getType(), val); - vIdx = BinaryOperator::Create(Instruction::Add, ciAddend, vIdx, "processGEPI_", pgepi); - } - - vCnt = BinaryOperator::Create(Instruction::Add, vCnt, ciAddend, "processGEPI_", pgepi); - + ConstantInt *pc = llvm::dyn_cast(vIdx); + if (pc) { + Type *pt = findTypeAtIndex(currType, pc); + if (pt) { + currType = pt; + ConstantInt *ciAddend = nullptr; + if (StructType *pst = llvm::dyn_cast(pt)) { + uint64_t val = computeOffsetInBytes(pst, pc); + ciAddend = ConstantInt::get(pc->getType(), val); + pCurrStruct = pst; + + } else { + uint64_t val = computeOffsetInBytes(pCurrStruct, pc); + ciAddend = ConstantInt::get(pc->getType(), val); + vIdx = BinaryOperator::Create(Instruction::Add, ciAddend, vIdx, "processGEPI_", pgepi); } - } else { - - size = getTypeSizeInBytes(currType); - Value * tmp = ConstantInt::get(vIdx->getType(), size); - vIdx = BinaryOperator::Create(Instruction::Mul, tmp, vIdx, "processGEPI_", pgepi); - - vCnt = BinaryOperator::Create(Instruction::Add, vCnt, vIdx, "processGEPI_", pgepi); + vCnt = BinaryOperator::Create(Instruction::Add, vCnt, ciAddend, "processGEPI_", pgepi); } - } + } else { - Constant * Zero = ConstantInt::get(vIdx->getType(), 0); - llvm::ArrayRef Idxs = {Zero, Zero}; + size = getTypeSizeInBytes(currType); + Value *tmp = ConstantInt::get(vIdx->getType(), size); + vIdx = BinaryOperator::Create(Instruction::Mul, tmp, vIdx, "processGEPI_", pgepi); - Value * gepiNew = underlyingObject; - if (gepiNew->getType()->getPointerElementType()->isArrayTy()){ - gepiNew = GetElementPtrInst::Create(nullptr, gepiNew, Idxs, "processGEPI_0_", pgepi); + vCnt = BinaryOperator::Create(Instruction::Add, vCnt, vIdx, "processGEPI_", pgepi); } + } - gepiNew = GetElementPtrInst::Create(nullptr, gepiNew, vCnt, "processGEPI_1_", pgepi); - - CastInst *ciNew = CastInst::CreatePointerCast(gepiNew, pgepi->getType(), "processGEPI_", pgepi); + Constant *Zero = ConstantInt::get(vIdx->getType(), 0); + llvm::ArrayRef Idxs = {Zero, Zero}; - pgepi->replaceAllUsesWith(ciNew); - pgepi->eraseFromParent(); + Value *gepiNew = underlyingObject; + if (gepiNew->getType()->getPointerElementType()->isArrayTy()) { + gepiNew = GetElementPtrInst::Create(nullptr, gepiNew, Idxs, "processGEPI_0_", pgepi); } - virtual Value* stripBitCasts(Value * pInst){ - if (BitCastInst * pbci = llvm::dyn_cast(pInst)){ - return stripBitCasts(pbci->getOperand(0)); - } + gepiNew = GetElementPtrInst::Create(nullptr, gepiNew, vCnt, "processGEPI_1_", pgepi); + + CastInst *ciNew = CastInst::CreatePointerCast(gepiNew, pgepi->getType(), "processGEPI_", pgepi); + + pgepi->replaceAllUsesWith(ciNew); + pgepi->eraseFromParent(); + } - return pInst; + virtual Value *stripBitCasts(Value *pInst) + { + if (BitCastInst *pbci = llvm::dyn_cast(pInst)) { + return stripBitCasts(pbci->getOperand(0)); } - virtual void processGEPI(GetElementPtrInst * pgepi){ + return pInst; + } - Type * pdst = Type::getInt8Ty(pMod->getContext()); + virtual void processGEPI(GetElementPtrInst *pgepi) + { - Value * vPtr = pgepi->getPointerOperand(); - if (BitCastInst * pbci = llvm::dyn_cast(vPtr)){ - vPtr = stripBitCasts(pbci); + Type *pdst = Type::getInt8Ty(pMod->getContext()); - Type * ptrType = vPtr->getType()->getPointerElementType(); + Value *vPtr = pgepi->getPointerOperand(); + if (BitCastInst *pbci = llvm::dyn_cast(vPtr)) { + vPtr = stripBitCasts(pbci); - if (ArrayType * pat = llvm::dyn_cast(ptrType)){ - assert ((pdst == pat->getArrayElementType()) && "ClamBCLowering did not do it's job"); - } else if (ptrType != pdst){ - assert (0 && "ClamBCLowering did not do it's job"); - } + Type *ptrType = vPtr->getType()->getPointerElementType(); - Type * gepiDstType = pbci->getType()->getPointerElementType(); - if (StructType * pst = llvm::dyn_cast(gepiDstType)){ - processGEPI(pgepi, pbci, vPtr, pst); - } else if (ArrayType * pat = llvm::dyn_cast(gepiDstType)){ - processGEPI(pgepi, pbci, vPtr, pat); - } + if (ArrayType *pat = llvm::dyn_cast(ptrType)) { + assert((pdst == pat->getArrayElementType()) && "ClamBCLowering did not do it's job"); + } else if (ptrType != pdst) { + assert(0 && "ClamBCLowering did not do it's job"); } - } - - virtual void convertArrayStructGEPIsToI8(Function * pFunc){ - std::vector gepis; - for (auto i = pFunc->begin(), e = pFunc->end(); i != e; i++){ - BasicBlock * pBB = llvm::cast(i); - for (auto bi = pBB->begin(), be = pBB->end(); bi != be; bi++){ - if (GetElementPtrInst* pgepi = llvm::dyn_cast(bi)){ - if (ignoreGEPI(pgepi)){ - continue; - } - gepis.push_back(pgepi); + Type *gepiDstType = pbci->getType()->getPointerElementType(); + if (StructType *pst = llvm::dyn_cast(gepiDstType)) { + processGEPI(pgepi, pbci, vPtr, pst); + } else if (ArrayType *pat = llvm::dyn_cast(gepiDstType)) { + processGEPI(pgepi, pbci, vPtr, pat); + } + } + } + + virtual void convertArrayStructGEPIsToI8(Function *pFunc) + { + std::vector gepis; + for (auto i = pFunc->begin(), e = pFunc->end(); i != e; i++) { + BasicBlock *pBB = llvm::cast(i); + for (auto bi = pBB->begin(), be = pBB->end(); bi != be; bi++) { + if (GetElementPtrInst *pgepi = llvm::dyn_cast(bi)) { + if (ignoreGEPI(pgepi)) { + continue; } + gepis.push_back(pgepi); } } - - for (size_t i = 0; i < gepis.size(); i++){ - GetElementPtrInst * pgepi = gepis[i]; - processGEPI(pgepi); - } } - virtual bool runOnModule(Module &m) - { - - pMod = &m; -#ifdef USE_ANALYZER - pAnalyzer = &getAnalysis(); -#endif + for (size_t i = 0; i < gepis.size(); i++) { + GetElementPtrInst *pgepi = gepis[i]; + processGEPI(pgepi); + } + } - for (auto i = pMod->begin(), e = pMod->end(); i != e; i++) { - Function *pFunc = llvm::cast(i); + virtual bool runOnModule(Module &m) + { - convertArrayStructGEPIsToI8(pFunc); - } + pMod = &m; + for (auto i = pMod->begin(), e = pMod->end(); i != e; i++) { + Function *pFunc = llvm::cast(i); - for (auto i = pMod->begin(), e = pMod->end(); i != e; i++) { - Function *pFunc = llvm::cast(i); + convertArrayStructGEPIsToI8(pFunc); + } - fixCasts(pFunc); - } + for (auto i = pMod->begin(), e = pMod->end(); i != e; i++) { + Function *pFunc = llvm::cast(i); - return true; + fixCasts(pFunc); } - virtual void fixCasts(Function *pFunc) - { + return true; + } - for (auto i = pFunc->begin(), e = pFunc->end(); i != e; i++) { - BasicBlock *pBB = llvm::cast(i); - fixCasts(pBB); - } - } + virtual void fixCasts(Function *pFunc) + { - virtual void fixCasts(BasicBlock *pBB) - { - for (auto i = pBB->begin(), e = pBB->end(); i != e; i++) { - if (CastInst *pci = llvm::dyn_cast(i)) { - if (GetElementPtrInst *pgepi = llvm::dyn_cast(pci->getOperand(0))) { - if (pgepi->hasAllZeroIndices()) { - if (AllocaInst *pai = llvm::dyn_cast(pgepi->getPointerOperand())) { - if (pai->getType() == pci->getType()) { - pci->replaceAllUsesWith(pai); - } + for (auto i = pFunc->begin(), e = pFunc->end(); i != e; i++) { + BasicBlock *pBB = llvm::cast(i); + fixCasts(pBB); + } + } + + virtual void fixCasts(BasicBlock *pBB) + { + for (auto i = pBB->begin(), e = pBB->end(); i != e; i++) { + if (CastInst *pci = llvm::dyn_cast(i)) { + if (GetElementPtrInst *pgepi = llvm::dyn_cast(pci->getOperand(0))) { + if (pgepi->hasAllZeroIndices()) { + if (AllocaInst *pai = llvm::dyn_cast(pgepi->getPointerOperand())) { + if (pai->getType() == pci->getType()) { + pci->replaceAllUsesWith(pai); } } } } } } - + } }; char ClamBCPrepareGEPsForWriter::ID = 0; static RegisterPass X("clambc-prepare-geps-for-writer", "ClamBCPrepareGEPsForWriter Pass", - false /* Only looks at CFG */, - false /* Analysis Pass */); + false /* Only looks at CFG */, + false /* Analysis Pass */); llvm::ModulePass *createClamBCPrepareGEPsForWriter() { diff --git a/libclambcc/ClamBCPreserveABIs/ClamBCPreserveABIs.cpp b/libclambcc/ClamBCPreserveABIs/ClamBCPreserveABIs.cpp new file mode 100644 index 0000000000..a8c1bb93d6 --- /dev/null +++ b/libclambcc/ClamBCPreserveABIs/ClamBCPreserveABIs.cpp @@ -0,0 +1,169 @@ + +#include +#include "llvm/IR/Module.h" +#include "llvm/IR/Module.h" +#include "llvm/IR/Instructions.h" +#include "llvm/Support/raw_ostream.h" + +#include + +#include "llvm/IR/LegacyPassManager.h" +#include "llvm/Transforms/IPO/PassManagerBuilder.h" + +#include "Common/clambc.h" +#include "Common/ClamBCUtilities.h" + +#include +#include +using namespace llvm; + +namespace +{ +/* + * Preserve ABIs, and guarantee that -O3 doesn't remove arguments in functions + * or calls. We do this by calling an extern function declaration with all of + * the parameters passed into the function, for each function in our module. + * This guarantees that those * arguments cannot be removed, even if they are + * unused. This also prevents the optimizer from adding 'undef' values to the + * call instruction when it sees that the argument is unused. + * + * This pass is run twice. When it is run, it looks for 'clambc.fakefunctions' + * metadata object. If it does not find it (the first time), it adds calls + * to fake functions. If it does find it (the second time), it removes those + * calls. + */ +class ClamBCPreserveABIs : public ModulePass +{ + protected: + llvm::Module *pMod = nullptr; + bool bChanged = false; + std::vector fakeFunctions; + const char *const CLAMBC_FAKE_FUNCTION_METADATA_NAME = "clambc.fakefunctions"; + + virtual void processFunction(Function *pFunc) + { + if (0 == pFunc->arg_size()){ + return; + } + FunctionType *pFunctionType = llvm::dyn_cast(pFunc->getType()); + std::string newname = pFunc->getName(); + newname += "_fake"; + pFunctionType = llvm::cast(llvm::cast(pFunc->getType())->getElementType()); + Function *fakeFunction = Function::Create(pFunctionType, Function::ExternalLinkage, newname, pFunc->getParent()); + fakeFunctions.push_back(fakeFunction); + std::vector args; + for (auto i = pFunc->arg_begin(), e = pFunc->arg_end(); i != e; i++) { + Value *pv = llvm::cast(i); + args.push_back(pv); + } + + Instruction *pInsertBefore = nullptr; + for (auto i = pFunc->begin()->begin(), e = pFunc->begin()->end(); i != e; i++) { + Instruction *pInst = llvm::cast(i); + if (not llvm::isa(pInst)) { + pInsertBefore = pInst; + break; + } + } + + assert(pInsertBefore && "IMPOSSIBLE"); + if (pFunc->getReturnType()->isVoidTy()) { + CallInst::Create(pFunctionType, fakeFunction, args, "", pInsertBefore); + } else { + CallInst::Create(pFunctionType, fakeFunction, args, "a", pInsertBefore); + } + } + + virtual void writeMetadata() + { + NamedMDNode *Node = pMod->getOrInsertNamedMetadata(CLAMBC_FAKE_FUNCTION_METADATA_NAME); + for (size_t i = 0; i < fakeFunctions.size(); i++) { + MDString *S = MDString::get(pMod->getContext(), llvm::StringRef(fakeFunctions[i]->getName())); + MDNode *N = MDNode::get(pMod->getContext(), S); + Node->addOperand(N); + } + bChanged = true; + } + + virtual bool removeFakeFunctions() + { + bool bRet = false; + NamedMDNode *node = pMod->getNamedMetadata(CLAMBC_FAKE_FUNCTION_METADATA_NAME); + if (nullptr != node) { + bRet = true; + + for (size_t i = 0; i < node->getNumOperands(); i++) { + MDNode *mdn = node->getOperand(i); + if (mdn->getNumOperands()) { + if (MDString *mds = llvm::dyn_cast(mdn->getOperand(0))) { + + Function *pf = pMod->getFunction(mds->getString()); + + std::set insts; + std::set globs; + getDependentValues(pf, insts, globs); + + assert(0 == globs.size() && "what globals"); + for (auto i : insts) { + if (CallInst *pci = llvm::dyn_cast(i)) { + pci->eraseFromParent(); + } else { + DEBUGERR << *i << "\n"; + assert(0 && "WHAT HAPPENED"); + } + } + pf->eraseFromParent(); + + } else { + assert(0 && "What happened here?"); + } + } + } + + node->eraseFromParent(); + } + + return bRet; + } + + public: + static char ID; + ClamBCPreserveABIs() + : ModulePass(ID) {} + + virtual ~ClamBCPreserveABIs() {} + + bool runOnModule(Module &m) override + { + pMod = &m; + + if (removeFakeFunctions()) { + return bChanged; + } + + for (auto i = pMod->begin(), e = pMod->end(); i != e; i++) { + Function *pFunc = llvm::cast(i); + if (pFunc->isDeclaration()) { + continue; + } + + if (GlobalValue::InternalLinkage == pFunc->getLinkage()) { + /*Set the linkage type to external so that the optimizer cannot remove the arguments.*/ + pFunc->setLinkage(GlobalValue::ExternalLinkage); + } + + processFunction(pFunc); + } + + writeMetadata(); + + return bChanged; + } +}; // end of struct ClamBCPreserveABIs + +} // end of anonymous namespace + +char ClamBCPreserveABIs::ID = 0; +static RegisterPass X("clambc-preserve-abis", "Preserve ABIs", + false /* Only looks at CFG */, + false /* Analysis Pass */); diff --git a/libclambcc/ClamBCRemovePointerPHIs/ClamBCRemovePointerPHIs.cpp b/libclambcc/ClamBCRemovePointerPHIs/ClamBCRemovePointerPHIs.cpp index 260226ca1a..4c8409641c 100644 --- a/libclambcc/ClamBCRemovePointerPHIs/ClamBCRemovePointerPHIs.cpp +++ b/libclambcc/ClamBCRemovePointerPHIs/ClamBCRemovePointerPHIs.cpp @@ -200,7 +200,7 @@ class ClambcRemovePointerPHIs : public FunctionPass //If this value is dependent on the phi node, then it cannot //be what the PHINode was initialized to the first time the //block was entered, which is what we are looking for. - if (not (phiIsDependent(incoming, pn))){ + if (not(phiIsDependent(incoming, pn))) { continue; } diff --git a/libclambcc/ClamBCRemoveUndefs/ClamBCRemoveUndefs.cpp b/libclambcc/ClamBCRemoveUndefs/ClamBCRemoveUndefs.cpp index 39d0d6de19..b970cd6892 100644 --- a/libclambcc/ClamBCRemoveUndefs/ClamBCRemoveUndefs.cpp +++ b/libclambcc/ClamBCRemoveUndefs/ClamBCRemoveUndefs.cpp @@ -61,7 +61,7 @@ class ClamBCRemoveUndefs : public ModulePass Constant *func_rterr = BB->getParent()->getParent()->getOrInsertFunction("bytecode_rt_error", rterrTy); BasicBlock *abort = BasicBlock::Create(BB->getContext(), "rterr.trig", BB->getParent()); - Constant *PN = ConstantInt::get(Type::getInt32Ty(BB->getContext()), 99); + Constant *PN = ConstantInt::get(Type::getInt32Ty(BB->getContext()), 99); if (MDDbgKind) { CallInst *RtErrCall = CallInst::Create(func_rterr, PN, "", abort); RtErrCall->setCallingConv(CallingConv::C); @@ -120,24 +120,24 @@ class ClamBCRemoveUndefs : public ModulePass delLst.push_back(term); bChanged = true; - } - virtual bool isSamePointer(Value * ptr1, Value * ptr2, std::set &visited) { + virtual bool isSamePointer(Value *ptr1, Value *ptr2, std::set &visited) + { if (visited.end() != std::find(visited.begin(), visited.end(), ptr1)) { return false; } visited.insert(ptr1); - if (ptr1 == ptr2){ + if (ptr1 == ptr2) { return true; } - if (User * pu = llvm::dyn_cast(ptr1)){ + if (User *pu = llvm::dyn_cast(ptr1)) { - for (size_t i = 0; i < pu->getNumOperands(); i++){ - if (isSamePointer(pu->getOperand(i), ptr2, visited)){ + for (size_t i = 0; i < pu->getNumOperands(); i++) { + if (isSamePointer(pu->getOperand(i), ptr2, visited)) { return true; } } @@ -145,7 +145,8 @@ class ClamBCRemoveUndefs : public ModulePass return false; } - virtual bool isSamePointer(Value * ptr1, Value * ptr2) { + virtual bool isSamePointer(Value *ptr1, Value *ptr2) + { std::set visited; return isSamePointer(ptr1, ptr2, visited); } @@ -159,7 +160,7 @@ class ClamBCRemoveUndefs : public ModulePass for (auto i : insts) { if (GetElementPtrInst *pgepi = llvm::dyn_cast(i)) { - if (isSamePointer(pgepi->getPointerOperand(), ptr)){ + if (isSamePointer(pgepi->getPointerOperand(), ptr)) { insertChecks(pgepi, size); } }