| Index: lib/Analysis/NaCl/PNaClABIVerifyFunctions.cpp
|
| diff --git a/lib/Analysis/NaCl/PNaClABIVerifyFunctions.cpp b/lib/Analysis/NaCl/PNaClABIVerifyFunctions.cpp
|
| index fa94733ef04fab95c98414bd97dc06e4b1e55837..5252584009d6419bad7b237b4173acf3068f8753 100644
|
| --- a/lib/Analysis/NaCl/PNaClABIVerifyFunctions.cpp
|
| +++ b/lib/Analysis/NaCl/PNaClABIVerifyFunctions.cpp
|
| @@ -30,13 +30,18 @@ namespace {
|
| class PNaClABIVerifyFunctions : public FunctionPass {
|
| public:
|
| static char ID;
|
| - PNaClABIVerifyFunctions() : FunctionPass(ID), Errors(ErrorsString) {}
|
| + PNaClABIVerifyFunctions() : FunctionPass(ID), Errors(ErrorsString),
|
| + Strict(false), ErrorCount(0) {}
|
| bool runOnFunction(Function &F);
|
| virtual void print(raw_ostream &O, const Module *M) const;
|
| + virtual void setStrict(bool Strict_) { Strict = Strict_; }
|
| + virtual int getErrorCount() { return ErrorCount; }
|
| private:
|
| PNaClABITypeChecker TC;
|
| std::string ErrorsString;
|
| raw_string_ostream Errors;
|
| + bool Strict;
|
| + int ErrorCount;
|
| };
|
|
|
| } // and anonymous namespace
|
| @@ -45,6 +50,7 @@ bool PNaClABIVerifyFunctions::runOnFunction(Function &F) {
|
| // For now just start with new errors on each function; this may change
|
| // once we want to do something with them other than just calling print()
|
| ErrorsString.clear();
|
| + ErrorCount = 0;
|
| // TODO: only report one error per instruction
|
| for (Function::const_iterator FI = F.begin(), FE = F.end();
|
| FI != FE; ++FI) {
|
| @@ -62,6 +68,7 @@ bool PNaClABIVerifyFunctions::runOnFunction(Function &F) {
|
| Errors << "Function " + F.getName() +
|
| " has disallowed instruction: " +
|
| BBI->getOpcodeName() + "\n";
|
| + ErrorCount++;
|
| break;
|
|
|
| // Terminator instructions
|
| @@ -129,6 +136,7 @@ bool PNaClABIVerifyFunctions::runOnFunction(Function &F) {
|
| Errors << "Function " + F.getName() +
|
| " has instruction with disallowed type: " +
|
| PNaClABITypeChecker::getTypeName(BBI->getType()) + "\n";
|
| + ErrorCount++;
|
| }
|
|
|
| // Check the instruction operands. Operands which are Instructions will
|
| @@ -141,10 +149,12 @@ bool PNaClABIVerifyFunctions::runOnFunction(Function &F) {
|
| OI != OE; OI++) {
|
| if (isa<Constant>(OI) && !isa<GlobalValue>(OI)) {
|
| Type *T = TC.checkTypesInConstant(cast<Constant>(*OI));
|
| - if (T)
|
| + if (T) {
|
| Errors << "Function " + F.getName() +
|
| " has instruction operand with disallowed type: " +
|
| PNaClABITypeChecker::getTypeName(T) + "\n";
|
| + ErrorCount++;
|
| + }
|
| }
|
| }
|
|
|
| @@ -153,15 +163,21 @@ bool PNaClABIVerifyFunctions::runOnFunction(Function &F) {
|
| BBI->getAllMetadataOtherThanDebugLoc(MDForInst);
|
| for (unsigned i = 0, e = MDForInst.size(); i != e; i++) {
|
| Type *T = TC.checkTypesInMDNode(MDForInst[i].second);
|
| - if (T)
|
| + if (T) {
|
| Errors << "Function " + F.getName() +
|
| " has instruction metadata containing disallowed type: " +
|
| PNaClABITypeChecker::getTypeName(T) + "\n";
|
| + ErrorCount++;
|
| + }
|
| }
|
| }
|
| }
|
|
|
| Errors.flush();
|
| + if (Strict && ErrorCount > 0) {
|
| + report_fatal_error("Function " + F.getName() +
|
| + " is not valid PNaCl bitcode:\n" + ErrorsString);
|
| + }
|
| return false;
|
| }
|
|
|
| @@ -175,6 +191,8 @@ char PNaClABIVerifyFunctions::ID = 0;
|
| static RegisterPass<PNaClABIVerifyFunctions> X("verify-pnaclabi-functions",
|
| "Verify functions for PNaCl", false, false);
|
|
|
| -FunctionPass *llvm::createPNaClABIVerifyFunctionsPass() {
|
| - return new PNaClABIVerifyFunctions();
|
| +FunctionPass *llvm::createPNaClABIVerifyFunctionsPass(bool Strict) {
|
| + PNaClABIVerifyFunctions *P = new PNaClABIVerifyFunctions();
|
| + P->setStrict(Strict);
|
| + return P;
|
| }
|
|
|