Outer.add(CCE->getConstructor(), Flags);
}
void VisitDesignatedInitExpr(const DesignatedInitExpr *DIE) {
- for (const DesignatedInitExpr::Designator &D :
- llvm::reverse(DIE->designators()))
+ for (const Designator &D : llvm::reverse(DIE->designators()))
if (D.isFieldDesignator()) {
Outer.add(D.getField(), Flags);
// We don't know which designator was intended, we assume the outer.
}
void VisitDesignatedInitExpr(const DesignatedInitExpr *DIE) {
- for (const DesignatedInitExpr::Designator &D : DIE->designators()) {
+ for (const Designator &D : DIE->designators()) {
if (!D.isFieldDesignator())
continue;
--- /dev/null
+//===--- Designator.h - Initialization Designator ---------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+//
+// This file defines interfaces used to represent designators (i.e. C99
+// designated initializers) during parsing and sema.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_CLANG_AST_DESIGNATOR_H
+#define LLVM_CLANG_AST_DESIGNATOR_H
+
+#include "clang/Basic/SourceLocation.h"
+#include "llvm/ADT/SmallVector.h"
+
+namespace clang {
+
+class Expr;
+class FieldDecl;
+class IdentifierInfo;
+class Sema;
+
+/// Designator - A designator in a C99 designated initializer.
+///
+/// This class is a discriminated union which holds the various
+/// different sorts of designators possible. A Designation is an array of
+/// these. An example of a designator are things like this:
+///
+/// [8] .field [47] // C99 designation: 3 designators
+/// [8 ... 47] field: // GNU extensions: 2 designators
+///
+/// These occur in initializers, e.g.:
+///
+/// int a[10] = {2, 4, [8]=9, 10};
+///
+class Designator {
+ enum DesignatorKind {
+ FieldDesignator,
+ ArrayDesignatorExpr,
+ ArrayDesignatorInt,
+ ArrayRangeDesignatorExpr,
+ ArrayRangeDesignatorInt,
+ };
+
+ DesignatorKind Kind;
+
+ /// A field designator, e.g., ".x = 42".
+ class FieldDesignatorInfo {
+ /// Refers to the field that is being initialized. The low bit of this
+ /// field determines whether this is actually a pointer to an
+ /// IdentifierInfo (if 1) or a FieldDecl (if 0). When initially
+ /// constructed, a field designator will store an IdentifierInfo*. After
+ /// semantic analysis has resolved that name, the field designator will
+ /// instead store a FieldDecl*.
+ uintptr_t NameOrField;
+
+ public:
+ /// The location of the '.' in the designated initializer.
+ SourceLocation DotLoc;
+
+ /// The location of the field name in the designated initializer.
+ SourceLocation NameLoc;
+
+ FieldDesignatorInfo(const IdentifierInfo *II, SourceLocation DotLoc,
+ SourceLocation NameLoc)
+ : NameOrField(reinterpret_cast<uintptr_t>(II) | 0x01), DotLoc(DotLoc),
+ NameLoc(NameLoc) {}
+
+ FieldDecl *getFieldDecl() const {
+ if (NameOrField & 0x01)
+ return nullptr;
+ return reinterpret_cast<FieldDecl *>(NameOrField);
+ }
+ const IdentifierInfo *getIdentifierInfo() const {
+ if (NameOrField & 0x01)
+ return reinterpret_cast<const IdentifierInfo *>(NameOrField & ~0x1);
+ return nullptr;
+ }
+
+ void set(FieldDecl *FD) { NameOrField = reinterpret_cast<uintptr_t>(FD); }
+ };
+
+ /// An array designator, e.g., "[42] = 0" and "[42 ... 50] = 1".
+ template <typename Ty> struct ArrayDesignatorInfo {
+ /// Location of the first and last index expression within the designated
+ /// initializer expression's list of subexpressions.
+ Ty Start;
+ Ty End;
+
+ /// The location of the '[' starting the array designator.
+ SourceLocation LBracketLoc;
+
+ /// The location of the ellipsis separating the start and end indices.
+ /// Only valid for GNU array-range designators.
+ SourceLocation EllipsisLoc;
+
+ /// The location of the ']' terminating the array designator.
+ SourceLocation RBracketLoc;
+
+ ArrayDesignatorInfo(Ty Start, Ty End, SourceLocation LBracketLoc,
+ SourceLocation EllipsisLoc, SourceLocation RBracketLoc)
+ : Start(Start), End(End), LBracketLoc(LBracketLoc),
+ EllipsisLoc(EllipsisLoc), RBracketLoc(RBracketLoc) {}
+
+ Ty getStart() const { return Start; }
+ Ty getEnd() const { return End; }
+ };
+
+ union {
+ FieldDesignatorInfo FieldInfo;
+ ArrayDesignatorInfo<Expr *> ArrayInfoExpr;
+ ArrayDesignatorInfo<unsigned> ArrayInfoInt;
+ };
+
+ Designator(DesignatorKind Kind) : Kind(Kind) {}
+
+public:
+ Designator() {}
+
+ bool isFieldDesignator() const { return Kind == FieldDesignator; }
+ bool isArrayDesignator() const {
+ return Kind == ArrayDesignatorExpr || Kind == ArrayDesignatorInt;
+ }
+ bool isArrayRangeDesignator() const {
+ return Kind == ArrayRangeDesignatorExpr || Kind == ArrayRangeDesignatorInt;
+ }
+
+ /// FieldDesignatorInfo:
+ static Designator CreateFieldDesignator(const IdentifierInfo *FieldName,
+ SourceLocation DotLoc,
+ SourceLocation NameLoc) {
+ Designator D(FieldDesignator);
+ new (&D.FieldInfo) FieldDesignatorInfo(FieldName, DotLoc, NameLoc);
+ return D;
+ }
+
+ const IdentifierInfo *getFieldName() const;
+
+ FieldDecl *getField() const {
+ assert(isFieldDesignator() && "Invalid accessor");
+ return FieldInfo.getFieldDecl();
+ }
+
+ void setField(FieldDecl *FD) {
+ assert(isFieldDesignator() && "Invalid accessor");
+ FieldInfo.set(FD);
+ }
+
+ SourceLocation getDotLoc() const {
+ assert(isFieldDesignator() && "Invalid accessor");
+ return FieldInfo.DotLoc;
+ }
+
+ SourceLocation getFieldLoc() const {
+ assert(isFieldDesignator() && "Invalid accessor");
+ return FieldInfo.NameLoc;
+ }
+
+ /// ArrayDesignatorInfo:
+ static Designator
+ CreateArrayDesignator(Expr *Start, SourceLocation LBracketLoc,
+ SourceLocation RBracketLoc = SourceLocation()) {
+ Designator D(ArrayDesignatorExpr);
+ new (&D.ArrayInfoExpr) ArrayDesignatorInfo<Expr *>(
+ Start, nullptr, LBracketLoc, SourceLocation(), RBracketLoc);
+ return D;
+ }
+ static Designator
+ CreateArrayDesignator(unsigned Start, SourceLocation LBracketLoc,
+ SourceLocation RBracketLoc = SourceLocation()) {
+ Designator D(ArrayDesignatorInt);
+ new (&D.ArrayInfoInt) ArrayDesignatorInfo<unsigned>(
+ Start, 0, LBracketLoc, SourceLocation(), RBracketLoc);
+ return D;
+ }
+
+ template <typename Ty = Expr *> Ty getArrayIndex() const {
+ assert(isArrayDesignator() && "Invalid accessor");
+ return ArrayInfoExpr.getStart();
+ }
+
+ /// ArrayRangeDesignatorInfo:
+ static Designator
+ CreateArrayRangeDesignator(Expr *Start, Expr *End, SourceLocation LBracketLoc,
+ SourceLocation EllipsisLoc,
+ SourceLocation RBracketLoc = SourceLocation()) {
+ Designator D(ArrayRangeDesignatorExpr);
+ new (&D.ArrayInfoExpr) ArrayDesignatorInfo<Expr *>(
+ Start, End, LBracketLoc, EllipsisLoc, RBracketLoc);
+ return D;
+ }
+ static Designator
+ CreateArrayRangeDesignator(unsigned Index, SourceLocation LBracketLoc,
+ SourceLocation EllipsisLoc,
+ SourceLocation RBracketLoc = SourceLocation()) {
+ Designator D(ArrayRangeDesignatorInt);
+ new (&D.ArrayInfoInt) ArrayDesignatorInfo<unsigned>(
+ Index, 0, LBracketLoc, EllipsisLoc, RBracketLoc);
+ return D;
+ }
+
+ Expr *getArrayRangeStart() const {
+ assert(isArrayRangeDesignator() && "Invalid accessor");
+ return ArrayInfoExpr.getStart();
+ }
+
+ Expr *getArrayRangeEnd() const {
+ assert(isArrayRangeDesignator() && "Invalid accessor");
+ return ArrayInfoExpr.getEnd();
+ }
+
+ SourceLocation getLBracketLoc() const {
+ switch (Kind) {
+ default:
+ break;
+ case ArrayDesignatorExpr:
+ case ArrayRangeDesignatorExpr:
+ return ArrayInfoExpr.LBracketLoc;
+ case ArrayDesignatorInt:
+ case ArrayRangeDesignatorInt:
+ return ArrayInfoInt.LBracketLoc;
+ }
+
+ assert(false && "Invalid accessor");
+ return SourceLocation();
+ }
+
+ SourceLocation getEllipsisLoc() const {
+ switch (Kind) {
+ default:
+ break;
+ case ArrayRangeDesignatorExpr:
+ return ArrayInfoExpr.EllipsisLoc;
+ case ArrayRangeDesignatorInt:
+ return ArrayInfoInt.EllipsisLoc;
+ }
+
+ assert(false && "Invalid accessor");
+ return SourceLocation();
+ }
+
+ SourceLocation getRBracketLoc() const {
+ switch (Kind) {
+ default:
+ break;
+ case ArrayDesignatorExpr:
+ case ArrayRangeDesignatorExpr:
+ return ArrayInfoExpr.RBracketLoc;
+ case ArrayDesignatorInt:
+ case ArrayRangeDesignatorInt:
+ return ArrayInfoInt.RBracketLoc;
+ }
+
+ assert(false && "Invalid accessor");
+ return SourceLocation();
+ }
+
+ void setRBracketLoc(SourceLocation RBracketLoc) {
+ switch (Kind) {
+ default:
+ assert(false && "Invalid accessor");
+ break;
+ case ArrayDesignatorExpr:
+ case ArrayRangeDesignatorExpr:
+ ArrayInfoExpr.RBracketLoc = RBracketLoc;
+ break;
+ case ArrayDesignatorInt:
+ case ArrayRangeDesignatorInt:
+ ArrayInfoInt.RBracketLoc = RBracketLoc;
+ break;
+ }
+ }
+
+ unsigned getFirstExprIndex() const {
+ if (Kind == ArrayDesignatorInt || Kind == ArrayRangeDesignatorInt)
+ return ArrayInfoInt.getStart();
+
+ assert(false && "Invalid accessor");
+ return 0;
+ }
+
+ /// Source location accessors.
+ SourceLocation getBeginLoc() const LLVM_READONLY {
+ if (isFieldDesignator())
+ return getDotLoc().isInvalid() ? getFieldLoc() : getDotLoc();
+ return getLBracketLoc();
+ }
+ SourceLocation getEndLoc() const LLVM_READONLY {
+ return isFieldDesignator() ? getFieldLoc() : getRBracketLoc();
+ }
+ SourceRange getSourceRange() const LLVM_READONLY {
+ return SourceRange(getBeginLoc(), getEndLoc());
+ }
+};
+
+/// Designation - Represent a full designation, which is a sequence of
+/// designators. This class is mostly a helper for InitListDesignations.
+class Designation {
+ /// Designators - The actual designators for this initializer.
+ SmallVector<Designator, 2> Designators;
+
+public:
+ /// AddDesignator - Add a designator to the end of this list.
+ void AddDesignator(Designator D) { Designators.push_back(D); }
+
+ bool empty() const { return Designators.empty(); }
+
+ unsigned getNumDesignators() const { return Designators.size(); }
+
+ const Designator &getDesignator(unsigned Idx) const {
+ assert(Idx < getNumDesignators());
+ return Designators[Idx];
+ }
+ Designator &getDesignator(unsigned Idx) {
+ assert(Idx < getNumDesignators());
+ return Designators[Idx];
+ }
+};
+
+} // end namespace clang
+
+#endif
#include "clang/AST/Decl.h"
#include "clang/AST/DeclAccessPair.h"
#include "clang/AST/DependenceFlags.h"
+#include "clang/AST/Designator.h"
#include "clang/AST/OperationKinds.h"
#include "clang/AST/Stmt.h"
#include "clang/AST/TemplateBase.h"
class DesignatedInitExpr final
: public Expr,
private llvm::TrailingObjects<DesignatedInitExpr, Stmt *> {
-public:
- /// Forward declaration of the Designator class.
- class Designator;
-
private:
/// The location of the '=' or ':' prior to the actual initializer
/// expression.
NumDesignators(0), NumSubExprs(NumSubExprs), Designators(nullptr) { }
public:
- /// A field designator, e.g., ".x".
- struct FieldDesignator {
- /// Refers to the field that is being initialized. The low bit
- /// of this field determines whether this is actually a pointer
- /// to an IdentifierInfo (if 1) or a FieldDecl (if 0). When
- /// initially constructed, a field designator will store an
- /// IdentifierInfo*. After semantic analysis has resolved that
- /// name, the field designator will instead store a FieldDecl*.
- uintptr_t NameOrField;
-
- /// The location of the '.' in the designated initializer.
- SourceLocation DotLoc;
-
- /// The location of the field name in the designated initializer.
- SourceLocation FieldLoc;
- };
-
- /// An array or GNU array-range designator, e.g., "[9]" or "[10..15]".
- struct ArrayOrRangeDesignator {
- /// Location of the first index expression within the designated
- /// initializer expression's list of subexpressions.
- unsigned Index;
- /// The location of the '[' starting the array range designator.
- SourceLocation LBracketLoc;
- /// The location of the ellipsis separating the start and end
- /// indices. Only valid for GNU array-range designators.
- SourceLocation EllipsisLoc;
- /// The location of the ']' terminating the array range designator.
- SourceLocation RBracketLoc;
- };
-
- /// Represents a single C99 designator.
- ///
- /// @todo This class is infuriatingly similar to clang::Designator,
- /// but minor differences (storing indices vs. storing pointers)
- /// keep us from reusing it. Try harder, later, to rectify these
- /// differences.
- class Designator {
- /// The kind of designator this describes.
- enum {
- FieldDesignator,
- ArrayDesignator,
- ArrayRangeDesignator
- } Kind;
-
- union {
- /// A field designator, e.g., ".x".
- struct FieldDesignator Field;
- /// An array or GNU array-range designator, e.g., "[9]" or "[10..15]".
- struct ArrayOrRangeDesignator ArrayOrRange;
- };
- friend class DesignatedInitExpr;
-
- public:
- Designator() {}
-
- /// Initializes a field designator.
- Designator(const IdentifierInfo *FieldName, SourceLocation DotLoc,
- SourceLocation FieldLoc)
- : Kind(FieldDesignator) {
- new (&Field) DesignatedInitExpr::FieldDesignator;
- Field.NameOrField = reinterpret_cast<uintptr_t>(FieldName) | 0x01;
- Field.DotLoc = DotLoc;
- Field.FieldLoc = FieldLoc;
- }
-
- /// Initializes an array designator.
- Designator(unsigned Index, SourceLocation LBracketLoc,
- SourceLocation RBracketLoc)
- : Kind(ArrayDesignator) {
- new (&ArrayOrRange) DesignatedInitExpr::ArrayOrRangeDesignator;
- ArrayOrRange.Index = Index;
- ArrayOrRange.LBracketLoc = LBracketLoc;
- ArrayOrRange.EllipsisLoc = SourceLocation();
- ArrayOrRange.RBracketLoc = RBracketLoc;
- }
-
- /// Initializes a GNU array-range designator.
- Designator(unsigned Index, SourceLocation LBracketLoc,
- SourceLocation EllipsisLoc, SourceLocation RBracketLoc)
- : Kind(ArrayRangeDesignator) {
- new (&ArrayOrRange) DesignatedInitExpr::ArrayOrRangeDesignator;
- ArrayOrRange.Index = Index;
- ArrayOrRange.LBracketLoc = LBracketLoc;
- ArrayOrRange.EllipsisLoc = EllipsisLoc;
- ArrayOrRange.RBracketLoc = RBracketLoc;
- }
-
- bool isFieldDesignator() const { return Kind == FieldDesignator; }
- bool isArrayDesignator() const { return Kind == ArrayDesignator; }
- bool isArrayRangeDesignator() const { return Kind == ArrayRangeDesignator; }
-
- IdentifierInfo *getFieldName() const;
-
- FieldDecl *getField() const {
- assert(Kind == FieldDesignator && "Only valid on a field designator");
- if (Field.NameOrField & 0x01)
- return nullptr;
- else
- return reinterpret_cast<FieldDecl *>(Field.NameOrField);
- }
-
- void setField(FieldDecl *FD) {
- assert(Kind == FieldDesignator && "Only valid on a field designator");
- Field.NameOrField = reinterpret_cast<uintptr_t>(FD);
- }
-
- SourceLocation getDotLoc() const {
- assert(Kind == FieldDesignator && "Only valid on a field designator");
- return Field.DotLoc;
- }
-
- SourceLocation getFieldLoc() const {
- assert(Kind == FieldDesignator && "Only valid on a field designator");
- return Field.FieldLoc;
- }
-
- SourceLocation getLBracketLoc() const {
- assert((Kind == ArrayDesignator || Kind == ArrayRangeDesignator) &&
- "Only valid on an array or array-range designator");
- return ArrayOrRange.LBracketLoc;
- }
-
- SourceLocation getRBracketLoc() const {
- assert((Kind == ArrayDesignator || Kind == ArrayRangeDesignator) &&
- "Only valid on an array or array-range designator");
- return ArrayOrRange.RBracketLoc;
- }
-
- SourceLocation getEllipsisLoc() const {
- assert(Kind == ArrayRangeDesignator &&
- "Only valid on an array-range designator");
- return ArrayOrRange.EllipsisLoc;
- }
-
- unsigned getFirstExprIndex() const {
- assert((Kind == ArrayDesignator || Kind == ArrayRangeDesignator) &&
- "Only valid on an array or array-range designator");
- return ArrayOrRange.Index;
- }
-
- SourceLocation getBeginLoc() const LLVM_READONLY {
- if (Kind == FieldDesignator)
- return getDotLoc().isInvalid()? getFieldLoc() : getDotLoc();
- else
- return getLBracketLoc();
- }
- SourceLocation getEndLoc() const LLVM_READONLY {
- return Kind == FieldDesignator ? getFieldLoc() : getRBracketLoc();
- }
- SourceRange getSourceRange() const LLVM_READONLY {
- return SourceRange(getBeginLoc(), getEndLoc());
- }
- };
-
static DesignatedInitExpr *Create(const ASTContext &C,
llvm::ArrayRef<Designator> Designators,
ArrayRef<Expr*> IndexExprs,
+++ /dev/null
-//===--- Designator.h - Initialization Designator ---------------*- C++ -*-===//
-//
-// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
-// See https://llvm.org/LICENSE.txt for license information.
-// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
-//
-//===----------------------------------------------------------------------===//
-//
-// This file defines interfaces used to represent designators (a la
-// C99 designated initializers) during parsing.
-//
-//===----------------------------------------------------------------------===//
-
-#ifndef LLVM_CLANG_SEMA_DESIGNATOR_H
-#define LLVM_CLANG_SEMA_DESIGNATOR_H
-
-#include "clang/Basic/SourceLocation.h"
-#include "llvm/ADT/SmallVector.h"
-
-namespace clang {
-
-class Expr;
-class IdentifierInfo;
-class Sema;
-
-/// Designator - A designator in a C99 designated initializer.
-///
-/// This class is a discriminated union which holds the various
-/// different sorts of designators possible. A Designation is an array of
-/// these. An example of a designator are things like this:
-/// [8] .field [47] // C99 designation: 3 designators
-/// [8 ... 47] field: // GNU extensions: 2 designators
-/// These occur in initializers, e.g.:
-/// int a[10] = {2, 4, [8]=9, 10};
-///
-class Designator {
-public:
- enum DesignatorKind {
- FieldDesignator, ArrayDesignator, ArrayRangeDesignator
- };
-private:
- Designator() {};
-
- DesignatorKind Kind;
-
- struct FieldDesignatorInfo {
- const IdentifierInfo *II;
- SourceLocation DotLoc;
- SourceLocation NameLoc;
- };
- struct ArrayDesignatorInfo {
- Expr *Index;
- SourceLocation LBracketLoc;
- mutable SourceLocation RBracketLoc;
- };
- struct ArrayRangeDesignatorInfo {
- Expr *Start, *End;
- SourceLocation LBracketLoc, EllipsisLoc;
- mutable SourceLocation RBracketLoc;
- };
-
- union {
- FieldDesignatorInfo FieldInfo;
- ArrayDesignatorInfo ArrayInfo;
- ArrayRangeDesignatorInfo ArrayRangeInfo;
- };
-
-public:
-
- DesignatorKind getKind() const { return Kind; }
- bool isFieldDesignator() const { return Kind == FieldDesignator; }
- bool isArrayDesignator() const { return Kind == ArrayDesignator; }
- bool isArrayRangeDesignator() const { return Kind == ArrayRangeDesignator; }
-
- const IdentifierInfo *getField() const {
- assert(isFieldDesignator() && "Invalid accessor");
- return FieldInfo.II;
- }
-
- SourceLocation getDotLoc() const {
- assert(isFieldDesignator() && "Invalid accessor");
- return FieldInfo.DotLoc;
- }
-
- SourceLocation getFieldLoc() const {
- assert(isFieldDesignator() && "Invalid accessor");
- return FieldInfo.NameLoc;
- }
-
- Expr *getArrayIndex() const {
- assert(isArrayDesignator() && "Invalid accessor");
- return ArrayInfo.Index;
- }
-
- Expr *getArrayRangeStart() const {
- assert(isArrayRangeDesignator() && "Invalid accessor");
- return ArrayRangeInfo.Start;
- }
- Expr *getArrayRangeEnd() const {
- assert(isArrayRangeDesignator() && "Invalid accessor");
- return ArrayRangeInfo.End;
- }
-
- SourceLocation getLBracketLoc() const {
- assert((isArrayDesignator() || isArrayRangeDesignator()) &&
- "Invalid accessor");
- if (isArrayDesignator())
- return ArrayInfo.LBracketLoc;
- else
- return ArrayRangeInfo.LBracketLoc;
- }
-
- SourceLocation getRBracketLoc() const {
- assert((isArrayDesignator() || isArrayRangeDesignator()) &&
- "Invalid accessor");
- if (isArrayDesignator())
- return ArrayInfo.RBracketLoc;
- else
- return ArrayRangeInfo.RBracketLoc;
- }
-
- SourceLocation getEllipsisLoc() const {
- assert(isArrayRangeDesignator() && "Invalid accessor");
- return ArrayRangeInfo.EllipsisLoc;
- }
-
- static Designator getField(const IdentifierInfo *II, SourceLocation DotLoc,
- SourceLocation NameLoc) {
- Designator D;
- D.Kind = FieldDesignator;
- new (&D.FieldInfo) FieldDesignatorInfo;
- D.FieldInfo.II = II;
- D.FieldInfo.DotLoc = DotLoc;
- D.FieldInfo.NameLoc = NameLoc;
- return D;
- }
-
- static Designator getArray(Expr *Index,
- SourceLocation LBracketLoc) {
- Designator D;
- D.Kind = ArrayDesignator;
- new (&D.ArrayInfo) ArrayDesignatorInfo;
- D.ArrayInfo.Index = Index;
- D.ArrayInfo.LBracketLoc = LBracketLoc;
- D.ArrayInfo.RBracketLoc = SourceLocation();
- return D;
- }
-
- static Designator getArrayRange(Expr *Start,
- Expr *End,
- SourceLocation LBracketLoc,
- SourceLocation EllipsisLoc) {
- Designator D;
- D.Kind = ArrayRangeDesignator;
- new (&D.ArrayRangeInfo) ArrayRangeDesignatorInfo;
- D.ArrayRangeInfo.Start = Start;
- D.ArrayRangeInfo.End = End;
- D.ArrayRangeInfo.LBracketLoc = LBracketLoc;
- D.ArrayRangeInfo.EllipsisLoc = EllipsisLoc;
- D.ArrayRangeInfo.RBracketLoc = SourceLocation();
- return D;
- }
-
- void setRBracketLoc(SourceLocation RBracketLoc) const {
- assert((isArrayDesignator() || isArrayRangeDesignator()) &&
- "Invalid accessor");
- if (isArrayDesignator())
- ArrayInfo.RBracketLoc = RBracketLoc;
- else
- ArrayRangeInfo.RBracketLoc = RBracketLoc;
- }
-
- /// ClearExprs - Null out any expression references, which prevents
- /// them from being 'delete'd later.
- void ClearExprs(Sema &Actions) {}
-
- /// FreeExprs - Release any unclaimed memory for the expressions in
- /// this designator.
- void FreeExprs(Sema &Actions) {}
-};
-
-
-/// Designation - Represent a full designation, which is a sequence of
-/// designators. This class is mostly a helper for InitListDesignations.
-class Designation {
- /// Designators - The actual designators for this initializer.
- SmallVector<Designator, 2> Designators;
-
-public:
- /// AddDesignator - Add a designator to the end of this list.
- void AddDesignator(Designator D) {
- Designators.push_back(D);
- }
-
- bool empty() const { return Designators.empty(); }
-
- unsigned getNumDesignators() const { return Designators.size(); }
- const Designator &getDesignator(unsigned Idx) const {
- assert(Idx < Designators.size());
- return Designators[Idx];
- }
-
- /// ClearExprs - Null out any expression references, which prevents them from
- /// being 'delete'd later.
- void ClearExprs(Sema &Actions) {}
-
- /// FreeExprs - Release any unclaimed memory for the expressions in this
- /// designation.
- void FreeExprs(Sema &Actions) {}
-};
-
-} // end namespace clang
-
-#endif
}
bool VisitDesignatedInitExpr(const DesignatedInitExpr *E) {
- for (const DesignatedInitExpr::Designator &D : E->designators()) {
+ for (const Designator &D : E->designators()) {
if (D.isFieldDesignator() && D.getField()) {
const FieldDecl *Decl = D.getField();
if (!visit(Decl, D.getFieldLoc(), D.getFieldLoc()))
#include "clang/AST/DeclTemplate.h"
#include "clang/AST/DeclVisitor.h"
#include "clang/AST/DeclarationName.h"
+#include "clang/AST/Designator.h"
#include "clang/AST/Expr.h"
#include "clang/AST/ExprCXX.h"
#include "clang/AST/ExprObjC.h"
Expected<CXXCastPath> ImportCastPath(CastExpr *E);
Expected<APValue> ImportAPValue(const APValue &FromValue);
- using Designator = DesignatedInitExpr::Designator;
-
/// What we should import from the definition.
enum ImportDefinitionKind {
/// Import the default subset of the definition, which might be
NumDecls);
}
-template <>
-Expected<ASTNodeImporter::Designator>
-ASTNodeImporter::import(const Designator &D) {
+template <> Expected<Designator> ASTNodeImporter::import(const Designator &D) {
if (D.isFieldDesignator()) {
IdentifierInfo *ToFieldName = Importer.Import(D.getFieldName());
if (!ToFieldLocOrErr)
return ToFieldLocOrErr.takeError();
- return Designator(ToFieldName, *ToDotLocOrErr, *ToFieldLocOrErr);
+ return Designator::CreateFieldDesignator(ToFieldName, *ToDotLocOrErr,
+ *ToFieldLocOrErr);
}
ExpectedSLoc ToLBracketLocOrErr = import(D.getLBracketLoc());
return ToRBracketLocOrErr.takeError();
if (D.isArrayDesignator())
- return Designator(D.getFirstExprIndex(),
- *ToLBracketLocOrErr, *ToRBracketLocOrErr);
+ return Designator::CreateArrayDesignator(
+ D.getFirstExprIndex(), *ToLBracketLocOrErr, *ToRBracketLocOrErr);
ExpectedSLoc ToEllipsisLocOrErr = import(D.getEllipsisLoc());
if (!ToEllipsisLocOrErr)
return ToEllipsisLocOrErr.takeError();
assert(D.isArrayRangeDesignator());
- return Designator(
+ return Designator::CreateArrayRangeDesignator(
D.getFirstExprIndex(), *ToLBracketLocOrErr, *ToEllipsisLocOrErr,
*ToRBracketLocOrErr);
}
// DesignatedInitExpr
//===----------------------------------------------------------------------===//
-IdentifierInfo *DesignatedInitExpr::Designator::getFieldName() const {
- assert(Kind == FieldDesignator && "Only valid on a field designator");
- if (Field.NameOrField & 0x01)
- return reinterpret_cast<IdentifierInfo *>(Field.NameOrField & ~0x01);
- return getField()->getIdentifier();
+const IdentifierInfo *Designator::getFieldName() const {
+ assert(isFieldDesignator() && "Invalid accessor");
+ if (auto *II = FieldInfo.getIdentifierInfo())
+ return II;
+ return FieldInfo.getFieldDecl()->getIdentifier();
}
DesignatedInitExpr::DesignatedInitExpr(const ASTContext &C, QualType Ty,
}
SourceLocation DesignatedInitExpr::getBeginLoc() const {
- SourceLocation StartLoc;
auto *DIE = const_cast<DesignatedInitExpr *>(this);
Designator &First = *DIE->getDesignator(0);
- if (First.isFieldDesignator())
- StartLoc = GNUSyntax ? First.Field.FieldLoc : First.Field.DotLoc;
- else
- StartLoc = First.ArrayOrRange.LBracketLoc;
- return StartLoc;
+ return First.getBeginLoc();
}
SourceLocation DesignatedInitExpr::getEndLoc() const {
}
Expr *DesignatedInitExpr::getArrayIndex(const Designator& D) const {
- assert(D.Kind == Designator::ArrayDesignator && "Requires array designator");
- return getSubExpr(D.ArrayOrRange.Index + 1);
+ assert(D.isArrayDesignator() && "Requires array designator");
+ return getSubExpr(D.getFirstExprIndex() + 1);
}
Expr *DesignatedInitExpr::getArrayRangeStart(const Designator &D) const {
- assert(D.Kind == Designator::ArrayRangeDesignator &&
- "Requires array range designator");
- return getSubExpr(D.ArrayOrRange.Index + 1);
+ assert(D.isArrayRangeDesignator() && "Requires array range designator");
+ return getSubExpr(D.getFirstExprIndex() + 1);
}
Expr *DesignatedInitExpr::getArrayRangeEnd(const Designator &D) const {
- assert(D.Kind == Designator::ArrayRangeDesignator &&
- "Requires array range designator");
- return getSubExpr(D.ArrayOrRange.Index + 2);
+ assert(D.isArrayRangeDesignator() && "Requires array range designator");
+ return getSubExpr(D.getFirstExprIndex() + 2);
}
/// Replaces the designator at index @p Idx with the series
void StmtPrinter::VisitDesignatedInitExpr(DesignatedInitExpr *Node) {
bool NeedsEquals = true;
- for (const DesignatedInitExpr::Designator &D : Node->designators()) {
+ for (const Designator &D : Node->designators()) {
if (D.isFieldDesignator()) {
if (D.getDotLoc().isInvalid()) {
- if (IdentifierInfo *II = D.getFieldName()) {
+ if (const IdentifierInfo *II = D.getFieldName()) {
OS << II->getName() << ":";
NeedsEquals = false;
}
void StmtProfiler::VisitDesignatedInitExpr(const DesignatedInitExpr *S) {
VisitExpr(S);
ID.AddBoolean(S->usesGNUSyntax());
- for (const DesignatedInitExpr::Designator &D : S->designators()) {
+ for (const Designator &D : S->designators()) {
if (D.isFieldDesignator()) {
ID.AddInteger(0);
VisitName(D.getFieldName());
}
bool VisitDesignatedInitExpr(DesignatedInitExpr *E) {
- for (DesignatedInitExpr::Designator &D : llvm::reverse(E->designators())) {
+ for (Designator &D : llvm::reverse(E->designators())) {
if (D.isFieldDesignator() && D.getField())
return IndexCtx.handleReference(D.getField(), D.getFieldLoc(), Parent,
ParentDC, SymbolRoleSet(), {}, E);
};
auto visitSyntacticDesignatedInitExpr = [&](DesignatedInitExpr *E) -> bool {
- for (DesignatedInitExpr::Designator &D : llvm::reverse(E->designators())) {
+ for (Designator &D : llvm::reverse(E->designators())) {
if (D.isFieldDesignator() && D.getField())
return IndexCtx.handleReference(D.getField(), D.getFieldLoc(),
Parent, ParentDC, SymbolRoleSet(),
//
//===----------------------------------------------------------------------===//
+#include "clang/AST/Designator.h"
#include "clang/Basic/TokenKinds.h"
#include "clang/Parse/ParseDiagnostic.h"
#include "clang/Parse/Parser.h"
#include "clang/Parse/RAIIObjectsForParser.h"
-#include "clang/Sema/Designator.h"
#include "clang/Sema/Ownership.h"
#include "clang/Sema/Scope.h"
#include "llvm/ADT/STLExtras.h"
NewSyntax);
Designation D;
- D.AddDesignator(Designator::getField(FieldName, SourceLocation(), NameLoc));
+ D.AddDesignator(Designator::CreateFieldDesignator(
+ FieldName, SourceLocation(), NameLoc));
PreferredType.enterDesignatedInitializer(
Tok.getLocation(), DesignatorCompletion.PreferredBaseType, D);
return Actions.ActOnDesignatedInitializer(D, ColonLoc, true,
return ExprError();
}
- Desig.AddDesignator(Designator::getField(Tok.getIdentifierInfo(), DotLoc,
- Tok.getLocation()));
+ Desig.AddDesignator(Designator::CreateFieldDesignator(
+ Tok.getIdentifierInfo(), DotLoc, Tok.getLocation()));
ConsumeToken(); // Eat the identifier.
continue;
}
// If this is a normal array designator, remember it.
if (Tok.isNot(tok::ellipsis)) {
- Desig.AddDesignator(Designator::getArray(Idx.get(), StartLoc));
+ Desig.AddDesignator(
+ Designator::CreateArrayDesignator(Idx.get(), StartLoc));
} else {
// Handle the gnu array range extension.
Diag(Tok, diag::ext_gnu_array_range);
SkipUntil(tok::r_square, StopAtSemi);
return RHS;
}
- Desig.AddDesignator(Designator::getArrayRange(Idx.get(),
- RHS.get(),
- StartLoc, EllipsisLoc));
+ Desig.AddDesignator(Designator::CreateArrayRangeDesignator(
+ Idx.get(), RHS.get(), StartLoc, EllipsisLoc));
}
T.consumeClose();
#include "clang/AST/DeclCXX.h"
#include "clang/AST/DeclObjC.h"
#include "clang/AST/DeclTemplate.h"
+#include "clang/AST/Designator.h"
#include "clang/AST/Expr.h"
#include "clang/AST/ExprCXX.h"
#include "clang/AST/ExprConcepts.h"
#include "clang/Lex/Preprocessor.h"
#include "clang/Sema/CodeCompleteConsumer.h"
#include "clang/Sema/DeclSpec.h"
-#include "clang/Sema/Designator.h"
#include "clang/Sema/Lookup.h"
#include "clang/Sema/Overload.h"
#include "clang/Sema/ParsedAttr.h"
// Look for designated initializers.
// They're in their syntactic form, not yet resolved to fields.
- IdentifierInfo *DesignatedFieldName = nullptr;
+ const IdentifierInfo *DesignatedFieldName = nullptr;
unsigned ArgsAfterDesignator = 0;
for (const Expr *Arg : Args) {
if (const auto *DIE = dyn_cast<DesignatedInitExpr>(Arg)) {
assert(D.isFieldDesignator());
auto *RD = getAsRecordDecl(BaseType);
if (RD && RD->isCompleteDefinition()) {
- for (const auto *Member : RD->lookup(D.getField()))
+ for (const auto *Member : RD->lookup(D.getFieldName()))
if (const FieldDecl *FD = llvm::dyn_cast<FieldDecl>(Member)) {
NextType = FD->getType();
break;
#include "clang/AST/CXXInheritance.h"
#include "clang/AST/DeclObjC.h"
#include "clang/AST/DeclTemplate.h"
+#include "clang/AST/Designator.h"
#include "clang/AST/EvaluatedExprVisitor.h"
#include "clang/AST/Expr.h"
#include "clang/AST/ExprCXX.h"
#include "clang/Sema/AnalysisBasedWarnings.h"
#include "clang/Sema/DeclSpec.h"
#include "clang/Sema/DelayedDiagnostic.h"
-#include "clang/Sema/Designator.h"
#include "clang/Sema/Initialization.h"
#include "clang/Sema/Lookup.h"
#include "clang/Sema/Overload.h"
#include "clang/AST/ASTContext.h"
#include "clang/AST/DeclObjC.h"
+#include "clang/AST/Designator.h"
#include "clang/AST/ExprCXX.h"
#include "clang/AST/ExprObjC.h"
#include "clang/AST/ExprOpenMP.h"
#include "clang/Basic/CharInfo.h"
#include "clang/Basic/SourceManager.h"
#include "clang/Basic/TargetInfo.h"
-#include "clang/Sema/Designator.h"
#include "clang/Sema/Initialization.h"
#include "clang/Sema/Lookup.h"
#include "clang/Sema/SemaInternal.h"
DesignatedInitExpr *DIE,
unsigned DesigIdx,
IndirectFieldDecl *IndirectField) {
- typedef DesignatedInitExpr::Designator Designator;
-
// Build the replacement designators.
SmallVector<Designator, 4> Replacements;
for (IndirectFieldDecl::chain_iterator PI = IndirectField->chain_begin(),
PE = IndirectField->chain_end(); PI != PE; ++PI) {
if (PI + 1 == PE)
- Replacements.push_back(Designator((IdentifierInfo *)nullptr,
- DIE->getDesignator(DesigIdx)->getDotLoc(),
- DIE->getDesignator(DesigIdx)->getFieldLoc()));
+ Replacements.push_back(Designator::CreateFieldDesignator(
+ nullptr, DIE->getDesignator(DesigIdx)->getDotLoc(),
+ DIE->getDesignator(DesigIdx)->getFieldLoc()));
else
- Replacements.push_back(Designator((IdentifierInfo *)nullptr,
- SourceLocation(), SourceLocation()));
+ Replacements.push_back(Designator::CreateFieldDesignator(
+ nullptr, SourceLocation(), SourceLocation()));
assert(isa<FieldDecl>(*PI));
Replacements.back().setField(cast<FieldDecl>(*PI));
}
return hadError && !prevHadError;
}
- DesignatedInitExpr::Designator *D = DIE->getDesignator(DesigIdx);
+ Designator *D = DIE->getDesignator(DesigIdx);
bool IsFirstDesignator = (DesigIdx == 0);
if (IsFirstDesignator ? FullyStructuredList : StructuredList) {
// Determine the structural initializer list that corresponds to the
FieldDecl *KnownField = D->getField();
if (!KnownField) {
- IdentifierInfo *FieldName = D->getFieldName();
+ const IdentifierInfo *FieldName = D->getFieldName();
DeclContext::lookup_result Lookup = RT->getDecl()->lookup(FieldName);
for (NamedDecl *ND : Lookup) {
if (auto *FD = dyn_cast<FieldDecl>(ND)) {
// We can't designate an object within the flexible array
// member (because GCC doesn't allow it).
if (!VerifyOnly) {
- DesignatedInitExpr::Designator *NextD
- = DIE->getDesignator(DesigIdx + 1);
+ Designator *NextD = DIE->getDesignator(DesigIdx + 1);
SemaRef.Diag(NextD->getBeginLoc(),
diag::err_designator_into_flexible_array_member)
<< SourceRange(NextD->getBeginLoc(), DIE->getEndLoc());
ExprResult Sema::ActOnDesignatedInitializer(Designation &Desig,
SourceLocation EqualOrColonLoc,
- bool GNUSyntax,
- ExprResult Init) {
- typedef DesignatedInitExpr::Designator ASTDesignator;
-
+ bool GNUSyntax, ExprResult Init) {
bool Invalid = false;
- SmallVector<ASTDesignator, 32> Designators;
+ SmallVector<Designator, 32> Designators;
SmallVector<Expr *, 32> InitExpressions;
// Build designators and check array designator expressions.
for (unsigned Idx = 0; Idx < Desig.getNumDesignators(); ++Idx) {
const Designator &D = Desig.getDesignator(Idx);
- switch (D.getKind()) {
- case Designator::FieldDesignator:
- Designators.push_back(ASTDesignator(D.getField(), D.getDotLoc(),
- D.getFieldLoc()));
- break;
- case Designator::ArrayDesignator: {
+ if (D.isFieldDesignator()) {
+ Designators.push_back(Designator::CreateFieldDesignator(
+ D.getFieldName(), D.getDotLoc(), D.getFieldLoc()));
+ } else if (D.isArrayDesignator()) {
Expr *Index = static_cast<Expr *>(D.getArrayIndex());
llvm::APSInt IndexValue;
+
if (!Index->isTypeDependent() && !Index->isValueDependent())
Index = CheckArrayDesignatorExpr(*this, Index, IndexValue).get();
if (!Index)
Invalid = true;
else {
- Designators.push_back(ASTDesignator(InitExpressions.size(),
- D.getLBracketLoc(),
- D.getRBracketLoc()));
+ Designators.push_back(Designator::CreateArrayDesignator(
+ InitExpressions.size(), D.getLBracketLoc(), D.getRBracketLoc()));
InitExpressions.push_back(Index);
}
- break;
- }
-
- case Designator::ArrayRangeDesignator: {
+ } else if (D.isArrayRangeDesignator()) {
Expr *StartIndex = static_cast<Expr *>(D.getArrayRangeStart());
Expr *EndIndex = static_cast<Expr *>(D.getArrayRangeEnd());
llvm::APSInt StartValue;
StartIndex->isValueDependent();
bool EndDependent = EndIndex->isTypeDependent() ||
EndIndex->isValueDependent();
+
if (!StartDependent)
StartIndex =
CheckArrayDesignatorExpr(*this, StartIndex, StartValue).get();
+
if (!EndDependent)
EndIndex = CheckArrayDesignatorExpr(*this, EndIndex, EndValue).get();
<< StartIndex->getSourceRange() << EndIndex->getSourceRange();
Invalid = true;
} else {
- Designators.push_back(ASTDesignator(InitExpressions.size(),
- D.getLBracketLoc(),
- D.getEllipsisLoc(),
- D.getRBracketLoc()));
+ Designators.push_back(Designator::CreateArrayRangeDesignator(
+ InitExpressions.size(), D.getLBracketLoc(), D.getEllipsisLoc(),
+ D.getRBracketLoc()));
InitExpressions.push_back(StartIndex);
InitExpressions.push_back(EndIndex);
}
}
- break;
- }
}
}
if (Invalid || Init.isInvalid())
return ExprError();
- // Clear out the expressions within the designation.
- Desig.ClearExprs(*this);
-
return DesignatedInitExpr::Create(Context, Designators, InitExpressions,
EqualOrColonLoc, GNUSyntax,
Init.getAs<Expr>());
#include "clang/AST/Decl.h"
#include "clang/AST/DeclObjC.h"
#include "clang/AST/DeclTemplate.h"
+#include "clang/AST/Designator.h"
#include "clang/AST/Expr.h"
-#include "clang/AST/ExprConcepts.h"
#include "clang/AST/ExprCXX.h"
+#include "clang/AST/ExprConcepts.h"
#include "clang/AST/ExprObjC.h"
#include "clang/AST/ExprOpenMP.h"
#include "clang/AST/OpenMPClause.h"
#include "clang/AST/StmtOpenMP.h"
#include "clang/Basic/DiagnosticParse.h"
#include "clang/Basic/OpenMPKinds.h"
-#include "clang/Sema/Designator.h"
#include "clang/Sema/Lookup.h"
#include "clang/Sema/Ownership.h"
#include "clang/Sema/ParsedTemplate.h"
// transform the designators.
SmallVector<Expr*, 4> ArrayExprs;
bool ExprChanged = false;
- for (const DesignatedInitExpr::Designator &D : E->designators()) {
+ for (const Designator &D : E->designators()) {
if (D.isFieldDesignator()) {
- Desig.AddDesignator(Designator::getField(D.getFieldName(),
- D.getDotLoc(),
- D.getFieldLoc()));
+ Desig.AddDesignator(Designator::CreateFieldDesignator(
+ D.getFieldName(), D.getDotLoc(), D.getFieldLoc()));
if (D.getField()) {
FieldDecl *Field = cast_or_null<FieldDecl>(
getDerived().TransformDecl(D.getFieldLoc(), D.getField()));
return ExprError();
Desig.AddDesignator(
- Designator::getArray(Index.get(), D.getLBracketLoc()));
+ Designator::CreateArrayDesignator(Index.get(), D.getLBracketLoc()));
ExprChanged = ExprChanged || Init.get() != E->getArrayIndex(D);
ArrayExprs.push_back(Index.get());
if (End.isInvalid())
return ExprError();
- Desig.AddDesignator(Designator::getArrayRange(Start.get(),
- End.get(),
- D.getLBracketLoc(),
- D.getEllipsisLoc()));
+ Desig.AddDesignator(Designator::CreateArrayRangeDesignator(
+ Start.get(), End.get(), D.getLBracketLoc(), D.getEllipsisLoc()));
ExprChanged = ExprChanged || Start.get() != E->getArrayRangeStart(D) ||
End.get() != E->getArrayRangeEnd(D);
}
void ASTStmtReader::VisitDesignatedInitExpr(DesignatedInitExpr *E) {
- using Designator = DesignatedInitExpr::Designator;
-
VisitExpr(E);
unsigned NumSubExprs = Record.readInt();
assert(NumSubExprs == E->getNumSubExprs() && "Wrong number of subexprs");
auto *Field = readDeclAs<FieldDecl>();
SourceLocation DotLoc = readSourceLocation();
SourceLocation FieldLoc = readSourceLocation();
- Designators.push_back(Designator(Field->getIdentifier(), DotLoc,
- FieldLoc));
+ Designators.push_back(Designator::CreateFieldDesignator(
+ Field->getIdentifier(), DotLoc, FieldLoc));
Designators.back().setField(Field);
break;
}
const IdentifierInfo *Name = Record.readIdentifier();
SourceLocation DotLoc = readSourceLocation();
SourceLocation FieldLoc = readSourceLocation();
- Designators.push_back(Designator(Name, DotLoc, FieldLoc));
+ Designators.push_back(
+ Designator::CreateFieldDesignator(Name, DotLoc, FieldLoc));
break;
}
unsigned Index = Record.readInt();
SourceLocation LBracketLoc = readSourceLocation();
SourceLocation RBracketLoc = readSourceLocation();
- Designators.push_back(Designator(Index, LBracketLoc, RBracketLoc));
+ Designators.push_back(
+ Designator::CreateArrayDesignator(Index, LBracketLoc, RBracketLoc));
break;
}
SourceLocation LBracketLoc = readSourceLocation();
SourceLocation EllipsisLoc = readSourceLocation();
SourceLocation RBracketLoc = readSourceLocation();
- Designators.push_back(Designator(Index, LBracketLoc, EllipsisLoc,
- RBracketLoc));
+ Designators.push_back(Designator::CreateArrayRangeDesignator(
+ Index, LBracketLoc, EllipsisLoc, RBracketLoc));
break;
}
}
Record.AddStmt(E->getSubExpr(I));
Record.AddSourceLocation(E->getEqualOrColonLoc());
Record.push_back(E->usesGNUSyntax());
- for (const DesignatedInitExpr::Designator &D : E->designators()) {
+ for (const Designator &D : E->designators()) {
if (D.isFieldDesignator()) {
if (FieldDecl *Field = D.getField()) {
Record.push_back(serialization::DESIG_FIELD_DECL);
}
bool VisitDesignatedInitExpr(const DesignatedInitExpr *E) {
- for (const DesignatedInitExpr::Designator &D : E->designators()) {
+ for (const Designator &D : E->designators()) {
if (D.isFieldDesignator() && D.getField()) {
const FieldDecl *Decl = D.getField();
if (isInUSRSet(Decl)) {
}
void EnqueueVisitor::VisitDesignatedInitExpr(const DesignatedInitExpr *E) {
AddStmt(E->getInit());
- for (const DesignatedInitExpr::Designator &D :
- llvm::reverse(E->designators())) {
+ for (const Designator &D : llvm::reverse(E->designators())) {
if (D.isFieldDesignator()) {
if (FieldDecl *Field = D.getField())
AddMemberRef(Field, D.getFieldLoc());