Deleted Added
full compact
Miscompilation.cpp (218885) Miscompilation.cpp (221337)
1//===- Miscompilation.cpp - Debug program miscompilations -----------------===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//

--- 20 unchanged lines hidden (view full) ---

29using namespace llvm;
30
31namespace llvm {
32 extern cl::opt<std::string> OutputPrefix;
33 extern cl::list<std::string> InputArgv;
34}
35
36namespace {
1//===- Miscompilation.cpp - Debug program miscompilations -----------------===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//

--- 20 unchanged lines hidden (view full) ---

29using namespace llvm;
30
31namespace llvm {
32 extern cl::opt<std::string> OutputPrefix;
33 extern cl::list<std::string> InputArgv;
34}
35
36namespace {
37 static llvm::cl::opt<bool>
38 DisableLoopExtraction("disable-loop-extraction",
37 static llvm::cl::opt
38 DisableLoopExtraction("disable-loop-extraction",
39 cl::desc("Don't extract loops when searching for miscompilations"),
40 cl::init(false));
39 cl::desc("Don't extract loops when searching for miscompilations"),
40 cl::init(false));
41 static llvm::cl::opt<bool>
42 DisableBlockExtraction("disable-block-extraction",
41 static llvm::cl::opt
42 DisableBlockExtraction("disable-block-extraction",
43 cl::desc("Don't extract blocks when searching for miscompilations"),
44 cl::init(false));
45
46 class ReduceMiscompilingPasses : public ListReducer<std::string> {
47 BugDriver &BD;
48 public:
49 ReduceMiscompilingPasses(BugDriver &bd) : BD(bd) {}
50

--- 19 unchanged lines hidden (view full) ---

70 if (BD.runPasses(BD.getProgram(), Suffix, BitcodeResult, false/*delete*/,
71 true/*quiet*/)) {
72 errs() << " Error running this sequence of passes"
73 << " on the input program!\n";
74 BD.setPassesToRun(Suffix);
75 BD.EmitProgressBitcode(BD.getProgram(), "pass-error", false);
76 exit(BD.debugOptimizerCrash());
77 }
43 cl::desc("Don't extract blocks when searching for miscompilations"),
44 cl::init(false));
45
46 class ReduceMiscompilingPasses : public ListReducer<std::string> {
47 BugDriver &BD;
48 public:
49 ReduceMiscompilingPasses(BugDriver &bd) : BD(bd) {}
50

--- 19 unchanged lines hidden (view full) ---

70 if (BD.runPasses(BD.getProgram(), Suffix, BitcodeResult, false/*delete*/,
71 true/*quiet*/)) {
72 errs() << " Error running this sequence of passes"
73 << " on the input program!\n";
74 BD.setPassesToRun(Suffix);
75 BD.EmitProgressBitcode(BD.getProgram(), "pass-error", false);
76 exit(BD.debugOptimizerCrash());
77 }
78
78
79 // Check to see if the finished program matches the reference output...
80 bool Diff = BD.diffProgram(BD.getProgram(), BitcodeResult, "",
81 true /*delete bitcode*/, &Error);
82 if (!Error.empty())
83 return InternalError;
84 if (Diff) {
85 outs() << " nope.\n";
86 if (Suffix.empty()) {

--- 217 unchanged lines hidden (view full) ---

304static bool ExtractLoops(BugDriver &BD,
305 bool (*TestFn)(BugDriver &, Module *, Module *,
306 std::string &),
307 std::vector<Function*> &MiscompiledFunctions,
308 std::string &Error) {
309 bool MadeChange = false;
310 while (1) {
311 if (BugpointIsInterrupted) return MadeChange;
79 // Check to see if the finished program matches the reference output...
80 bool Diff = BD.diffProgram(BD.getProgram(), BitcodeResult, "",
81 true /*delete bitcode*/, &Error);
82 if (!Error.empty())
83 return InternalError;
84 if (Diff) {
85 outs() << " nope.\n";
86 if (Suffix.empty()) {

--- 217 unchanged lines hidden (view full) ---

304static bool ExtractLoops(BugDriver &BD,
305 bool (*TestFn)(BugDriver &, Module *, Module *,
306 std::string &),
307 std::vector<Function*> &MiscompiledFunctions,
308 std::string &Error) {
309 bool MadeChange = false;
310 while (1) {
311 if (BugpointIsInterrupted) return MadeChange;
312
312
313 ValueToValueMapTy VMap;
314 Module *ToNotOptimize = CloneModule(BD.getProgram(), VMap);
315 Module *ToOptimize = SplitFunctionsOutOfModule(ToNotOptimize,
316 MiscompiledFunctions,
317 VMap);
318 Module *ToOptimizeLoopExtracted = BD.ExtractLoop(ToOptimize);
319 if (!ToOptimizeLoopExtracted) {
320 // If the loop extractor crashed or if there were no extractible loops,

--- 28 unchanged lines hidden (view full) ---

349
350 BD.writeProgramToFile(OutputPrefix + "-loop-extract-fail-tno.bc",
351 ToNotOptimize);
352 BD.writeProgramToFile(OutputPrefix + "-loop-extract-fail-to.bc",
353 ToOptimize);
354 BD.writeProgramToFile(OutputPrefix + "-loop-extract-fail-to-le.bc",
355 ToOptimizeLoopExtracted);
356
313 ValueToValueMapTy VMap;
314 Module *ToNotOptimize = CloneModule(BD.getProgram(), VMap);
315 Module *ToOptimize = SplitFunctionsOutOfModule(ToNotOptimize,
316 MiscompiledFunctions,
317 VMap);
318 Module *ToOptimizeLoopExtracted = BD.ExtractLoop(ToOptimize);
319 if (!ToOptimizeLoopExtracted) {
320 // If the loop extractor crashed or if there were no extractible loops,

--- 28 unchanged lines hidden (view full) ---

349
350 BD.writeProgramToFile(OutputPrefix + "-loop-extract-fail-tno.bc",
351 ToNotOptimize);
352 BD.writeProgramToFile(OutputPrefix + "-loop-extract-fail-to.bc",
353 ToOptimize);
354 BD.writeProgramToFile(OutputPrefix + "-loop-extract-fail-to-le.bc",
355 ToOptimizeLoopExtracted);
356
357 errs() << "Please submit the "
357 errs() << "Please submit the "
358 << OutputPrefix << "-loop-extract-fail-*.bc files.\n";
359 delete ToOptimize;
360 delete ToNotOptimize;
361 delete ToOptimizeLoopExtracted;
362 return MadeChange;
363 }
364 delete ToOptimize;
365 BD.switchToInterpreter(AI);

--- 38 unchanged lines hidden (view full) ---

404 delete ToOptimizeLoopExtracted;
405
406 // All of the Function*'s in the MiscompiledFunctions list are in the old
407 // module. Update this list to include all of the functions in the
408 // optimized and loop extracted module.
409 MiscompiledFunctions.clear();
410 for (unsigned i = 0, e = MisCompFunctions.size(); i != e; ++i) {
411 Function *NewF = ToNotOptimize->getFunction(MisCompFunctions[i].first);
358 << OutputPrefix << "-loop-extract-fail-*.bc files.\n";
359 delete ToOptimize;
360 delete ToNotOptimize;
361 delete ToOptimizeLoopExtracted;
362 return MadeChange;
363 }
364 delete ToOptimize;
365 BD.switchToInterpreter(AI);

--- 38 unchanged lines hidden (view full) ---

404 delete ToOptimizeLoopExtracted;
405
406 // All of the Function*'s in the MiscompiledFunctions list are in the old
407 // module. Update this list to include all of the functions in the
408 // optimized and loop extracted module.
409 MiscompiledFunctions.clear();
410 for (unsigned i = 0, e = MisCompFunctions.size(); i != e; ++i) {
411 Function *NewF = ToNotOptimize->getFunction(MisCompFunctions[i].first);
412
412
413 assert(NewF && "Function not found??");
413 assert(NewF && "Function not found??");
414 assert(NewF->getFunctionType() == MisCompFunctions[i].second &&
414 assert(NewF->getFunctionType() == MisCompFunctions[i].second &&
415 "found wrong function type?");
416 MiscompiledFunctions.push_back(NewF);
417 }
418
419 BD.setNewProgram(ToNotOptimize);
420 MadeChange = true;
421 }
422}

--- 95 unchanged lines hidden (view full) ---

518/// the bug.
519///
520static bool ExtractBlocks(BugDriver &BD,
521 bool (*TestFn)(BugDriver &, Module *, Module *,
522 std::string &),
523 std::vector<Function*> &MiscompiledFunctions,
524 std::string &Error) {
525 if (BugpointIsInterrupted) return false;
415 "found wrong function type?");
416 MiscompiledFunctions.push_back(NewF);
417 }
418
419 BD.setNewProgram(ToNotOptimize);
420 MadeChange = true;
421 }
422}

--- 95 unchanged lines hidden (view full) ---

518/// the bug.
519///
520static bool ExtractBlocks(BugDriver &BD,
521 bool (*TestFn)(BugDriver &, Module *, Module *,
522 std::string &),
523 std::vector<Function*> &MiscompiledFunctions,
524 std::string &Error) {
525 if (BugpointIsInterrupted) return false;
526
526
527 std::vector<BasicBlock*> Blocks;
528 for (unsigned i = 0, e = MiscompiledFunctions.size(); i != e; ++i)
529 for (Function::iterator I = MiscompiledFunctions[i]->begin(),
530 E = MiscompiledFunctions[i]->end(); I != E; ++I)
531 Blocks.push_back(I);
532
533 // Use the list reducer to identify blocks that can be extracted without
534 // obscuring the bug. The Blocks list will end up containing blocks that must

--- 53 unchanged lines hidden (view full) ---

588 BD.setNewProgram(ProgClone);
589
590 // Update the list of miscompiled functions.
591 MiscompiledFunctions.clear();
592
593 for (unsigned i = 0, e = MisCompFunctions.size(); i != e; ++i) {
594 Function *NewF = ProgClone->getFunction(MisCompFunctions[i].first);
595 assert(NewF && "Function not found??");
527 std::vector<BasicBlock*> Blocks;
528 for (unsigned i = 0, e = MiscompiledFunctions.size(); i != e; ++i)
529 for (Function::iterator I = MiscompiledFunctions[i]->begin(),
530 E = MiscompiledFunctions[i]->end(); I != E; ++I)
531 Blocks.push_back(I);
532
533 // Use the list reducer to identify blocks that can be extracted without
534 // obscuring the bug. The Blocks list will end up containing blocks that must

--- 53 unchanged lines hidden (view full) ---

588 BD.setNewProgram(ProgClone);
589
590 // Update the list of miscompiled functions.
591 MiscompiledFunctions.clear();
592
593 for (unsigned i = 0, e = MisCompFunctions.size(); i != e; ++i) {
594 Function *NewF = ProgClone->getFunction(MisCompFunctions[i].first);
595 assert(NewF && "Function not found??");
596 assert(NewF->getFunctionType() == MisCompFunctions[i].second &&
596 assert(NewF->getFunctionType() == MisCompFunctions[i].second &&
597 "Function has wrong type??");
598 MiscompiledFunctions.push_back(NewF);
599 }
600
601 return true;
602}
603
604

--- 121 unchanged lines hidden (view full) ---

726 return;
727 }
728
729 outs() << "\n*** Found miscompiling pass"
730 << (getPassesToRun().size() == 1 ? "" : "es") << ": "
731 << getPassesString(getPassesToRun()) << '\n';
732 EmitProgressBitcode(Program, "passinput");
733
597 "Function has wrong type??");
598 MiscompiledFunctions.push_back(NewF);
599 }
600
601 return true;
602}
603
604

--- 121 unchanged lines hidden (view full) ---

726 return;
727 }
728
729 outs() << "\n*** Found miscompiling pass"
730 << (getPassesToRun().size() == 1 ? "" : "es") << ": "
731 << getPassesString(getPassesToRun()) << '\n';
732 EmitProgressBitcode(Program, "passinput");
733
734 std::vector<Function *> MiscompiledFunctions =
734 std::vector MiscompiledFunctions =
735 DebugAMiscompilation(*this, TestOptimizer, *Error);
736 if (!Error->empty())
737 return;
738
739 // Output a bunch of bitcode files for the user...
740 outs() << "Outputting reduced bitcode files which expose the problem:\n";
741 ValueToValueMapTy VMap;
742 Module *ToNotOptimize = CloneModule(getProgram(), VMap);

--- 97 unchanged lines hidden (view full) ---

840 ResolverArgs.push_back(GEP);
841
842 // Rewrite uses of F in global initializers, etc. to uses of a wrapper
843 // function that dynamically resolves the calls to F via our JIT API
844 if (!F->use_empty()) {
845 // Create a new global to hold the cached function pointer.
846 Constant *NullPtr = ConstantPointerNull::get(F->getType());
847 GlobalVariable *Cache =
735 DebugAMiscompilation(*this, TestOptimizer, *Error);
736 if (!Error->empty())
737 return;
738
739 // Output a bunch of bitcode files for the user...
740 outs() << "Outputting reduced bitcode files which expose the problem:\n";
741 ValueToValueMapTy VMap;
742 Module *ToNotOptimize = CloneModule(getProgram(), VMap);

--- 97 unchanged lines hidden (view full) ---

840 ResolverArgs.push_back(GEP);
841
842 // Rewrite uses of F in global initializers, etc. to uses of a wrapper
843 // function that dynamically resolves the calls to F via our JIT API
844 if (!F->use_empty()) {
845 // Create a new global to hold the cached function pointer.
846 Constant *NullPtr = ConstantPointerNull::get(F->getType());
847 GlobalVariable *Cache =
848 new GlobalVariable(*F->getParent(), F->getType(),
848 new GlobalVariable(*F->getParent(), F->getType(),
849 false, GlobalValue::InternalLinkage,
850 NullPtr,F->getName()+".fpcache");
851
852 // Construct a new stub function that will re-route calls to F
853 const FunctionType *FuncTy = F->getFunctionType();
854 Function *FuncWrapper = Function::Create(FuncTy,
855 GlobalValue::InternalLinkage,
856 F->getName() + "_wrapper",

--- 23 unchanged lines hidden (view full) ---

880 new BitCastInst(Resolver,
881 PointerType::getUnqual(F->getFunctionType()),
882 "resolverCast", LookupBB);
883
884 // Save the value in our cache.
885 new StoreInst(CastedResolver, Cache, LookupBB);
886 BranchInst::Create(DoCallBB, LookupBB);
887
849 false, GlobalValue::InternalLinkage,
850 NullPtr,F->getName()+".fpcache");
851
852 // Construct a new stub function that will re-route calls to F
853 const FunctionType *FuncTy = F->getFunctionType();
854 Function *FuncWrapper = Function::Create(FuncTy,
855 GlobalValue::InternalLinkage,
856 F->getName() + "_wrapper",

--- 23 unchanged lines hidden (view full) ---

880 new BitCastInst(Resolver,
881 PointerType::getUnqual(F->getFunctionType()),
882 "resolverCast", LookupBB);
883
884 // Save the value in our cache.
885 new StoreInst(CastedResolver, Cache, LookupBB);
886 BranchInst::Create(DoCallBB, LookupBB);
887
888 PHINode *FuncPtr = PHINode::Create(NullPtr->getType(),
888 PHINode *FuncPtr = PHINode::Create(NullPtr->getType(), 2,
889 "fp", DoCallBB);
890 FuncPtr->addIncoming(CastedResolver, LookupBB);
891 FuncPtr->addIncoming(CachedVal, EntryBB);
892
893 // Save the argument list.
894 std::vector<Value*> Args;
895 for (Function::arg_iterator i = FuncWrapper->arg_begin(),
896 e = FuncWrapper->arg_end(); i != e; ++i)

--- 41 unchanged lines hidden (view full) ---

938 }
939 if (BD.writeProgramToFile(TestModuleBC.str(), Test)) {
940 errs() << "Error writing bitcode to `" << TestModuleBC.str()
941 << "'\nExiting.";
942 exit(1);
943 }
944 delete Test;
945
889 "fp", DoCallBB);
890 FuncPtr->addIncoming(CastedResolver, LookupBB);
891 FuncPtr->addIncoming(CachedVal, EntryBB);
892
893 // Save the argument list.
894 std::vector<Value*> Args;
895 for (Function::arg_iterator i = FuncWrapper->arg_begin(),
896 e = FuncWrapper->arg_end(); i != e; ++i)

--- 41 unchanged lines hidden (view full) ---

938 }
939 if (BD.writeProgramToFile(TestModuleBC.str(), Test)) {
940 errs() << "Error writing bitcode to `" << TestModuleBC.str()
941 << "'\nExiting.";
942 exit(1);
943 }
944 delete Test;
945
946 FileRemover TestModuleBCRemover(TestModuleBC, !SaveTemps);
946 FileRemover TestModuleBCRemover(TestModuleBC.str(), !SaveTemps);
947
948 // Make the shared library
949 sys::Path SafeModuleBC("bugpoint.safe.bc");
950 if (SafeModuleBC.makeUnique(true, &ErrMsg)) {
951 errs() << BD.getToolName() << "Error making unique filename: "
952 << ErrMsg << "\n";
953 exit(1);
954 }
955
956 if (BD.writeProgramToFile(SafeModuleBC.str(), Safe)) {
957 errs() << "Error writing bitcode to `" << SafeModuleBC.str()
958 << "'\nExiting.";
959 exit(1);
960 }
961
947
948 // Make the shared library
949 sys::Path SafeModuleBC("bugpoint.safe.bc");
950 if (SafeModuleBC.makeUnique(true, &ErrMsg)) {
951 errs() << BD.getToolName() << "Error making unique filename: "
952 << ErrMsg << "\n";
953 exit(1);
954 }
955
956 if (BD.writeProgramToFile(SafeModuleBC.str(), Safe)) {
957 errs() << "Error writing bitcode to `" << SafeModuleBC.str()
958 << "'\nExiting.";
959 exit(1);
960 }
961
962 FileRemover SafeModuleBCRemover(SafeModuleBC, !SaveTemps);
962 FileRemover SafeModuleBCRemover(SafeModuleBC.str(), !SaveTemps);
963
964 std::string SharedObject = BD.compileSharedObject(SafeModuleBC.str(), Error);
965 if (!Error.empty())
966 return false;
967 delete Safe;
968
963
964 std::string SharedObject = BD.compileSharedObject(SafeModuleBC.str(), Error);
965 if (!Error.empty())
966 return false;
967 delete Safe;
968
969 FileRemover SharedObjectRemover(sys::Path(SharedObject), !SaveTemps);
969 FileRemover SharedObjectRemover(SharedObject, !SaveTemps);
970
971 // Run the code generator on the `Test' code, loading the shared library.
972 // The function returns whether or not the new output differs from reference.
973 bool Result = BD.diffProgram(BD.getProgram(), TestModuleBC.str(),
974 SharedObject, false, &Error);
975 if (!Error.empty())
976 return false;
977

--- 105 unchanged lines hidden ---
970
971 // Run the code generator on the `Test' code, loading the shared library.
972 // The function returns whether or not the new output differs from reference.
973 bool Result = BD.diffProgram(BD.getProgram(), TestModuleBC.str(),
974 SharedObject, false, &Error);
975 if (!Error.empty())
976 return false;
977

--- 105 unchanged lines hidden ---