SemaExceptionSpec.cpp revision 243830
1//===--- SemaExceptionSpec.cpp - C++ Exception Specifications ---*- C++ -*-===//
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//===----------------------------------------------------------------------===//
9//
10// This file provides Sema routines for C++ exception specification testing.
11//
12//===----------------------------------------------------------------------===//
13
14#include "clang/Sema/SemaInternal.h"
15#include "clang/AST/CXXInheritance.h"
16#include "clang/AST/Expr.h"
17#include "clang/AST/ExprCXX.h"
18#include "clang/AST/TypeLoc.h"
19#include "clang/Lex/Preprocessor.h"
20#include "clang/Basic/Diagnostic.h"
21#include "clang/Basic/SourceManager.h"
22#include "llvm/ADT/SmallPtrSet.h"
23#include "llvm/ADT/SmallString.h"
24
25namespace clang {
26
27static const FunctionProtoType *GetUnderlyingFunction(QualType T)
28{
29  if (const PointerType *PtrTy = T->getAs<PointerType>())
30    T = PtrTy->getPointeeType();
31  else if (const ReferenceType *RefTy = T->getAs<ReferenceType>())
32    T = RefTy->getPointeeType();
33  else if (const MemberPointerType *MPTy = T->getAs<MemberPointerType>())
34    T = MPTy->getPointeeType();
35  return T->getAs<FunctionProtoType>();
36}
37
38/// CheckSpecifiedExceptionType - Check if the given type is valid in an
39/// exception specification. Incomplete types, or pointers to incomplete types
40/// other than void are not allowed.
41bool Sema::CheckSpecifiedExceptionType(QualType T, const SourceRange &Range) {
42
43  // This check (and the similar one below) deals with issue 437, that changes
44  // C++ 9.2p2 this way:
45  // Within the class member-specification, the class is regarded as complete
46  // within function bodies, default arguments, exception-specifications, and
47  // constructor ctor-initializers (including such things in nested classes).
48  if (T->isRecordType() && T->getAs<RecordType>()->isBeingDefined())
49    return false;
50
51  // C++ 15.4p2: A type denoted in an exception-specification shall not denote
52  //   an incomplete type.
53  if (RequireCompleteType(Range.getBegin(), T,
54                          diag::err_incomplete_in_exception_spec,
55                          /*direct*/0, Range))
56    return true;
57
58  // C++ 15.4p2: A type denoted in an exception-specification shall not denote
59  //   an incomplete type a pointer or reference to an incomplete type, other
60  //   than (cv) void*.
61  int kind;
62  if (const PointerType* IT = T->getAs<PointerType>()) {
63    T = IT->getPointeeType();
64    kind = 1;
65  } else if (const ReferenceType* IT = T->getAs<ReferenceType>()) {
66    T = IT->getPointeeType();
67    kind = 2;
68  } else
69    return false;
70
71  // Again as before
72  if (T->isRecordType() && T->getAs<RecordType>()->isBeingDefined())
73    return false;
74
75  if (!T->isVoidType() &&
76      RequireCompleteType(Range.getBegin(), T,
77                          diag::err_incomplete_in_exception_spec, kind, Range))
78    return true;
79
80  return false;
81}
82
83/// CheckDistantExceptionSpec - Check if the given type is a pointer or pointer
84/// to member to a function with an exception specification. This means that
85/// it is invalid to add another level of indirection.
86bool Sema::CheckDistantExceptionSpec(QualType T) {
87  if (const PointerType *PT = T->getAs<PointerType>())
88    T = PT->getPointeeType();
89  else if (const MemberPointerType *PT = T->getAs<MemberPointerType>())
90    T = PT->getPointeeType();
91  else
92    return false;
93
94  const FunctionProtoType *FnT = T->getAs<FunctionProtoType>();
95  if (!FnT)
96    return false;
97
98  return FnT->hasExceptionSpec();
99}
100
101const FunctionProtoType *
102Sema::ResolveExceptionSpec(SourceLocation Loc, const FunctionProtoType *FPT) {
103  if (!isUnresolvedExceptionSpec(FPT->getExceptionSpecType()))
104    return FPT;
105
106  FunctionDecl *SourceDecl = FPT->getExceptionSpecDecl();
107  const FunctionProtoType *SourceFPT =
108      SourceDecl->getType()->castAs<FunctionProtoType>();
109
110  // If the exception specification has already been resolved, just return it.
111  if (!isUnresolvedExceptionSpec(SourceFPT->getExceptionSpecType()))
112    return SourceFPT;
113
114  // Compute or instantiate the exception specification now.
115  if (FPT->getExceptionSpecType() == EST_Unevaluated)
116    EvaluateImplicitExceptionSpec(Loc, cast<CXXMethodDecl>(SourceDecl));
117  else
118    InstantiateExceptionSpec(Loc, SourceDecl);
119
120  return SourceDecl->getType()->castAs<FunctionProtoType>();
121}
122
123/// Determine whether a function has an implicitly-generated exception
124/// specification.
125static bool hasImplicitExceptionSpec(FunctionDecl *Decl) {
126  if (!isa<CXXDestructorDecl>(Decl) &&
127      Decl->getDeclName().getCXXOverloadedOperator() != OO_Delete &&
128      Decl->getDeclName().getCXXOverloadedOperator() != OO_Array_Delete)
129    return false;
130
131  // If the user didn't declare the function, its exception specification must
132  // be implicit.
133  if (!Decl->getTypeSourceInfo())
134    return true;
135
136  const FunctionProtoType *Ty =
137    Decl->getTypeSourceInfo()->getType()->getAs<FunctionProtoType>();
138  return !Ty->hasExceptionSpec();
139}
140
141bool Sema::CheckEquivalentExceptionSpec(FunctionDecl *Old, FunctionDecl *New) {
142  OverloadedOperatorKind OO = New->getDeclName().getCXXOverloadedOperator();
143  bool IsOperatorNew = OO == OO_New || OO == OO_Array_New;
144  bool MissingExceptionSpecification = false;
145  bool MissingEmptyExceptionSpecification = false;
146  unsigned DiagID = diag::err_mismatched_exception_spec;
147  if (getLangOpts().MicrosoftExt)
148    DiagID = diag::warn_mismatched_exception_spec;
149
150  // Check the types as written: they must match before any exception
151  // specification adjustment is applied.
152  if (!CheckEquivalentExceptionSpec(
153        PDiag(DiagID), PDiag(diag::note_previous_declaration),
154        Old->getType()->getAs<FunctionProtoType>(), Old->getLocation(),
155        New->getType()->getAs<FunctionProtoType>(), New->getLocation(),
156        &MissingExceptionSpecification, &MissingEmptyExceptionSpecification,
157        /*AllowNoexceptAllMatchWithNoSpec=*/true, IsOperatorNew)) {
158    // C++11 [except.spec]p4 [DR1492]:
159    //   If a declaration of a function has an implicit
160    //   exception-specification, other declarations of the function shall
161    //   not specify an exception-specification.
162    if (getLangOpts().CPlusPlus0x &&
163        hasImplicitExceptionSpec(Old) != hasImplicitExceptionSpec(New)) {
164      Diag(New->getLocation(), diag::ext_implicit_exception_spec_mismatch)
165        << hasImplicitExceptionSpec(Old);
166      if (!Old->getLocation().isInvalid())
167        Diag(Old->getLocation(), diag::note_previous_declaration);
168    }
169    return false;
170  }
171
172  // The failure was something other than an empty exception
173  // specification; return an error.
174  if (!MissingExceptionSpecification && !MissingEmptyExceptionSpecification)
175    return true;
176
177  const FunctionProtoType *NewProto =
178    New->getType()->getAs<FunctionProtoType>();
179
180  // The new function declaration is only missing an empty exception
181  // specification "throw()". If the throw() specification came from a
182  // function in a system header that has C linkage, just add an empty
183  // exception specification to the "new" declaration. This is an
184  // egregious workaround for glibc, which adds throw() specifications
185  // to many libc functions as an optimization. Unfortunately, that
186  // optimization isn't permitted by the C++ standard, so we're forced
187  // to work around it here.
188  if (MissingEmptyExceptionSpecification && NewProto &&
189      (Old->getLocation().isInvalid() ||
190       Context.getSourceManager().isInSystemHeader(Old->getLocation())) &&
191      Old->isExternC()) {
192    FunctionProtoType::ExtProtoInfo EPI = NewProto->getExtProtoInfo();
193    EPI.ExceptionSpecType = EST_DynamicNone;
194    QualType NewType = Context.getFunctionType(NewProto->getResultType(),
195                                               NewProto->arg_type_begin(),
196                                               NewProto->getNumArgs(),
197                                               EPI);
198    New->setType(NewType);
199    return false;
200  }
201
202  if (MissingExceptionSpecification && NewProto) {
203    const FunctionProtoType *OldProto =
204      Old->getType()->getAs<FunctionProtoType>();
205
206    FunctionProtoType::ExtProtoInfo EPI = NewProto->getExtProtoInfo();
207    EPI.ExceptionSpecType = OldProto->getExceptionSpecType();
208    if (EPI.ExceptionSpecType == EST_Dynamic) {
209      EPI.NumExceptions = OldProto->getNumExceptions();
210      EPI.Exceptions = OldProto->exception_begin();
211    } else if (EPI.ExceptionSpecType == EST_ComputedNoexcept) {
212      // FIXME: We can't just take the expression from the old prototype. It
213      // likely contains references to the old prototype's parameters.
214    }
215
216    // Update the type of the function with the appropriate exception
217    // specification.
218    QualType NewType = Context.getFunctionType(NewProto->getResultType(),
219                                               NewProto->arg_type_begin(),
220                                               NewProto->getNumArgs(),
221                                               EPI);
222    New->setType(NewType);
223
224    // If exceptions are disabled, suppress the warning about missing
225    // exception specifications for new and delete operators.
226    if (!getLangOpts().CXXExceptions) {
227      switch (New->getDeclName().getCXXOverloadedOperator()) {
228      case OO_New:
229      case OO_Array_New:
230      case OO_Delete:
231      case OO_Array_Delete:
232        if (New->getDeclContext()->isTranslationUnit())
233          return false;
234        break;
235
236      default:
237        break;
238      }
239    }
240
241    // Warn about the lack of exception specification.
242    SmallString<128> ExceptionSpecString;
243    llvm::raw_svector_ostream OS(ExceptionSpecString);
244    switch (OldProto->getExceptionSpecType()) {
245    case EST_DynamicNone:
246      OS << "throw()";
247      break;
248
249    case EST_Dynamic: {
250      OS << "throw(";
251      bool OnFirstException = true;
252      for (FunctionProtoType::exception_iterator E = OldProto->exception_begin(),
253                                              EEnd = OldProto->exception_end();
254           E != EEnd;
255           ++E) {
256        if (OnFirstException)
257          OnFirstException = false;
258        else
259          OS << ", ";
260
261        OS << E->getAsString(getPrintingPolicy());
262      }
263      OS << ")";
264      break;
265    }
266
267    case EST_BasicNoexcept:
268      OS << "noexcept";
269      break;
270
271    case EST_ComputedNoexcept:
272      OS << "noexcept(";
273      OldProto->getNoexceptExpr()->printPretty(OS, 0, getPrintingPolicy());
274      OS << ")";
275      break;
276
277    default:
278      llvm_unreachable("This spec type is compatible with none.");
279    }
280    OS.flush();
281
282    SourceLocation FixItLoc;
283    if (TypeSourceInfo *TSInfo = New->getTypeSourceInfo()) {
284      TypeLoc TL = TSInfo->getTypeLoc().IgnoreParens();
285      if (const FunctionTypeLoc *FTLoc = dyn_cast<FunctionTypeLoc>(&TL))
286        FixItLoc = PP.getLocForEndOfToken(FTLoc->getLocalRangeEnd());
287    }
288
289    if (FixItLoc.isInvalid())
290      Diag(New->getLocation(), diag::warn_missing_exception_specification)
291        << New << OS.str();
292    else {
293      // FIXME: This will get more complicated with C++0x
294      // late-specified return types.
295      Diag(New->getLocation(), diag::warn_missing_exception_specification)
296        << New << OS.str()
297        << FixItHint::CreateInsertion(FixItLoc, " " + OS.str().str());
298    }
299
300    if (!Old->getLocation().isInvalid())
301      Diag(Old->getLocation(), diag::note_previous_declaration);
302
303    return false;
304  }
305
306  Diag(New->getLocation(), DiagID);
307  Diag(Old->getLocation(), diag::note_previous_declaration);
308  return true;
309}
310
311/// CheckEquivalentExceptionSpec - Check if the two types have equivalent
312/// exception specifications. Exception specifications are equivalent if
313/// they allow exactly the same set of exception types. It does not matter how
314/// that is achieved. See C++ [except.spec]p2.
315bool Sema::CheckEquivalentExceptionSpec(
316    const FunctionProtoType *Old, SourceLocation OldLoc,
317    const FunctionProtoType *New, SourceLocation NewLoc) {
318  unsigned DiagID = diag::err_mismatched_exception_spec;
319  if (getLangOpts().MicrosoftExt)
320    DiagID = diag::warn_mismatched_exception_spec;
321  return CheckEquivalentExceptionSpec(PDiag(DiagID),
322                                      PDiag(diag::note_previous_declaration),
323                                      Old, OldLoc, New, NewLoc);
324}
325
326/// CheckEquivalentExceptionSpec - Check if the two types have compatible
327/// exception specifications. See C++ [except.spec]p3.
328///
329/// \return \c false if the exception specifications match, \c true if there is
330/// a problem. If \c true is returned, either a diagnostic has already been
331/// produced or \c *MissingExceptionSpecification is set to \c true.
332bool Sema::CheckEquivalentExceptionSpec(const PartialDiagnostic &DiagID,
333                                        const PartialDiagnostic & NoteID,
334                                        const FunctionProtoType *Old,
335                                        SourceLocation OldLoc,
336                                        const FunctionProtoType *New,
337                                        SourceLocation NewLoc,
338                                        bool *MissingExceptionSpecification,
339                                        bool*MissingEmptyExceptionSpecification,
340                                        bool AllowNoexceptAllMatchWithNoSpec,
341                                        bool IsOperatorNew) {
342  // Just completely ignore this under -fno-exceptions.
343  if (!getLangOpts().CXXExceptions)
344    return false;
345
346  if (MissingExceptionSpecification)
347    *MissingExceptionSpecification = false;
348
349  if (MissingEmptyExceptionSpecification)
350    *MissingEmptyExceptionSpecification = false;
351
352  Old = ResolveExceptionSpec(NewLoc, Old);
353  if (!Old)
354    return false;
355  New = ResolveExceptionSpec(NewLoc, New);
356  if (!New)
357    return false;
358
359  // C++0x [except.spec]p3: Two exception-specifications are compatible if:
360  //   - both are non-throwing, regardless of their form,
361  //   - both have the form noexcept(constant-expression) and the constant-
362  //     expressions are equivalent,
363  //   - both are dynamic-exception-specifications that have the same set of
364  //     adjusted types.
365  //
366  // C++0x [except.spec]p12: An exception-specifcation is non-throwing if it is
367  //   of the form throw(), noexcept, or noexcept(constant-expression) where the
368  //   constant-expression yields true.
369  //
370  // C++0x [except.spec]p4: If any declaration of a function has an exception-
371  //   specifier that is not a noexcept-specification allowing all exceptions,
372  //   all declarations [...] of that function shall have a compatible
373  //   exception-specification.
374  //
375  // That last point basically means that noexcept(false) matches no spec.
376  // It's considered when AllowNoexceptAllMatchWithNoSpec is true.
377
378  ExceptionSpecificationType OldEST = Old->getExceptionSpecType();
379  ExceptionSpecificationType NewEST = New->getExceptionSpecType();
380
381  assert(!isUnresolvedExceptionSpec(OldEST) &&
382         !isUnresolvedExceptionSpec(NewEST) &&
383         "Shouldn't see unknown exception specifications here");
384
385  // Shortcut the case where both have no spec.
386  if (OldEST == EST_None && NewEST == EST_None)
387    return false;
388
389  FunctionProtoType::NoexceptResult OldNR = Old->getNoexceptSpec(Context);
390  FunctionProtoType::NoexceptResult NewNR = New->getNoexceptSpec(Context);
391  if (OldNR == FunctionProtoType::NR_BadNoexcept ||
392      NewNR == FunctionProtoType::NR_BadNoexcept)
393    return false;
394
395  // Dependent noexcept specifiers are compatible with each other, but nothing
396  // else.
397  // One noexcept is compatible with another if the argument is the same
398  if (OldNR == NewNR &&
399      OldNR != FunctionProtoType::NR_NoNoexcept &&
400      NewNR != FunctionProtoType::NR_NoNoexcept)
401    return false;
402  if (OldNR != NewNR &&
403      OldNR != FunctionProtoType::NR_NoNoexcept &&
404      NewNR != FunctionProtoType::NR_NoNoexcept) {
405    Diag(NewLoc, DiagID);
406    if (NoteID.getDiagID() != 0)
407      Diag(OldLoc, NoteID);
408    return true;
409  }
410
411  // The MS extension throw(...) is compatible with itself.
412  if (OldEST == EST_MSAny && NewEST == EST_MSAny)
413    return false;
414
415  // It's also compatible with no spec.
416  if ((OldEST == EST_None && NewEST == EST_MSAny) ||
417      (OldEST == EST_MSAny && NewEST == EST_None))
418    return false;
419
420  // It's also compatible with noexcept(false).
421  if (OldEST == EST_MSAny && NewNR == FunctionProtoType::NR_Throw)
422    return false;
423  if (NewEST == EST_MSAny && OldNR == FunctionProtoType::NR_Throw)
424    return false;
425
426  // As described above, noexcept(false) matches no spec only for functions.
427  if (AllowNoexceptAllMatchWithNoSpec) {
428    if (OldEST == EST_None && NewNR == FunctionProtoType::NR_Throw)
429      return false;
430    if (NewEST == EST_None && OldNR == FunctionProtoType::NR_Throw)
431      return false;
432  }
433
434  // Any non-throwing specifications are compatible.
435  bool OldNonThrowing = OldNR == FunctionProtoType::NR_Nothrow ||
436                        OldEST == EST_DynamicNone;
437  bool NewNonThrowing = NewNR == FunctionProtoType::NR_Nothrow ||
438                        NewEST == EST_DynamicNone;
439  if (OldNonThrowing && NewNonThrowing)
440    return false;
441
442  // As a special compatibility feature, under C++0x we accept no spec and
443  // throw(std::bad_alloc) as equivalent for operator new and operator new[].
444  // This is because the implicit declaration changed, but old code would break.
445  if (getLangOpts().CPlusPlus0x && IsOperatorNew) {
446    const FunctionProtoType *WithExceptions = 0;
447    if (OldEST == EST_None && NewEST == EST_Dynamic)
448      WithExceptions = New;
449    else if (OldEST == EST_Dynamic && NewEST == EST_None)
450      WithExceptions = Old;
451    if (WithExceptions && WithExceptions->getNumExceptions() == 1) {
452      // One has no spec, the other throw(something). If that something is
453      // std::bad_alloc, all conditions are met.
454      QualType Exception = *WithExceptions->exception_begin();
455      if (CXXRecordDecl *ExRecord = Exception->getAsCXXRecordDecl()) {
456        IdentifierInfo* Name = ExRecord->getIdentifier();
457        if (Name && Name->getName() == "bad_alloc") {
458          // It's called bad_alloc, but is it in std?
459          DeclContext* DC = ExRecord->getDeclContext();
460          DC = DC->getEnclosingNamespaceContext();
461          if (NamespaceDecl* NS = dyn_cast<NamespaceDecl>(DC)) {
462            IdentifierInfo* NSName = NS->getIdentifier();
463            DC = DC->getParent();
464            if (NSName && NSName->getName() == "std" &&
465                DC->getEnclosingNamespaceContext()->isTranslationUnit()) {
466              return false;
467            }
468          }
469        }
470      }
471    }
472  }
473
474  // At this point, the only remaining valid case is two matching dynamic
475  // specifications. We return here unless both specifications are dynamic.
476  if (OldEST != EST_Dynamic || NewEST != EST_Dynamic) {
477    if (MissingExceptionSpecification && Old->hasExceptionSpec() &&
478        !New->hasExceptionSpec()) {
479      // The old type has an exception specification of some sort, but
480      // the new type does not.
481      *MissingExceptionSpecification = true;
482
483      if (MissingEmptyExceptionSpecification && OldNonThrowing) {
484        // The old type has a throw() or noexcept(true) exception specification
485        // and the new type has no exception specification, and the caller asked
486        // to handle this itself.
487        *MissingEmptyExceptionSpecification = true;
488      }
489
490      return true;
491    }
492
493    Diag(NewLoc, DiagID);
494    if (NoteID.getDiagID() != 0)
495      Diag(OldLoc, NoteID);
496    return true;
497  }
498
499  assert(OldEST == EST_Dynamic && NewEST == EST_Dynamic &&
500      "Exception compatibility logic error: non-dynamic spec slipped through.");
501
502  bool Success = true;
503  // Both have a dynamic exception spec. Collect the first set, then compare
504  // to the second.
505  llvm::SmallPtrSet<CanQualType, 8> OldTypes, NewTypes;
506  for (FunctionProtoType::exception_iterator I = Old->exception_begin(),
507       E = Old->exception_end(); I != E; ++I)
508    OldTypes.insert(Context.getCanonicalType(*I).getUnqualifiedType());
509
510  for (FunctionProtoType::exception_iterator I = New->exception_begin(),
511       E = New->exception_end(); I != E && Success; ++I) {
512    CanQualType TypePtr = Context.getCanonicalType(*I).getUnqualifiedType();
513    if(OldTypes.count(TypePtr))
514      NewTypes.insert(TypePtr);
515    else
516      Success = false;
517  }
518
519  Success = Success && OldTypes.size() == NewTypes.size();
520
521  if (Success) {
522    return false;
523  }
524  Diag(NewLoc, DiagID);
525  if (NoteID.getDiagID() != 0)
526    Diag(OldLoc, NoteID);
527  return true;
528}
529
530/// CheckExceptionSpecSubset - Check whether the second function type's
531/// exception specification is a subset (or equivalent) of the first function
532/// type. This is used by override and pointer assignment checks.
533bool Sema::CheckExceptionSpecSubset(
534    const PartialDiagnostic &DiagID, const PartialDiagnostic & NoteID,
535    const FunctionProtoType *Superset, SourceLocation SuperLoc,
536    const FunctionProtoType *Subset, SourceLocation SubLoc) {
537
538  // Just auto-succeed under -fno-exceptions.
539  if (!getLangOpts().CXXExceptions)
540    return false;
541
542  // FIXME: As usual, we could be more specific in our error messages, but
543  // that better waits until we've got types with source locations.
544
545  if (!SubLoc.isValid())
546    SubLoc = SuperLoc;
547
548  // Resolve the exception specifications, if needed.
549  Superset = ResolveExceptionSpec(SuperLoc, Superset);
550  if (!Superset)
551    return false;
552  Subset = ResolveExceptionSpec(SubLoc, Subset);
553  if (!Subset)
554    return false;
555
556  ExceptionSpecificationType SuperEST = Superset->getExceptionSpecType();
557
558  // If superset contains everything, we're done.
559  if (SuperEST == EST_None || SuperEST == EST_MSAny)
560    return CheckParamExceptionSpec(NoteID, Superset, SuperLoc, Subset, SubLoc);
561
562  // If there are dependent noexcept specs, assume everything is fine. Unlike
563  // with the equivalency check, this is safe in this case, because we don't
564  // want to merge declarations. Checks after instantiation will catch any
565  // omissions we make here.
566  // We also shortcut checking if a noexcept expression was bad.
567
568  FunctionProtoType::NoexceptResult SuperNR =Superset->getNoexceptSpec(Context);
569  if (SuperNR == FunctionProtoType::NR_BadNoexcept ||
570      SuperNR == FunctionProtoType::NR_Dependent)
571    return false;
572
573  // Another case of the superset containing everything.
574  if (SuperNR == FunctionProtoType::NR_Throw)
575    return CheckParamExceptionSpec(NoteID, Superset, SuperLoc, Subset, SubLoc);
576
577  ExceptionSpecificationType SubEST = Subset->getExceptionSpecType();
578
579  assert(!isUnresolvedExceptionSpec(SuperEST) &&
580         !isUnresolvedExceptionSpec(SubEST) &&
581         "Shouldn't see unknown exception specifications here");
582
583  // It does not. If the subset contains everything, we've failed.
584  if (SubEST == EST_None || SubEST == EST_MSAny) {
585    Diag(SubLoc, DiagID);
586    if (NoteID.getDiagID() != 0)
587      Diag(SuperLoc, NoteID);
588    return true;
589  }
590
591  FunctionProtoType::NoexceptResult SubNR = Subset->getNoexceptSpec(Context);
592  if (SubNR == FunctionProtoType::NR_BadNoexcept ||
593      SubNR == FunctionProtoType::NR_Dependent)
594    return false;
595
596  // Another case of the subset containing everything.
597  if (SubNR == FunctionProtoType::NR_Throw) {
598    Diag(SubLoc, DiagID);
599    if (NoteID.getDiagID() != 0)
600      Diag(SuperLoc, NoteID);
601    return true;
602  }
603
604  // If the subset contains nothing, we're done.
605  if (SubEST == EST_DynamicNone || SubNR == FunctionProtoType::NR_Nothrow)
606    return CheckParamExceptionSpec(NoteID, Superset, SuperLoc, Subset, SubLoc);
607
608  // Otherwise, if the superset contains nothing, we've failed.
609  if (SuperEST == EST_DynamicNone || SuperNR == FunctionProtoType::NR_Nothrow) {
610    Diag(SubLoc, DiagID);
611    if (NoteID.getDiagID() != 0)
612      Diag(SuperLoc, NoteID);
613    return true;
614  }
615
616  assert(SuperEST == EST_Dynamic && SubEST == EST_Dynamic &&
617         "Exception spec subset: non-dynamic case slipped through.");
618
619  // Neither contains everything or nothing. Do a proper comparison.
620  for (FunctionProtoType::exception_iterator SubI = Subset->exception_begin(),
621       SubE = Subset->exception_end(); SubI != SubE; ++SubI) {
622    // Take one type from the subset.
623    QualType CanonicalSubT = Context.getCanonicalType(*SubI);
624    // Unwrap pointers and references so that we can do checks within a class
625    // hierarchy. Don't unwrap member pointers; they don't have hierarchy
626    // conversions on the pointee.
627    bool SubIsPointer = false;
628    if (const ReferenceType *RefTy = CanonicalSubT->getAs<ReferenceType>())
629      CanonicalSubT = RefTy->getPointeeType();
630    if (const PointerType *PtrTy = CanonicalSubT->getAs<PointerType>()) {
631      CanonicalSubT = PtrTy->getPointeeType();
632      SubIsPointer = true;
633    }
634    bool SubIsClass = CanonicalSubT->isRecordType();
635    CanonicalSubT = CanonicalSubT.getLocalUnqualifiedType();
636
637    CXXBasePaths Paths(/*FindAmbiguities=*/true, /*RecordPaths=*/true,
638                       /*DetectVirtual=*/false);
639
640    bool Contained = false;
641    // Make sure it's in the superset.
642    for (FunctionProtoType::exception_iterator SuperI =
643           Superset->exception_begin(), SuperE = Superset->exception_end();
644         SuperI != SuperE; ++SuperI) {
645      QualType CanonicalSuperT = Context.getCanonicalType(*SuperI);
646      // SubT must be SuperT or derived from it, or pointer or reference to
647      // such types.
648      if (const ReferenceType *RefTy = CanonicalSuperT->getAs<ReferenceType>())
649        CanonicalSuperT = RefTy->getPointeeType();
650      if (SubIsPointer) {
651        if (const PointerType *PtrTy = CanonicalSuperT->getAs<PointerType>())
652          CanonicalSuperT = PtrTy->getPointeeType();
653        else {
654          continue;
655        }
656      }
657      CanonicalSuperT = CanonicalSuperT.getLocalUnqualifiedType();
658      // If the types are the same, move on to the next type in the subset.
659      if (CanonicalSubT == CanonicalSuperT) {
660        Contained = true;
661        break;
662      }
663
664      // Otherwise we need to check the inheritance.
665      if (!SubIsClass || !CanonicalSuperT->isRecordType())
666        continue;
667
668      Paths.clear();
669      if (!IsDerivedFrom(CanonicalSubT, CanonicalSuperT, Paths))
670        continue;
671
672      if (Paths.isAmbiguous(Context.getCanonicalType(CanonicalSuperT)))
673        continue;
674
675      // Do this check from a context without privileges.
676      switch (CheckBaseClassAccess(SourceLocation(),
677                                   CanonicalSuperT, CanonicalSubT,
678                                   Paths.front(),
679                                   /*Diagnostic*/ 0,
680                                   /*ForceCheck*/ true,
681                                   /*ForceUnprivileged*/ true)) {
682      case AR_accessible: break;
683      case AR_inaccessible: continue;
684      case AR_dependent:
685        llvm_unreachable("access check dependent for unprivileged context");
686      case AR_delayed:
687        llvm_unreachable("access check delayed in non-declaration");
688      }
689
690      Contained = true;
691      break;
692    }
693    if (!Contained) {
694      Diag(SubLoc, DiagID);
695      if (NoteID.getDiagID() != 0)
696        Diag(SuperLoc, NoteID);
697      return true;
698    }
699  }
700  // We've run half the gauntlet.
701  return CheckParamExceptionSpec(NoteID, Superset, SuperLoc, Subset, SubLoc);
702}
703
704static bool CheckSpecForTypesEquivalent(Sema &S,
705    const PartialDiagnostic &DiagID, const PartialDiagnostic & NoteID,
706    QualType Target, SourceLocation TargetLoc,
707    QualType Source, SourceLocation SourceLoc)
708{
709  const FunctionProtoType *TFunc = GetUnderlyingFunction(Target);
710  if (!TFunc)
711    return false;
712  const FunctionProtoType *SFunc = GetUnderlyingFunction(Source);
713  if (!SFunc)
714    return false;
715
716  return S.CheckEquivalentExceptionSpec(DiagID, NoteID, TFunc, TargetLoc,
717                                        SFunc, SourceLoc);
718}
719
720/// CheckParamExceptionSpec - Check if the parameter and return types of the
721/// two functions have equivalent exception specs. This is part of the
722/// assignment and override compatibility check. We do not check the parameters
723/// of parameter function pointers recursively, as no sane programmer would
724/// even be able to write such a function type.
725bool Sema::CheckParamExceptionSpec(const PartialDiagnostic & NoteID,
726    const FunctionProtoType *Target, SourceLocation TargetLoc,
727    const FunctionProtoType *Source, SourceLocation SourceLoc)
728{
729  if (CheckSpecForTypesEquivalent(*this,
730                           PDiag(diag::err_deep_exception_specs_differ) << 0,
731                                  PDiag(),
732                                  Target->getResultType(), TargetLoc,
733                                  Source->getResultType(), SourceLoc))
734    return true;
735
736  // We shouldn't even be testing this unless the arguments are otherwise
737  // compatible.
738  assert(Target->getNumArgs() == Source->getNumArgs() &&
739         "Functions have different argument counts.");
740  for (unsigned i = 0, E = Target->getNumArgs(); i != E; ++i) {
741    if (CheckSpecForTypesEquivalent(*this,
742                           PDiag(diag::err_deep_exception_specs_differ) << 1,
743                                    PDiag(),
744                                    Target->getArgType(i), TargetLoc,
745                                    Source->getArgType(i), SourceLoc))
746      return true;
747  }
748  return false;
749}
750
751bool Sema::CheckExceptionSpecCompatibility(Expr *From, QualType ToType)
752{
753  // First we check for applicability.
754  // Target type must be a function, function pointer or function reference.
755  const FunctionProtoType *ToFunc = GetUnderlyingFunction(ToType);
756  if (!ToFunc)
757    return false;
758
759  // SourceType must be a function or function pointer.
760  const FunctionProtoType *FromFunc = GetUnderlyingFunction(From->getType());
761  if (!FromFunc)
762    return false;
763
764  // Now we've got the correct types on both sides, check their compatibility.
765  // This means that the source of the conversion can only throw a subset of
766  // the exceptions of the target, and any exception specs on arguments or
767  // return types must be equivalent.
768  return CheckExceptionSpecSubset(PDiag(diag::err_incompatible_exception_specs),
769                                  PDiag(), ToFunc,
770                                  From->getSourceRange().getBegin(),
771                                  FromFunc, SourceLocation());
772}
773
774bool Sema::CheckOverridingFunctionExceptionSpec(const CXXMethodDecl *New,
775                                                const CXXMethodDecl *Old) {
776  if (getLangOpts().CPlusPlus0x && isa<CXXDestructorDecl>(New)) {
777    // Don't check uninstantiated template destructors at all. We can only
778    // synthesize correct specs after the template is instantiated.
779    if (New->getParent()->isDependentType())
780      return false;
781    if (New->getParent()->isBeingDefined()) {
782      // The destructor might be updated once the definition is finished. So
783      // remember it and check later.
784      DelayedDestructorExceptionSpecChecks.push_back(std::make_pair(
785        cast<CXXDestructorDecl>(New), cast<CXXDestructorDecl>(Old)));
786      return false;
787    }
788  }
789  unsigned DiagID = diag::err_override_exception_spec;
790  if (getLangOpts().MicrosoftExt)
791    DiagID = diag::warn_override_exception_spec;
792  return CheckExceptionSpecSubset(PDiag(DiagID),
793                                  PDiag(diag::note_overridden_virtual_function),
794                                  Old->getType()->getAs<FunctionProtoType>(),
795                                  Old->getLocation(),
796                                  New->getType()->getAs<FunctionProtoType>(),
797                                  New->getLocation());
798}
799
800static CanThrowResult canSubExprsThrow(Sema &S, const Expr *CE) {
801  Expr *E = const_cast<Expr*>(CE);
802  CanThrowResult R = CT_Cannot;
803  for (Expr::child_range I = E->children(); I && R != CT_Can; ++I)
804    R = mergeCanThrow(R, S.canThrow(cast<Expr>(*I)));
805  return R;
806}
807
808static CanThrowResult canCalleeThrow(Sema &S, const Expr *E,
809                                           const Decl *D,
810                                           bool NullThrows = true) {
811  if (!D)
812    return NullThrows ? CT_Can : CT_Cannot;
813
814  // See if we can get a function type from the decl somehow.
815  const ValueDecl *VD = dyn_cast<ValueDecl>(D);
816  if (!VD) // If we have no clue what we're calling, assume the worst.
817    return CT_Can;
818
819  // As an extension, we assume that __attribute__((nothrow)) functions don't
820  // throw.
821  if (isa<FunctionDecl>(D) && D->hasAttr<NoThrowAttr>())
822    return CT_Cannot;
823
824  QualType T = VD->getType();
825  const FunctionProtoType *FT;
826  if ((FT = T->getAs<FunctionProtoType>())) {
827  } else if (const PointerType *PT = T->getAs<PointerType>())
828    FT = PT->getPointeeType()->getAs<FunctionProtoType>();
829  else if (const ReferenceType *RT = T->getAs<ReferenceType>())
830    FT = RT->getPointeeType()->getAs<FunctionProtoType>();
831  else if (const MemberPointerType *MT = T->getAs<MemberPointerType>())
832    FT = MT->getPointeeType()->getAs<FunctionProtoType>();
833  else if (const BlockPointerType *BT = T->getAs<BlockPointerType>())
834    FT = BT->getPointeeType()->getAs<FunctionProtoType>();
835
836  if (!FT)
837    return CT_Can;
838
839  FT = S.ResolveExceptionSpec(E->getLocStart(), FT);
840  if (!FT)
841    return CT_Can;
842
843  return FT->isNothrow(S.Context) ? CT_Cannot : CT_Can;
844}
845
846static CanThrowResult canDynamicCastThrow(const CXXDynamicCastExpr *DC) {
847  if (DC->isTypeDependent())
848    return CT_Dependent;
849
850  if (!DC->getTypeAsWritten()->isReferenceType())
851    return CT_Cannot;
852
853  if (DC->getSubExpr()->isTypeDependent())
854    return CT_Dependent;
855
856  return DC->getCastKind() == clang::CK_Dynamic? CT_Can : CT_Cannot;
857}
858
859static CanThrowResult canTypeidThrow(Sema &S, const CXXTypeidExpr *DC) {
860  if (DC->isTypeOperand())
861    return CT_Cannot;
862
863  Expr *Op = DC->getExprOperand();
864  if (Op->isTypeDependent())
865    return CT_Dependent;
866
867  const RecordType *RT = Op->getType()->getAs<RecordType>();
868  if (!RT)
869    return CT_Cannot;
870
871  if (!cast<CXXRecordDecl>(RT->getDecl())->isPolymorphic())
872    return CT_Cannot;
873
874  if (Op->Classify(S.Context).isPRValue())
875    return CT_Cannot;
876
877  return CT_Can;
878}
879
880CanThrowResult Sema::canThrow(const Expr *E) {
881  // C++ [expr.unary.noexcept]p3:
882  //   [Can throw] if in a potentially-evaluated context the expression would
883  //   contain:
884  switch (E->getStmtClass()) {
885  case Expr::CXXThrowExprClass:
886    //   - a potentially evaluated throw-expression
887    return CT_Can;
888
889  case Expr::CXXDynamicCastExprClass: {
890    //   - a potentially evaluated dynamic_cast expression dynamic_cast<T>(v),
891    //     where T is a reference type, that requires a run-time check
892    CanThrowResult CT = canDynamicCastThrow(cast<CXXDynamicCastExpr>(E));
893    if (CT == CT_Can)
894      return CT;
895    return mergeCanThrow(CT, canSubExprsThrow(*this, E));
896  }
897
898  case Expr::CXXTypeidExprClass:
899    //   - a potentially evaluated typeid expression applied to a glvalue
900    //     expression whose type is a polymorphic class type
901    return canTypeidThrow(*this, cast<CXXTypeidExpr>(E));
902
903    //   - a potentially evaluated call to a function, member function, function
904    //     pointer, or member function pointer that does not have a non-throwing
905    //     exception-specification
906  case Expr::CallExprClass:
907  case Expr::CXXMemberCallExprClass:
908  case Expr::CXXOperatorCallExprClass:
909  case Expr::UserDefinedLiteralClass: {
910    const CallExpr *CE = cast<CallExpr>(E);
911    CanThrowResult CT;
912    if (E->isTypeDependent())
913      CT = CT_Dependent;
914    else if (isa<CXXPseudoDestructorExpr>(CE->getCallee()->IgnoreParens()))
915      CT = CT_Cannot;
916    else
917      CT = canCalleeThrow(*this, E, CE->getCalleeDecl());
918    if (CT == CT_Can)
919      return CT;
920    return mergeCanThrow(CT, canSubExprsThrow(*this, E));
921  }
922
923  case Expr::CXXConstructExprClass:
924  case Expr::CXXTemporaryObjectExprClass: {
925    CanThrowResult CT = canCalleeThrow(*this, E,
926        cast<CXXConstructExpr>(E)->getConstructor());
927    if (CT == CT_Can)
928      return CT;
929    return mergeCanThrow(CT, canSubExprsThrow(*this, E));
930  }
931
932  case Expr::LambdaExprClass: {
933    const LambdaExpr *Lambda = cast<LambdaExpr>(E);
934    CanThrowResult CT = CT_Cannot;
935    for (LambdaExpr::capture_init_iterator Cap = Lambda->capture_init_begin(),
936                                        CapEnd = Lambda->capture_init_end();
937         Cap != CapEnd; ++Cap)
938      CT = mergeCanThrow(CT, canThrow(*Cap));
939    return CT;
940  }
941
942  case Expr::CXXNewExprClass: {
943    CanThrowResult CT;
944    if (E->isTypeDependent())
945      CT = CT_Dependent;
946    else
947      CT = canCalleeThrow(*this, E, cast<CXXNewExpr>(E)->getOperatorNew());
948    if (CT == CT_Can)
949      return CT;
950    return mergeCanThrow(CT, canSubExprsThrow(*this, E));
951  }
952
953  case Expr::CXXDeleteExprClass: {
954    CanThrowResult CT;
955    QualType DTy = cast<CXXDeleteExpr>(E)->getDestroyedType();
956    if (DTy.isNull() || DTy->isDependentType()) {
957      CT = CT_Dependent;
958    } else {
959      CT = canCalleeThrow(*this, E,
960                          cast<CXXDeleteExpr>(E)->getOperatorDelete());
961      if (const RecordType *RT = DTy->getAs<RecordType>()) {
962        const CXXRecordDecl *RD = cast<CXXRecordDecl>(RT->getDecl());
963        CT = mergeCanThrow(CT, canCalleeThrow(*this, E, RD->getDestructor()));
964      }
965      if (CT == CT_Can)
966        return CT;
967    }
968    return mergeCanThrow(CT, canSubExprsThrow(*this, E));
969  }
970
971  case Expr::CXXBindTemporaryExprClass: {
972    // The bound temporary has to be destroyed again, which might throw.
973    CanThrowResult CT = canCalleeThrow(*this, E,
974      cast<CXXBindTemporaryExpr>(E)->getTemporary()->getDestructor());
975    if (CT == CT_Can)
976      return CT;
977    return mergeCanThrow(CT, canSubExprsThrow(*this, E));
978  }
979
980    // ObjC message sends are like function calls, but never have exception
981    // specs.
982  case Expr::ObjCMessageExprClass:
983  case Expr::ObjCPropertyRefExprClass:
984  case Expr::ObjCSubscriptRefExprClass:
985    return CT_Can;
986
987    // All the ObjC literals that are implemented as calls are
988    // potentially throwing unless we decide to close off that
989    // possibility.
990  case Expr::ObjCArrayLiteralClass:
991  case Expr::ObjCDictionaryLiteralClass:
992  case Expr::ObjCBoxedExprClass:
993    return CT_Can;
994
995    // Many other things have subexpressions, so we have to test those.
996    // Some are simple:
997  case Expr::ConditionalOperatorClass:
998  case Expr::CompoundLiteralExprClass:
999  case Expr::CXXConstCastExprClass:
1000  case Expr::CXXDefaultArgExprClass:
1001  case Expr::CXXReinterpretCastExprClass:
1002  case Expr::DesignatedInitExprClass:
1003  case Expr::ExprWithCleanupsClass:
1004  case Expr::ExtVectorElementExprClass:
1005  case Expr::InitListExprClass:
1006  case Expr::MemberExprClass:
1007  case Expr::ObjCIsaExprClass:
1008  case Expr::ObjCIvarRefExprClass:
1009  case Expr::ParenExprClass:
1010  case Expr::ParenListExprClass:
1011  case Expr::ShuffleVectorExprClass:
1012  case Expr::VAArgExprClass:
1013    return canSubExprsThrow(*this, E);
1014
1015    // Some might be dependent for other reasons.
1016  case Expr::ArraySubscriptExprClass:
1017  case Expr::BinaryOperatorClass:
1018  case Expr::CompoundAssignOperatorClass:
1019  case Expr::CStyleCastExprClass:
1020  case Expr::CXXStaticCastExprClass:
1021  case Expr::CXXFunctionalCastExprClass:
1022  case Expr::ImplicitCastExprClass:
1023  case Expr::MaterializeTemporaryExprClass:
1024  case Expr::UnaryOperatorClass: {
1025    CanThrowResult CT = E->isTypeDependent() ? CT_Dependent : CT_Cannot;
1026    return mergeCanThrow(CT, canSubExprsThrow(*this, E));
1027  }
1028
1029    // FIXME: We should handle StmtExpr, but that opens a MASSIVE can of worms.
1030  case Expr::StmtExprClass:
1031    return CT_Can;
1032
1033  case Expr::ChooseExprClass:
1034    if (E->isTypeDependent() || E->isValueDependent())
1035      return CT_Dependent;
1036    return canThrow(cast<ChooseExpr>(E)->getChosenSubExpr(Context));
1037
1038  case Expr::GenericSelectionExprClass:
1039    if (cast<GenericSelectionExpr>(E)->isResultDependent())
1040      return CT_Dependent;
1041    return canThrow(cast<GenericSelectionExpr>(E)->getResultExpr());
1042
1043    // Some expressions are always dependent.
1044  case Expr::CXXDependentScopeMemberExprClass:
1045  case Expr::CXXUnresolvedConstructExprClass:
1046  case Expr::DependentScopeDeclRefExprClass:
1047    return CT_Dependent;
1048
1049  case Expr::AsTypeExprClass:
1050  case Expr::BinaryConditionalOperatorClass:
1051  case Expr::BlockExprClass:
1052  case Expr::CUDAKernelCallExprClass:
1053  case Expr::DeclRefExprClass:
1054  case Expr::ObjCBridgedCastExprClass:
1055  case Expr::ObjCIndirectCopyRestoreExprClass:
1056  case Expr::ObjCProtocolExprClass:
1057  case Expr::ObjCSelectorExprClass:
1058  case Expr::OffsetOfExprClass:
1059  case Expr::PackExpansionExprClass:
1060  case Expr::PseudoObjectExprClass:
1061  case Expr::SubstNonTypeTemplateParmExprClass:
1062  case Expr::SubstNonTypeTemplateParmPackExprClass:
1063  case Expr::FunctionParmPackExprClass:
1064  case Expr::UnaryExprOrTypeTraitExprClass:
1065  case Expr::UnresolvedLookupExprClass:
1066  case Expr::UnresolvedMemberExprClass:
1067    // FIXME: Can any of the above throw?  If so, when?
1068    return CT_Cannot;
1069
1070  case Expr::AddrLabelExprClass:
1071  case Expr::ArrayTypeTraitExprClass:
1072  case Expr::AtomicExprClass:
1073  case Expr::BinaryTypeTraitExprClass:
1074  case Expr::TypeTraitExprClass:
1075  case Expr::CXXBoolLiteralExprClass:
1076  case Expr::CXXNoexceptExprClass:
1077  case Expr::CXXNullPtrLiteralExprClass:
1078  case Expr::CXXPseudoDestructorExprClass:
1079  case Expr::CXXScalarValueInitExprClass:
1080  case Expr::CXXThisExprClass:
1081  case Expr::CXXUuidofExprClass:
1082  case Expr::CharacterLiteralClass:
1083  case Expr::ExpressionTraitExprClass:
1084  case Expr::FloatingLiteralClass:
1085  case Expr::GNUNullExprClass:
1086  case Expr::ImaginaryLiteralClass:
1087  case Expr::ImplicitValueInitExprClass:
1088  case Expr::IntegerLiteralClass:
1089  case Expr::ObjCEncodeExprClass:
1090  case Expr::ObjCStringLiteralClass:
1091  case Expr::ObjCBoolLiteralExprClass:
1092  case Expr::OpaqueValueExprClass:
1093  case Expr::PredefinedExprClass:
1094  case Expr::SizeOfPackExprClass:
1095  case Expr::StringLiteralClass:
1096  case Expr::UnaryTypeTraitExprClass:
1097    // These expressions can never throw.
1098    return CT_Cannot;
1099
1100#define STMT(CLASS, PARENT) case Expr::CLASS##Class:
1101#define STMT_RANGE(Base, First, Last)
1102#define LAST_STMT_RANGE(BASE, FIRST, LAST)
1103#define EXPR(CLASS, PARENT)
1104#define ABSTRACT_STMT(STMT)
1105#include "clang/AST/StmtNodes.inc"
1106  case Expr::NoStmtClass:
1107    llvm_unreachable("Invalid class for expression");
1108  }
1109  llvm_unreachable("Bogus StmtClass");
1110}
1111
1112} // end namespace clang
1113