- // Set a flag indicating if the machine function makes a call to setjmp /
- // sigsetjmp (i.e., a function marked "returns_twice"). We'll use this to
- // disable certain optimizations which cannot handle such control flows.
- //
- // FIXME: This goes beyond the setjmp/sigsetjmp functions. We should check for
- // the GCC "returns twice" attribute.
- const Module *M = Fn.getParent();
- const Function *SetJmp = M->getFunction("setjmp");
- const Function *SigSetJmp = M->getFunction("sigsetjmp");
- bool HasReturnsTwiceCall = false;
-
- if (SetJmp || SigSetJmp) {
- if (SetJmp && !SetJmp->use_empty())
- for (Value::const_use_iterator
- I = SetJmp->use_begin(), E = SetJmp->use_end(); I != E; ++I)
- if (const CallInst *CI = dyn_cast<CallInst>(I))
- if (CI->getParent()->getParent() == &Fn) {
- HasReturnsTwiceCall = true;
- break;
- }
-
- if (!HasReturnsTwiceCall && SigSetJmp && !SigSetJmp->use_empty())
- for (Value::const_use_iterator
- I = SigSetJmp->use_begin(), E = SigSetJmp->use_end(); I != E; ++I)
- if (const CallInst *CI = dyn_cast<CallInst>(I))
- if (CI->getParent()->getParent() == &Fn) {
- HasReturnsTwiceCall = true;
- break;
- }
-
- mf.setReturnsTwiceCall(HasReturnsTwiceCall);
- }
-