mirror of
https://github.com/intel/llvm.git
synced 2026-01-24 08:30:34 +08:00
Convert the ObjC @synchronized cleanups to laziness. This is not actually
a big deal, except that I want to eliminate the shared-code EH cleanups in preparation for a significant algorithmic fix. llvm-svn: 108973
This commit is contained in:
@@ -1855,6 +1855,19 @@ llvm::Constant *CGObjCGNU::EnumerationMutationFunction() {
|
||||
return CGM.CreateRuntimeFunction(FTy, "objc_enumerationMutation");
|
||||
}
|
||||
|
||||
namespace {
|
||||
struct CallSyncExit : EHScopeStack::LazyCleanup {
|
||||
llvm::Value *SyncExitFn;
|
||||
llvm::Value *SyncArg;
|
||||
CallSyncExit(llvm::Value *SyncExitFn, llvm::Value *SyncArg)
|
||||
: SyncExitFn(SyncExitFn), SyncArg(SyncArg) {}
|
||||
|
||||
void Emit(CodeGenFunction &CGF, bool IsForEHCleanup) {
|
||||
CGF.Builder.CreateCall(SyncExitFn, SyncArg)->setDoesNotThrow();
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
void CGObjCGNU::EmitSynchronizedStmt(CodeGen::CodeGenFunction &CGF,
|
||||
const ObjCAtSynchronizedStmt &S) {
|
||||
std::vector<const llvm::Type*> Args(1, IdTy);
|
||||
@@ -1871,13 +1884,9 @@ void CGObjCGNU::EmitSynchronizedStmt(CodeGen::CodeGenFunction &CGF,
|
||||
CGF.Builder.CreateCall(SyncEnter, SyncArg);
|
||||
|
||||
// Register an all-paths cleanup to release the lock.
|
||||
{
|
||||
CodeGenFunction::CleanupBlock ReleaseScope(CGF, NormalAndEHCleanup);
|
||||
|
||||
llvm::Value *SyncExit = CGM.CreateRuntimeFunction(FTy, "objc_sync_exit");
|
||||
SyncArg = CGF.Builder.CreateBitCast(SyncArg, IdTy);
|
||||
CGF.Builder.CreateCall(SyncExit, SyncArg);
|
||||
}
|
||||
llvm::Value *SyncExit = CGM.CreateRuntimeFunction(FTy, "objc_sync_exit");
|
||||
CGF.EHStack.pushLazyCleanup<CallSyncExit>(NormalAndEHCleanup,
|
||||
SyncExit, SyncArg);
|
||||
|
||||
// Emit the body of the statement.
|
||||
CGF.EmitStmt(S.getSynchBody());
|
||||
|
||||
@@ -5695,6 +5695,19 @@ void CGObjCNonFragileABIMac::EmitObjCGlobalAssign(CodeGen::CodeGenFunction &CGF,
|
||||
return;
|
||||
}
|
||||
|
||||
namespace {
|
||||
struct CallSyncExit : EHScopeStack::LazyCleanup {
|
||||
llvm::Value *SyncExitFn;
|
||||
llvm::Value *SyncArg;
|
||||
CallSyncExit(llvm::Value *SyncExitFn, llvm::Value *SyncArg)
|
||||
: SyncExitFn(SyncExitFn), SyncArg(SyncArg) {}
|
||||
|
||||
void Emit(CodeGenFunction &CGF, bool IsForEHCleanup) {
|
||||
CGF.Builder.CreateCall(SyncExitFn, SyncArg)->setDoesNotThrow();
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
void
|
||||
CGObjCNonFragileABIMac::EmitSynchronizedStmt(CodeGen::CodeGenFunction &CGF,
|
||||
const ObjCAtSynchronizedStmt &S) {
|
||||
@@ -5707,12 +5720,9 @@ CGObjCNonFragileABIMac::EmitSynchronizedStmt(CodeGen::CodeGenFunction &CGF,
|
||||
->setDoesNotThrow();
|
||||
|
||||
// Register an all-paths cleanup to release the lock.
|
||||
{
|
||||
CodeGenFunction::CleanupBlock ReleaseScope(CGF, NormalAndEHCleanup);
|
||||
|
||||
CGF.Builder.CreateCall(ObjCTypes.getSyncExitFn(), SyncArg)
|
||||
->setDoesNotThrow();
|
||||
}
|
||||
CGF.EHStack.pushLazyCleanup<CallSyncExit>(NormalAndEHCleanup,
|
||||
ObjCTypes.getSyncExitFn(),
|
||||
SyncArg);
|
||||
|
||||
// Emit the body of the statement.
|
||||
CGF.EmitStmt(S.getSynchBody());
|
||||
|
||||
Reference in New Issue
Block a user