forked from OSchip/llvm-project
Support for catching objc pointer objects in c++ catch-statement
in fragile abi mode and some other cleanups. // rdar://8940528 llvm-svn: 133747
This commit is contained in:
parent
402491558b
commit
831f0fc2e0
|
@ -296,3 +296,6 @@ def GNU : DiagGroup<"gnu", [GNUDesignator, VLA]>;
|
|||
|
||||
// A warning group for warnings about Microsoft extensions.
|
||||
def Microsoft : DiagGroup<"microsoft">;
|
||||
|
||||
def ObjCNonUnifiedException : DiagGroup<"objc-nonunified-exceptions">;
|
||||
|
||||
|
|
|
@ -3154,11 +3154,8 @@ def err_qualified_objc_catch_parm : Error<
|
|||
def err_objc_pointer_cxx_catch_gnu : Error<
|
||||
"can't catch Objective C exceptions in C++ in the GNU runtime">;
|
||||
def warn_objc_pointer_cxx_catch_fragile : Warning<
|
||||
"catching Objective C id's exceptions in C++ in the non-unified "
|
||||
"exception model">;
|
||||
def err_objc_pointer_cxx_catch_fragile : Error<
|
||||
"can't catch Objective C exceptions in C++ in the non-unified "
|
||||
"exception model">;
|
||||
"catching Objective C exceptions in C++ in the non-unified "
|
||||
"exception model">, InGroup<ObjCNonUnifiedException>;
|
||||
def err_objc_object_catch : Error<
|
||||
"can't catch an Objective C object by value">;
|
||||
def err_incomplete_type_objc_at_encode : Error<
|
||||
|
|
|
@ -521,7 +521,7 @@ void CodeGenFunction::EnterCXXTryStmt(const CXXTryStmt &S, bool IsFnTryBlock) {
|
|||
|
||||
llvm::Value *TypeInfo = 0;
|
||||
if (CaughtType->isObjCObjectPointerType())
|
||||
TypeInfo = CGM.getObjCRuntime().GetEHType(CaughtType, this);
|
||||
TypeInfo = CGM.getObjCRuntime().GetEHType(CaughtType);
|
||||
else
|
||||
TypeInfo = CGM.GetAddrOfRTTIDescriptor(CaughtType, /*ForEH=*/true);
|
||||
CatchScope->setHandler(I, TypeInfo, Handler);
|
||||
|
|
|
@ -438,7 +438,7 @@ public:
|
|||
bool lval = false);
|
||||
virtual llvm::Value *GetSelector(CGBuilderTy &Builder, const ObjCMethodDecl
|
||||
*Method);
|
||||
virtual llvm::Constant *GetEHType(QualType T, const CodeGenFunction *CGF=0);
|
||||
virtual llvm::Constant *GetEHType(QualType T);
|
||||
|
||||
virtual llvm::Function *GenerateMethod(const ObjCMethodDecl *OMD,
|
||||
const ObjCContainerDecl *CD);
|
||||
|
@ -832,7 +832,7 @@ llvm::Value *CGObjCGNU::GetSelector(CGBuilderTy &Builder, const ObjCMethodDecl
|
|||
return GetSelector(Builder, Method->getSelector(), SelTypes, false);
|
||||
}
|
||||
|
||||
llvm::Constant *CGObjCGNU::GetEHType(QualType T, const CodeGenFunction *CGF) {
|
||||
llvm::Constant *CGObjCGNU::GetEHType(QualType T) {
|
||||
if (!CGM.getLangOptions().CPlusPlus) {
|
||||
if (T->isObjCIdType()
|
||||
|| T->isObjCQualifiedIdType()) {
|
||||
|
|
|
@ -1010,7 +1010,7 @@ public:
|
|||
virtual llvm::Value *GetSelector(CGBuilderTy &Builder,
|
||||
const ObjCMethodDecl *Method);
|
||||
|
||||
virtual llvm::Constant *GetEHType(QualType T, const CodeGenFunction *CGF=0);
|
||||
virtual llvm::Constant *GetEHType(QualType T);
|
||||
|
||||
virtual void GenerateCategory(const ObjCCategoryImplDecl *CMD);
|
||||
|
||||
|
@ -1271,7 +1271,7 @@ public:
|
|||
virtual llvm::Value *GenerateProtocolRef(CGBuilderTy &Builder,
|
||||
const ObjCProtocolDecl *PD);
|
||||
|
||||
virtual llvm::Constant *GetEHType(QualType T, const CodeGenFunction *CGF=0);
|
||||
virtual llvm::Constant *GetEHType(QualType T);
|
||||
|
||||
virtual llvm::Constant *GetPropertyGetFunction() {
|
||||
return ObjCTypes.getGetPropertyFn();
|
||||
|
@ -1414,12 +1414,20 @@ llvm::Value *CGObjCMac::GetSelector(CGBuilderTy &Builder, const ObjCMethodDecl
|
|||
return EmitSelector(Builder, Method->getSelector());
|
||||
}
|
||||
|
||||
llvm::Constant *CGObjCMac::GetEHType(QualType T, const CodeGenFunction *CGF) {
|
||||
llvm::Constant *CGObjCMac::GetEHType(QualType T) {
|
||||
if (T->isObjCIdType() ||
|
||||
T->isObjCQualifiedIdType()) {
|
||||
return CGM.GetAddrOfRTTIDescriptor(
|
||||
CGF->getContext().ObjCIdRedefinitionType, /*ForEH=*/true);
|
||||
CGM.getContext().ObjCIdRedefinitionType, /*ForEH=*/true);
|
||||
}
|
||||
if (T->isObjCClassType() ||
|
||||
T->isObjCQualifiedClassType()) {
|
||||
return CGM.GetAddrOfRTTIDescriptor(
|
||||
CGM.getContext().ObjCClassRedefinitionType, /*ForEH=*/true);
|
||||
}
|
||||
if (T->isObjCObjectPointerType())
|
||||
return CGM.GetAddrOfRTTIDescriptor(T, /*ForEH=*/true);
|
||||
|
||||
llvm_unreachable("asking for catch type for ObjC type in fragile runtime");
|
||||
return 0;
|
||||
}
|
||||
|
@ -6021,7 +6029,7 @@ CGObjCNonFragileABIMac::EmitSynchronizedStmt(CodeGen::CodeGenFunction &CGF,
|
|||
}
|
||||
|
||||
llvm::Constant *
|
||||
CGObjCNonFragileABIMac::GetEHType(QualType T, const CodeGenFunction *CGF) {
|
||||
CGObjCNonFragileABIMac::GetEHType(QualType T) {
|
||||
// There's a particular fixed type info for 'id'.
|
||||
if (T->isObjCIdType() ||
|
||||
T->isObjCQualifiedIdType()) {
|
||||
|
|
|
@ -128,8 +128,7 @@ public:
|
|||
/// This is used externally to implement catching ObjC types in C++.
|
||||
/// Runtimes which don't support this should add the appropriate
|
||||
/// error to Sema.
|
||||
virtual llvm::Constant *GetEHType(QualType T,
|
||||
const CodeGenFunction *CGF=0) = 0;
|
||||
virtual llvm::Constant *GetEHType(QualType T) = 0;
|
||||
|
||||
/// Generate a constant string object.
|
||||
virtual llvm::Constant *GenerateConstantString(const StringLiteral *) = 0;
|
||||
|
|
|
@ -8045,14 +8045,8 @@ VarDecl *Sema::BuildExceptionDeclaration(Scope *S,
|
|||
Diag(Loc, diag::err_objc_object_catch);
|
||||
Invalid = true;
|
||||
} else if (T->isObjCObjectPointerType()) {
|
||||
if (!getLangOptions().ObjCNonFragileABI) {
|
||||
if (T->isObjCIdType() || T->isObjCQualifiedIdType())
|
||||
Diag(Loc, diag::warn_objc_pointer_cxx_catch_fragile);
|
||||
else {
|
||||
Diag(Loc, diag::err_objc_pointer_cxx_catch_fragile);
|
||||
Invalid = true;
|
||||
}
|
||||
}
|
||||
if (!getLangOptions().ObjCNonFragileABI)
|
||||
Diag(Loc, diag::warn_objc_pointer_cxx_catch_fragile);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -11,18 +11,33 @@
|
|||
|
||||
id Groups();
|
||||
|
||||
@protocol P @end;
|
||||
|
||||
@interface INTF<P> {
|
||||
double dd;
|
||||
}
|
||||
@end
|
||||
|
||||
id FUNC() {
|
||||
id groups;
|
||||
try
|
||||
{
|
||||
groups = Groups(); // throws on errors.
|
||||
}
|
||||
catch( INTF<P>* error )
|
||||
{
|
||||
Groups();
|
||||
}
|
||||
catch( id error )
|
||||
{
|
||||
// CHECK: call i32 (i8*, i8*, ...)* @llvm.eh.selector({{.*}} @__gxx_personality_v0 {{.*}} @_ZTIP11objc_object
|
||||
// CHECK: call i32 (i8*, i8*, ...)* @llvm.eh.selector({{.*}} @__gxx_personality_v0 {{.*}} @_ZTIP4INTF {{.*}} @_ZTIP11objc_object {{.*}} @_ZTIP10objc_class
|
||||
error = error;
|
||||
groups = [ns_array array];
|
||||
}
|
||||
catch (Class cl) {
|
||||
cl = cl;
|
||||
groups = [ns_array array];
|
||||
}
|
||||
return groups;
|
||||
|
||||
}
|
||||
|
|
|
@ -6,7 +6,7 @@ void opaque();
|
|||
namespace test0 {
|
||||
void test() {
|
||||
try {
|
||||
} catch (NSException *e) { // expected-error {{can't catch Objective C exceptions in C++ in the non-unified exception model}}
|
||||
} catch (NSException *e) { // expected-warning {{catching Objective C exceptions in C++ in the non-unified exception model [-Wobjc-nonunified-exceptions]}}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue