Coverage Report

Created: 2020-09-19 12:23

/Users/buildslave/jenkins/workspace/coverage/llvm-project/clang/lib/AST/ExprObjC.cpp
Line
Count
Source (jump to first uncovered line)
1
//===- ExprObjC.cpp - (ObjC) Expression AST Node Implementation -----------===//
2
//
3
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4
// See https://llvm.org/LICENSE.txt for license information.
5
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6
//
7
//===----------------------------------------------------------------------===//
8
//
9
// This file implements the subclesses of Expr class declared in ExprObjC.h
10
//
11
//===----------------------------------------------------------------------===//
12
13
#include "clang/AST/ExprObjC.h"
14
#include "clang/AST/ASTContext.h"
15
#include "clang/AST/ComputeDependence.h"
16
#include "clang/AST/DependenceFlags.h"
17
#include "clang/AST/SelectorLocationsKind.h"
18
#include "clang/AST/Type.h"
19
#include "clang/AST/TypeLoc.h"
20
#include "llvm/ADT/SmallVector.h"
21
#include "llvm/Support/ErrorHandling.h"
22
#include <algorithm>
23
#include <cassert>
24
#include <cstdint>
25
26
using namespace clang;
27
28
ObjCArrayLiteral::ObjCArrayLiteral(ArrayRef<Expr *> Elements, QualType T,
29
                                   ObjCMethodDecl *Method, SourceRange SR)
30
    : Expr(ObjCArrayLiteralClass, T, VK_RValue, OK_Ordinary),
31
285
      NumElements(Elements.size()), Range(SR), ArrayWithObjectsMethod(Method) {
32
285
  Expr **SaveElements = getElements();
33
758
  for (unsigned I = 0, N = Elements.size(); I != N; 
++I473
)
34
473
    SaveElements[I] = Elements[I];
35
285
36
285
  setDependence(computeDependence(this));
37
285
}
38
39
ObjCArrayLiteral *ObjCArrayLiteral::Create(const ASTContext &C,
40
                                           ArrayRef<Expr *> Elements,
41
                                           QualType T, ObjCMethodDecl *Method,
42
285
                                           SourceRange SR) {
43
285
  void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(Elements.size()));
44
285
  return new (Mem) ObjCArrayLiteral(Elements, T, Method, SR);
45
285
}
46
47
ObjCArrayLiteral *ObjCArrayLiteral::CreateEmpty(const ASTContext &C,
48
4
                                                unsigned NumElements) {
49
4
  void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(NumElements));
50
4
  return new (Mem) ObjCArrayLiteral(EmptyShell(), NumElements);
51
4
}
52
53
ObjCDictionaryLiteral::ObjCDictionaryLiteral(ArrayRef<ObjCDictionaryElement> VK,
54
                                             bool HasPackExpansions, QualType T,
55
                                             ObjCMethodDecl *method,
56
                                             SourceRange SR)
57
    : Expr(ObjCDictionaryLiteralClass, T, VK_RValue, OK_Ordinary),
58
      NumElements(VK.size()), HasPackExpansions(HasPackExpansions), Range(SR),
59
213
      DictWithObjectsMethod(method) {
60
213
  KeyValuePair *KeyValues = getTrailingObjects<KeyValuePair>();
61
213
  ExpansionData *Expansions =
62
210
      HasPackExpansions ? 
getTrailingObjects<ExpansionData>()3
: nullptr;
63
540
  for (unsigned I = 0; I < NumElements; 
I++327
) {
64
327
    KeyValues[I].Key = VK[I].Key;
65
327
    KeyValues[I].Value = VK[I].Value;
66
327
    if (Expansions) {
67
6
      Expansions[I].EllipsisLoc = VK[I].EllipsisLoc;
68
6
      if (VK[I].NumExpansions)
69
0
        Expansions[I].NumExpansionsPlusOne = *VK[I].NumExpansions + 1;
70
6
      else
71
6
        Expansions[I].NumExpansionsPlusOne = 0;
72
6
    }
73
327
  }
74
213
  setDependence(computeDependence(this));
75
213
}
76
77
ObjCDictionaryLiteral *
78
ObjCDictionaryLiteral::Create(const ASTContext &C,
79
                              ArrayRef<ObjCDictionaryElement> VK,
80
                              bool HasPackExpansions, QualType T,
81
213
                              ObjCMethodDecl *method, SourceRange SR) {
82
213
  void *Mem = C.Allocate(totalSizeToAlloc<KeyValuePair, ExpansionData>(
83
210
      VK.size(), HasPackExpansions ? 
VK.size()3
: 0));
84
213
  return new (Mem) ObjCDictionaryLiteral(VK, HasPackExpansions, T, method, SR);
85
213
}
86
87
ObjCDictionaryLiteral *
88
ObjCDictionaryLiteral::CreateEmpty(const ASTContext &C, unsigned NumElements,
89
7
                                   bool HasPackExpansions) {
90
7
  void *Mem = C.Allocate(totalSizeToAlloc<KeyValuePair, ExpansionData>(
91
4
      NumElements, HasPackExpansions ? 
NumElements3
: 0));
92
7
  return new (Mem)
93
7
      ObjCDictionaryLiteral(EmptyShell(), NumElements, HasPackExpansions);
94
7
}
95
96
3.58k
QualType ObjCPropertyRefExpr::getReceiverType(const ASTContext &ctx) const {
97
3.58k
  if (isClassReceiver())
98
183
    return ctx.getObjCInterfaceType(getClassReceiver());
99
3.39k
100
3.39k
  if (isSuperReceiver())
101
121
    return getSuperReceiverType();
102
3.27k
103
3.27k
  return getBase()->getType();
104
3.27k
}
105
106
ObjCMessageExpr::ObjCMessageExpr(QualType T, ExprValueKind VK,
107
                                 SourceLocation LBracLoc,
108
                                 SourceLocation SuperLoc, bool IsInstanceSuper,
109
                                 QualType SuperType, Selector Sel,
110
                                 ArrayRef<SourceLocation> SelLocs,
111
                                 SelectorLocationsKind SelLocsK,
112
                                 ObjCMethodDecl *Method, ArrayRef<Expr *> Args,
113
                                 SourceLocation RBracLoc, bool isImplicit)
114
    : Expr(ObjCMessageExprClass, T, VK, OK_Ordinary),
115
      SelectorOrMethod(
116
          reinterpret_cast<uintptr_t>(Method ? Method : Sel.getAsOpaquePtr())),
117
      Kind(IsInstanceSuper ? SuperInstance : SuperClass),
118
      HasMethod(Method != nullptr), IsDelegateInitCall(false),
119
      IsImplicit(isImplicit), SuperLoc(SuperLoc), LBracLoc(LBracLoc),
120
1.25k
      RBracLoc(RBracLoc) {
121
1.25k
  initArgsAndSelLocs(Args, SelLocs, SelLocsK);
122
1.25k
  setReceiverPointer(SuperType.getAsOpaquePtr());
123
1.25k
  setDependence(computeDependence(this));
124
1.25k
}
125
126
ObjCMessageExpr::ObjCMessageExpr(QualType T, ExprValueKind VK,
127
                                 SourceLocation LBracLoc,
128
                                 TypeSourceInfo *Receiver, Selector Sel,
129
                                 ArrayRef<SourceLocation> SelLocs,
130
                                 SelectorLocationsKind SelLocsK,
131
                                 ObjCMethodDecl *Method, ArrayRef<Expr *> Args,
132
                                 SourceLocation RBracLoc, bool isImplicit)
133
    : Expr(ObjCMessageExprClass, T, VK, OK_Ordinary),
134
      SelectorOrMethod(
135
          reinterpret_cast<uintptr_t>(Method ? Method : Sel.getAsOpaquePtr())),
136
      Kind(Class), HasMethod(Method != nullptr), IsDelegateInitCall(false),
137
7.86k
      IsImplicit(isImplicit), LBracLoc(LBracLoc), RBracLoc(RBracLoc) {
138
7.86k
  initArgsAndSelLocs(Args, SelLocs, SelLocsK);
139
7.86k
  setReceiverPointer(Receiver);
140
7.86k
  setDependence(computeDependence(this));
141
7.86k
}
142
143
ObjCMessageExpr::ObjCMessageExpr(QualType T, ExprValueKind VK,
144
                                 SourceLocation LBracLoc, Expr *Receiver,
145
                                 Selector Sel, ArrayRef<SourceLocation> SelLocs,
146
                                 SelectorLocationsKind SelLocsK,
147
                                 ObjCMethodDecl *Method, ArrayRef<Expr *> Args,
148
                                 SourceLocation RBracLoc, bool isImplicit)
149
    : Expr(ObjCMessageExprClass, T, VK, OK_Ordinary),
150
      SelectorOrMethod(
151
          reinterpret_cast<uintptr_t>(Method ? Method : Sel.getAsOpaquePtr())),
152
      Kind(Instance), HasMethod(Method != nullptr), IsDelegateInitCall(false),
153
16.8k
      IsImplicit(isImplicit), LBracLoc(LBracLoc), RBracLoc(RBracLoc) {
154
16.8k
  initArgsAndSelLocs(Args, SelLocs, SelLocsK);
155
16.8k
  setReceiverPointer(Receiver);
156
16.8k
  setDependence(computeDependence(this));
157
16.8k
}
158
159
void ObjCMessageExpr::initArgsAndSelLocs(ArrayRef<Expr *> Args,
160
                                         ArrayRef<SourceLocation> SelLocs,
161
25.9k
                                         SelectorLocationsKind SelLocsK) {
162
25.9k
  setNumArgs(Args.size());
163
25.9k
  Expr **MyArgs = getArgs();
164
45.5k
  for (unsigned I = 0; I != Args.size(); 
++I19.5k
)
165
19.5k
    MyArgs[I] = Args[I];
166
25.9k
167
25.9k
  SelLocsKind = SelLocsK;
168
25.9k
  if (!isImplicit()) {
169
23.1k
    if (SelLocsK == SelLoc_NonStandard)
170
1.56k
      std::copy(SelLocs.begin(), SelLocs.end(), getStoredSelLocs());
171
23.1k
  }
172
25.9k
}
173
174
ObjCMessageExpr *
175
ObjCMessageExpr::Create(const ASTContext &Context, QualType T, ExprValueKind VK,
176
                        SourceLocation LBracLoc, SourceLocation SuperLoc,
177
                        bool IsInstanceSuper, QualType SuperType, Selector Sel,
178
                        ArrayRef<SourceLocation> SelLocs,
179
                        ObjCMethodDecl *Method, ArrayRef<Expr *> Args,
180
1.25k
                        SourceLocation RBracLoc, bool isImplicit) {
181
1.25k
  assert((!SelLocs.empty() || isImplicit) &&
182
1.25k
         "No selector locs for non-implicit message");
183
1.25k
  ObjCMessageExpr *Mem;
184
1.25k
  SelectorLocationsKind SelLocsK = SelectorLocationsKind();
185
1.25k
  if (isImplicit)
186
74
    Mem = alloc(Context, Args.size(), 0);
187
1.18k
  else
188
1.18k
    Mem = alloc(Context, Args, RBracLoc, SelLocs, Sel, SelLocsK);
189
1.25k
  return new (Mem) ObjCMessageExpr(T, VK, LBracLoc, SuperLoc, IsInstanceSuper,
190
1.25k
                                   SuperType, Sel, SelLocs, SelLocsK, Method,
191
1.25k
                                   Args, RBracLoc, isImplicit);
192
1.25k
}
193
194
ObjCMessageExpr *
195
ObjCMessageExpr::Create(const ASTContext &Context, QualType T, ExprValueKind VK,
196
                        SourceLocation LBracLoc, TypeSourceInfo *Receiver,
197
                        Selector Sel, ArrayRef<SourceLocation> SelLocs,
198
                        ObjCMethodDecl *Method, ArrayRef<Expr *> Args,
199
7.86k
                        SourceLocation RBracLoc, bool isImplicit) {
200
7.86k
  assert((!SelLocs.empty() || isImplicit) &&
201
7.86k
         "No selector locs for non-implicit message");
202
7.86k
  ObjCMessageExpr *Mem;
203
7.86k
  SelectorLocationsKind SelLocsK = SelectorLocationsKind();
204
7.86k
  if (isImplicit)
205
198
    Mem = alloc(Context, Args.size(), 0);
206
7.66k
  else
207
7.66k
    Mem = alloc(Context, Args, RBracLoc, SelLocs, Sel, SelLocsK);
208
7.86k
  return new (Mem)
209
7.86k
      ObjCMessageExpr(T, VK, LBracLoc, Receiver, Sel, SelLocs, SelLocsK, Method,
210
7.86k
                      Args, RBracLoc, isImplicit);
211
7.86k
}
212
213
ObjCMessageExpr *
214
ObjCMessageExpr::Create(const ASTContext &Context, QualType T, ExprValueKind VK,
215
                        SourceLocation LBracLoc, Expr *Receiver, Selector Sel,
216
                        ArrayRef<SourceLocation> SelLocs,
217
                        ObjCMethodDecl *Method, ArrayRef<Expr *> Args,
218
16.8k
                        SourceLocation RBracLoc, bool isImplicit) {
219
16.8k
  assert((!SelLocs.empty() || isImplicit) &&
220
16.8k
         "No selector locs for non-implicit message");
221
16.8k
  ObjCMessageExpr *Mem;
222
16.8k
  SelectorLocationsKind SelLocsK = SelectorLocationsKind();
223
16.8k
  if (isImplicit)
224
2.50k
    Mem = alloc(Context, Args.size(), 0);
225
14.3k
  else
226
14.3k
    Mem = alloc(Context, Args, RBracLoc, SelLocs, Sel, SelLocsK);
227
16.8k
  return new (Mem)
228
16.8k
      ObjCMessageExpr(T, VK, LBracLoc, Receiver, Sel, SelLocs, SelLocsK, Method,
229
16.8k
                      Args, RBracLoc, isImplicit);
230
16.8k
}
231
232
ObjCMessageExpr *ObjCMessageExpr::CreateEmpty(const ASTContext &Context,
233
                                              unsigned NumArgs,
234
41
                                              unsigned NumStoredSelLocs) {
235
41
  ObjCMessageExpr *Mem = alloc(Context, NumArgs, NumStoredSelLocs);
236
41
  return new (Mem) ObjCMessageExpr(EmptyShell(), NumArgs);
237
41
}
238
239
ObjCMessageExpr *ObjCMessageExpr::alloc(const ASTContext &C,
240
                                        ArrayRef<Expr *> Args,
241
                                        SourceLocation RBraceLoc,
242
                                        ArrayRef<SourceLocation> SelLocs,
243
                                        Selector Sel,
244
23.1k
                                        SelectorLocationsKind &SelLocsK) {
245
23.1k
  SelLocsK = hasStandardSelectorLocs(Sel, SelLocs, Args, RBraceLoc);
246
23.1k
  unsigned NumStoredSelLocs =
247
21.6k
      (SelLocsK == SelLoc_NonStandard) ? 
SelLocs.size()1.56k
: 0;
248
23.1k
  return alloc(C, Args.size(), NumStoredSelLocs);
249
23.1k
}
250
251
ObjCMessageExpr *ObjCMessageExpr::alloc(const ASTContext &C, unsigned NumArgs,
252
26.0k
                                        unsigned NumStoredSelLocs) {
253
26.0k
  return (ObjCMessageExpr *)C.Allocate(
254
26.0k
      totalSizeToAlloc<void *, SourceLocation>(NumArgs + 1, NumStoredSelLocs),
255
26.0k
      alignof(ObjCMessageExpr));
256
26.0k
}
257
258
void ObjCMessageExpr::getSelectorLocs(
259
660
    SmallVectorImpl<SourceLocation> &SelLocs) const {
260
1.30k
  for (unsigned i = 0, e = getNumSelectorLocs(); i != e; 
++i642
)
261
642
    SelLocs.push_back(getSelectorLoc(i));
262
660
}
263
264
265
9
QualType ObjCMessageExpr::getCallReturnType(ASTContext &Ctx) const {
266
9
  if (const ObjCMethodDecl *MD = getMethodDecl()) {
267
9
    QualType QT = MD->getReturnType();
268
9
    if (QT == Ctx.getObjCInstanceType()) {
269
      // instancetype corresponds to expression types.
270
0
      return getType();
271
0
    }
272
9
    return QT;
273
9
  }
274
0
275
  // Expression type might be different from an expected call return type,
276
  // as expression type would never be a reference even if call returns a
277
  // reference. Reconstruct the original expression type.
278
0
  QualType QT = getType();
279
0
  switch (getValueKind()) {
280
0
  case VK_LValue:
281
0
    return Ctx.getLValueReferenceType(QT);
282
0
  case VK_XValue:
283
0
    return Ctx.getRValueReferenceType(QT);
284
0
  case VK_RValue:
285
0
    return QT;
286
0
  }
287
0
  llvm_unreachable("Unsupported ExprValueKind");
288
0
}
289
290
72
SourceRange ObjCMessageExpr::getReceiverRange() const {
291
72
  switch (getReceiverKind()) {
292
72
  case Instance:
293
72
    return getInstanceReceiver()->getSourceRange();
294
0
295
0
  case Class:
296
0
    return getClassReceiverTypeInfo()->getTypeLoc().getSourceRange();
297
0
298
0
  case SuperInstance:
299
0
  case SuperClass:
300
0
    return getSuperLoc();
301
0
  }
302
0
303
0
  llvm_unreachable("Invalid ReceiverKind!");
304
0
}
305
306
49.9k
Selector ObjCMessageExpr::getSelector() const {
307
49.9k
  if (HasMethod)
308
49.1k
    return reinterpret_cast<const ObjCMethodDecl *>(SelectorOrMethod)
309
49.1k
        ->getSelector();
310
822
  return Selector(SelectorOrMethod);
311
822
}
312
313
92.9k
QualType ObjCMessageExpr::getReceiverType() const {
314
92.9k
  switch (getReceiverKind()) {
315
81.1k
  case Instance:
316
81.1k
    return getInstanceReceiver()->getType();
317
7.24k
  case Class:
318
7.24k
    return getClassReceiver();
319
4.56k
  case SuperInstance:
320
4.56k
  case SuperClass:
321
4.56k
    return getSuperType();
322
0
  }
323
0
324
0
  llvm_unreachable("unexpected receiver kind");
325
0
}
326
327
92.7k
ObjCInterfaceDecl *ObjCMessageExpr::getReceiverInterface() const {
328
92.7k
  QualType T = getReceiverType();
329
92.7k
330
92.7k
  if (const ObjCObjectPointerType *Ptr = T->getAs<ObjCObjectPointerType>())
331
85.3k
    return Ptr->getInterfaceDecl();
332
7.37k
333
7.37k
  if (const ObjCObjectType *Ty = T->getAs<ObjCObjectType>())
334
7.26k
    return Ty->getInterface();
335
108
336
108
  return nullptr;
337
108
}
338
339
87.6k
Stmt::child_range ObjCMessageExpr::children() {
340
87.6k
  Stmt **begin;
341
87.6k
  if (getReceiverKind() == Instance)
342
58.5k
    begin = reinterpret_cast<Stmt **>(getTrailingObjects<void *>());
343
29.1k
  else
344
29.1k
    begin = reinterpret_cast<Stmt **>(getArgs());
345
87.6k
  return child_range(begin,
346
87.6k
                     reinterpret_cast<Stmt **>(getArgs() + getNumArgs()));
347
87.6k
}
348
349
0
Stmt::const_child_range ObjCMessageExpr::children() const {
350
0
  auto Children = const_cast<ObjCMessageExpr *>(this)->children();
351
0
  return const_child_range(Children.begin(), Children.end());
352
0
}
353
354
4
StringRef ObjCBridgedCastExpr::getBridgeKindName() const {
355
4
  switch (getBridgeKind()) {
356
4
  case OBC_Bridge:
357
4
    return "__bridge";
358
0
  case OBC_BridgeTransfer:
359
0
    return "__bridge_transfer";
360
0
  case OBC_BridgeRetained:
361
0
    return "__bridge_retained";
362
0
  }
363
0
364
0
  llvm_unreachable("Invalid BridgeKind!");
365
0
}