CanonicalType.h revision f85e193739c953358c865005855253af4f68a497
150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor//===-- CanonicalType.h - C Language Family Type Representation -*- C++ -*-===// 250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor// 350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor// The LLVM Compiler Infrastructure 450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor// 550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor// This file is distributed under the University of Illinois Open Source 650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor// License. See LICENSE.TXT for details. 750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor// 850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor//===----------------------------------------------------------------------===// 950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor// 1050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor// This file defines the CanQual class template, which provides access to 1150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor// canonical types. 1250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor// 1350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor//===----------------------------------------------------------------------===// 1450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 1550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor#ifndef LLVM_CLANG_AST_CANONICAL_TYPE_H 1650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor#define LLVM_CLANG_AST_CANONICAL_TYPE_H 1750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 1850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor#include "clang/AST/Type.h" 1950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor#include "llvm/Support/Casting.h" 2050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor#include "llvm/Support/type_traits.h" 2150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor#include <iterator> 2250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 2350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregornamespace clang { 241eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<typename T> class CanProxy; 2650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<typename T> struct CanProxyAdaptor; 2750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 2850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor//----------------------------------------------------------------------------// 2950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor// Canonical, qualified type template 3050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor//----------------------------------------------------------------------------// 311eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 3250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// \brief Represents a canonical, potentially-qualified type. 3350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// 3450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// The CanQual template is a lightweight smart pointer that provides access 3550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// to the canonical representation of a type, where all typedefs and other 361eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// syntactic sugar has been eliminated. A CanQualType may also have various 3750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// qualifiers (const, volatile, restrict) attached to it. 3850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// 391eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// The template type parameter @p T is one of the Type classes (PointerType, 4050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// BuiltinType, etc.). The type stored within @c CanQual<T> will be of that 4150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// type (or some subclass of that type). The typedef @c CanQualType is just 4250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// a shorthand for @c CanQual<Type>. 4350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// 441eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// An instance of @c CanQual<T> can be implicitly converted to a 4550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// @c CanQual<U> when T is derived from U, which essentially provides an 461eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// implicit upcast. For example, @c CanQual<LValueReferenceType> can be 471eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// converted to @c CanQual<ReferenceType>. Note that any @c CanQual type can 4850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// be implicitly converted to a QualType, but the reverse operation requires 4950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// a call to ASTContext::getCanonicalType(). 501eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// 511eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// 5250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<typename T = Type> 5350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorclass CanQual { 541eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump /// \brief The actual, canonical type. 5550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor QualType Stored; 561eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 5750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorpublic: 5850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Constructs a NULL canonical type. 5950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanQual() : Stored() { } 601eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 6150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Converting constructor that permits implicit upcasting of 6250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// canonical type pointers. 6350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor template<typename U> 641eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump CanQual(const CanQual<U>& Other, 6550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor typename llvm::enable_if<llvm::is_base_of<T, U>, int>::type = 0); 661eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 671eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump /// \brief Retrieve the underlying type pointer, which refers to a 6850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// canonical type. 691ab55e9bb87d98bff1d42c7a0ee502c64755d9f5Douglas Gregor /// 701ab55e9bb87d98bff1d42c7a0ee502c64755d9f5Douglas Gregor /// The underlying pointer must not be NULL. 71f4c7371fb1d3cebcfb40abad4537bb82515704eaJohn McCall const T *getTypePtr() const { return cast<T>(Stored.getTypePtr()); } 721ab55e9bb87d98bff1d42c7a0ee502c64755d9f5Douglas Gregor 731ab55e9bb87d98bff1d42c7a0ee502c64755d9f5Douglas Gregor /// \brief Retrieve the underlying type pointer, which refers to a 741ab55e9bb87d98bff1d42c7a0ee502c64755d9f5Douglas Gregor /// canonical type, or NULL. 751ab55e9bb87d98bff1d42c7a0ee502c64755d9f5Douglas Gregor /// 76f4c7371fb1d3cebcfb40abad4537bb82515704eaJohn McCall const T *getTypePtrOrNull() const { 771ab55e9bb87d98bff1d42c7a0ee502c64755d9f5Douglas Gregor return cast_or_null<T>(Stored.getTypePtrOrNull()); 781ab55e9bb87d98bff1d42c7a0ee502c64755d9f5Douglas Gregor } 791eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 8050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Implicit conversion to a qualified type. 8150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor operator QualType() const { return Stored; } 821eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 83cffecd08f1974dc7cc328bd620b2f69daf442fdaDouglas Gregor /// \brief Implicit conversion to bool. 84cffecd08f1974dc7cc328bd620b2f69daf442fdaDouglas Gregor operator bool() const { return !isNull(); } 85cffecd08f1974dc7cc328bd620b2f69daf442fdaDouglas Gregor 86e27ec8ad56dbf1efb2de004b90fbbb86f740e3f1John McCall bool isNull() const { 87e27ec8ad56dbf1efb2de004b90fbbb86f740e3f1John McCall return Stored.isNull(); 88e27ec8ad56dbf1efb2de004b90fbbb86f740e3f1John McCall } 89e27ec8ad56dbf1efb2de004b90fbbb86f740e3f1John McCall 90f4c7371fb1d3cebcfb40abad4537bb82515704eaJohn McCall SplitQualType split() const { return Stored.split(); } 91f4c7371fb1d3cebcfb40abad4537bb82515704eaJohn McCall 9250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Retrieve a canonical type pointer with a different static type, 9350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// upcasting or downcasting as needed. 9450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// 951eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump /// The getAs() function is typically used to try to downcast to a 9650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// more specific (canonical) type in the type system. For example: 9750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// 9850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// @code 9950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// void f(CanQual<Type> T) { 10050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// if (CanQual<PointerType> Ptr = T->getAs<PointerType>()) { 10150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// // look at Ptr's pointee type 10250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// } 10350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// } 10450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// @endcode 10550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// 10650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \returns A proxy pointer to the same type, but with the specified 10750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// static type (@p U). If the dynamic type is not the specified static type 10850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// or a derived class thereof, a NULL canonical type. 10950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor template<typename U> CanProxy<U> getAs() const; 1101eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 11150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Overloaded arrow operator that produces a canonical type 11250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// proxy. 11350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanProxy<T> operator->() const; 1141eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1150953e767ff7817f97b3ab20896b229891eeff45bJohn McCall /// \brief Retrieve all qualifiers. 116a4923eb7c4b04d360cb2747641a5e92818edf804Douglas Gregor Qualifiers getQualifiers() const { return Stored.getLocalQualifiers(); } 1170953e767ff7817f97b3ab20896b229891eeff45bJohn McCall 11850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Retrieve the const/volatile/restrict qualifiers. 119a4923eb7c4b04d360cb2747641a5e92818edf804Douglas Gregor unsigned getCVRQualifiers() const { return Stored.getLocalCVRQualifiers(); } 1201eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1210953e767ff7817f97b3ab20896b229891eeff45bJohn McCall /// \brief Determines whether this type has any qualifiers 122a4923eb7c4b04d360cb2747641a5e92818edf804Douglas Gregor bool hasQualifiers() const { return Stored.hasLocalQualifiers(); } 1231eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 12450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor bool isConstQualified() const { 125a4923eb7c4b04d360cb2747641a5e92818edf804Douglas Gregor return Stored.isLocalConstQualified(); 12650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 12750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor bool isVolatileQualified() const { 128a4923eb7c4b04d360cb2747641a5e92818edf804Douglas Gregor return Stored.isLocalVolatileQualified(); 12950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 13050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor bool isRestrictQualified() const { 131a4923eb7c4b04d360cb2747641a5e92818edf804Douglas Gregor return Stored.isLocalRestrictQualified(); 1321eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump } 1331eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 134ead608af31b6c9abeae1ca6d0b75094dac4641c0John McCall /// \brief Determines if this canonical type is furthermore 135ead608af31b6c9abeae1ca6d0b75094dac4641c0John McCall /// canonical as a parameter. The parameter-canonicalization 136ead608af31b6c9abeae1ca6d0b75094dac4641c0John McCall /// process decays arrays to pointers and drops top-level qualifiers. 137ead608af31b6c9abeae1ca6d0b75094dac4641c0John McCall bool isCanonicalAsParam() const { 138ead608af31b6c9abeae1ca6d0b75094dac4641c0John McCall return Stored.isCanonicalAsParam(); 139ead608af31b6c9abeae1ca6d0b75094dac4641c0John McCall } 140ead608af31b6c9abeae1ca6d0b75094dac4641c0John McCall 14150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Retrieve the unqualified form of this type. 14250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanQual<T> getUnqualifiedType() const; 1431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 144e27ec8ad56dbf1efb2de004b90fbbb86f740e3f1John McCall /// \brief Retrieves a version of this type with const applied. 145e27ec8ad56dbf1efb2de004b90fbbb86f740e3f1John McCall /// Note that this does not always yield a canonical type. 146e27ec8ad56dbf1efb2de004b90fbbb86f740e3f1John McCall QualType withConst() const { 147e27ec8ad56dbf1efb2de004b90fbbb86f740e3f1John McCall return Stored.withConst(); 14850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 1491eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1501eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump /// \brief Determines whether this canonical type is more qualified than 15150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// the @p Other canonical type. 15250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor bool isMoreQualifiedThan(CanQual<T> Other) const { 15350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return Stored.isMoreQualifiedThan(Other.Stored); 15450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 1551eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 15650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Determines whether this canonical type is at least as qualified as 15750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// the @p Other canonical type. 15850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor bool isAtLeastAsQualifiedAs(CanQual<T> Other) const { 15950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return Stored.isAtLeastAsQualifiedAs(Other.Stored); 16050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 1611eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 16250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief If the canonical type is a reference type, returns the type that 163b890f04174d52e41db19b883244abb17a3254ef1Douglas Gregor /// it refers to; otherwise, returns the type itself. 16450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanQual<Type> getNonReferenceType() const; 1651eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 16650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Retrieve the internal representation of this canonical type. 16750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor void *getAsOpaquePtr() const { return Stored.getAsOpaquePtr(); } 1681eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 16950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Construct a canonical type from its internal representation. 17050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor static CanQual<T> getFromOpaquePtr(void *Ptr); 1711eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 17250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Builds a canonical type from a QualType. 17350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// 1741eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump /// This routine is inherently unsafe, because it requires the user to 1751eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump /// ensure that the given type is a canonical type with the correct 1761eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump // (dynamic) type. 17750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor static CanQual<T> CreateUnsafe(QualType Other); 178ead608af31b6c9abeae1ca6d0b75094dac4641c0John McCall 179d9ab76bbce7b8a563aa847cfcdcd39d8280f11bdNuno Lopes void dump() const { Stored.dump(); } 180d9ab76bbce7b8a563aa847cfcdcd39d8280f11bdNuno Lopes 181ead608af31b6c9abeae1ca6d0b75094dac4641c0John McCall void Profile(llvm::FoldingSetNodeID &ID) const { 182ead608af31b6c9abeae1ca6d0b75094dac4641c0John McCall ID.AddPointer(getAsOpaquePtr()); 183ead608af31b6c9abeae1ca6d0b75094dac4641c0John McCall } 18450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 18550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 18650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<typename T, typename U> 18750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorinline bool operator==(CanQual<T> x, CanQual<U> y) { 18850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return x.getAsOpaquePtr() == y.getAsOpaquePtr(); 18950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor} 19050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 19150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<typename T, typename U> 19250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorinline bool operator!=(CanQual<T> x, CanQual<U> y) { 19350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return x.getAsOpaquePtr() != y.getAsOpaquePtr(); 19450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor} 19550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 19650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// \brief Represents a canonical, potentially-qualified type. 19750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortypedef CanQual<Type> CanQualType; 19850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 199ead608af31b6c9abeae1ca6d0b75094dac4641c0John McCallinline CanQualType Type::getCanonicalTypeUnqualified() const { 200ead608af31b6c9abeae1ca6d0b75094dac4641c0John McCall return CanQualType::CreateUnsafe(getCanonicalTypeInternal()); 201ead608af31b6c9abeae1ca6d0b75094dac4641c0John McCall} 202ead608af31b6c9abeae1ca6d0b75094dac4641c0John McCall 2039d59ecb4d2c2e8efdb214589753826b662246d82Anders Carlssoninline const DiagnosticBuilder &operator<<(const DiagnosticBuilder &DB, 2049d59ecb4d2c2e8efdb214589753826b662246d82Anders Carlsson CanQualType T) { 2059d59ecb4d2c2e8efdb214589753826b662246d82Anders Carlsson DB << static_cast<QualType>(T); 2069d59ecb4d2c2e8efdb214589753826b662246d82Anders Carlsson return DB; 2079d59ecb4d2c2e8efdb214589753826b662246d82Anders Carlsson} 2089d59ecb4d2c2e8efdb214589753826b662246d82Anders Carlsson 20950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor//----------------------------------------------------------------------------// 21050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor// Internal proxy classes used by canonical types 21150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor//----------------------------------------------------------------------------// 2121eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 21350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor#define LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(Accessor) \ 21450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas GregorCanQualType Accessor() const { \ 21550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorreturn CanQualType::CreateUnsafe(this->getTypePtr()->Accessor()); \ 21650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor} 21750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 21850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor#define LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(Type, Accessor) \ 21950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas GregorType Accessor() const { return this->getTypePtr()->Accessor(); } 22050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 22150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// \brief Base class of all canonical proxy types, which is responsible for 22250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// storing the underlying canonical type and providing basic conversions. 2231eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumptemplate<typename T> 22450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorclass CanProxyBase { 22550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorprotected: 22650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanQual<T> Stored; 2271eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 22850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorpublic: 22950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Retrieve the pointer to the underlying Type 230f4c7371fb1d3cebcfb40abad4537bb82515704eaJohn McCall const T *getTypePtr() const { return Stored.getTypePtr(); } 2311eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 23250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Implicit conversion to the underlying pointer. 23350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// 23450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// Also provides the ability to use canonical type proxies in a Boolean 2351eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump // context,e.g., 23650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// @code 23750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// if (CanQual<PointerType> Ptr = T->getAs<PointerType>()) { ... } 23850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// @endcode 2391ab55e9bb87d98bff1d42c7a0ee502c64755d9f5Douglas Gregor operator const T*() const { return this->Stored.getTypePtrOrNull(); } 2401eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 24150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Try to convert the given canonical type to a specific structural 24250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// type. 2431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump template<typename U> CanProxy<U> getAs() const { 2441eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump return this->Stored.template getAs<U>(); 24550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 2461eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 24750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(Type::TypeClass, getTypeClass) 2481eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 24950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor // Type predicates 25050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isObjectType) 25150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isIncompleteType) 25250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isIncompleteOrObjectType) 25350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isVariablyModifiedType) 25450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isIntegerType) 25550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isEnumeralType) 25650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isBooleanType) 25750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isCharType) 25850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isWideCharType) 25950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isIntegralType) 2602ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isIntegralOrEnumerationType) 26150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isRealFloatingType) 26250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isComplexType) 26350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isAnyComplexType) 26450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isFloatingType) 26550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isRealType) 26650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isArithmeticType) 26750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isVoidType) 26850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isDerivedType) 26950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isScalarType) 27050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isAggregateType) 27150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isAnyPointerType) 27250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isVoidPointerType) 27350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isFunctionPointerType) 27450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isMemberFunctionPointerType) 27550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isClassType) 27650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isStructureType) 277fb87b89fc9eb103e19fb8e4b925c23f0bd091b99Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isStructureOrClassType) 27850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isUnionType) 27950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isComplexIntegerType) 28050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isNullPtrType) 28150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isDependentType) 28250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isOverloadableType) 283f4c46193637631fc993d926ff31c7cb18c090d21Sebastian Redl LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isArrayType) 28450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, hasPointerRepresentation) 28550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, hasObjCPointerRepresentation) 286f60946222721d9ba3c059563935c17b84703187aDouglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, hasIntegerRepresentation) 287f60946222721d9ba3c059563935c17b84703187aDouglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, hasSignedIntegerRepresentation) 288f60946222721d9ba3c059563935c17b84703187aDouglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, hasUnsignedIntegerRepresentation) 2898eee119bf4f1693dde17b8552c1f9f81bf2b681eDouglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, hasFloatingRepresentation) 29050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isPromotableIntegerType) 29150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isSignedIntegerType) 29250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isUnsignedIntegerType) 293575a1c9dc8dc5b4977194993e289f9eda7295c39Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isSignedIntegerOrEnumerationType) 294575a1c9dc8dc5b4977194993e289f9eda7295c39Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isUnsignedIntegerOrEnumerationType) 29550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isConstantSizeType) 29650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isSpecifierType) 297f85e193739c953358c865005855253af4f68a497John McCall LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(CXXRecordDecl*, getAsCXXRecordDecl) 29850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 29950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Retrieve the proxy-adaptor type. 30050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// 30150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// This arrow operator is used when CanProxyAdaptor has been specialized 30250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// for the given type T. In that case, we reference members of the 30350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// CanProxyAdaptor specialization. Otherwise, this operator will be hidden 30450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// by the arrow operator in the primary CanProxyAdaptor template. 30550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor const CanProxyAdaptor<T> *operator->() const { 30650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return static_cast<const CanProxyAdaptor<T> *>(this); 30750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 30850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 30950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 31050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// \brief Replacable canonical proxy adaptor class that provides the link 31150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// between a canonical type and the accessors of the type. 31250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// 31350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// The CanProxyAdaptor is a replaceable class template that is instantiated 31450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// as part of each canonical proxy type. The primary template merely provides 31550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// redirection to the underlying type (T), e.g., @c PointerType. One can 31650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// provide specializations of this class template for each underlying type 31750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// that provide accessors returning canonical types (@c CanQualType) rather 31850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// than the more typical @c QualType, to propagate the notion of "canonical" 31950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// through the system. 3201eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumptemplate<typename T> 32150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorstruct CanProxyAdaptor : CanProxyBase<T> { }; 32250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 32350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// \brief Canonical proxy type returned when retrieving the members of a 3241eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// canonical type or as the result of the @c CanQual<T>::getAs member 32550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// function. 32650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// 32750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// The CanProxy type mainly exists as a proxy through which operator-> will 3281eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// look to either map down to a raw T* (e.g., PointerType*) or to a proxy 32950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// type that provides canonical-type access to the fields of the type. 33050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<typename T> 33150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorclass CanProxy : public CanProxyAdaptor<T> { 33250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorpublic: 33350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Build a NULL proxy. 33450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanProxy() { } 3351eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 33650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Build a proxy to the given canonical type. 33750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanProxy(CanQual<T> Stored) { this->Stored = Stored; } 3381eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 33950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor /// \brief Implicit conversion to the stored canonical type. 34050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor operator CanQual<T>() const { return this->Stored; } 34150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 3421eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 34350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor} // end namespace clang 34450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 34550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregornamespace llvm { 3461eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 3471eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// Implement simplify_type for CanQual<T>, so that we can dyn_cast from 34850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// CanQual<T> to a specific Type class. We're prefer isa/dyn_cast/cast/etc. 34950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// to return smart pointer (proxies?). 3501eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumptemplate<typename T> 35150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorstruct simplify_type<const ::clang::CanQual<T> > { 352f4c7371fb1d3cebcfb40abad4537bb82515704eaJohn McCall typedef const T *SimpleType; 35350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor static SimpleType getSimplifiedValue(const ::clang::CanQual<T> &Val) { 3544472fc641ea3069463798fb56a04043c28ea2910Douglas Gregor return Val.getTypePtr(); 35550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 35650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 3571eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumptemplate<typename T> 35850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorstruct simplify_type< ::clang::CanQual<T> > 35950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor: public simplify_type<const ::clang::CanQual<T> > {}; 36050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 36150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor// Teach SmallPtrSet that CanQual<T> is "basically a pointer". 36250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<typename T> 36350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorclass PointerLikeTypeTraits<clang::CanQual<T> > { 36450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorpublic: 36550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor static inline void *getAsVoidPointer(clang::CanQual<T> P) { 36650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return P.getAsOpaquePtr(); 36750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 36850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor static inline clang::CanQual<T> getFromVoidPointer(void *P) { 36950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return clang::CanQual<T>::getFromOpaquePtr(P); 37050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 3710953e767ff7817f97b3ab20896b229891eeff45bJohn McCall // qualifier information is encoded in the low bits. 37250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor enum { NumLowBitsAvailable = 0 }; 37350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 3741eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 37550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor} // end namespace llvm 37650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 37750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregornamespace clang { 3781eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 37950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor//----------------------------------------------------------------------------// 38050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor// Canonical proxy adaptors for canonical type nodes. 38150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor//----------------------------------------------------------------------------// 3821eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 3831eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// \brief Iterator adaptor that turns an iterator over canonical QualTypes 38450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor/// into an iterator over CanQualTypes. 38550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<typename InputIterator> 38650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorclass CanTypeIterator { 38750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor InputIterator Iter; 3881eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 38950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorpublic: 39050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor typedef CanQualType value_type; 39150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor typedef value_type reference; 39250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor typedef CanProxy<Type> pointer; 39350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor typedef typename std::iterator_traits<InputIterator>::difference_type 39450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor difference_type; 39550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor typedef typename std::iterator_traits<InputIterator>::iterator_category 39650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor iterator_category; 3971eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 39850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanTypeIterator() : Iter() { } 39950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor explicit CanTypeIterator(InputIterator Iter) : Iter(Iter) { } 4001eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 40150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor // Input iterator 40250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor reference operator*() const { 40350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return CanQualType::CreateUnsafe(*Iter); 40450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 4051eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 40650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor pointer operator->() const; 4071eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 40850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanTypeIterator &operator++() { 40950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor ++Iter; 41050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return *this; 41150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 4121eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 41350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanTypeIterator operator++(int) { 41450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanTypeIterator Tmp(*this); 41550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor ++Iter; 41650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return Tmp; 41750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 4181eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 41950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor friend bool operator==(const CanTypeIterator& X, const CanTypeIterator &Y) { 42050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return X.Iter == Y.Iter; 42150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 42250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor friend bool operator!=(const CanTypeIterator& X, const CanTypeIterator &Y) { 42350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return X.Iter != Y.Iter; 42450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 4251eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 42650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor // Bidirectional iterator 42750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanTypeIterator &operator--() { 42850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor --Iter; 42950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return *this; 43050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 4311eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 43250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanTypeIterator operator--(int) { 43350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanTypeIterator Tmp(*this); 43450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor --Iter; 43550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return Tmp; 43650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 4371eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 43850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor // Random access iterator 43950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor reference operator[](difference_type n) const { 44050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return CanQualType::CreateUnsafe(Iter[n]); 44150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 4421eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 44350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanTypeIterator &operator+=(difference_type n) { 44450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor Iter += n; 44550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return *this; 44650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 4471eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 44850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanTypeIterator &operator-=(difference_type n) { 44950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor Iter -= n; 45050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return *this; 45150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 4521eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 45350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor friend CanTypeIterator operator+(CanTypeIterator X, difference_type n) { 45450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor X += n; 45550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return X; 45650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 45750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 45850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor friend CanTypeIterator operator+(difference_type n, CanTypeIterator X) { 45950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor X += n; 46050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return X; 46150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 4621eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 46350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor friend CanTypeIterator operator-(CanTypeIterator X, difference_type n) { 46450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor X -= n; 46550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return X; 46650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 4671eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 4681eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump friend difference_type operator-(const CanTypeIterator &X, 46950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor const CanTypeIterator &Y) { 4701eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump return X - Y; 47150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 47250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 47350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 47450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 47550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorstruct CanProxyAdaptor<ComplexType> : public CanProxyBase<ComplexType> { 47650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getElementType) 47750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 47850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 47950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 48050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorstruct CanProxyAdaptor<PointerType> : public CanProxyBase<PointerType> { 48150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getPointeeType) 48250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 4831eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 48450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 4851eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstruct CanProxyAdaptor<BlockPointerType> 4861eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump : public CanProxyBase<BlockPointerType> { 48750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getPointeeType) 48850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 4891eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 49050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 49150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorstruct CanProxyAdaptor<ReferenceType> : public CanProxyBase<ReferenceType> { 49250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getPointeeType) 49350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 49450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 49550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 4961eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstruct CanProxyAdaptor<LValueReferenceType> 4971eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump : public CanProxyBase<LValueReferenceType> { 49850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getPointeeType) 49950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 50050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 50150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 5021eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstruct CanProxyAdaptor<RValueReferenceType> 5031eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump : public CanProxyBase<RValueReferenceType> { 50450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getPointeeType) 50550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 50650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 50750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 5081eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstruct CanProxyAdaptor<MemberPointerType> 5091eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump : public CanProxyBase<MemberPointerType> { 51050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getPointeeType) 51150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(const Type *, getClass) 51250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 5131eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 51450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 51550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorstruct CanProxyAdaptor<ArrayType> : public CanProxyBase<ArrayType> { 51650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getElementType) 5171eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(ArrayType::ArraySizeModifier, 51850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor getSizeModifier) 5190953e767ff7817f97b3ab20896b229891eeff45bJohn McCall LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(Qualifiers, getIndexTypeQualifiers) 52050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 52150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 52250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 5231eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstruct CanProxyAdaptor<ConstantArrayType> 5241eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump : public CanProxyBase<ConstantArrayType> { 52550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getElementType) 5261eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(ArrayType::ArraySizeModifier, 52750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor getSizeModifier) 5280953e767ff7817f97b3ab20896b229891eeff45bJohn McCall LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(Qualifiers, getIndexTypeQualifiers) 52950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(const llvm::APInt &, getSize) 53050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 53150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 53250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 5331eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstruct CanProxyAdaptor<IncompleteArrayType> 5341eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump : public CanProxyBase<IncompleteArrayType> { 53550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getElementType) 5361eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(ArrayType::ArraySizeModifier, 53750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor getSizeModifier) 5380953e767ff7817f97b3ab20896b229891eeff45bJohn McCall LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(Qualifiers, getIndexTypeQualifiers) 53950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 5401eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 54150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 5421eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstruct CanProxyAdaptor<VariableArrayType> 5431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump : public CanProxyBase<VariableArrayType> { 54450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getElementType) 5451eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(ArrayType::ArraySizeModifier, 54650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor getSizeModifier) 5470953e767ff7817f97b3ab20896b229891eeff45bJohn McCall LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(Qualifiers, getIndexTypeQualifiers) 54850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(Expr *, getSizeExpr) 54950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(SourceRange, getBracketsRange) 55050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(SourceLocation, getLBracketLoc) 55150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(SourceLocation, getRBracketLoc) 55250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 55350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 55450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 5551eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstruct CanProxyAdaptor<DependentSizedArrayType> 5561eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump : public CanProxyBase<DependentSizedArrayType> { 55750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getElementType) 55850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(Expr *, getSizeExpr) 55950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(SourceRange, getBracketsRange) 56050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(SourceLocation, getLBracketLoc) 56150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(SourceLocation, getRBracketLoc) 56250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 56350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 56450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 5651eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstruct CanProxyAdaptor<DependentSizedExtVectorType> 5661eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump : public CanProxyBase<DependentSizedExtVectorType> { 56750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getElementType) 56850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(const Expr *, getSizeExpr) 5691eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(SourceLocation, getAttributeLoc) 57050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 5711eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 57250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 57350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorstruct CanProxyAdaptor<VectorType> : public CanProxyBase<VectorType> { 57450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getElementType) 57550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(unsigned, getNumElements) 57650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 57750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 57850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 57950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorstruct CanProxyAdaptor<ExtVectorType> : public CanProxyBase<ExtVectorType> { 58050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getElementType) 58150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(unsigned, getNumElements) 58250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 58350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 58450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 58550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorstruct CanProxyAdaptor<FunctionType> : public CanProxyBase<FunctionType> { 58650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getResultType) 587264ba48dc98f3f843935a485d5b086f7e0fdc4f1Rafael Espindola LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(FunctionType::ExtInfo, getExtInfo) 58850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 58950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 59050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 5911eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstruct CanProxyAdaptor<FunctionNoProtoType> 5921eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump : public CanProxyBase<FunctionNoProtoType> { 59350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getResultType) 594264ba48dc98f3f843935a485d5b086f7e0fdc4f1Rafael Espindola LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(FunctionType::ExtInfo, getExtInfo) 59550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 5961eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 59750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 5981eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstruct CanProxyAdaptor<FunctionProtoType> 5991eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump : public CanProxyBase<FunctionProtoType> { 60050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getResultType) 601264ba48dc98f3f843935a485d5b086f7e0fdc4f1Rafael Espindola LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(FunctionType::ExtInfo, getExtInfo) 6027177dee8aee4b432911c91f1b788963bec0cac9fDaniel Dunbar LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(unsigned, getNumArgs) 60350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanQualType getArgType(unsigned i) const { 60450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return CanQualType::CreateUnsafe(this->getTypePtr()->getArgType(i)); 60550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 6061eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 60750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isVariadic) 60850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(unsigned, getTypeQuals) 6091eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 6101eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump typedef CanTypeIterator<FunctionProtoType::arg_type_iterator> 61150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor arg_type_iterator; 6121eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 61350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor arg_type_iterator arg_type_begin() const { 61450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return arg_type_iterator(this->getTypePtr()->arg_type_begin()); 61550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 61650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 61750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor arg_type_iterator arg_type_end() const { 61850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return arg_type_iterator(this->getTypePtr()->arg_type_end()); 61950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor } 6201eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 62150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor // Note: canonical function types never have exception specifications 62250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 6231eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 62450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 62550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorstruct CanProxyAdaptor<TypeOfType> : public CanProxyBase<TypeOfType> { 62650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getUnderlyingType) 62750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 62850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 62950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 63050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorstruct CanProxyAdaptor<DecltypeType> : public CanProxyBase<DecltypeType> { 63150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(Expr *, getUnderlyingExpr) 63250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getUnderlyingType) 63350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 63450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 635ca63c200346c0ca9e00194ec6e34a5a7b0ed9321Sean Hunttemplate <> 636ca63c200346c0ca9e00194ec6e34a5a7b0ed9321Sean Huntstruct CanProxyAdaptor<UnaryTransformType> 637ca63c200346c0ca9e00194ec6e34a5a7b0ed9321Sean Hunt : public CanProxyBase<UnaryTransformType> { 638ca63c200346c0ca9e00194ec6e34a5a7b0ed9321Sean Hunt LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getBaseType) 639ca63c200346c0ca9e00194ec6e34a5a7b0ed9321Sean Hunt LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getUnderlyingType) 640ca63c200346c0ca9e00194ec6e34a5a7b0ed9321Sean Hunt LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(UnaryTransformType::UTTKind, getUTTKind) 641ca63c200346c0ca9e00194ec6e34a5a7b0ed9321Sean Hunt}; 642ca63c200346c0ca9e00194ec6e34a5a7b0ed9321Sean Hunt 64350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 64450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorstruct CanProxyAdaptor<TagType> : public CanProxyBase<TagType> { 64550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(TagDecl *, getDecl) 64650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isBeingDefined) 64750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 64850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 64950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 65050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorstruct CanProxyAdaptor<RecordType> : public CanProxyBase<RecordType> { 65150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(RecordDecl *, getDecl) 65250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isBeingDefined) 65350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, hasConstFields) 65450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 6551eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 65650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 65750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorstruct CanProxyAdaptor<EnumType> : public CanProxyBase<EnumType> { 65850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(EnumDecl *, getDecl) 65950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isBeingDefined) 66050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 6611eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 66250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 6631eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstruct CanProxyAdaptor<TemplateTypeParmType> 6641eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump : public CanProxyBase<TemplateTypeParmType> { 66550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(unsigned, getDepth) 66650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(unsigned, getIndex) 66750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isParameterPack) 6684fb86f8c4585e53c21c847ad3de9e3b2de123cd9Chandler Carruth LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(TemplateTypeParmDecl *, getDecl) 669b7efff4bae117604f442bb6859c844f90b15f3ffChandler Carruth LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(IdentifierInfo *, getIdentifier) 67050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 6711eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 67250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<> 673c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCallstruct CanProxyAdaptor<ObjCObjectType> 674c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCall : public CanProxyBase<ObjCObjectType> { 675c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCall LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getBaseType) 676c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCall LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(const ObjCInterfaceDecl *, 677c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCall getInterface) 678c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCall LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isObjCUnqualifiedId) 679c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCall LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isObjCUnqualifiedClass) 680c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCall LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isObjCQualifiedId) 681c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCall LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isObjCQualifiedClass) 682c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCall 683c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCall typedef ObjCObjectPointerType::qual_iterator qual_iterator; 684c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCall LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(qual_iterator, qual_begin) 685c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCall LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(qual_iterator, qual_end) 686c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCall LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, qual_empty) 687c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCall LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(unsigned, getNumProtocols) 688c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCall}; 689c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCall 690c12c5bba6ceb6acd4e51e7a0fc03257da9cfd44eJohn McCalltemplate<> 6911eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstruct CanProxyAdaptor<ObjCObjectPointerType> 6921eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump : public CanProxyBase<ObjCObjectPointerType> { 69350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_TYPE_ACCESSOR(getPointeeType) 6941eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(const ObjCInterfaceType *, 69550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor getInterfaceType) 69650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isObjCIdType) 69750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isObjCClassType) 69850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isObjCQualifiedIdType) 69950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, isObjCQualifiedClassType) 7001eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 70150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor typedef ObjCObjectPointerType::qual_iterator qual_iterator; 70250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(qual_iterator, qual_begin) 70350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(qual_iterator, qual_end) 70450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(bool, qual_empty) 70550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor LLVM_CLANG_CANPROXY_SIMPLE_ACCESSOR(unsigned, getNumProtocols) 70650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor}; 7071eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 70850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor//----------------------------------------------------------------------------// 70950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor// Method and function definitions 71050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor//----------------------------------------------------------------------------// 71150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<typename T> 71250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorinline CanQual<T> CanQual<T>::getUnqualifiedType() const { 713a4923eb7c4b04d360cb2747641a5e92818edf804Douglas Gregor return CanQual<T>::CreateUnsafe(Stored.getLocalUnqualifiedType()); 71450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor} 71550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 71650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<typename T> 71750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregorinline CanQual<Type> CanQual<T>::getNonReferenceType() const { 71850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor if (CanQual<ReferenceType> RefType = getAs<ReferenceType>()) 71950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return RefType->getPointeeType(); 72050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor else 72150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return *this; 72250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor} 72350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 72450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<typename T> 72550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas GregorCanQual<T> CanQual<T>::getFromOpaquePtr(void *Ptr) { 72650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanQual<T> Result; 727f5586f6b311c98e1022a8fe0609053849b70d323Douglas Gregor Result.Stored = QualType::getFromOpaquePtr(Ptr); 728f5586f6b311c98e1022a8fe0609053849b70d323Douglas Gregor assert((!Result || Result.Stored.getAsOpaquePtr() == (void*)-1 || 729f5586f6b311c98e1022a8fe0609053849b70d323Douglas Gregor Result.Stored.isCanonical()) && "Type is not canonical!"); 73050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return Result; 73150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor} 73250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 7331eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumptemplate<typename T> 73450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas GregorCanQual<T> CanQual<T>::CreateUnsafe(QualType Other) { 735467b27b9a24bdc823218ad1ad0e37673b6cc1e83John McCall assert((Other.isNull() || Other.isCanonical()) && "Type is not canonical!"); 73650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor assert((Other.isNull() || isa<T>(Other.getTypePtr())) && 73750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor "Dynamic type does not meet the static type's requires"); 73850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor CanQual<T> Result; 73950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor Result.Stored = Other; 74050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return Result; 74150d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor} 74250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 7431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumptemplate<typename T> 7441eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumptemplate<typename U> 74550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas GregorCanProxy<U> CanQual<T>::getAs() const { 74650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor if (Stored.isNull()) 74750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return CanProxy<U>(); 7481eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 74950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor if (isa<U>(Stored.getTypePtr())) 75050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return CanQual<U>::CreateUnsafe(Stored); 7511eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 75250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return CanProxy<U>(); 75350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor} 75450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 75550d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<typename T> 75650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas GregorCanProxy<T> CanQual<T>::operator->() const { 75750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return CanProxy<T>(*this); 75850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor} 7591eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 76050d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregortemplate<typename InputIterator> 7611eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumptypename CanTypeIterator<InputIterator>::pointer 76250d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas GregorCanTypeIterator<InputIterator>::operator->() const { 76350d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor return CanProxy<Type>(*this); 76450d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor} 7651eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 76650d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor} 76750d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 76850d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor 76950d62d1b4a98adbc83de8f8cd1379ea1c25656f7Douglas Gregor#endif // LLVM_CLANG_AST_CANONICAL_TYPE_H 770