int main(int argc, char **argv) { LLVMContext &Context = getGlobalContext(); SMDiagnostic Err; cl::ParseCommandLineOptions(argc, argv, "PNaCl Bitcode ABI checker\n"); OwningPtr<Module> Mod( NaClParseIRFile(InputFilename, InputFileFormat, Err, Context)); if (Mod.get() == 0) { Err.print(argv[0], errs()); return 1; } PNaClABIErrorReporter ABIErrorReporter; ABIErrorReporter.setNonFatal(); bool ErrorsFound = false; OwningPtr<ModulePass> ModuleChecker( createPNaClABIVerifyModulePass(&ABIErrorReporter)); ModuleChecker->doInitialization(*Mod); ModuleChecker->runOnModule(*Mod); ErrorsFound |= CheckABIVerifyErrors(ABIErrorReporter, "Module"); OwningPtr<FunctionPassManager> PM(new FunctionPassManager(&*Mod)); PM->add(new DataLayout(&*Mod)); PM->add(createPNaClABIVerifyFunctionsPass(&ABIErrorReporter)); PM->doInitialization(); for (Module::iterator I = Mod->begin(), E = Mod->end(); I != E; ++I) { PM->run(*I); ErrorsFound |= CheckABIVerifyErrors(ABIErrorReporter, "Function " + I->getName()); } PM->doFinalization(); return ErrorsFound ? 1 : 0; }
// Print any errors collected by the error reporter. Return true if // there were any. static bool CheckABIVerifyErrors(PNaClABIErrorReporter &Reporter, const Twine &Name) { bool HasErrors = Reporter.getErrorCount() > 0; if (HasErrors) { if (!Quiet) { outs() << "ERROR: " << Name << " is not valid PNaCl bitcode:\n"; Reporter.printErrors(outs()); } } Reporter.reset(); return HasErrors; }
static void CheckABIVerifyErrors(PNaClABIErrorReporter &Reporter, const Twine &Name) { if (PNaClABIVerify && Reporter.getErrorCount() > 0) { std::string errors; raw_string_ostream os(errors); os << (PNaClABIVerifyFatalErrors ? "ERROR: " : "WARNING: "); os << Name << " is not valid PNaCl bitcode:\n"; Reporter.printErrors(os); if (PNaClABIVerifyFatalErrors) { report_fatal_error(os.str()); } errs() << os.str(); } Reporter.reset(); }