1 //===- unittests/IR/MetadataTest.cpp - Metadata unit tests ----------------===//
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
7 //===----------------------------------------------------------------------===//
9 #include "llvm/IR/Metadata.h"
10 #include "llvm/ADT/STLExtras.h"
11 #include "llvm/IR/Constants.h"
12 #include "llvm/IR/DebugInfo.h"
13 #include "llvm/IR/DebugInfoMetadata.h"
14 #include "llvm/IR/Function.h"
15 #include "llvm/IR/Instructions.h"
16 #include "llvm/IR/LLVMContext.h"
17 #include "llvm/IR/Module.h"
18 #include "llvm/IR/ModuleSlotTracker.h"
19 #include "llvm/IR/Type.h"
20 #include "llvm/IR/Verifier.h"
21 #include "llvm/Support/raw_ostream.h"
22 #include "gtest/gtest.h"
27 TEST(ContextAndReplaceableUsesTest
, FromContext
) {
29 ContextAndReplaceableUses
CRU(Context
);
30 EXPECT_EQ(&Context
, &CRU
.getContext());
31 EXPECT_FALSE(CRU
.hasReplaceableUses());
32 EXPECT_FALSE(CRU
.getReplaceableUses());
35 TEST(ContextAndReplaceableUsesTest
, FromReplaceableUses
) {
37 ContextAndReplaceableUses
CRU(std::make_unique
<ReplaceableMetadataImpl
>(Context
));
38 EXPECT_EQ(&Context
, &CRU
.getContext());
39 EXPECT_TRUE(CRU
.hasReplaceableUses());
40 EXPECT_TRUE(CRU
.getReplaceableUses());
43 TEST(ContextAndReplaceableUsesTest
, makeReplaceable
) {
45 ContextAndReplaceableUses
CRU(Context
);
46 CRU
.makeReplaceable(std::make_unique
<ReplaceableMetadataImpl
>(Context
));
47 EXPECT_EQ(&Context
, &CRU
.getContext());
48 EXPECT_TRUE(CRU
.hasReplaceableUses());
49 EXPECT_TRUE(CRU
.getReplaceableUses());
52 TEST(ContextAndReplaceableUsesTest
, takeReplaceableUses
) {
54 auto ReplaceableUses
= std::make_unique
<ReplaceableMetadataImpl
>(Context
);
55 auto *Ptr
= ReplaceableUses
.get();
56 ContextAndReplaceableUses
CRU(std::move(ReplaceableUses
));
57 ReplaceableUses
= CRU
.takeReplaceableUses();
58 EXPECT_EQ(&Context
, &CRU
.getContext());
59 EXPECT_FALSE(CRU
.hasReplaceableUses());
60 EXPECT_FALSE(CRU
.getReplaceableUses());
61 EXPECT_EQ(Ptr
, ReplaceableUses
.get());
64 class MetadataTest
: public testing::Test
{
66 MetadataTest() : M("test", Context
), Counter(0) {}
73 MDNode
*getNode() { return MDNode::get(Context
, None
); }
74 MDNode
*getNode(Metadata
*MD
) { return MDNode::get(Context
, MD
); }
75 MDNode
*getNode(Metadata
*MD1
, Metadata
*MD2
) {
76 Metadata
*MDs
[] = {MD1
, MD2
};
77 return MDNode::get(Context
, MDs
);
80 MDTuple
*getTuple() { return MDTuple::getDistinct(Context
, None
); }
81 DISubroutineType
*getSubroutineType() {
82 return DISubroutineType::getDistinct(Context
, DINode::FlagZero
, 0,
85 DISubprogram
*getSubprogram() {
86 return DISubprogram::getDistinct(
87 Context
, nullptr, "", "", nullptr, 0, nullptr, 0, nullptr, 0, 0,
88 DINode::FlagZero
, DISubprogram::SPFlagZero
, nullptr);
91 return DIFile::getDistinct(Context
, "file.c", "/path/to/dir");
93 DICompileUnit
*getUnit() {
94 return DICompileUnit::getDistinct(
95 Context
, 1, getFile(), "clang", false, "-g", 2, "",
96 DICompileUnit::FullDebug
, getTuple(), getTuple(), getTuple(),
97 getTuple(), getTuple(), 0, true, false,
98 DICompileUnit::DebugNameTableKind::Default
, false);
100 DIType
*getBasicType(StringRef Name
) {
101 return DIBasicType::get(Context
, dwarf::DW_TAG_unspecified_type
, Name
);
103 DIType
*getDerivedType() {
104 return DIDerivedType::getDistinct(
105 Context
, dwarf::DW_TAG_pointer_type
, "", nullptr, 0, nullptr,
106 getBasicType("basictype"), 1, 2, 0, None
, DINode::FlagZero
);
108 Constant
*getConstant() {
109 return ConstantInt::get(Type::getInt32Ty(Context
), Counter
++);
111 ConstantAsMetadata
*getConstantAsMetadata() {
112 return ConstantAsMetadata::get(getConstant());
114 DIType
*getCompositeType() {
115 return DICompositeType::getDistinct(
116 Context
, dwarf::DW_TAG_structure_type
, "", nullptr, 0, nullptr, nullptr,
117 32, 32, 0, DINode::FlagZero
, nullptr, 0, nullptr, nullptr, "");
119 Function
*getFunction(StringRef Name
) {
120 return Function::Create(
121 FunctionType::get(Type::getVoidTy(Context
), None
, false),
122 Function::ExternalLinkage
, Name
, M
);
125 typedef MetadataTest MDStringTest
;
127 // Test that construction of MDString with different value produces different
128 // MDString objects, even with the same string pointer and nulls in the string.
129 TEST_F(MDStringTest
, CreateDifferent
) {
130 char x
[3] = { 'f', 0, 'A' };
131 MDString
*s1
= MDString::get(Context
, StringRef(&x
[0], 3));
133 MDString
*s2
= MDString::get(Context
, StringRef(&x
[0], 3));
137 // Test that creation of MDStrings with the same string contents produces the
138 // same MDString object, even with different pointers.
139 TEST_F(MDStringTest
, CreateSame
) {
140 char x
[4] = { 'a', 'b', 'c', 'X' };
141 char y
[4] = { 'a', 'b', 'c', 'Y' };
143 MDString
*s1
= MDString::get(Context
, StringRef(&x
[0], 3));
144 MDString
*s2
= MDString::get(Context
, StringRef(&y
[0], 3));
148 // Test that MDString prints out the string we fed it.
149 TEST_F(MDStringTest
, PrintingSimple
) {
150 char str
[14] = "testing 1 2 3";
151 MDString
*s
= MDString::get(Context
, StringRef(&str
[0], 13));
152 strncpy(str
, "aaaaaaaaaaaaa", 14);
155 raw_string_ostream
oss(Str
);
157 EXPECT_STREQ("!\"testing 1 2 3\"", oss
.str().c_str());
160 // Test printing of MDString with non-printable characters.
161 TEST_F(MDStringTest
, PrintingComplex
) {
162 char str
[5] = {0, '\n', '"', '\\', (char)-1};
163 MDString
*s
= MDString::get(Context
, StringRef(str
+0, 5));
165 raw_string_ostream
oss(Str
);
167 EXPECT_STREQ("!\"\\00\\0A\\22\\5C\\FF\"", oss
.str().c_str());
170 typedef MetadataTest MDNodeTest
;
172 // Test the two constructors, and containing other Constants.
173 TEST_F(MDNodeTest
, Simple
) {
174 char x
[3] = { 'a', 'b', 'c' };
175 char y
[3] = { '1', '2', '3' };
177 MDString
*s1
= MDString::get(Context
, StringRef(&x
[0], 3));
178 MDString
*s2
= MDString::get(Context
, StringRef(&y
[0], 3));
179 ConstantAsMetadata
*CI
=
180 ConstantAsMetadata::get(ConstantInt::get(Context
, APInt(8, 0)));
182 std::vector
<Metadata
*> V
;
187 MDNode
*n1
= MDNode::get(Context
, V
);
188 Metadata
*const c1
= n1
;
189 MDNode
*n2
= MDNode::get(Context
, c1
);
190 Metadata
*const c2
= n2
;
191 MDNode
*n3
= MDNode::get(Context
, V
);
192 MDNode
*n4
= MDNode::getIfExists(Context
, V
);
193 MDNode
*n5
= MDNode::getIfExists(Context
, c1
);
194 MDNode
*n6
= MDNode::getIfExists(Context
, c2
);
199 EXPECT_EQ(n6
, (Metadata
*)nullptr);
201 EXPECT_EQ(3u, n1
->getNumOperands());
202 EXPECT_EQ(s1
, n1
->getOperand(0));
203 EXPECT_EQ(CI
, n1
->getOperand(1));
204 EXPECT_EQ(s2
, n1
->getOperand(2));
206 EXPECT_EQ(1u, n2
->getNumOperands());
207 EXPECT_EQ(n1
, n2
->getOperand(0));
210 TEST_F(MDNodeTest
, Delete
) {
211 Constant
*C
= ConstantInt::get(Type::getInt32Ty(Context
), 1);
212 Instruction
*I
= new BitCastInst(C
, Type::getInt32Ty(Context
));
214 Metadata
*const V
= LocalAsMetadata::get(I
);
215 MDNode
*n
= MDNode::get(Context
, V
);
216 TrackingMDRef
wvh(n
);
223 TEST_F(MDNodeTest
, SelfReference
) {
227 auto Temp
= MDNode::getTemporary(Context
, None
);
228 Metadata
*Args
[] = {Temp
.get()};
229 MDNode
*Self
= MDNode::get(Context
, Args
);
230 Self
->replaceOperandWith(0, Self
);
231 ASSERT_EQ(Self
, Self
->getOperand(0));
233 // Self-references should be distinct, so MDNode::get() should grab a
234 // uniqued node that references Self, not Self.
236 MDNode
*Ref1
= MDNode::get(Context
, Args
);
237 MDNode
*Ref2
= MDNode::get(Context
, Args
);
238 EXPECT_NE(Self
, Ref1
);
239 EXPECT_EQ(Ref1
, Ref2
);
245 auto Temp
= MDNode::getTemporary(Context
, None
);
246 Metadata
*Args
[] = {Temp
.get(), MDNode::get(Context
, None
)};
247 MDNode
*Self
= MDNode::get(Context
, Args
);
248 Self
->replaceOperandWith(0, Self
);
249 ASSERT_EQ(Self
, Self
->getOperand(0));
251 // Self-references should be distinct, so MDNode::get() should grab a
252 // uniqued node that references Self, not Self itself.
254 MDNode
*Ref1
= MDNode::get(Context
, Args
);
255 MDNode
*Ref2
= MDNode::get(Context
, Args
);
256 EXPECT_NE(Self
, Ref1
);
257 EXPECT_EQ(Ref1
, Ref2
);
261 TEST_F(MDNodeTest
, Print
) {
262 Constant
*C
= ConstantInt::get(Type::getInt32Ty(Context
), 7);
263 MDString
*S
= MDString::get(Context
, "foo");
264 MDNode
*N0
= getNode();
265 MDNode
*N1
= getNode(N0
);
266 MDNode
*N2
= getNode(N0
, N1
);
268 Metadata
*Args
[] = {ConstantAsMetadata::get(C
), S
, nullptr, N0
, N1
, N2
};
269 MDNode
*N
= MDNode::get(Context
, Args
);
271 std::string Expected
;
273 raw_string_ostream
OS(Expected
);
274 OS
<< "<" << (void *)N
<< "> = !{";
275 C
->printAsOperand(OS
);
277 S
->printAsOperand(OS
);
279 MDNode
*Nodes
[] = {N0
, N1
, N2
};
280 for (auto *Node
: Nodes
)
281 OS
<< ", <" << (void *)Node
<< ">";
287 raw_string_ostream
OS(Actual
);
291 EXPECT_EQ(Expected
, Actual
);
294 #define EXPECT_PRINTER_EQ(EXPECTED, PRINT) \
296 std::string Actual_; \
297 raw_string_ostream OS(Actual_); \
300 std::string Expected_(EXPECTED); \
301 EXPECT_EQ(Expected_, Actual_); \
304 TEST_F(MDNodeTest
, PrintTemporary
) {
305 MDNode
*Arg
= getNode();
306 TempMDNode Temp
= MDNode::getTemporary(Context
, Arg
);
307 MDNode
*N
= getNode(Temp
.get());
308 Module
M("test", Context
);
309 NamedMDNode
*NMD
= M
.getOrInsertNamedMetadata("named");
312 EXPECT_PRINTER_EQ("!0 = !{!1}", N
->print(OS
, &M
));
313 EXPECT_PRINTER_EQ("!1 = <temporary!> !{!2}", Temp
->print(OS
, &M
));
314 EXPECT_PRINTER_EQ("!2 = !{}", Arg
->print(OS
, &M
));
317 Temp
->replaceAllUsesWith(Arg
);
320 TEST_F(MDNodeTest
, PrintFromModule
) {
321 Constant
*C
= ConstantInt::get(Type::getInt32Ty(Context
), 7);
322 MDString
*S
= MDString::get(Context
, "foo");
323 MDNode
*N0
= getNode();
324 MDNode
*N1
= getNode(N0
);
325 MDNode
*N2
= getNode(N0
, N1
);
327 Metadata
*Args
[] = {ConstantAsMetadata::get(C
), S
, nullptr, N0
, N1
, N2
};
328 MDNode
*N
= MDNode::get(Context
, Args
);
329 Module
M("test", Context
);
330 NamedMDNode
*NMD
= M
.getOrInsertNamedMetadata("named");
333 std::string Expected
;
335 raw_string_ostream
OS(Expected
);
337 C
->printAsOperand(OS
);
339 S
->printAsOperand(OS
);
340 OS
<< ", null, !1, !2, !3}";
343 EXPECT_PRINTER_EQ(Expected
, N
->print(OS
, &M
));
346 TEST_F(MDNodeTest
, PrintFromFunction
) {
347 Module
M("test", Context
);
348 auto *FTy
= FunctionType::get(Type::getVoidTy(Context
), false);
349 auto *F0
= Function::Create(FTy
, GlobalValue::ExternalLinkage
, "F0", &M
);
350 auto *F1
= Function::Create(FTy
, GlobalValue::ExternalLinkage
, "F1", &M
);
351 auto *BB0
= BasicBlock::Create(Context
, "entry", F0
);
352 auto *BB1
= BasicBlock::Create(Context
, "entry", F1
);
353 auto *R0
= ReturnInst::Create(Context
, BB0
);
354 auto *R1
= ReturnInst::Create(Context
, BB1
);
355 auto *N0
= MDNode::getDistinct(Context
, None
);
356 auto *N1
= MDNode::getDistinct(Context
, None
);
357 R0
->setMetadata("md", N0
);
358 R1
->setMetadata("md", N1
);
360 EXPECT_PRINTER_EQ("!0 = distinct !{}", N0
->print(OS
, &M
));
361 EXPECT_PRINTER_EQ("!1 = distinct !{}", N1
->print(OS
, &M
));
363 ModuleSlotTracker
MST(&M
);
364 EXPECT_PRINTER_EQ("!0 = distinct !{}", N0
->print(OS
, MST
));
365 EXPECT_PRINTER_EQ("!1 = distinct !{}", N1
->print(OS
, MST
));
368 TEST_F(MDNodeTest
, PrintFromMetadataAsValue
) {
369 Module
M("test", Context
);
372 Function::Create(FunctionType::get(Type::getVoidTy(Context
),
373 Type::getMetadataTy(Context
), false),
374 GlobalValue::ExternalLinkage
, "llvm.intrinsic", &M
);
376 auto *FTy
= FunctionType::get(Type::getVoidTy(Context
), false);
377 auto *F0
= Function::Create(FTy
, GlobalValue::ExternalLinkage
, "F0", &M
);
378 auto *F1
= Function::Create(FTy
, GlobalValue::ExternalLinkage
, "F1", &M
);
379 auto *BB0
= BasicBlock::Create(Context
, "entry", F0
);
380 auto *BB1
= BasicBlock::Create(Context
, "entry", F1
);
381 auto *N0
= MDNode::getDistinct(Context
, None
);
382 auto *N1
= MDNode::getDistinct(Context
, None
);
383 auto *MAV0
= MetadataAsValue::get(Context
, N0
);
384 auto *MAV1
= MetadataAsValue::get(Context
, N1
);
385 CallInst::Create(Intrinsic
, MAV0
, "", BB0
);
386 CallInst::Create(Intrinsic
, MAV1
, "", BB1
);
388 EXPECT_PRINTER_EQ("!0 = distinct !{}", MAV0
->print(OS
));
389 EXPECT_PRINTER_EQ("!1 = distinct !{}", MAV1
->print(OS
));
390 EXPECT_PRINTER_EQ("!0", MAV0
->printAsOperand(OS
, false));
391 EXPECT_PRINTER_EQ("!1", MAV1
->printAsOperand(OS
, false));
392 EXPECT_PRINTER_EQ("metadata !0", MAV0
->printAsOperand(OS
, true));
393 EXPECT_PRINTER_EQ("metadata !1", MAV1
->printAsOperand(OS
, true));
395 ModuleSlotTracker
MST(&M
);
396 EXPECT_PRINTER_EQ("!0 = distinct !{}", MAV0
->print(OS
, MST
));
397 EXPECT_PRINTER_EQ("!1 = distinct !{}", MAV1
->print(OS
, MST
));
398 EXPECT_PRINTER_EQ("!0", MAV0
->printAsOperand(OS
, false, MST
));
399 EXPECT_PRINTER_EQ("!1", MAV1
->printAsOperand(OS
, false, MST
));
400 EXPECT_PRINTER_EQ("metadata !0", MAV0
->printAsOperand(OS
, true, MST
));
401 EXPECT_PRINTER_EQ("metadata !1", MAV1
->printAsOperand(OS
, true, MST
));
404 TEST_F(MDNodeTest
, PrintWithDroppedCallOperand
) {
405 Module
M("test", Context
);
407 auto *FTy
= FunctionType::get(Type::getVoidTy(Context
), false);
408 auto *F0
= Function::Create(FTy
, GlobalValue::ExternalLinkage
, "F0", &M
);
409 auto *F1
= Function::Create(FTy
, GlobalValue::ExternalLinkage
, "F1", &M
);
410 auto *BB0
= BasicBlock::Create(Context
, "entry", F0
);
412 CallInst
*CI0
= CallInst::Create(F1
, "", BB0
);
413 CI0
->dropAllReferences();
415 auto *R0
= ReturnInst::Create(Context
, BB0
);
416 auto *N0
= MDNode::getDistinct(Context
, None
);
417 R0
->setMetadata("md", N0
);
419 // Printing the metadata node would previously result in a failed assertion
420 // due to the call instruction's dropped function operand.
421 ModuleSlotTracker
MST(&M
);
422 EXPECT_PRINTER_EQ("!0 = distinct !{}", N0
->print(OS
, MST
));
424 #undef EXPECT_PRINTER_EQ
426 TEST_F(MDNodeTest
, NullOperand
) {
428 MDNode
*Empty
= MDNode::get(Context
, None
);
430 // metadata !{metadata !{}}
431 Metadata
*Ops
[] = {Empty
};
432 MDNode
*N
= MDNode::get(Context
, Ops
);
433 ASSERT_EQ(Empty
, N
->getOperand(0));
435 // metadata !{metadata !{}} => metadata !{null}
436 N
->replaceOperandWith(0, nullptr);
437 ASSERT_EQ(nullptr, N
->getOperand(0));
441 MDNode
*NullOp
= MDNode::get(Context
, Ops
);
442 ASSERT_EQ(nullptr, NullOp
->getOperand(0));
443 EXPECT_EQ(N
, NullOp
);
446 TEST_F(MDNodeTest
, DistinctOnUniquingCollision
) {
448 MDNode
*Empty
= MDNode::get(Context
, None
);
449 ASSERT_TRUE(Empty
->isResolved());
450 EXPECT_FALSE(Empty
->isDistinct());
453 Metadata
*Wrapped1Ops
[] = {Empty
};
454 MDNode
*Wrapped1
= MDNode::get(Context
, Wrapped1Ops
);
455 ASSERT_EQ(Empty
, Wrapped1
->getOperand(0));
456 ASSERT_TRUE(Wrapped1
->isResolved());
457 EXPECT_FALSE(Wrapped1
->isDistinct());
460 Metadata
*Wrapped2Ops
[] = {Wrapped1
};
461 MDNode
*Wrapped2
= MDNode::get(Context
, Wrapped2Ops
);
462 ASSERT_EQ(Wrapped1
, Wrapped2
->getOperand(0));
463 ASSERT_TRUE(Wrapped2
->isResolved());
464 EXPECT_FALSE(Wrapped2
->isDistinct());
466 // !{!{!{}}} => !{!{}}
467 Wrapped2
->replaceOperandWith(0, Empty
);
468 ASSERT_EQ(Empty
, Wrapped2
->getOperand(0));
469 EXPECT_TRUE(Wrapped2
->isDistinct());
470 EXPECT_FALSE(Wrapped1
->isDistinct());
473 TEST_F(MDNodeTest
, UniquedOnDeletedOperand
) {
475 TempMDTuple T
= MDTuple::getTemporary(Context
, None
);
478 Metadata
*Ops
[] = {T
.get()};
479 MDTuple
*N
= MDTuple::get(Context
, Ops
);
481 // !{temp !{}} => !{null}
483 ASSERT_TRUE(N
->isUniqued());
484 Metadata
*NullOps
[] = {nullptr};
485 ASSERT_EQ(N
, MDTuple::get(Context
, NullOps
));
488 TEST_F(MDNodeTest
, DistinctOnDeletedValueOperand
) {
490 Type
*Ty
= Type::getInt1PtrTy(Context
);
491 std::unique_ptr
<GlobalVariable
> GV(
492 new GlobalVariable(Ty
, false, GlobalValue::ExternalLinkage
));
493 ConstantAsMetadata
*Op
= ConstantAsMetadata::get(GV
.get());
496 Metadata
*Ops
[] = {Op
};
497 MDTuple
*N
= MDTuple::get(Context
, Ops
);
499 // !{i1* @GV} => !{null}
501 ASSERT_TRUE(N
->isDistinct());
502 ASSERT_EQ(nullptr, N
->getOperand(0));
503 Metadata
*NullOps
[] = {nullptr};
504 ASSERT_NE(N
, MDTuple::get(Context
, NullOps
));
507 TEST_F(MDNodeTest
, getDistinct
) {
509 MDNode
*Empty
= MDNode::get(Context
, None
);
510 ASSERT_TRUE(Empty
->isResolved());
511 ASSERT_FALSE(Empty
->isDistinct());
512 ASSERT_EQ(Empty
, MDNode::get(Context
, None
));
515 MDNode
*Distinct1
= MDNode::getDistinct(Context
, None
);
516 MDNode
*Distinct2
= MDNode::getDistinct(Context
, None
);
517 EXPECT_TRUE(Distinct1
->isResolved());
518 EXPECT_TRUE(Distinct2
->isDistinct());
519 EXPECT_NE(Empty
, Distinct1
);
520 EXPECT_NE(Empty
, Distinct2
);
521 EXPECT_NE(Distinct1
, Distinct2
);
524 ASSERT_EQ(Empty
, MDNode::get(Context
, None
));
527 TEST_F(MDNodeTest
, isUniqued
) {
528 MDNode
*U
= MDTuple::get(Context
, None
);
529 MDNode
*D
= MDTuple::getDistinct(Context
, None
);
530 auto T
= MDTuple::getTemporary(Context
, None
);
531 EXPECT_TRUE(U
->isUniqued());
532 EXPECT_FALSE(D
->isUniqued());
533 EXPECT_FALSE(T
->isUniqued());
536 TEST_F(MDNodeTest
, isDistinct
) {
537 MDNode
*U
= MDTuple::get(Context
, None
);
538 MDNode
*D
= MDTuple::getDistinct(Context
, None
);
539 auto T
= MDTuple::getTemporary(Context
, None
);
540 EXPECT_FALSE(U
->isDistinct());
541 EXPECT_TRUE(D
->isDistinct());
542 EXPECT_FALSE(T
->isDistinct());
545 TEST_F(MDNodeTest
, isTemporary
) {
546 MDNode
*U
= MDTuple::get(Context
, None
);
547 MDNode
*D
= MDTuple::getDistinct(Context
, None
);
548 auto T
= MDTuple::getTemporary(Context
, None
);
549 EXPECT_FALSE(U
->isTemporary());
550 EXPECT_FALSE(D
->isTemporary());
551 EXPECT_TRUE(T
->isTemporary());
554 TEST_F(MDNodeTest
, getDistinctWithUnresolvedOperands
) {
556 auto Temp
= MDTuple::getTemporary(Context
, None
);
557 ASSERT_FALSE(Temp
->isResolved());
559 // distinct !{temporary !{}}
560 Metadata
*Ops
[] = {Temp
.get()};
561 MDNode
*Distinct
= MDNode::getDistinct(Context
, Ops
);
562 EXPECT_TRUE(Distinct
->isResolved());
563 EXPECT_EQ(Temp
.get(), Distinct
->getOperand(0));
565 // temporary !{} => !{}
566 MDNode
*Empty
= MDNode::get(Context
, None
);
567 Temp
->replaceAllUsesWith(Empty
);
568 EXPECT_EQ(Empty
, Distinct
->getOperand(0));
571 TEST_F(MDNodeTest
, handleChangedOperandRecursion
) {
573 MDNode
*N0
= MDNode::get(Context
, None
);
576 auto Temp3
= MDTuple::getTemporary(Context
, None
);
577 Metadata
*Ops1
[] = {Temp3
.get(), nullptr};
578 MDNode
*N1
= MDNode::get(Context
, Ops1
);
581 Metadata
*Ops2
[] = {Temp3
.get(), N0
};
582 MDNode
*N2
= MDNode::get(Context
, Ops2
);
585 Metadata
*Ops3
[] = {N2
};
586 MDNode
*N3
= MDNode::get(Context
, Ops3
);
587 Temp3
->replaceAllUsesWith(N3
);
590 Metadata
*Ops4
[] = {N1
};
591 MDNode
*N4
= MDNode::get(Context
, Ops4
);
593 // Confirm that the cycle prevented RAUW from getting dropped.
594 EXPECT_TRUE(N0
->isResolved());
595 EXPECT_FALSE(N1
->isResolved());
596 EXPECT_FALSE(N2
->isResolved());
597 EXPECT_FALSE(N3
->isResolved());
598 EXPECT_FALSE(N4
->isResolved());
600 // Create a couple of distinct nodes to observe what's going on.
602 // !5 = distinct !{!2}
603 // !6 = distinct !{!3}
604 Metadata
*Ops5
[] = {N2
};
605 MDNode
*N5
= MDNode::getDistinct(Context
, Ops5
);
606 Metadata
*Ops6
[] = {N3
};
607 MDNode
*N6
= MDNode::getDistinct(Context
, Ops6
);
609 // Mutate !2 to look like !1, causing a uniquing collision (and an RAUW).
610 // This will ripple up, with !3 colliding with !4, and RAUWing. Since !2
611 // references !3, this can cause a re-entry of handleChangedOperand() when !3
612 // is not ready for it.
614 // !2->replaceOperandWith(1, nullptr)
615 // !2: !{!3, !0} => !{!3, null}
616 // !2->replaceAllUsesWith(!1)
617 // !3: !{!2] => !{!1}
618 // !3->replaceAllUsesWith(!4)
619 N2
->replaceOperandWith(1, nullptr);
621 // If all has gone well, N2 and N3 will have been RAUW'ed and deleted from
622 // under us. Just check that the other nodes are sane.
626 // !5 = distinct !{!1}
627 // !6 = distinct !{!4}
628 EXPECT_EQ(N4
, N1
->getOperand(0));
629 EXPECT_EQ(N1
, N4
->getOperand(0));
630 EXPECT_EQ(N1
, N5
->getOperand(0));
631 EXPECT_EQ(N4
, N6
->getOperand(0));
634 TEST_F(MDNodeTest
, replaceResolvedOperand
) {
635 // Check code for replacing one resolved operand with another. If doing this
636 // directly (via replaceOperandWith()) becomes illegal, change the operand to
637 // a global value that gets RAUW'ed.
639 // Use a temporary node to keep N from being resolved.
640 auto Temp
= MDTuple::getTemporary(Context
, None
);
641 Metadata
*Ops
[] = {nullptr, Temp
.get()};
643 MDNode
*Empty
= MDTuple::get(Context
, ArrayRef
<Metadata
*>());
644 MDNode
*N
= MDTuple::get(Context
, Ops
);
645 EXPECT_EQ(nullptr, N
->getOperand(0));
646 ASSERT_FALSE(N
->isResolved());
648 // Check code for replacing resolved nodes.
649 N
->replaceOperandWith(0, Empty
);
650 EXPECT_EQ(Empty
, N
->getOperand(0));
652 // Check code for adding another unresolved operand.
653 N
->replaceOperandWith(0, Temp
.get());
654 EXPECT_EQ(Temp
.get(), N
->getOperand(0));
656 // Remove the references to Temp; required for teardown.
657 Temp
->replaceAllUsesWith(nullptr);
660 TEST_F(MDNodeTest
, replaceWithUniqued
) {
661 auto *Empty
= MDTuple::get(Context
, None
);
662 MDTuple
*FirstUniqued
;
664 Metadata
*Ops
[] = {Empty
};
665 auto Temp
= MDTuple::getTemporary(Context
, Ops
);
666 EXPECT_TRUE(Temp
->isTemporary());
668 // Don't expect a collision.
669 auto *Current
= Temp
.get();
670 FirstUniqued
= MDNode::replaceWithUniqued(std::move(Temp
));
671 EXPECT_TRUE(FirstUniqued
->isUniqued());
672 EXPECT_TRUE(FirstUniqued
->isResolved());
673 EXPECT_EQ(Current
, FirstUniqued
);
676 Metadata
*Ops
[] = {Empty
};
677 auto Temp
= MDTuple::getTemporary(Context
, Ops
);
678 EXPECT_TRUE(Temp
->isTemporary());
680 // Should collide with Uniqued above this time.
681 auto *Uniqued
= MDNode::replaceWithUniqued(std::move(Temp
));
682 EXPECT_TRUE(Uniqued
->isUniqued());
683 EXPECT_TRUE(Uniqued
->isResolved());
684 EXPECT_EQ(FirstUniqued
, Uniqued
);
687 auto Unresolved
= MDTuple::getTemporary(Context
, None
);
688 Metadata
*Ops
[] = {Unresolved
.get()};
689 auto Temp
= MDTuple::getTemporary(Context
, Ops
);
690 EXPECT_TRUE(Temp
->isTemporary());
692 // Shouldn't be resolved.
693 auto *Uniqued
= MDNode::replaceWithUniqued(std::move(Temp
));
694 EXPECT_TRUE(Uniqued
->isUniqued());
695 EXPECT_FALSE(Uniqued
->isResolved());
697 // Should be a different node.
698 EXPECT_NE(FirstUniqued
, Uniqued
);
700 // Should resolve when we update its node (note: be careful to avoid a
701 // collision with any other nodes above).
702 Uniqued
->replaceOperandWith(0, nullptr);
703 EXPECT_TRUE(Uniqued
->isResolved());
707 TEST_F(MDNodeTest
, replaceWithUniquedResolvingOperand
) {
709 MDTuple
*Op
= MDTuple::getTemporary(Context
, None
).release();
710 EXPECT_FALSE(Op
->isResolved());
713 Metadata
*Ops
[] = {Op
};
714 MDTuple
*N
= MDTuple::getTemporary(Context
, Ops
).release();
715 EXPECT_FALSE(N
->isResolved());
717 // temp !{temp !{}} => !{temp !{}}
718 ASSERT_EQ(N
, MDNode::replaceWithUniqued(TempMDTuple(N
)));
719 EXPECT_FALSE(N
->isResolved());
721 // !{temp !{}} => !{!{}}
722 ASSERT_EQ(Op
, MDNode::replaceWithUniqued(TempMDTuple(Op
)));
723 EXPECT_TRUE(Op
->isResolved());
724 EXPECT_TRUE(N
->isResolved());
727 TEST_F(MDNodeTest
, replaceWithUniquedDeletedOperand
) {
729 Type
*Ty
= Type::getInt1PtrTy(Context
);
730 std::unique_ptr
<GlobalVariable
> GV(
731 new GlobalVariable(Ty
, false, GlobalValue::ExternalLinkage
));
732 ConstantAsMetadata
*Op
= ConstantAsMetadata::get(GV
.get());
735 Metadata
*Ops
[] = {Op
};
736 MDTuple
*N
= MDTuple::getTemporary(Context
, Ops
).release();
738 // temp !{i1* @GV} => !{i1* @GV}
739 ASSERT_EQ(N
, MDNode::replaceWithUniqued(TempMDTuple(N
)));
740 ASSERT_TRUE(N
->isUniqued());
742 // !{i1* @GV} => !{null}
744 ASSERT_TRUE(N
->isDistinct());
745 ASSERT_EQ(nullptr, N
->getOperand(0));
746 Metadata
*NullOps
[] = {nullptr};
747 ASSERT_NE(N
, MDTuple::get(Context
, NullOps
));
750 TEST_F(MDNodeTest
, replaceWithUniquedChangedOperand
) {
752 Type
*Ty
= Type::getInt1PtrTy(Context
);
753 std::unique_ptr
<GlobalVariable
> GV(
754 new GlobalVariable(Ty
, false, GlobalValue::ExternalLinkage
));
755 ConstantAsMetadata
*Op
= ConstantAsMetadata::get(GV
.get());
758 Metadata
*Ops
[] = {Op
};
759 MDTuple
*N
= MDTuple::getTemporary(Context
, Ops
).release();
761 // temp !{i1* @GV} => !{i1* @GV}
762 ASSERT_EQ(N
, MDNode::replaceWithUniqued(TempMDTuple(N
)));
763 ASSERT_TRUE(N
->isUniqued());
765 // !{i1* @GV} => !{i1* @GV2}
766 std::unique_ptr
<GlobalVariable
> GV2(
767 new GlobalVariable(Ty
, false, GlobalValue::ExternalLinkage
));
768 GV
->replaceAllUsesWith(GV2
.get());
769 ASSERT_TRUE(N
->isUniqued());
770 Metadata
*NullOps
[] = {ConstantAsMetadata::get(GV2
.get())};
771 ASSERT_EQ(N
, MDTuple::get(Context
, NullOps
));
774 TEST_F(MDNodeTest
, replaceWithDistinct
) {
776 auto *Empty
= MDTuple::get(Context
, None
);
777 Metadata
*Ops
[] = {Empty
};
778 auto Temp
= MDTuple::getTemporary(Context
, Ops
);
779 EXPECT_TRUE(Temp
->isTemporary());
781 // Don't expect a collision.
782 auto *Current
= Temp
.get();
783 auto *Distinct
= MDNode::replaceWithDistinct(std::move(Temp
));
784 EXPECT_TRUE(Distinct
->isDistinct());
785 EXPECT_TRUE(Distinct
->isResolved());
786 EXPECT_EQ(Current
, Distinct
);
789 auto Unresolved
= MDTuple::getTemporary(Context
, None
);
790 Metadata
*Ops
[] = {Unresolved
.get()};
791 auto Temp
= MDTuple::getTemporary(Context
, Ops
);
792 EXPECT_TRUE(Temp
->isTemporary());
794 // Don't expect a collision.
795 auto *Current
= Temp
.get();
796 auto *Distinct
= MDNode::replaceWithDistinct(std::move(Temp
));
797 EXPECT_TRUE(Distinct
->isDistinct());
798 EXPECT_TRUE(Distinct
->isResolved());
799 EXPECT_EQ(Current
, Distinct
);
801 // Cleanup; required for teardown.
802 Unresolved
->replaceAllUsesWith(nullptr);
806 TEST_F(MDNodeTest
, replaceWithPermanent
) {
807 Metadata
*Ops
[] = {nullptr};
808 auto Temp
= MDTuple::getTemporary(Context
, Ops
);
809 auto *T
= Temp
.get();
811 // U is a normal, uniqued node that references T.
812 auto *U
= MDTuple::get(Context
, T
);
813 EXPECT_TRUE(U
->isUniqued());
815 // Make Temp self-referencing.
816 Temp
->replaceOperandWith(0, T
);
818 // Try to uniquify Temp. This should, despite the name in the API, give a
819 // 'distinct' node, since self-references aren't allowed to be uniqued.
821 // Since it's distinct, N should have the same address as when it was a
822 // temporary (i.e., be equal to T not U).
823 auto *N
= MDNode::replaceWithPermanent(std::move(Temp
));
825 EXPECT_TRUE(N
->isDistinct());
827 // U should be the canonical unique node with N as the argument.
828 EXPECT_EQ(U
, MDTuple::get(Context
, N
));
829 EXPECT_TRUE(U
->isUniqued());
831 // This temporary should collide with U when replaced, but it should still be
833 EXPECT_EQ(U
, MDNode::replaceWithPermanent(MDTuple::getTemporary(Context
, N
)));
834 EXPECT_TRUE(U
->isUniqued());
836 // This temporary should become a new uniqued node.
837 auto Temp2
= MDTuple::getTemporary(Context
, U
);
838 auto *V
= Temp2
.get();
839 EXPECT_EQ(V
, MDNode::replaceWithPermanent(std::move(Temp2
)));
840 EXPECT_TRUE(V
->isUniqued());
841 EXPECT_EQ(U
, V
->getOperand(0));
844 TEST_F(MDNodeTest
, deleteTemporaryWithTrackingRef
) {
846 EXPECT_EQ(nullptr, Ref
.get());
848 auto Temp
= MDTuple::getTemporary(Context
, None
);
849 Ref
.reset(Temp
.get());
850 EXPECT_EQ(Temp
.get(), Ref
.get());
852 EXPECT_EQ(nullptr, Ref
.get());
855 typedef MetadataTest DILocationTest
;
857 TEST_F(DILocationTest
, Overflow
) {
858 DISubprogram
*N
= getSubprogram();
860 DILocation
*L
= DILocation::get(Context
, 2, 7, N
);
861 EXPECT_EQ(2u, L
->getLine());
862 EXPECT_EQ(7u, L
->getColumn());
864 unsigned U16
= 1u << 16;
866 DILocation
*L
= DILocation::get(Context
, UINT32_MAX
, U16
- 1, N
);
867 EXPECT_EQ(UINT32_MAX
, L
->getLine());
868 EXPECT_EQ(U16
- 1, L
->getColumn());
871 DILocation
*L
= DILocation::get(Context
, UINT32_MAX
, U16
, N
);
872 EXPECT_EQ(UINT32_MAX
, L
->getLine());
873 EXPECT_EQ(0u, L
->getColumn());
876 DILocation
*L
= DILocation::get(Context
, UINT32_MAX
, U16
+ 1, N
);
877 EXPECT_EQ(UINT32_MAX
, L
->getLine());
878 EXPECT_EQ(0u, L
->getColumn());
882 TEST_F(DILocationTest
, Merge
) {
883 DISubprogram
*N
= getSubprogram();
884 DIScope
*S
= DILexicalBlock::get(Context
, N
, getFile(), 3, 4);
888 auto *A
= DILocation::get(Context
, 2, 7, N
);
889 auto *B
= DILocation::get(Context
, 2, 7, N
);
890 auto *M
= DILocation::getMergedLocation(A
, B
);
891 EXPECT_EQ(2u, M
->getLine());
892 EXPECT_EQ(7u, M
->getColumn());
893 EXPECT_EQ(N
, M
->getScope());
897 // Identical, different scopes.
898 auto *A
= DILocation::get(Context
, 2, 7, N
);
899 auto *B
= DILocation::get(Context
, 2, 7, S
);
900 auto *M
= DILocation::getMergedLocation(A
, B
);
901 EXPECT_EQ(0u, M
->getLine()); // FIXME: Should this be 2?
902 EXPECT_EQ(0u, M
->getColumn()); // FIXME: Should this be 7?
903 EXPECT_EQ(N
, M
->getScope());
907 // Different lines, same scopes.
908 auto *A
= DILocation::get(Context
, 1, 6, N
);
909 auto *B
= DILocation::get(Context
, 2, 7, N
);
910 auto *M
= DILocation::getMergedLocation(A
, B
);
911 EXPECT_EQ(0u, M
->getLine());
912 EXPECT_EQ(0u, M
->getColumn());
913 EXPECT_EQ(N
, M
->getScope());
917 // Twisty locations, all different, same function.
918 auto *A
= DILocation::get(Context
, 1, 6, N
);
919 auto *B
= DILocation::get(Context
, 2, 7, S
);
920 auto *M
= DILocation::getMergedLocation(A
, B
);
921 EXPECT_EQ(0u, M
->getLine());
922 EXPECT_EQ(0u, M
->getColumn());
923 EXPECT_EQ(N
, M
->getScope());
927 // Different function, same inlined-at.
929 auto *SP1
= DISubprogram::getDistinct(Context
, F
, "a", "a", F
, 0, nullptr,
930 0, nullptr, 0, 0, DINode::FlagZero
,
931 DISubprogram::SPFlagZero
, nullptr);
932 auto *SP2
= DISubprogram::getDistinct(Context
, F
, "b", "b", F
, 0, nullptr,
933 0, nullptr, 0, 0, DINode::FlagZero
,
934 DISubprogram::SPFlagZero
, nullptr);
936 auto *I
= DILocation::get(Context
, 2, 7, N
);
937 auto *A
= DILocation::get(Context
, 1, 6, SP1
, I
);
938 auto *B
= DILocation::get(Context
, 2, 7, SP2
, I
);
939 auto *M
= DILocation::getMergedLocation(A
, B
);
940 EXPECT_EQ(0u, M
->getLine());
941 EXPECT_EQ(0u, M
->getColumn());
942 EXPECT_TRUE(isa
<DILocalScope
>(M
->getScope()));
943 EXPECT_EQ(I
, M
->getInlinedAt());
947 // Completely different.
948 auto *I
= DILocation::get(Context
, 2, 7, N
);
949 auto *A
= DILocation::get(Context
, 1, 6, S
, I
);
950 auto *B
= DILocation::get(Context
, 2, 7, getSubprogram());
951 auto *M
= DILocation::getMergedLocation(A
, B
);
952 EXPECT_EQ(0u, M
->getLine());
953 EXPECT_EQ(0u, M
->getColumn());
954 EXPECT_TRUE(isa
<DILocalScope
>(M
->getScope()));
955 EXPECT_EQ(S
, M
->getScope());
956 EXPECT_EQ(nullptr, M
->getInlinedAt());
960 TEST_F(DILocationTest
, getDistinct
) {
961 MDNode
*N
= getSubprogram();
962 DILocation
*L0
= DILocation::getDistinct(Context
, 2, 7, N
);
963 EXPECT_TRUE(L0
->isDistinct());
964 DILocation
*L1
= DILocation::get(Context
, 2, 7, N
);
965 EXPECT_FALSE(L1
->isDistinct());
966 EXPECT_EQ(L1
, DILocation::get(Context
, 2, 7, N
));
969 TEST_F(DILocationTest
, getTemporary
) {
970 MDNode
*N
= MDNode::get(Context
, None
);
971 auto L
= DILocation::getTemporary(Context
, 2, 7, N
);
972 EXPECT_TRUE(L
->isTemporary());
973 EXPECT_FALSE(L
->isResolved());
976 TEST_F(DILocationTest
, cloneTemporary
) {
977 MDNode
*N
= MDNode::get(Context
, None
);
978 auto L
= DILocation::getTemporary(Context
, 2, 7, N
);
979 EXPECT_TRUE(L
->isTemporary());
980 auto L2
= L
->clone();
981 EXPECT_TRUE(L2
->isTemporary());
984 TEST_F(DILocationTest
, discriminatorEncoding
) {
985 EXPECT_EQ(0U, DILocation::encodeDiscriminator(0, 0, 0).getValue());
987 // Encode base discriminator as a component: lsb is 0, then the value.
988 // The other components are all absent, so we leave all the other bits 0.
989 EXPECT_EQ(2U, DILocation::encodeDiscriminator(1, 0, 0).getValue());
991 // Base discriminator component is empty, so lsb is 1. Next component is not
992 // empty, so its lsb is 0, then its value (1). Next component is empty.
993 // So the bit pattern is 101.
994 EXPECT_EQ(5U, DILocation::encodeDiscriminator(0, 1, 0).getValue());
996 // First 2 components are empty, so the bit pattern is 11. Then the
997 // next component - ending up with 1011.
998 EXPECT_EQ(0xbU
, DILocation::encodeDiscriminator(0, 0, 1).getValue());
1000 // The bit pattern for the first 2 components is 11. The next bit is 0,
1001 // because the last component is not empty. We have 29 bits usable for
1002 // encoding, but we cap it at 12 bits uniformously for all components. We
1003 // encode the last component over 14 bits.
1004 EXPECT_EQ(0xfffbU
, DILocation::encodeDiscriminator(0, 0, 0xfff).getValue());
1006 EXPECT_EQ(0x102U
, DILocation::encodeDiscriminator(1, 1, 0).getValue());
1008 EXPECT_EQ(0x13eU
, DILocation::encodeDiscriminator(0x1f, 1, 0).getValue());
1010 EXPECT_EQ(0x87feU
, DILocation::encodeDiscriminator(0x1ff, 1, 0).getValue());
1012 EXPECT_EQ(0x1f3eU
, DILocation::encodeDiscriminator(0x1f, 0x1f, 0).getValue());
1015 DILocation::encodeDiscriminator(0x1f, 0x1ff, 0).getValue());
1017 EXPECT_EQ(0x1ff87feU
,
1018 DILocation::encodeDiscriminator(0x1ff, 0x1ff, 0).getValue());
1020 EXPECT_EQ(0xfff9f3eU
,
1021 DILocation::encodeDiscriminator(0x1f, 0x1f, 0xfff).getValue());
1023 EXPECT_EQ(0xffc3ff3eU
,
1024 DILocation::encodeDiscriminator(0x1f, 0x1ff, 0x1ff).getValue());
1026 EXPECT_EQ(0xffcf87feU
,
1027 DILocation::encodeDiscriminator(0x1ff, 0x1f, 0x1ff).getValue());
1029 EXPECT_EQ(0xe1ff87feU
,
1030 DILocation::encodeDiscriminator(0x1ff, 0x1ff, 7).getValue());
1033 TEST_F(DILocationTest
, discriminatorEncodingNegativeTests
) {
1034 EXPECT_EQ(None
, DILocation::encodeDiscriminator(0, 0, 0x1000));
1035 EXPECT_EQ(None
, DILocation::encodeDiscriminator(0x1000, 0, 0));
1036 EXPECT_EQ(None
, DILocation::encodeDiscriminator(0, 0x1000, 0));
1037 EXPECT_EQ(None
, DILocation::encodeDiscriminator(0, 0, 0x1000));
1038 EXPECT_EQ(None
, DILocation::encodeDiscriminator(0x1ff, 0x1ff, 8));
1040 DILocation::encodeDiscriminator(std::numeric_limits
<uint32_t>::max(),
1041 std::numeric_limits
<uint32_t>::max(),
1045 TEST_F(DILocationTest
, discriminatorSpecialCases
) {
1046 // We don't test getCopyIdentifier here because the only way
1047 // to set it is by constructing an encoded discriminator using
1048 // encodeDiscriminator, which is already tested.
1049 auto L1
= DILocation::get(Context
, 1, 2, getSubprogram());
1050 EXPECT_EQ(0U, L1
->getBaseDiscriminator());
1051 EXPECT_EQ(1U, L1
->getDuplicationFactor());
1053 EXPECT_EQ(L1
, L1
->cloneWithBaseDiscriminator(0).getValue());
1054 EXPECT_EQ(L1
, L1
->cloneByMultiplyingDuplicationFactor(0).getValue());
1055 EXPECT_EQ(L1
, L1
->cloneByMultiplyingDuplicationFactor(1).getValue());
1057 auto L2
= L1
->cloneWithBaseDiscriminator(1).getValue();
1058 EXPECT_EQ(0U, L1
->getBaseDiscriminator());
1059 EXPECT_EQ(1U, L1
->getDuplicationFactor());
1061 EXPECT_EQ(1U, L2
->getBaseDiscriminator());
1062 EXPECT_EQ(1U, L2
->getDuplicationFactor());
1064 auto L3
= L2
->cloneByMultiplyingDuplicationFactor(2).getValue();
1065 EXPECT_EQ(1U, L3
->getBaseDiscriminator());
1066 EXPECT_EQ(2U, L3
->getDuplicationFactor());
1068 EXPECT_EQ(L2
, L2
->cloneByMultiplyingDuplicationFactor(1).getValue());
1070 auto L4
= L3
->cloneByMultiplyingDuplicationFactor(4).getValue();
1071 EXPECT_EQ(1U, L4
->getBaseDiscriminator());
1072 EXPECT_EQ(8U, L4
->getDuplicationFactor());
1074 auto L5
= L4
->cloneWithBaseDiscriminator(2).getValue();
1075 EXPECT_EQ(2U, L5
->getBaseDiscriminator());
1076 EXPECT_EQ(8U, L5
->getDuplicationFactor());
1078 // Check extreme cases
1079 auto L6
= L1
->cloneWithBaseDiscriminator(0xfff).getValue();
1080 EXPECT_EQ(0xfffU
, L6
->getBaseDiscriminator());
1081 EXPECT_EQ(0xfffU
, L6
->cloneByMultiplyingDuplicationFactor(0xfff)
1083 ->getDuplicationFactor());
1085 // Check we return None for unencodable cases.
1086 EXPECT_EQ(None
, L4
->cloneWithBaseDiscriminator(0x1000));
1087 EXPECT_EQ(None
, L4
->cloneByMultiplyingDuplicationFactor(0x1000));
1091 typedef MetadataTest GenericDINodeTest
;
1093 TEST_F(GenericDINodeTest
, get
) {
1094 StringRef Header
= "header";
1095 auto *Empty
= MDNode::get(Context
, None
);
1096 Metadata
*Ops1
[] = {Empty
};
1097 auto *N
= GenericDINode::get(Context
, 15, Header
, Ops1
);
1098 EXPECT_EQ(15u, N
->getTag());
1099 EXPECT_EQ(2u, N
->getNumOperands());
1100 EXPECT_EQ(Header
, N
->getHeader());
1101 EXPECT_EQ(MDString::get(Context
, Header
), N
->getOperand(0));
1102 EXPECT_EQ(1u, N
->getNumDwarfOperands());
1103 EXPECT_EQ(Empty
, N
->getDwarfOperand(0));
1104 EXPECT_EQ(Empty
, N
->getOperand(1));
1105 ASSERT_TRUE(N
->isUniqued());
1107 EXPECT_EQ(N
, GenericDINode::get(Context
, 15, Header
, Ops1
));
1109 N
->replaceOperandWith(1, nullptr);
1110 EXPECT_EQ(15u, N
->getTag());
1111 EXPECT_EQ(Header
, N
->getHeader());
1112 EXPECT_EQ(nullptr, N
->getDwarfOperand(0));
1113 ASSERT_TRUE(N
->isUniqued());
1115 Metadata
*Ops2
[] = {nullptr};
1116 EXPECT_EQ(N
, GenericDINode::get(Context
, 15, Header
, Ops2
));
1118 N
->replaceDwarfOperandWith(0, Empty
);
1119 EXPECT_EQ(15u, N
->getTag());
1120 EXPECT_EQ(Header
, N
->getHeader());
1121 EXPECT_EQ(Empty
, N
->getDwarfOperand(0));
1122 ASSERT_TRUE(N
->isUniqued());
1123 EXPECT_EQ(N
, GenericDINode::get(Context
, 15, Header
, Ops1
));
1125 TempGenericDINode Temp
= N
->clone();
1126 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
1129 TEST_F(GenericDINodeTest
, getEmptyHeader
) {
1130 // Canonicalize !"" to null.
1131 auto *N
= GenericDINode::get(Context
, 15, StringRef(), None
);
1132 EXPECT_EQ(StringRef(), N
->getHeader());
1133 EXPECT_EQ(nullptr, N
->getOperand(0));
1136 typedef MetadataTest DISubrangeTest
;
1138 TEST_F(DISubrangeTest
, get
) {
1139 auto *N
= DISubrange::get(Context
, 5, 7);
1140 auto Count
= N
->getCount();
1141 EXPECT_EQ(dwarf::DW_TAG_subrange_type
, N
->getTag());
1143 ASSERT_TRUE(Count
.is
<ConstantInt
*>());
1144 EXPECT_EQ(5, Count
.get
<ConstantInt
*>()->getSExtValue());
1145 EXPECT_EQ(7, N
->getLowerBound());
1146 EXPECT_EQ(N
, DISubrange::get(Context
, 5, 7));
1147 EXPECT_EQ(DISubrange::get(Context
, 5, 0), DISubrange::get(Context
, 5));
1149 TempDISubrange Temp
= N
->clone();
1150 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
1153 TEST_F(DISubrangeTest
, getEmptyArray
) {
1154 auto *N
= DISubrange::get(Context
, -1, 0);
1155 auto Count
= N
->getCount();
1156 EXPECT_EQ(dwarf::DW_TAG_subrange_type
, N
->getTag());
1158 ASSERT_TRUE(Count
.is
<ConstantInt
*>());
1159 EXPECT_EQ(-1, Count
.get
<ConstantInt
*>()->getSExtValue());
1160 EXPECT_EQ(0, N
->getLowerBound());
1161 EXPECT_EQ(N
, DISubrange::get(Context
, -1, 0));
1164 TEST_F(DISubrangeTest
, getVariableCount
) {
1165 DILocalScope
*Scope
= getSubprogram();
1166 DIFile
*File
= getFile();
1167 DIType
*Type
= getDerivedType();
1168 DINode::DIFlags Flags
= static_cast<DINode::DIFlags
>(7);
1169 auto *VlaExpr
= DILocalVariable::get(Context
, Scope
, "vla_expr", File
, 8,
1172 auto *N
= DISubrange::get(Context
, VlaExpr
, 0);
1173 auto Count
= N
->getCount();
1175 ASSERT_TRUE(Count
.is
<DIVariable
*>());
1176 EXPECT_EQ(VlaExpr
, Count
.get
<DIVariable
*>());
1177 ASSERT_TRUE(isa
<DIVariable
>(N
->getRawCountNode()));
1178 EXPECT_EQ(0, N
->getLowerBound());
1179 EXPECT_EQ("vla_expr", Count
.get
<DIVariable
*>()->getName());
1180 EXPECT_EQ(N
, DISubrange::get(Context
, VlaExpr
, 0));
1183 typedef MetadataTest DIEnumeratorTest
;
1185 TEST_F(DIEnumeratorTest
, get
) {
1186 auto *N
= DIEnumerator::get(Context
, 7, false, "name");
1187 EXPECT_EQ(dwarf::DW_TAG_enumerator
, N
->getTag());
1188 EXPECT_EQ(7, N
->getValue());
1189 EXPECT_FALSE(N
->isUnsigned());
1190 EXPECT_EQ("name", N
->getName());
1191 EXPECT_EQ(N
, DIEnumerator::get(Context
, 7, false, "name"));
1193 EXPECT_NE(N
, DIEnumerator::get(Context
, 7, true, "name"));
1194 EXPECT_NE(N
, DIEnumerator::get(Context
, 8, false, "name"));
1195 EXPECT_NE(N
, DIEnumerator::get(Context
, 7, false, "nam"));
1197 TempDIEnumerator Temp
= N
->clone();
1198 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
1201 typedef MetadataTest DIBasicTypeTest
;
1203 TEST_F(DIBasicTypeTest
, get
) {
1205 DIBasicType::get(Context
, dwarf::DW_TAG_base_type
, "special", 33, 26, 7,
1207 EXPECT_EQ(dwarf::DW_TAG_base_type
, N
->getTag());
1208 EXPECT_EQ("special", N
->getName());
1209 EXPECT_EQ(33u, N
->getSizeInBits());
1210 EXPECT_EQ(26u, N
->getAlignInBits());
1211 EXPECT_EQ(7u, N
->getEncoding());
1212 EXPECT_EQ(0u, N
->getLine());
1213 EXPECT_EQ(DINode::FlagZero
, N
->getFlags());
1214 EXPECT_EQ(N
, DIBasicType::get(Context
, dwarf::DW_TAG_base_type
, "special", 33,
1215 26, 7, DINode::FlagZero
));
1217 EXPECT_NE(N
, DIBasicType::get(Context
, dwarf::DW_TAG_unspecified_type
,
1218 "special", 33, 26, 7, DINode::FlagZero
));
1220 DIBasicType::get(Context
, dwarf::DW_TAG_base_type
, "s", 33, 26, 7,
1222 EXPECT_NE(N
, DIBasicType::get(Context
, dwarf::DW_TAG_base_type
, "special", 32,
1223 26, 7, DINode::FlagZero
));
1224 EXPECT_NE(N
, DIBasicType::get(Context
, dwarf::DW_TAG_base_type
, "special", 33,
1225 25, 7, DINode::FlagZero
));
1226 EXPECT_NE(N
, DIBasicType::get(Context
, dwarf::DW_TAG_base_type
, "special", 33,
1227 26, 6, DINode::FlagZero
));
1228 EXPECT_NE(N
, DIBasicType::get(Context
, dwarf::DW_TAG_base_type
, "special", 33,
1229 26, 7, DINode::FlagBigEndian
));
1230 EXPECT_NE(N
, DIBasicType::get(Context
, dwarf::DW_TAG_base_type
, "special", 33,
1231 26, 7, DINode::FlagLittleEndian
));
1233 TempDIBasicType Temp
= N
->clone();
1234 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
1237 TEST_F(DIBasicTypeTest
, getWithLargeValues
) {
1238 auto *N
= DIBasicType::get(Context
, dwarf::DW_TAG_base_type
, "special",
1239 UINT64_MAX
, UINT32_MAX
- 1, 7, DINode::FlagZero
);
1240 EXPECT_EQ(UINT64_MAX
, N
->getSizeInBits());
1241 EXPECT_EQ(UINT32_MAX
- 1, N
->getAlignInBits());
1244 TEST_F(DIBasicTypeTest
, getUnspecified
) {
1246 DIBasicType::get(Context
, dwarf::DW_TAG_unspecified_type
, "unspecified");
1247 EXPECT_EQ(dwarf::DW_TAG_unspecified_type
, N
->getTag());
1248 EXPECT_EQ("unspecified", N
->getName());
1249 EXPECT_EQ(0u, N
->getSizeInBits());
1250 EXPECT_EQ(0u, N
->getAlignInBits());
1251 EXPECT_EQ(0u, N
->getEncoding());
1252 EXPECT_EQ(0u, N
->getLine());
1253 EXPECT_EQ(DINode::FlagZero
, N
->getFlags());
1256 typedef MetadataTest DITypeTest
;
1258 TEST_F(DITypeTest
, clone
) {
1259 // Check that DIType has a specialized clone that returns TempDIType.
1260 DIType
*N
= DIBasicType::get(Context
, dwarf::DW_TAG_base_type
, "int", 32, 32,
1261 dwarf::DW_ATE_signed
, DINode::FlagZero
);
1263 TempDIType Temp
= N
->clone();
1264 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
1267 TEST_F(DITypeTest
, cloneWithFlags
) {
1269 Metadata
*TypesOps
[] = {nullptr};
1270 Metadata
*Types
= MDTuple::get(Context
, TypesOps
);
1273 DISubroutineType::getDistinct(Context
, DINode::FlagZero
, 0, Types
);
1274 EXPECT_EQ(DINode::FlagZero
, D
->getFlags());
1275 TempDIType D2
= D
->cloneWithFlags(DINode::FlagRValueReference
);
1276 EXPECT_EQ(DINode::FlagRValueReference
, D2
->getFlags());
1277 EXPECT_EQ(DINode::FlagZero
, D
->getFlags());
1280 DISubroutineType::getTemporary(Context
, DINode::FlagZero
, 0, Types
);
1281 EXPECT_EQ(DINode::FlagZero
, T
->getFlags());
1282 TempDIType T2
= T
->cloneWithFlags(DINode::FlagRValueReference
);
1283 EXPECT_EQ(DINode::FlagRValueReference
, T2
->getFlags());
1284 EXPECT_EQ(DINode::FlagZero
, T
->getFlags());
1287 typedef MetadataTest DIDerivedTypeTest
;
1289 TEST_F(DIDerivedTypeTest
, get
) {
1290 DIFile
*File
= getFile();
1291 DIScope
*Scope
= getSubprogram();
1292 DIType
*BaseType
= getBasicType("basic");
1293 MDTuple
*ExtraData
= getTuple();
1294 unsigned DWARFAddressSpace
= 8;
1295 DINode::DIFlags Flags5
= static_cast<DINode::DIFlags
>(5);
1296 DINode::DIFlags Flags4
= static_cast<DINode::DIFlags
>(4);
1299 DIDerivedType::get(Context
, dwarf::DW_TAG_pointer_type
, "something", File
,
1300 1, Scope
, BaseType
, 2, 3, 4, DWARFAddressSpace
, Flags5
,
1302 EXPECT_EQ(dwarf::DW_TAG_pointer_type
, N
->getTag());
1303 EXPECT_EQ("something", N
->getName());
1304 EXPECT_EQ(File
, N
->getFile());
1305 EXPECT_EQ(1u, N
->getLine());
1306 EXPECT_EQ(Scope
, N
->getScope());
1307 EXPECT_EQ(BaseType
, N
->getBaseType());
1308 EXPECT_EQ(2u, N
->getSizeInBits());
1309 EXPECT_EQ(3u, N
->getAlignInBits());
1310 EXPECT_EQ(4u, N
->getOffsetInBits());
1311 EXPECT_EQ(DWARFAddressSpace
, N
->getDWARFAddressSpace().getValue());
1312 EXPECT_EQ(5u, N
->getFlags());
1313 EXPECT_EQ(ExtraData
, N
->getExtraData());
1314 EXPECT_EQ(N
, DIDerivedType::get(Context
, dwarf::DW_TAG_pointer_type
,
1315 "something", File
, 1, Scope
, BaseType
, 2, 3,
1316 4, DWARFAddressSpace
, Flags5
, ExtraData
));
1318 EXPECT_NE(N
, DIDerivedType::get(Context
, dwarf::DW_TAG_reference_type
,
1319 "something", File
, 1, Scope
, BaseType
, 2, 3,
1320 4, DWARFAddressSpace
, Flags5
, ExtraData
));
1321 EXPECT_NE(N
, DIDerivedType::get(Context
, dwarf::DW_TAG_pointer_type
, "else",
1322 File
, 1, Scope
, BaseType
, 2, 3,
1323 4, DWARFAddressSpace
, Flags5
, ExtraData
));
1324 EXPECT_NE(N
, DIDerivedType::get(Context
, dwarf::DW_TAG_pointer_type
,
1325 "something", getFile(), 1, Scope
, BaseType
, 2,
1326 3, 4, DWARFAddressSpace
, Flags5
, ExtraData
));
1327 EXPECT_NE(N
, DIDerivedType::get(Context
, dwarf::DW_TAG_pointer_type
,
1328 "something", File
, 2, Scope
, BaseType
, 2, 3,
1329 4, DWARFAddressSpace
, Flags5
, ExtraData
));
1330 EXPECT_NE(N
, DIDerivedType::get(Context
, dwarf::DW_TAG_pointer_type
,
1331 "something", File
, 1, getSubprogram(),
1332 BaseType
, 2, 3, 4, DWARFAddressSpace
, Flags5
,
1334 EXPECT_NE(N
, DIDerivedType::get(
1335 Context
, dwarf::DW_TAG_pointer_type
, "something", File
, 1,
1336 Scope
, getBasicType("basic2"), 2, 3, 4, DWARFAddressSpace
,
1337 Flags5
, ExtraData
));
1338 EXPECT_NE(N
, DIDerivedType::get(Context
, dwarf::DW_TAG_pointer_type
,
1339 "something", File
, 1, Scope
, BaseType
, 3, 3,
1340 4, DWARFAddressSpace
, Flags5
, ExtraData
));
1341 EXPECT_NE(N
, DIDerivedType::get(Context
, dwarf::DW_TAG_pointer_type
,
1342 "something", File
, 1, Scope
, BaseType
, 2, 2,
1343 4, DWARFAddressSpace
, Flags5
, ExtraData
));
1344 EXPECT_NE(N
, DIDerivedType::get(Context
, dwarf::DW_TAG_pointer_type
,
1345 "something", File
, 1, Scope
, BaseType
, 2, 3,
1346 5, DWARFAddressSpace
, Flags5
, ExtraData
));
1347 EXPECT_NE(N
, DIDerivedType::get(Context
, dwarf::DW_TAG_pointer_type
,
1348 "something", File
, 1, Scope
, BaseType
, 2, 3,
1349 4, DWARFAddressSpace
+ 1, Flags5
, ExtraData
));
1350 EXPECT_NE(N
, DIDerivedType::get(Context
, dwarf::DW_TAG_pointer_type
,
1351 "something", File
, 1, Scope
, BaseType
, 2, 3,
1352 4, DWARFAddressSpace
, Flags4
, ExtraData
));
1353 EXPECT_NE(N
, DIDerivedType::get(Context
, dwarf::DW_TAG_pointer_type
,
1354 "something", File
, 1, Scope
, BaseType
, 2, 3,
1355 4, DWARFAddressSpace
, Flags5
, getTuple()));
1357 TempDIDerivedType Temp
= N
->clone();
1358 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
1361 TEST_F(DIDerivedTypeTest
, getWithLargeValues
) {
1362 DIFile
*File
= getFile();
1363 DIScope
*Scope
= getSubprogram();
1364 DIType
*BaseType
= getBasicType("basic");
1365 MDTuple
*ExtraData
= getTuple();
1366 DINode::DIFlags Flags
= static_cast<DINode::DIFlags
>(5);
1368 auto *N
= DIDerivedType::get(
1369 Context
, dwarf::DW_TAG_pointer_type
, "something", File
, 1, Scope
,
1370 BaseType
, UINT64_MAX
, UINT32_MAX
- 1, UINT64_MAX
- 2, UINT32_MAX
- 3,
1372 EXPECT_EQ(UINT64_MAX
, N
->getSizeInBits());
1373 EXPECT_EQ(UINT32_MAX
- 1, N
->getAlignInBits());
1374 EXPECT_EQ(UINT64_MAX
- 2, N
->getOffsetInBits());
1375 EXPECT_EQ(UINT32_MAX
- 3, N
->getDWARFAddressSpace().getValue());
1378 typedef MetadataTest DICompositeTypeTest
;
1380 TEST_F(DICompositeTypeTest
, get
) {
1381 unsigned Tag
= dwarf::DW_TAG_structure_type
;
1382 StringRef Name
= "some name";
1383 DIFile
*File
= getFile();
1385 DIScope
*Scope
= getSubprogram();
1386 DIType
*BaseType
= getCompositeType();
1387 uint64_t SizeInBits
= 2;
1388 uint32_t AlignInBits
= 3;
1389 uint64_t OffsetInBits
= 4;
1390 DINode::DIFlags Flags
= static_cast<DINode::DIFlags
>(5);
1391 MDTuple
*Elements
= getTuple();
1392 unsigned RuntimeLang
= 6;
1393 DIType
*VTableHolder
= getCompositeType();
1394 MDTuple
*TemplateParams
= getTuple();
1395 StringRef Identifier
= "some id";
1397 auto *N
= DICompositeType::get(Context
, Tag
, Name
, File
, Line
, Scope
,
1398 BaseType
, SizeInBits
, AlignInBits
,
1399 OffsetInBits
, Flags
, Elements
, RuntimeLang
,
1400 VTableHolder
, TemplateParams
, Identifier
);
1401 EXPECT_EQ(Tag
, N
->getTag());
1402 EXPECT_EQ(Name
, N
->getName());
1403 EXPECT_EQ(File
, N
->getFile());
1404 EXPECT_EQ(Line
, N
->getLine());
1405 EXPECT_EQ(Scope
, N
->getScope());
1406 EXPECT_EQ(BaseType
, N
->getBaseType());
1407 EXPECT_EQ(SizeInBits
, N
->getSizeInBits());
1408 EXPECT_EQ(AlignInBits
, N
->getAlignInBits());
1409 EXPECT_EQ(OffsetInBits
, N
->getOffsetInBits());
1410 EXPECT_EQ(Flags
, N
->getFlags());
1411 EXPECT_EQ(Elements
, N
->getElements().get());
1412 EXPECT_EQ(RuntimeLang
, N
->getRuntimeLang());
1413 EXPECT_EQ(VTableHolder
, N
->getVTableHolder());
1414 EXPECT_EQ(TemplateParams
, N
->getTemplateParams().get());
1415 EXPECT_EQ(Identifier
, N
->getIdentifier());
1417 EXPECT_EQ(N
, DICompositeType::get(Context
, Tag
, Name
, File
, Line
, Scope
,
1418 BaseType
, SizeInBits
, AlignInBits
,
1419 OffsetInBits
, Flags
, Elements
, RuntimeLang
,
1420 VTableHolder
, TemplateParams
, Identifier
));
1422 EXPECT_NE(N
, DICompositeType::get(Context
, Tag
+ 1, Name
, File
, Line
, Scope
,
1423 BaseType
, SizeInBits
, AlignInBits
,
1424 OffsetInBits
, Flags
, Elements
, RuntimeLang
,
1425 VTableHolder
, TemplateParams
, Identifier
));
1426 EXPECT_NE(N
, DICompositeType::get(Context
, Tag
, "abc", File
, Line
, Scope
,
1427 BaseType
, SizeInBits
, AlignInBits
,
1428 OffsetInBits
, Flags
, Elements
, RuntimeLang
,
1429 VTableHolder
, TemplateParams
, Identifier
));
1430 EXPECT_NE(N
, DICompositeType::get(Context
, Tag
, Name
, getFile(), Line
, Scope
,
1431 BaseType
, SizeInBits
, AlignInBits
,
1432 OffsetInBits
, Flags
, Elements
, RuntimeLang
,
1433 VTableHolder
, TemplateParams
, Identifier
));
1434 EXPECT_NE(N
, DICompositeType::get(Context
, Tag
, Name
, File
, Line
+ 1, Scope
,
1435 BaseType
, SizeInBits
, AlignInBits
,
1436 OffsetInBits
, Flags
, Elements
, RuntimeLang
,
1437 VTableHolder
, TemplateParams
, Identifier
));
1438 EXPECT_NE(N
, DICompositeType::get(
1439 Context
, Tag
, Name
, File
, Line
, getSubprogram(), BaseType
,
1440 SizeInBits
, AlignInBits
, OffsetInBits
, Flags
, Elements
,
1441 RuntimeLang
, VTableHolder
, TemplateParams
, Identifier
));
1442 EXPECT_NE(N
, DICompositeType::get(
1443 Context
, Tag
, Name
, File
, Line
, Scope
, getBasicType("other"),
1444 SizeInBits
, AlignInBits
, OffsetInBits
, Flags
, Elements
,
1445 RuntimeLang
, VTableHolder
, TemplateParams
, Identifier
));
1446 EXPECT_NE(N
, DICompositeType::get(Context
, Tag
, Name
, File
, Line
, Scope
,
1447 BaseType
, SizeInBits
+ 1, AlignInBits
,
1448 OffsetInBits
, Flags
, Elements
, RuntimeLang
,
1449 VTableHolder
, TemplateParams
, Identifier
));
1450 EXPECT_NE(N
, DICompositeType::get(Context
, Tag
, Name
, File
, Line
, Scope
,
1451 BaseType
, SizeInBits
, AlignInBits
+ 1,
1452 OffsetInBits
, Flags
, Elements
, RuntimeLang
,
1453 VTableHolder
, TemplateParams
, Identifier
));
1454 EXPECT_NE(N
, DICompositeType::get(
1455 Context
, Tag
, Name
, File
, Line
, Scope
, BaseType
, SizeInBits
,
1456 AlignInBits
, OffsetInBits
+ 1, Flags
, Elements
, RuntimeLang
,
1457 VTableHolder
, TemplateParams
, Identifier
));
1458 DINode::DIFlags FlagsPOne
= static_cast<DINode::DIFlags
>(Flags
+ 1);
1459 EXPECT_NE(N
, DICompositeType::get(
1460 Context
, Tag
, Name
, File
, Line
, Scope
, BaseType
, SizeInBits
,
1461 AlignInBits
, OffsetInBits
, FlagsPOne
, Elements
, RuntimeLang
,
1462 VTableHolder
, TemplateParams
, Identifier
));
1463 EXPECT_NE(N
, DICompositeType::get(
1464 Context
, Tag
, Name
, File
, Line
, Scope
, BaseType
, SizeInBits
,
1465 AlignInBits
, OffsetInBits
, Flags
, getTuple(), RuntimeLang
,
1466 VTableHolder
, TemplateParams
, Identifier
));
1467 EXPECT_NE(N
, DICompositeType::get(
1468 Context
, Tag
, Name
, File
, Line
, Scope
, BaseType
, SizeInBits
,
1469 AlignInBits
, OffsetInBits
, Flags
, Elements
, RuntimeLang
+ 1,
1470 VTableHolder
, TemplateParams
, Identifier
));
1471 EXPECT_NE(N
, DICompositeType::get(
1472 Context
, Tag
, Name
, File
, Line
, Scope
, BaseType
, SizeInBits
,
1473 AlignInBits
, OffsetInBits
, Flags
, Elements
, RuntimeLang
,
1474 getCompositeType(), TemplateParams
, Identifier
));
1475 EXPECT_NE(N
, DICompositeType::get(Context
, Tag
, Name
, File
, Line
, Scope
,
1476 BaseType
, SizeInBits
, AlignInBits
,
1477 OffsetInBits
, Flags
, Elements
, RuntimeLang
,
1478 VTableHolder
, getTuple(), Identifier
));
1479 EXPECT_NE(N
, DICompositeType::get(Context
, Tag
, Name
, File
, Line
, Scope
,
1480 BaseType
, SizeInBits
, AlignInBits
,
1481 OffsetInBits
, Flags
, Elements
, RuntimeLang
,
1482 VTableHolder
, TemplateParams
, "other"));
1484 // Be sure that missing identifiers get null pointers.
1485 EXPECT_FALSE(DICompositeType::get(Context
, Tag
, Name
, File
, Line
, Scope
,
1486 BaseType
, SizeInBits
, AlignInBits
,
1487 OffsetInBits
, Flags
, Elements
, RuntimeLang
,
1488 VTableHolder
, TemplateParams
, "")
1489 ->getRawIdentifier());
1490 EXPECT_FALSE(DICompositeType::get(Context
, Tag
, Name
, File
, Line
, Scope
,
1491 BaseType
, SizeInBits
, AlignInBits
,
1492 OffsetInBits
, Flags
, Elements
, RuntimeLang
,
1493 VTableHolder
, TemplateParams
)
1494 ->getRawIdentifier());
1496 TempDICompositeType Temp
= N
->clone();
1497 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
1500 TEST_F(DICompositeTypeTest
, getWithLargeValues
) {
1501 unsigned Tag
= dwarf::DW_TAG_structure_type
;
1502 StringRef Name
= "some name";
1503 DIFile
*File
= getFile();
1505 DIScope
*Scope
= getSubprogram();
1506 DIType
*BaseType
= getCompositeType();
1507 uint64_t SizeInBits
= UINT64_MAX
;
1508 uint32_t AlignInBits
= UINT32_MAX
- 1;
1509 uint64_t OffsetInBits
= UINT64_MAX
- 2;
1510 DINode::DIFlags Flags
= static_cast<DINode::DIFlags
>(5);
1511 MDTuple
*Elements
= getTuple();
1512 unsigned RuntimeLang
= 6;
1513 DIType
*VTableHolder
= getCompositeType();
1514 MDTuple
*TemplateParams
= getTuple();
1515 StringRef Identifier
= "some id";
1517 auto *N
= DICompositeType::get(Context
, Tag
, Name
, File
, Line
, Scope
,
1518 BaseType
, SizeInBits
, AlignInBits
,
1519 OffsetInBits
, Flags
, Elements
, RuntimeLang
,
1520 VTableHolder
, TemplateParams
, Identifier
);
1521 EXPECT_EQ(SizeInBits
, N
->getSizeInBits());
1522 EXPECT_EQ(AlignInBits
, N
->getAlignInBits());
1523 EXPECT_EQ(OffsetInBits
, N
->getOffsetInBits());
1526 TEST_F(DICompositeTypeTest
, replaceOperands
) {
1527 unsigned Tag
= dwarf::DW_TAG_structure_type
;
1528 StringRef Name
= "some name";
1529 DIFile
*File
= getFile();
1531 DIScope
*Scope
= getSubprogram();
1532 DIType
*BaseType
= getCompositeType();
1533 uint64_t SizeInBits
= 2;
1534 uint32_t AlignInBits
= 3;
1535 uint64_t OffsetInBits
= 4;
1536 DINode::DIFlags Flags
= static_cast<DINode::DIFlags
>(5);
1537 unsigned RuntimeLang
= 6;
1538 StringRef Identifier
= "some id";
1540 auto *N
= DICompositeType::get(
1541 Context
, Tag
, Name
, File
, Line
, Scope
, BaseType
, SizeInBits
, AlignInBits
,
1542 OffsetInBits
, Flags
, nullptr, RuntimeLang
, nullptr, nullptr, Identifier
);
1544 auto *Elements
= MDTuple::getDistinct(Context
, None
);
1545 EXPECT_EQ(nullptr, N
->getElements().get());
1546 N
->replaceElements(Elements
);
1547 EXPECT_EQ(Elements
, N
->getElements().get());
1548 N
->replaceElements(nullptr);
1549 EXPECT_EQ(nullptr, N
->getElements().get());
1551 DIType
*VTableHolder
= getCompositeType();
1552 EXPECT_EQ(nullptr, N
->getVTableHolder());
1553 N
->replaceVTableHolder(VTableHolder
);
1554 EXPECT_EQ(VTableHolder
, N
->getVTableHolder());
1555 // As an extension, the containing type can be anything. This is
1556 // used by Rust to associate vtables with their concrete type.
1557 DIType
*BasicType
= getBasicType("basic");
1558 N
->replaceVTableHolder(BasicType
);
1559 EXPECT_EQ(BasicType
, N
->getVTableHolder());
1560 N
->replaceVTableHolder(nullptr);
1561 EXPECT_EQ(nullptr, N
->getVTableHolder());
1563 auto *TemplateParams
= MDTuple::getDistinct(Context
, None
);
1564 EXPECT_EQ(nullptr, N
->getTemplateParams().get());
1565 N
->replaceTemplateParams(TemplateParams
);
1566 EXPECT_EQ(TemplateParams
, N
->getTemplateParams().get());
1567 N
->replaceTemplateParams(nullptr);
1568 EXPECT_EQ(nullptr, N
->getTemplateParams().get());
1571 TEST_F(DICompositeTypeTest
, variant_part
) {
1572 unsigned Tag
= dwarf::DW_TAG_variant_part
;
1573 StringRef Name
= "some name";
1574 DIFile
*File
= getFile();
1576 DIScope
*Scope
= getSubprogram();
1577 DIType
*BaseType
= getCompositeType();
1578 uint64_t SizeInBits
= 2;
1579 uint32_t AlignInBits
= 3;
1580 uint64_t OffsetInBits
= 4;
1581 DINode::DIFlags Flags
= static_cast<DINode::DIFlags
>(5);
1582 unsigned RuntimeLang
= 6;
1583 StringRef Identifier
= "some id";
1584 DIDerivedType
*Discriminator
= cast
<DIDerivedType
>(getDerivedType());
1585 DIDerivedType
*Discriminator2
= cast
<DIDerivedType
>(getDerivedType());
1587 EXPECT_NE(Discriminator
, Discriminator2
);
1589 auto *N
= DICompositeType::get(
1590 Context
, Tag
, Name
, File
, Line
, Scope
, BaseType
, SizeInBits
, AlignInBits
,
1591 OffsetInBits
, Flags
, nullptr, RuntimeLang
, nullptr, nullptr, Identifier
,
1594 // Test the hashing.
1595 auto *Same
= DICompositeType::get(
1596 Context
, Tag
, Name
, File
, Line
, Scope
, BaseType
, SizeInBits
, AlignInBits
,
1597 OffsetInBits
, Flags
, nullptr, RuntimeLang
, nullptr, nullptr, Identifier
,
1599 auto *Other
= DICompositeType::get(
1600 Context
, Tag
, Name
, File
, Line
, Scope
, BaseType
, SizeInBits
, AlignInBits
,
1601 OffsetInBits
, Flags
, nullptr, RuntimeLang
, nullptr, nullptr, Identifier
,
1603 auto *NoDisc
= DICompositeType::get(
1604 Context
, Tag
, Name
, File
, Line
, Scope
, BaseType
, SizeInBits
, AlignInBits
,
1605 OffsetInBits
, Flags
, nullptr, RuntimeLang
, nullptr, nullptr, Identifier
,
1609 EXPECT_NE(Same
, Other
);
1610 EXPECT_NE(Same
, NoDisc
);
1611 EXPECT_NE(Other
, NoDisc
);
1613 EXPECT_EQ(N
->getDiscriminator(), Discriminator
);
1616 typedef MetadataTest DISubroutineTypeTest
;
1618 TEST_F(DISubroutineTypeTest
, get
) {
1619 DINode::DIFlags Flags
= static_cast<DINode::DIFlags
>(1);
1620 DINode::DIFlags FlagsPOne
= static_cast<DINode::DIFlags
>(Flags
+ 1);
1621 MDTuple
*TypeArray
= getTuple();
1623 auto *N
= DISubroutineType::get(Context
, Flags
, 0, TypeArray
);
1624 EXPECT_EQ(dwarf::DW_TAG_subroutine_type
, N
->getTag());
1625 EXPECT_EQ(Flags
, N
->getFlags());
1626 EXPECT_EQ(TypeArray
, N
->getTypeArray().get());
1627 EXPECT_EQ(N
, DISubroutineType::get(Context
, Flags
, 0, TypeArray
));
1629 EXPECT_NE(N
, DISubroutineType::get(Context
, FlagsPOne
, 0, TypeArray
));
1630 EXPECT_NE(N
, DISubroutineType::get(Context
, Flags
, 0, getTuple()));
1632 // Test the hashing of calling conventions.
1633 auto *Fast
= DISubroutineType::get(
1634 Context
, Flags
, dwarf::DW_CC_BORLAND_msfastcall
, TypeArray
);
1635 auto *Std
= DISubroutineType::get(Context
, Flags
,
1636 dwarf::DW_CC_BORLAND_stdcall
, TypeArray
);
1638 DISubroutineType::get(Context
, Flags
,
1639 dwarf::DW_CC_BORLAND_msfastcall
, TypeArray
));
1640 EXPECT_EQ(Std
, DISubroutineType::get(
1641 Context
, Flags
, dwarf::DW_CC_BORLAND_stdcall
, TypeArray
));
1645 EXPECT_NE(Fast
, Std
);
1647 TempDISubroutineType Temp
= N
->clone();
1648 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
1650 // Test always-empty operands.
1651 EXPECT_EQ(nullptr, N
->getScope());
1652 EXPECT_EQ(nullptr, N
->getFile());
1653 EXPECT_EQ("", N
->getName());
1656 typedef MetadataTest DIFileTest
;
1658 TEST_F(DIFileTest
, get
) {
1659 StringRef Filename
= "file";
1660 StringRef Directory
= "dir";
1661 DIFile::ChecksumKind CSKind
= DIFile::ChecksumKind::CSK_MD5
;
1662 StringRef ChecksumString
= "000102030405060708090a0b0c0d0e0f";
1663 DIFile::ChecksumInfo
<StringRef
> Checksum(CSKind
, ChecksumString
);
1664 StringRef Source
= "source";
1665 auto *N
= DIFile::get(Context
, Filename
, Directory
, Checksum
, Source
);
1667 EXPECT_EQ(dwarf::DW_TAG_file_type
, N
->getTag());
1668 EXPECT_EQ(Filename
, N
->getFilename());
1669 EXPECT_EQ(Directory
, N
->getDirectory());
1670 EXPECT_EQ(Checksum
, N
->getChecksum());
1671 EXPECT_EQ(Source
, N
->getSource());
1672 EXPECT_EQ(N
, DIFile::get(Context
, Filename
, Directory
, Checksum
, Source
));
1674 EXPECT_NE(N
, DIFile::get(Context
, "other", Directory
, Checksum
, Source
));
1675 EXPECT_NE(N
, DIFile::get(Context
, Filename
, "other", Checksum
, Source
));
1676 DIFile::ChecksumInfo
<StringRef
> OtherChecksum(DIFile::ChecksumKind::CSK_SHA1
, ChecksumString
);
1678 N
, DIFile::get(Context
, Filename
, Directory
, OtherChecksum
));
1679 StringRef OtherSource
= "other";
1680 EXPECT_NE(N
, DIFile::get(Context
, Filename
, Directory
, Checksum
, OtherSource
));
1681 EXPECT_NE(N
, DIFile::get(Context
, Filename
, Directory
, Checksum
));
1682 EXPECT_NE(N
, DIFile::get(Context
, Filename
, Directory
));
1684 TempDIFile Temp
= N
->clone();
1685 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
1688 TEST_F(DIFileTest
, ScopeGetFile
) {
1689 // Ensure that DIScope::getFile() returns itself.
1690 DIScope
*N
= DIFile::get(Context
, "file", "dir");
1691 EXPECT_EQ(N
, N
->getFile());
1694 typedef MetadataTest DICompileUnitTest
;
1696 TEST_F(DICompileUnitTest
, get
) {
1697 unsigned SourceLanguage
= 1;
1698 DIFile
*File
= getFile();
1699 StringRef Producer
= "some producer";
1700 bool IsOptimized
= false;
1701 StringRef Flags
= "flag after flag";
1702 unsigned RuntimeVersion
= 2;
1703 StringRef SplitDebugFilename
= "another/file";
1704 auto EmissionKind
= DICompileUnit::FullDebug
;
1705 MDTuple
*EnumTypes
= getTuple();
1706 MDTuple
*RetainedTypes
= getTuple();
1707 MDTuple
*GlobalVariables
= getTuple();
1708 MDTuple
*ImportedEntities
= getTuple();
1709 uint64_t DWOId
= 0x10000000c0ffee;
1710 MDTuple
*Macros
= getTuple();
1711 auto *N
= DICompileUnit::getDistinct(
1712 Context
, SourceLanguage
, File
, Producer
, IsOptimized
, Flags
,
1713 RuntimeVersion
, SplitDebugFilename
, EmissionKind
, EnumTypes
,
1714 RetainedTypes
, GlobalVariables
, ImportedEntities
, Macros
, DWOId
, true,
1715 false, DICompileUnit::DebugNameTableKind::Default
, false);
1717 EXPECT_EQ(dwarf::DW_TAG_compile_unit
, N
->getTag());
1718 EXPECT_EQ(SourceLanguage
, N
->getSourceLanguage());
1719 EXPECT_EQ(File
, N
->getFile());
1720 EXPECT_EQ(Producer
, N
->getProducer());
1721 EXPECT_EQ(IsOptimized
, N
->isOptimized());
1722 EXPECT_EQ(Flags
, N
->getFlags());
1723 EXPECT_EQ(RuntimeVersion
, N
->getRuntimeVersion());
1724 EXPECT_EQ(SplitDebugFilename
, N
->getSplitDebugFilename());
1725 EXPECT_EQ(EmissionKind
, N
->getEmissionKind());
1726 EXPECT_EQ(EnumTypes
, N
->getEnumTypes().get());
1727 EXPECT_EQ(RetainedTypes
, N
->getRetainedTypes().get());
1728 EXPECT_EQ(GlobalVariables
, N
->getGlobalVariables().get());
1729 EXPECT_EQ(ImportedEntities
, N
->getImportedEntities().get());
1730 EXPECT_EQ(Macros
, N
->getMacros().get());
1731 EXPECT_EQ(DWOId
, N
->getDWOId());
1733 TempDICompileUnit Temp
= N
->clone();
1734 EXPECT_EQ(dwarf::DW_TAG_compile_unit
, Temp
->getTag());
1735 EXPECT_EQ(SourceLanguage
, Temp
->getSourceLanguage());
1736 EXPECT_EQ(File
, Temp
->getFile());
1737 EXPECT_EQ(Producer
, Temp
->getProducer());
1738 EXPECT_EQ(IsOptimized
, Temp
->isOptimized());
1739 EXPECT_EQ(Flags
, Temp
->getFlags());
1740 EXPECT_EQ(RuntimeVersion
, Temp
->getRuntimeVersion());
1741 EXPECT_EQ(SplitDebugFilename
, Temp
->getSplitDebugFilename());
1742 EXPECT_EQ(EmissionKind
, Temp
->getEmissionKind());
1743 EXPECT_EQ(EnumTypes
, Temp
->getEnumTypes().get());
1744 EXPECT_EQ(RetainedTypes
, Temp
->getRetainedTypes().get());
1745 EXPECT_EQ(GlobalVariables
, Temp
->getGlobalVariables().get());
1746 EXPECT_EQ(ImportedEntities
, Temp
->getImportedEntities().get());
1747 EXPECT_EQ(Macros
, Temp
->getMacros().get());
1748 EXPECT_EQ(DWOId
, Temp
->getDWOId());
1750 auto *TempAddress
= Temp
.get();
1751 auto *Clone
= MDNode::replaceWithPermanent(std::move(Temp
));
1752 EXPECT_TRUE(Clone
->isDistinct());
1753 EXPECT_EQ(TempAddress
, Clone
);
1756 TEST_F(DICompileUnitTest
, replaceArrays
) {
1757 unsigned SourceLanguage
= 1;
1758 DIFile
*File
= getFile();
1759 StringRef Producer
= "some producer";
1760 bool IsOptimized
= false;
1761 StringRef Flags
= "flag after flag";
1762 unsigned RuntimeVersion
= 2;
1763 StringRef SplitDebugFilename
= "another/file";
1764 auto EmissionKind
= DICompileUnit::FullDebug
;
1765 MDTuple
*EnumTypes
= MDTuple::getDistinct(Context
, None
);
1766 MDTuple
*RetainedTypes
= MDTuple::getDistinct(Context
, None
);
1767 MDTuple
*ImportedEntities
= MDTuple::getDistinct(Context
, None
);
1768 uint64_t DWOId
= 0xc0ffee;
1769 auto *N
= DICompileUnit::getDistinct(
1770 Context
, SourceLanguage
, File
, Producer
, IsOptimized
, Flags
,
1771 RuntimeVersion
, SplitDebugFilename
, EmissionKind
, EnumTypes
,
1772 RetainedTypes
, nullptr, ImportedEntities
, nullptr, DWOId
, true, false,
1773 DICompileUnit::DebugNameTableKind::Default
, false);
1775 auto *GlobalVariables
= MDTuple::getDistinct(Context
, None
);
1776 EXPECT_EQ(nullptr, N
->getGlobalVariables().get());
1777 N
->replaceGlobalVariables(GlobalVariables
);
1778 EXPECT_EQ(GlobalVariables
, N
->getGlobalVariables().get());
1779 N
->replaceGlobalVariables(nullptr);
1780 EXPECT_EQ(nullptr, N
->getGlobalVariables().get());
1782 auto *Macros
= MDTuple::getDistinct(Context
, None
);
1783 EXPECT_EQ(nullptr, N
->getMacros().get());
1784 N
->replaceMacros(Macros
);
1785 EXPECT_EQ(Macros
, N
->getMacros().get());
1786 N
->replaceMacros(nullptr);
1787 EXPECT_EQ(nullptr, N
->getMacros().get());
1790 typedef MetadataTest DISubprogramTest
;
1792 TEST_F(DISubprogramTest
, get
) {
1793 DIScope
*Scope
= getCompositeType();
1794 StringRef Name
= "name";
1795 StringRef LinkageName
= "linkage";
1796 DIFile
*File
= getFile();
1798 DISubroutineType
*Type
= getSubroutineType();
1799 bool IsLocalToUnit
= false;
1800 bool IsDefinition
= true;
1801 unsigned ScopeLine
= 3;
1802 DIType
*ContainingType
= getCompositeType();
1803 unsigned Virtuality
= 2;
1804 unsigned VirtualIndex
= 5;
1805 int ThisAdjustment
= -3;
1806 DINode::DIFlags Flags
= static_cast<DINode::DIFlags
>(6);
1807 bool IsOptimized
= false;
1808 MDTuple
*TemplateParams
= getTuple();
1809 DISubprogram
*Declaration
= getSubprogram();
1810 MDTuple
*RetainedNodes
= getTuple();
1811 MDTuple
*ThrownTypes
= getTuple();
1812 DICompileUnit
*Unit
= getUnit();
1813 DISubprogram::DISPFlags SPFlags
=
1814 static_cast<DISubprogram::DISPFlags
>(Virtuality
);
1815 assert(!IsLocalToUnit
&& IsDefinition
&& !IsOptimized
&&
1816 "bools and SPFlags have to match");
1817 SPFlags
|= DISubprogram::SPFlagDefinition
;
1819 auto *N
= DISubprogram::get(
1820 Context
, Scope
, Name
, LinkageName
, File
, Line
, Type
, ScopeLine
,
1821 ContainingType
, VirtualIndex
, ThisAdjustment
, Flags
, SPFlags
, Unit
,
1822 TemplateParams
, Declaration
, RetainedNodes
, ThrownTypes
);
1824 EXPECT_EQ(dwarf::DW_TAG_subprogram
, N
->getTag());
1825 EXPECT_EQ(Scope
, N
->getScope());
1826 EXPECT_EQ(Name
, N
->getName());
1827 EXPECT_EQ(LinkageName
, N
->getLinkageName());
1828 EXPECT_EQ(File
, N
->getFile());
1829 EXPECT_EQ(Line
, N
->getLine());
1830 EXPECT_EQ(Type
, N
->getType());
1831 EXPECT_EQ(IsLocalToUnit
, N
->isLocalToUnit());
1832 EXPECT_EQ(IsDefinition
, N
->isDefinition());
1833 EXPECT_EQ(ScopeLine
, N
->getScopeLine());
1834 EXPECT_EQ(ContainingType
, N
->getContainingType());
1835 EXPECT_EQ(Virtuality
, N
->getVirtuality());
1836 EXPECT_EQ(VirtualIndex
, N
->getVirtualIndex());
1837 EXPECT_EQ(ThisAdjustment
, N
->getThisAdjustment());
1838 EXPECT_EQ(Flags
, N
->getFlags());
1839 EXPECT_EQ(IsOptimized
, N
->isOptimized());
1840 EXPECT_EQ(Unit
, N
->getUnit());
1841 EXPECT_EQ(TemplateParams
, N
->getTemplateParams().get());
1842 EXPECT_EQ(Declaration
, N
->getDeclaration());
1843 EXPECT_EQ(RetainedNodes
, N
->getRetainedNodes().get());
1844 EXPECT_EQ(ThrownTypes
, N
->getThrownTypes().get());
1845 EXPECT_EQ(N
, DISubprogram::get(Context
, Scope
, Name
, LinkageName
, File
, Line
,
1846 Type
, ScopeLine
, ContainingType
, VirtualIndex
,
1847 ThisAdjustment
, Flags
, SPFlags
, Unit
,
1848 TemplateParams
, Declaration
, RetainedNodes
,
1851 EXPECT_NE(N
, DISubprogram::get(Context
, getCompositeType(), Name
, LinkageName
,
1852 File
, Line
, Type
, ScopeLine
, ContainingType
,
1853 VirtualIndex
, ThisAdjustment
, Flags
, SPFlags
,
1854 Unit
, TemplateParams
, Declaration
,
1855 RetainedNodes
, ThrownTypes
));
1856 EXPECT_NE(N
, DISubprogram::get(Context
, Scope
, "other", LinkageName
, File
,
1857 Line
, Type
, ScopeLine
, ContainingType
,
1858 VirtualIndex
, ThisAdjustment
, Flags
, SPFlags
,
1859 Unit
, TemplateParams
, Declaration
,
1860 RetainedNodes
, ThrownTypes
));
1861 EXPECT_NE(N
, DISubprogram::get(Context
, Scope
, Name
, "other", File
, Line
,
1862 Type
, ScopeLine
, ContainingType
, VirtualIndex
,
1863 ThisAdjustment
, Flags
, SPFlags
, Unit
,
1864 TemplateParams
, Declaration
, RetainedNodes
,
1866 EXPECT_NE(N
, DISubprogram::get(Context
, Scope
, Name
, LinkageName
, getFile(),
1867 Line
, Type
, ScopeLine
, ContainingType
,
1868 VirtualIndex
, ThisAdjustment
, Flags
, SPFlags
,
1869 Unit
, TemplateParams
, Declaration
,
1870 RetainedNodes
, ThrownTypes
));
1871 EXPECT_NE(N
, DISubprogram::get(Context
, Scope
, Name
, LinkageName
, File
,
1872 Line
+ 1, Type
, ScopeLine
, ContainingType
,
1873 VirtualIndex
, ThisAdjustment
, Flags
, SPFlags
,
1874 Unit
, TemplateParams
, Declaration
,
1875 RetainedNodes
, ThrownTypes
));
1876 EXPECT_NE(N
, DISubprogram::get(Context
, Scope
, Name
, LinkageName
, File
, Line
,
1877 getSubroutineType(), ScopeLine
, ContainingType
,
1878 VirtualIndex
, ThisAdjustment
, Flags
, SPFlags
,
1879 Unit
, TemplateParams
, Declaration
,
1880 RetainedNodes
, ThrownTypes
));
1881 EXPECT_NE(N
, DISubprogram::get(
1882 Context
, Scope
, Name
, LinkageName
, File
, Line
, Type
,
1883 ScopeLine
, ContainingType
, VirtualIndex
, ThisAdjustment
,
1884 Flags
, SPFlags
^ DISubprogram::SPFlagLocalToUnit
, Unit
,
1885 TemplateParams
, Declaration
, RetainedNodes
, ThrownTypes
));
1886 EXPECT_NE(N
, DISubprogram::get(
1887 Context
, Scope
, Name
, LinkageName
, File
, Line
, Type
,
1888 ScopeLine
, ContainingType
, VirtualIndex
, ThisAdjustment
,
1889 Flags
, SPFlags
^ DISubprogram::SPFlagDefinition
, Unit
,
1890 TemplateParams
, Declaration
, RetainedNodes
, ThrownTypes
));
1891 EXPECT_NE(N
, DISubprogram::get(Context
, Scope
, Name
, LinkageName
, File
, Line
,
1892 Type
, ScopeLine
+ 1, ContainingType
,
1893 VirtualIndex
, ThisAdjustment
, Flags
, SPFlags
,
1894 Unit
, TemplateParams
, Declaration
,
1895 RetainedNodes
, ThrownTypes
));
1896 EXPECT_NE(N
, DISubprogram::get(Context
, Scope
, Name
, LinkageName
, File
, Line
,
1897 Type
, ScopeLine
, getCompositeType(),
1898 VirtualIndex
, ThisAdjustment
, Flags
, SPFlags
,
1899 Unit
, TemplateParams
, Declaration
,
1900 RetainedNodes
, ThrownTypes
));
1901 EXPECT_NE(N
, DISubprogram::get(
1902 Context
, Scope
, Name
, LinkageName
, File
, Line
, Type
,
1903 ScopeLine
, ContainingType
, VirtualIndex
, ThisAdjustment
,
1904 Flags
, SPFlags
^ DISubprogram::SPFlagVirtual
, Unit
,
1905 TemplateParams
, Declaration
, RetainedNodes
, ThrownTypes
));
1906 EXPECT_NE(N
, DISubprogram::get(Context
, Scope
, Name
, LinkageName
, File
, Line
,
1907 Type
, ScopeLine
, ContainingType
,
1908 VirtualIndex
+ 1, ThisAdjustment
, Flags
,
1909 SPFlags
, Unit
, TemplateParams
, Declaration
,
1910 RetainedNodes
, ThrownTypes
));
1911 EXPECT_NE(N
, DISubprogram::get(
1912 Context
, Scope
, Name
, LinkageName
, File
, Line
, Type
,
1913 ScopeLine
, ContainingType
, VirtualIndex
, ThisAdjustment
,
1914 Flags
, SPFlags
^ DISubprogram::SPFlagOptimized
, Unit
,
1915 TemplateParams
, Declaration
, RetainedNodes
, ThrownTypes
));
1916 EXPECT_NE(N
, DISubprogram::get(Context
, Scope
, Name
, LinkageName
, File
, Line
,
1917 Type
, ScopeLine
, ContainingType
, VirtualIndex
,
1918 ThisAdjustment
, Flags
, SPFlags
, nullptr,
1919 TemplateParams
, Declaration
, RetainedNodes
,
1922 DISubprogram::get(Context
, Scope
, Name
, LinkageName
, File
, Line
,
1923 Type
, ScopeLine
, ContainingType
, VirtualIndex
,
1924 ThisAdjustment
, Flags
, SPFlags
, Unit
, getTuple(),
1925 Declaration
, RetainedNodes
, ThrownTypes
));
1926 EXPECT_NE(N
, DISubprogram::get(Context
, Scope
, Name
, LinkageName
, File
, Line
,
1927 Type
, ScopeLine
, ContainingType
, VirtualIndex
,
1928 ThisAdjustment
, Flags
, SPFlags
, Unit
,
1929 TemplateParams
, getSubprogram(), RetainedNodes
,
1931 EXPECT_NE(N
, DISubprogram::get(Context
, Scope
, Name
, LinkageName
, File
, Line
,
1932 Type
, ScopeLine
, ContainingType
, VirtualIndex
,
1933 ThisAdjustment
, Flags
, SPFlags
, Unit
,
1934 TemplateParams
, Declaration
, getTuple()));
1935 EXPECT_NE(N
, DISubprogram::get(Context
, Scope
, Name
, LinkageName
, File
, Line
,
1936 Type
, ScopeLine
, ContainingType
, VirtualIndex
,
1937 ThisAdjustment
, Flags
, SPFlags
, Unit
,
1938 TemplateParams
, Declaration
, RetainedNodes
,
1941 TempDISubprogram Temp
= N
->clone();
1942 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
1945 typedef MetadataTest DILexicalBlockTest
;
1947 TEST_F(DILexicalBlockTest
, get
) {
1948 DILocalScope
*Scope
= getSubprogram();
1949 DIFile
*File
= getFile();
1951 unsigned Column
= 8;
1953 auto *N
= DILexicalBlock::get(Context
, Scope
, File
, Line
, Column
);
1955 EXPECT_EQ(dwarf::DW_TAG_lexical_block
, N
->getTag());
1956 EXPECT_EQ(Scope
, N
->getScope());
1957 EXPECT_EQ(File
, N
->getFile());
1958 EXPECT_EQ(Line
, N
->getLine());
1959 EXPECT_EQ(Column
, N
->getColumn());
1960 EXPECT_EQ(N
, DILexicalBlock::get(Context
, Scope
, File
, Line
, Column
));
1963 DILexicalBlock::get(Context
, getSubprogram(), File
, Line
, Column
));
1964 EXPECT_NE(N
, DILexicalBlock::get(Context
, Scope
, getFile(), Line
, Column
));
1965 EXPECT_NE(N
, DILexicalBlock::get(Context
, Scope
, File
, Line
+ 1, Column
));
1966 EXPECT_NE(N
, DILexicalBlock::get(Context
, Scope
, File
, Line
, Column
+ 1));
1968 TempDILexicalBlock Temp
= N
->clone();
1969 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
1972 TEST_F(DILexicalBlockTest
, Overflow
) {
1973 DISubprogram
*SP
= getSubprogram();
1974 DIFile
*F
= getFile();
1976 auto *LB
= DILexicalBlock::get(Context
, SP
, F
, 2, 7);
1977 EXPECT_EQ(2u, LB
->getLine());
1978 EXPECT_EQ(7u, LB
->getColumn());
1980 unsigned U16
= 1u << 16;
1982 auto *LB
= DILexicalBlock::get(Context
, SP
, F
, UINT32_MAX
, U16
- 1);
1983 EXPECT_EQ(UINT32_MAX
, LB
->getLine());
1984 EXPECT_EQ(U16
- 1, LB
->getColumn());
1987 auto *LB
= DILexicalBlock::get(Context
, SP
, F
, UINT32_MAX
, U16
);
1988 EXPECT_EQ(UINT32_MAX
, LB
->getLine());
1989 EXPECT_EQ(0u, LB
->getColumn());
1992 auto *LB
= DILexicalBlock::get(Context
, SP
, F
, UINT32_MAX
, U16
+ 1);
1993 EXPECT_EQ(UINT32_MAX
, LB
->getLine());
1994 EXPECT_EQ(0u, LB
->getColumn());
1998 typedef MetadataTest DILexicalBlockFileTest
;
2000 TEST_F(DILexicalBlockFileTest
, get
) {
2001 DILocalScope
*Scope
= getSubprogram();
2002 DIFile
*File
= getFile();
2003 unsigned Discriminator
= 5;
2005 auto *N
= DILexicalBlockFile::get(Context
, Scope
, File
, Discriminator
);
2007 EXPECT_EQ(dwarf::DW_TAG_lexical_block
, N
->getTag());
2008 EXPECT_EQ(Scope
, N
->getScope());
2009 EXPECT_EQ(File
, N
->getFile());
2010 EXPECT_EQ(Discriminator
, N
->getDiscriminator());
2011 EXPECT_EQ(N
, DILexicalBlockFile::get(Context
, Scope
, File
, Discriminator
));
2013 EXPECT_NE(N
, DILexicalBlockFile::get(Context
, getSubprogram(), File
,
2016 DILexicalBlockFile::get(Context
, Scope
, getFile(), Discriminator
));
2018 DILexicalBlockFile::get(Context
, Scope
, File
, Discriminator
+ 1));
2020 TempDILexicalBlockFile Temp
= N
->clone();
2021 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
2024 typedef MetadataTest DINamespaceTest
;
2026 TEST_F(DINamespaceTest
, get
) {
2027 DIScope
*Scope
= getFile();
2028 StringRef Name
= "namespace";
2029 bool ExportSymbols
= true;
2031 auto *N
= DINamespace::get(Context
, Scope
, Name
, ExportSymbols
);
2033 EXPECT_EQ(dwarf::DW_TAG_namespace
, N
->getTag());
2034 EXPECT_EQ(Scope
, N
->getScope());
2035 EXPECT_EQ(Name
, N
->getName());
2036 EXPECT_EQ(N
, DINamespace::get(Context
, Scope
, Name
, ExportSymbols
));
2037 EXPECT_NE(N
, DINamespace::get(Context
, getFile(), Name
, ExportSymbols
));
2038 EXPECT_NE(N
, DINamespace::get(Context
, Scope
, "other", ExportSymbols
));
2039 EXPECT_NE(N
, DINamespace::get(Context
, Scope
, Name
, !ExportSymbols
));
2041 TempDINamespace Temp
= N
->clone();
2042 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
2045 typedef MetadataTest DIModuleTest
;
2047 TEST_F(DIModuleTest
, get
) {
2048 DIScope
*Scope
= getFile();
2049 StringRef Name
= "module";
2050 StringRef ConfigMacro
= "-DNDEBUG";
2051 StringRef Includes
= "-I.";
2052 StringRef Sysroot
= "/";
2054 auto *N
= DIModule::get(Context
, Scope
, Name
, ConfigMacro
, Includes
, Sysroot
);
2056 EXPECT_EQ(dwarf::DW_TAG_module
, N
->getTag());
2057 EXPECT_EQ(Scope
, N
->getScope());
2058 EXPECT_EQ(Name
, N
->getName());
2059 EXPECT_EQ(ConfigMacro
, N
->getConfigurationMacros());
2060 EXPECT_EQ(Includes
, N
->getIncludePath());
2061 EXPECT_EQ(Sysroot
, N
->getISysRoot());
2062 EXPECT_EQ(N
, DIModule::get(Context
, Scope
, Name
,
2063 ConfigMacro
, Includes
, Sysroot
));
2064 EXPECT_NE(N
, DIModule::get(Context
, getFile(), Name
,
2065 ConfigMacro
, Includes
, Sysroot
));
2066 EXPECT_NE(N
, DIModule::get(Context
, Scope
, "other",
2067 ConfigMacro
, Includes
, Sysroot
));
2068 EXPECT_NE(N
, DIModule::get(Context
, Scope
, Name
,
2069 "other", Includes
, Sysroot
));
2070 EXPECT_NE(N
, DIModule::get(Context
, Scope
, Name
,
2071 ConfigMacro
, "other", Sysroot
));
2072 EXPECT_NE(N
, DIModule::get(Context
, Scope
, Name
,
2073 ConfigMacro
, Includes
, "other"));
2075 TempDIModule Temp
= N
->clone();
2076 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
2079 typedef MetadataTest DITemplateTypeParameterTest
;
2081 TEST_F(DITemplateTypeParameterTest
, get
) {
2082 StringRef Name
= "template";
2083 DIType
*Type
= getBasicType("basic");
2085 auto *N
= DITemplateTypeParameter::get(Context
, Name
, Type
);
2087 EXPECT_EQ(dwarf::DW_TAG_template_type_parameter
, N
->getTag());
2088 EXPECT_EQ(Name
, N
->getName());
2089 EXPECT_EQ(Type
, N
->getType());
2090 EXPECT_EQ(N
, DITemplateTypeParameter::get(Context
, Name
, Type
));
2092 EXPECT_NE(N
, DITemplateTypeParameter::get(Context
, "other", Type
));
2094 DITemplateTypeParameter::get(Context
, Name
, getBasicType("other")));
2096 TempDITemplateTypeParameter Temp
= N
->clone();
2097 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
2100 typedef MetadataTest DITemplateValueParameterTest
;
2102 TEST_F(DITemplateValueParameterTest
, get
) {
2103 unsigned Tag
= dwarf::DW_TAG_template_value_parameter
;
2104 StringRef Name
= "template";
2105 DIType
*Type
= getBasicType("basic");
2106 Metadata
*Value
= getConstantAsMetadata();
2108 auto *N
= DITemplateValueParameter::get(Context
, Tag
, Name
, Type
, Value
);
2109 EXPECT_EQ(Tag
, N
->getTag());
2110 EXPECT_EQ(Name
, N
->getName());
2111 EXPECT_EQ(Type
, N
->getType());
2112 EXPECT_EQ(Value
, N
->getValue());
2113 EXPECT_EQ(N
, DITemplateValueParameter::get(Context
, Tag
, Name
, Type
, Value
));
2115 EXPECT_NE(N
, DITemplateValueParameter::get(
2116 Context
, dwarf::DW_TAG_GNU_template_template_param
, Name
,
2119 DITemplateValueParameter::get(Context
, Tag
, "other", Type
, Value
));
2120 EXPECT_NE(N
, DITemplateValueParameter::get(Context
, Tag
, Name
,
2121 getBasicType("other"), Value
));
2122 EXPECT_NE(N
, DITemplateValueParameter::get(Context
, Tag
, Name
, Type
,
2123 getConstantAsMetadata()));
2125 TempDITemplateValueParameter Temp
= N
->clone();
2126 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
2129 typedef MetadataTest DIGlobalVariableTest
;
2131 TEST_F(DIGlobalVariableTest
, get
) {
2132 DIScope
*Scope
= getSubprogram();
2133 StringRef Name
= "name";
2134 StringRef LinkageName
= "linkage";
2135 DIFile
*File
= getFile();
2137 DIType
*Type
= getDerivedType();
2138 bool IsLocalToUnit
= false;
2139 bool IsDefinition
= true;
2140 MDTuple
*templateParams
= getTuple();
2141 DIDerivedType
*StaticDataMemberDeclaration
=
2142 cast
<DIDerivedType
>(getDerivedType());
2144 uint32_t AlignInBits
= 8;
2146 auto *N
= DIGlobalVariable::get(
2147 Context
, Scope
, Name
, LinkageName
, File
, Line
, Type
, IsLocalToUnit
,
2148 IsDefinition
, StaticDataMemberDeclaration
, templateParams
, AlignInBits
);
2150 EXPECT_EQ(dwarf::DW_TAG_variable
, N
->getTag());
2151 EXPECT_EQ(Scope
, N
->getScope());
2152 EXPECT_EQ(Name
, N
->getName());
2153 EXPECT_EQ(LinkageName
, N
->getLinkageName());
2154 EXPECT_EQ(File
, N
->getFile());
2155 EXPECT_EQ(Line
, N
->getLine());
2156 EXPECT_EQ(Type
, N
->getType());
2157 EXPECT_EQ(IsLocalToUnit
, N
->isLocalToUnit());
2158 EXPECT_EQ(IsDefinition
, N
->isDefinition());
2159 EXPECT_EQ(StaticDataMemberDeclaration
, N
->getStaticDataMemberDeclaration());
2160 EXPECT_EQ(templateParams
, N
->getTemplateParams());
2161 EXPECT_EQ(AlignInBits
, N
->getAlignInBits());
2162 EXPECT_EQ(N
, DIGlobalVariable::get(Context
, Scope
, Name
, LinkageName
, File
,
2163 Line
, Type
, IsLocalToUnit
, IsDefinition
,
2164 StaticDataMemberDeclaration
,
2165 templateParams
, AlignInBits
));
2167 EXPECT_NE(N
, DIGlobalVariable::get(
2168 Context
, getSubprogram(), Name
, LinkageName
, File
, Line
,
2169 Type
, IsLocalToUnit
, IsDefinition
,
2170 StaticDataMemberDeclaration
, templateParams
, AlignInBits
));
2171 EXPECT_NE(N
, DIGlobalVariable::get(Context
, Scope
, "other", LinkageName
, File
,
2172 Line
, Type
, IsLocalToUnit
, IsDefinition
,
2173 StaticDataMemberDeclaration
,
2174 templateParams
, AlignInBits
));
2175 EXPECT_NE(N
, DIGlobalVariable::get(Context
, Scope
, Name
, "other", File
, Line
,
2176 Type
, IsLocalToUnit
, IsDefinition
,
2177 StaticDataMemberDeclaration
,
2178 templateParams
, AlignInBits
));
2179 EXPECT_NE(N
, DIGlobalVariable::get(Context
, Scope
, Name
, LinkageName
,
2180 getFile(), Line
, Type
, IsLocalToUnit
,
2181 IsDefinition
, StaticDataMemberDeclaration
,
2182 templateParams
, AlignInBits
));
2183 EXPECT_NE(N
, DIGlobalVariable::get(Context
, Scope
, Name
, LinkageName
, File
,
2184 Line
+ 1, Type
, IsLocalToUnit
,
2185 IsDefinition
, StaticDataMemberDeclaration
,
2186 templateParams
, AlignInBits
));
2187 EXPECT_NE(N
, DIGlobalVariable::get(Context
, Scope
, Name
, LinkageName
, File
,
2188 Line
, getDerivedType(), IsLocalToUnit
,
2189 IsDefinition
, StaticDataMemberDeclaration
,
2190 templateParams
, AlignInBits
));
2191 EXPECT_NE(N
, DIGlobalVariable::get(Context
, Scope
, Name
, LinkageName
, File
,
2192 Line
, Type
, !IsLocalToUnit
, IsDefinition
,
2193 StaticDataMemberDeclaration
,
2194 templateParams
, AlignInBits
));
2195 EXPECT_NE(N
, DIGlobalVariable::get(Context
, Scope
, Name
, LinkageName
, File
,
2196 Line
, Type
, IsLocalToUnit
, !IsDefinition
,
2197 StaticDataMemberDeclaration
,
2198 templateParams
, AlignInBits
));
2199 EXPECT_NE(N
, DIGlobalVariable::get(Context
, Scope
, Name
, LinkageName
, File
,
2200 Line
, Type
, IsLocalToUnit
, IsDefinition
,
2201 cast
<DIDerivedType
>(getDerivedType()),
2202 templateParams
, AlignInBits
));
2203 EXPECT_NE(N
, DIGlobalVariable::get(Context
, Scope
, Name
, LinkageName
, File
,
2204 Line
, Type
, IsLocalToUnit
, IsDefinition
,
2205 StaticDataMemberDeclaration
, nullptr,
2207 EXPECT_NE(N
, DIGlobalVariable::get(Context
, Scope
, Name
, LinkageName
, File
,
2208 Line
, Type
, IsLocalToUnit
, IsDefinition
,
2209 StaticDataMemberDeclaration
,
2210 templateParams
, (AlignInBits
<< 1)));
2212 TempDIGlobalVariable Temp
= N
->clone();
2213 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
2216 typedef MetadataTest DIGlobalVariableExpressionTest
;
2218 TEST_F(DIGlobalVariableExpressionTest
, get
) {
2219 DIScope
*Scope
= getSubprogram();
2220 StringRef Name
= "name";
2221 StringRef LinkageName
= "linkage";
2222 DIFile
*File
= getFile();
2224 DIType
*Type
= getDerivedType();
2225 bool IsLocalToUnit
= false;
2226 bool IsDefinition
= true;
2227 MDTuple
*templateParams
= getTuple();
2228 auto *Expr
= DIExpression::get(Context
, {1, 2});
2229 auto *Expr2
= DIExpression::get(Context
, {1, 2, 3});
2230 DIDerivedType
*StaticDataMemberDeclaration
=
2231 cast
<DIDerivedType
>(getDerivedType());
2232 uint32_t AlignInBits
= 8;
2234 auto *Var
= DIGlobalVariable::get(
2235 Context
, Scope
, Name
, LinkageName
, File
, Line
, Type
, IsLocalToUnit
,
2236 IsDefinition
, StaticDataMemberDeclaration
, templateParams
, AlignInBits
);
2237 auto *Var2
= DIGlobalVariable::get(
2238 Context
, Scope
, "other", LinkageName
, File
, Line
, Type
, IsLocalToUnit
,
2239 IsDefinition
, StaticDataMemberDeclaration
, templateParams
, AlignInBits
);
2240 auto *N
= DIGlobalVariableExpression::get(Context
, Var
, Expr
);
2242 EXPECT_EQ(Var
, N
->getVariable());
2243 EXPECT_EQ(Expr
, N
->getExpression());
2244 EXPECT_EQ(N
, DIGlobalVariableExpression::get(Context
, Var
, Expr
));
2245 EXPECT_NE(N
, DIGlobalVariableExpression::get(Context
, Var2
, Expr
));
2246 EXPECT_NE(N
, DIGlobalVariableExpression::get(Context
, Var
, Expr2
));
2248 TempDIGlobalVariableExpression Temp
= N
->clone();
2249 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
2252 typedef MetadataTest DILocalVariableTest
;
2254 TEST_F(DILocalVariableTest
, get
) {
2255 DILocalScope
*Scope
= getSubprogram();
2256 StringRef Name
= "name";
2257 DIFile
*File
= getFile();
2259 DIType
*Type
= getDerivedType();
2261 DINode::DIFlags Flags
= static_cast<DINode::DIFlags
>(7);
2262 uint32_t AlignInBits
= 8;
2265 DILocalVariable::get(Context
, Scope
, Name
, File
, Line
, Type
, Arg
, Flags
,
2267 EXPECT_TRUE(N
->isParameter());
2268 EXPECT_EQ(Scope
, N
->getScope());
2269 EXPECT_EQ(Name
, N
->getName());
2270 EXPECT_EQ(File
, N
->getFile());
2271 EXPECT_EQ(Line
, N
->getLine());
2272 EXPECT_EQ(Type
, N
->getType());
2273 EXPECT_EQ(Arg
, N
->getArg());
2274 EXPECT_EQ(Flags
, N
->getFlags());
2275 EXPECT_EQ(AlignInBits
, N
->getAlignInBits());
2276 EXPECT_EQ(N
, DILocalVariable::get(Context
, Scope
, Name
, File
, Line
, Type
, Arg
,
2277 Flags
, AlignInBits
));
2280 DILocalVariable::get(Context
, Scope
, Name
, File
, Line
, Type
, 0, Flags
,
2281 AlignInBits
)->isParameter());
2282 EXPECT_NE(N
, DILocalVariable::get(Context
, getSubprogram(), Name
, File
, Line
,
2283 Type
, Arg
, Flags
, AlignInBits
));
2284 EXPECT_NE(N
, DILocalVariable::get(Context
, Scope
, "other", File
, Line
, Type
,
2285 Arg
, Flags
, AlignInBits
));
2286 EXPECT_NE(N
, DILocalVariable::get(Context
, Scope
, Name
, getFile(), Line
, Type
,
2287 Arg
, Flags
, AlignInBits
));
2288 EXPECT_NE(N
, DILocalVariable::get(Context
, Scope
, Name
, File
, Line
+ 1, Type
,
2289 Arg
, Flags
, AlignInBits
));
2290 EXPECT_NE(N
, DILocalVariable::get(Context
, Scope
, Name
, File
, Line
,
2291 getDerivedType(), Arg
, Flags
, AlignInBits
));
2292 EXPECT_NE(N
, DILocalVariable::get(Context
, Scope
, Name
, File
, Line
, Type
,
2293 Arg
+ 1, Flags
, AlignInBits
));
2294 EXPECT_NE(N
, DILocalVariable::get(Context
, Scope
, Name
, File
, Line
, Type
,
2295 Arg
, Flags
, (AlignInBits
<< 1)));
2297 TempDILocalVariable Temp
= N
->clone();
2298 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
2301 TEST_F(DILocalVariableTest
, getArg256
) {
2302 EXPECT_EQ(255u, DILocalVariable::get(Context
, getSubprogram(), "", getFile(),
2303 0, nullptr, 255, DINode::FlagZero
, 0)
2305 EXPECT_EQ(256u, DILocalVariable::get(Context
, getSubprogram(), "", getFile(),
2306 0, nullptr, 256, DINode::FlagZero
, 0)
2308 EXPECT_EQ(257u, DILocalVariable::get(Context
, getSubprogram(), "", getFile(),
2309 0, nullptr, 257, DINode::FlagZero
, 0)
2311 unsigned Max
= UINT16_MAX
;
2312 EXPECT_EQ(Max
, DILocalVariable::get(Context
, getSubprogram(), "", getFile(),
2313 0, nullptr, Max
, DINode::FlagZero
, 0)
2317 typedef MetadataTest DIExpressionTest
;
2319 TEST_F(DIExpressionTest
, get
) {
2320 uint64_t Elements
[] = {2, 6, 9, 78, 0};
2321 auto *N
= DIExpression::get(Context
, Elements
);
2322 EXPECT_EQ(makeArrayRef(Elements
), N
->getElements());
2323 EXPECT_EQ(N
, DIExpression::get(Context
, Elements
));
2325 EXPECT_EQ(5u, N
->getNumElements());
2326 EXPECT_EQ(2u, N
->getElement(0));
2327 EXPECT_EQ(6u, N
->getElement(1));
2328 EXPECT_EQ(9u, N
->getElement(2));
2329 EXPECT_EQ(78u, N
->getElement(3));
2330 EXPECT_EQ(0u, N
->getElement(4));
2332 TempDIExpression Temp
= N
->clone();
2333 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
2335 // Test DIExpression::prepend().
2336 uint64_t Elts0
[] = {dwarf::DW_OP_LLVM_fragment
, 0, 32};
2337 auto *N0
= DIExpression::get(Context
, Elts0
);
2338 uint8_t DIExprFlags
= DIExpression::ApplyOffset
;
2339 DIExprFlags
|= DIExpression::DerefBefore
;
2340 DIExprFlags
|= DIExpression::DerefAfter
;
2341 DIExprFlags
|= DIExpression::StackValue
;
2342 auto *N0WithPrependedOps
= DIExpression::prepend(N0
, DIExprFlags
, 64);
2343 uint64_t Elts1
[] = {dwarf::DW_OP_deref
,
2344 dwarf::DW_OP_plus_uconst
, 64,
2346 dwarf::DW_OP_stack_value
,
2347 dwarf::DW_OP_LLVM_fragment
, 0, 32};
2348 auto *N1
= DIExpression::get(Context
, Elts1
);
2349 EXPECT_EQ(N0WithPrependedOps
, N1
);
2351 // Test DIExpression::append().
2352 uint64_t Elts2
[] = {dwarf::DW_OP_deref
, dwarf::DW_OP_plus_uconst
, 64,
2353 dwarf::DW_OP_deref
, dwarf::DW_OP_stack_value
};
2354 auto *N2
= DIExpression::append(N0
, Elts2
);
2355 EXPECT_EQ(N0WithPrependedOps
, N2
);
2358 TEST_F(DIExpressionTest
, isValid
) {
2359 #define EXPECT_VALID(...) \
2361 uint64_t Elements[] = {__VA_ARGS__}; \
2362 EXPECT_TRUE(DIExpression::get(Context, Elements)->isValid()); \
2364 #define EXPECT_INVALID(...) \
2366 uint64_t Elements[] = {__VA_ARGS__}; \
2367 EXPECT_FALSE(DIExpression::get(Context, Elements)->isValid()); \
2370 // Empty expression should be valid.
2371 EXPECT_TRUE(DIExpression::get(Context
, None
));
2373 // Valid constructions.
2374 EXPECT_VALID(dwarf::DW_OP_plus_uconst
, 6);
2375 EXPECT_VALID(dwarf::DW_OP_constu
, 6, dwarf::DW_OP_plus
);
2376 EXPECT_VALID(dwarf::DW_OP_deref
);
2377 EXPECT_VALID(dwarf::DW_OP_LLVM_fragment
, 3, 7);
2378 EXPECT_VALID(dwarf::DW_OP_plus_uconst
, 6, dwarf::DW_OP_deref
);
2379 EXPECT_VALID(dwarf::DW_OP_deref
, dwarf::DW_OP_plus_uconst
, 6);
2380 EXPECT_VALID(dwarf::DW_OP_deref
, dwarf::DW_OP_LLVM_fragment
, 3, 7);
2381 EXPECT_VALID(dwarf::DW_OP_deref
, dwarf::DW_OP_plus_uconst
, 6,
2382 dwarf::DW_OP_LLVM_fragment
, 3, 7);
2384 // Invalid constructions.
2385 EXPECT_INVALID(~0u);
2386 EXPECT_INVALID(dwarf::DW_OP_plus
, 0);
2387 EXPECT_INVALID(dwarf::DW_OP_plus_uconst
);
2388 EXPECT_INVALID(dwarf::DW_OP_LLVM_fragment
);
2389 EXPECT_INVALID(dwarf::DW_OP_LLVM_fragment
, 3);
2390 EXPECT_INVALID(dwarf::DW_OP_LLVM_fragment
, 3, 7, dwarf::DW_OP_plus_uconst
, 3);
2391 EXPECT_INVALID(dwarf::DW_OP_LLVM_fragment
, 3, 7, dwarf::DW_OP_deref
);
2394 #undef EXPECT_INVALID
2397 typedef MetadataTest DIObjCPropertyTest
;
2399 TEST_F(DIObjCPropertyTest
, get
) {
2400 StringRef Name
= "name";
2401 DIFile
*File
= getFile();
2403 StringRef GetterName
= "getter";
2404 StringRef SetterName
= "setter";
2405 unsigned Attributes
= 7;
2406 DIType
*Type
= getBasicType("basic");
2408 auto *N
= DIObjCProperty::get(Context
, Name
, File
, Line
, GetterName
,
2409 SetterName
, Attributes
, Type
);
2411 EXPECT_EQ(dwarf::DW_TAG_APPLE_property
, N
->getTag());
2412 EXPECT_EQ(Name
, N
->getName());
2413 EXPECT_EQ(File
, N
->getFile());
2414 EXPECT_EQ(Line
, N
->getLine());
2415 EXPECT_EQ(GetterName
, N
->getGetterName());
2416 EXPECT_EQ(SetterName
, N
->getSetterName());
2417 EXPECT_EQ(Attributes
, N
->getAttributes());
2418 EXPECT_EQ(Type
, N
->getType());
2419 EXPECT_EQ(N
, DIObjCProperty::get(Context
, Name
, File
, Line
, GetterName
,
2420 SetterName
, Attributes
, Type
));
2422 EXPECT_NE(N
, DIObjCProperty::get(Context
, "other", File
, Line
, GetterName
,
2423 SetterName
, Attributes
, Type
));
2424 EXPECT_NE(N
, DIObjCProperty::get(Context
, Name
, getFile(), Line
, GetterName
,
2425 SetterName
, Attributes
, Type
));
2426 EXPECT_NE(N
, DIObjCProperty::get(Context
, Name
, File
, Line
+ 1, GetterName
,
2427 SetterName
, Attributes
, Type
));
2428 EXPECT_NE(N
, DIObjCProperty::get(Context
, Name
, File
, Line
, "other",
2429 SetterName
, Attributes
, Type
));
2430 EXPECT_NE(N
, DIObjCProperty::get(Context
, Name
, File
, Line
, GetterName
,
2431 "other", Attributes
, Type
));
2432 EXPECT_NE(N
, DIObjCProperty::get(Context
, Name
, File
, Line
, GetterName
,
2433 SetterName
, Attributes
+ 1, Type
));
2434 EXPECT_NE(N
, DIObjCProperty::get(Context
, Name
, File
, Line
, GetterName
,
2435 SetterName
, Attributes
,
2436 getBasicType("other")));
2438 TempDIObjCProperty Temp
= N
->clone();
2439 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
2442 typedef MetadataTest DIImportedEntityTest
;
2444 TEST_F(DIImportedEntityTest
, get
) {
2445 unsigned Tag
= dwarf::DW_TAG_imported_module
;
2446 DIScope
*Scope
= getSubprogram();
2447 DINode
*Entity
= getCompositeType();
2448 DIFile
*File
= getFile();
2450 StringRef Name
= "name";
2453 DIImportedEntity::get(Context
, Tag
, Scope
, Entity
, File
, Line
, Name
);
2455 EXPECT_EQ(Tag
, N
->getTag());
2456 EXPECT_EQ(Scope
, N
->getScope());
2457 EXPECT_EQ(Entity
, N
->getEntity());
2458 EXPECT_EQ(File
, N
->getFile());
2459 EXPECT_EQ(Line
, N
->getLine());
2460 EXPECT_EQ(Name
, N
->getName());
2462 N
, DIImportedEntity::get(Context
, Tag
, Scope
, Entity
, File
, Line
, Name
));
2465 DIImportedEntity::get(Context
, dwarf::DW_TAG_imported_declaration
,
2466 Scope
, Entity
, File
, Line
, Name
));
2467 EXPECT_NE(N
, DIImportedEntity::get(Context
, Tag
, getSubprogram(), Entity
,
2469 EXPECT_NE(N
, DIImportedEntity::get(Context
, Tag
, Scope
, getCompositeType(),
2471 EXPECT_NE(N
, DIImportedEntity::get(Context
, Tag
, Scope
, Entity
, nullptr, Line
,
2473 EXPECT_NE(N
, DIImportedEntity::get(Context
, Tag
, Scope
, Entity
, File
,
2475 EXPECT_NE(N
, DIImportedEntity::get(Context
, Tag
, Scope
, Entity
, File
, Line
,
2478 TempDIImportedEntity Temp
= N
->clone();
2479 EXPECT_EQ(N
, MDNode::replaceWithUniqued(std::move(Temp
)));
2482 typedef MetadataTest MetadataAsValueTest
;
2484 TEST_F(MetadataAsValueTest
, MDNode
) {
2485 MDNode
*N
= MDNode::get(Context
, None
);
2486 auto *V
= MetadataAsValue::get(Context
, N
);
2487 EXPECT_TRUE(V
->getType()->isMetadataTy());
2488 EXPECT_EQ(N
, V
->getMetadata());
2490 auto *V2
= MetadataAsValue::get(Context
, N
);
2494 TEST_F(MetadataAsValueTest
, MDNodeMDNode
) {
2495 MDNode
*N
= MDNode::get(Context
, None
);
2496 Metadata
*Ops
[] = {N
};
2497 MDNode
*N2
= MDNode::get(Context
, Ops
);
2498 auto *V
= MetadataAsValue::get(Context
, N2
);
2499 EXPECT_TRUE(V
->getType()->isMetadataTy());
2500 EXPECT_EQ(N2
, V
->getMetadata());
2502 auto *V2
= MetadataAsValue::get(Context
, N2
);
2505 auto *V3
= MetadataAsValue::get(Context
, N
);
2506 EXPECT_TRUE(V3
->getType()->isMetadataTy());
2508 EXPECT_EQ(N
, V3
->getMetadata());
2511 TEST_F(MetadataAsValueTest
, MDNodeConstant
) {
2512 auto *C
= ConstantInt::getTrue(Context
);
2513 auto *MD
= ConstantAsMetadata::get(C
);
2514 Metadata
*Ops
[] = {MD
};
2515 auto *N
= MDNode::get(Context
, Ops
);
2517 auto *V
= MetadataAsValue::get(Context
, MD
);
2518 EXPECT_TRUE(V
->getType()->isMetadataTy());
2519 EXPECT_EQ(MD
, V
->getMetadata());
2521 auto *V2
= MetadataAsValue::get(Context
, N
);
2522 EXPECT_EQ(MD
, V2
->getMetadata());
2526 typedef MetadataTest ValueAsMetadataTest
;
2528 TEST_F(ValueAsMetadataTest
, UpdatesOnRAUW
) {
2529 Type
*Ty
= Type::getInt1PtrTy(Context
);
2530 std::unique_ptr
<GlobalVariable
> GV0(
2531 new GlobalVariable(Ty
, false, GlobalValue::ExternalLinkage
));
2532 auto *MD
= ValueAsMetadata::get(GV0
.get());
2533 EXPECT_TRUE(MD
->getValue() == GV0
.get());
2534 ASSERT_TRUE(GV0
->use_empty());
2536 std::unique_ptr
<GlobalVariable
> GV1(
2537 new GlobalVariable(Ty
, false, GlobalValue::ExternalLinkage
));
2538 GV0
->replaceAllUsesWith(GV1
.get());
2539 EXPECT_TRUE(MD
->getValue() == GV1
.get());
2542 TEST_F(ValueAsMetadataTest
, TempTempReplacement
) {
2543 // Create a constant.
2544 ConstantAsMetadata
*CI
=
2545 ConstantAsMetadata::get(ConstantInt::get(Context
, APInt(8, 0)));
2547 auto Temp1
= MDTuple::getTemporary(Context
, None
);
2548 auto Temp2
= MDTuple::getTemporary(Context
, {CI
});
2549 auto *N
= MDTuple::get(Context
, {Temp1
.get()});
2551 // Test replacing a temporary node with another temporary node.
2552 Temp1
->replaceAllUsesWith(Temp2
.get());
2553 EXPECT_EQ(N
->getOperand(0), Temp2
.get());
2555 // Clean up Temp2 for teardown.
2556 Temp2
->replaceAllUsesWith(nullptr);
2559 TEST_F(ValueAsMetadataTest
, CollidingDoubleUpdates
) {
2560 // Create a constant.
2561 ConstantAsMetadata
*CI
=
2562 ConstantAsMetadata::get(ConstantInt::get(Context
, APInt(8, 0)));
2564 // Create a temporary to prevent nodes from resolving.
2565 auto Temp
= MDTuple::getTemporary(Context
, None
);
2567 // When the first operand of N1 gets reset to nullptr, it'll collide with N2.
2568 Metadata
*Ops1
[] = {CI
, CI
, Temp
.get()};
2569 Metadata
*Ops2
[] = {nullptr, CI
, Temp
.get()};
2571 auto *N1
= MDTuple::get(Context
, Ops1
);
2572 auto *N2
= MDTuple::get(Context
, Ops2
);
2575 // Tell metadata that the constant is getting deleted.
2577 // After this, N1 will be invalid, so don't touch it.
2578 ValueAsMetadata::handleDeletion(CI
->getValue());
2579 EXPECT_EQ(nullptr, N2
->getOperand(0));
2580 EXPECT_EQ(nullptr, N2
->getOperand(1));
2581 EXPECT_EQ(Temp
.get(), N2
->getOperand(2));
2583 // Clean up Temp for teardown.
2584 Temp
->replaceAllUsesWith(nullptr);
2587 typedef MetadataTest TrackingMDRefTest
;
2589 TEST_F(TrackingMDRefTest
, UpdatesOnRAUW
) {
2590 Type
*Ty
= Type::getInt1PtrTy(Context
);
2591 std::unique_ptr
<GlobalVariable
> GV0(
2592 new GlobalVariable(Ty
, false, GlobalValue::ExternalLinkage
));
2593 TypedTrackingMDRef
<ValueAsMetadata
> MD(ValueAsMetadata::get(GV0
.get()));
2594 EXPECT_TRUE(MD
->getValue() == GV0
.get());
2595 ASSERT_TRUE(GV0
->use_empty());
2597 std::unique_ptr
<GlobalVariable
> GV1(
2598 new GlobalVariable(Ty
, false, GlobalValue::ExternalLinkage
));
2599 GV0
->replaceAllUsesWith(GV1
.get());
2600 EXPECT_TRUE(MD
->getValue() == GV1
.get());
2602 // Reset it, so we don't inadvertently test deletion.
2606 TEST_F(TrackingMDRefTest
, UpdatesOnDeletion
) {
2607 Type
*Ty
= Type::getInt1PtrTy(Context
);
2608 std::unique_ptr
<GlobalVariable
> GV(
2609 new GlobalVariable(Ty
, false, GlobalValue::ExternalLinkage
));
2610 TypedTrackingMDRef
<ValueAsMetadata
> MD(ValueAsMetadata::get(GV
.get()));
2611 EXPECT_TRUE(MD
->getValue() == GV
.get());
2612 ASSERT_TRUE(GV
->use_empty());
2618 TEST(NamedMDNodeTest
, Search
) {
2619 LLVMContext Context
;
2620 ConstantAsMetadata
*C
=
2621 ConstantAsMetadata::get(ConstantInt::get(Type::getInt32Ty(Context
), 1));
2622 ConstantAsMetadata
*C2
=
2623 ConstantAsMetadata::get(ConstantInt::get(Type::getInt32Ty(Context
), 2));
2625 Metadata
*const V
= C
;
2626 Metadata
*const V2
= C2
;
2627 MDNode
*n
= MDNode::get(Context
, V
);
2628 MDNode
*n2
= MDNode::get(Context
, V2
);
2630 Module
M("MyModule", Context
);
2631 const char *Name
= "llvm.NMD1";
2632 NamedMDNode
*NMD
= M
.getOrInsertNamedMetadata(Name
);
2634 NMD
->addOperand(n2
);
2637 raw_string_ostream
oss(Str
);
2639 EXPECT_STREQ("!llvm.NMD1 = !{!0, !1}\n",
2643 typedef MetadataTest FunctionAttachmentTest
;
2644 TEST_F(FunctionAttachmentTest
, setMetadata
) {
2645 Function
*F
= getFunction("foo");
2646 ASSERT_FALSE(F
->hasMetadata());
2647 EXPECT_EQ(nullptr, F
->getMetadata(LLVMContext::MD_dbg
));
2648 EXPECT_EQ(nullptr, F
->getMetadata("dbg"));
2649 EXPECT_EQ(nullptr, F
->getMetadata("other"));
2651 DISubprogram
*SP1
= getSubprogram();
2652 DISubprogram
*SP2
= getSubprogram();
2653 ASSERT_NE(SP1
, SP2
);
2655 F
->setMetadata("dbg", SP1
);
2656 EXPECT_TRUE(F
->hasMetadata());
2657 EXPECT_EQ(SP1
, F
->getMetadata(LLVMContext::MD_dbg
));
2658 EXPECT_EQ(SP1
, F
->getMetadata("dbg"));
2659 EXPECT_EQ(nullptr, F
->getMetadata("other"));
2661 F
->setMetadata(LLVMContext::MD_dbg
, SP2
);
2662 EXPECT_TRUE(F
->hasMetadata());
2663 EXPECT_EQ(SP2
, F
->getMetadata(LLVMContext::MD_dbg
));
2664 EXPECT_EQ(SP2
, F
->getMetadata("dbg"));
2665 EXPECT_EQ(nullptr, F
->getMetadata("other"));
2667 F
->setMetadata("dbg", nullptr);
2668 EXPECT_FALSE(F
->hasMetadata());
2669 EXPECT_EQ(nullptr, F
->getMetadata(LLVMContext::MD_dbg
));
2670 EXPECT_EQ(nullptr, F
->getMetadata("dbg"));
2671 EXPECT_EQ(nullptr, F
->getMetadata("other"));
2673 MDTuple
*T1
= getTuple();
2674 MDTuple
*T2
= getTuple();
2677 F
->setMetadata("other1", T1
);
2678 F
->setMetadata("other2", T2
);
2679 EXPECT_TRUE(F
->hasMetadata());
2680 EXPECT_EQ(T1
, F
->getMetadata("other1"));
2681 EXPECT_EQ(T2
, F
->getMetadata("other2"));
2682 EXPECT_EQ(nullptr, F
->getMetadata("dbg"));
2684 F
->setMetadata("other1", T2
);
2685 F
->setMetadata("other2", T1
);
2686 EXPECT_EQ(T2
, F
->getMetadata("other1"));
2687 EXPECT_EQ(T1
, F
->getMetadata("other2"));
2689 F
->setMetadata("other1", nullptr);
2690 F
->setMetadata("other2", nullptr);
2691 EXPECT_FALSE(F
->hasMetadata());
2692 EXPECT_EQ(nullptr, F
->getMetadata("other1"));
2693 EXPECT_EQ(nullptr, F
->getMetadata("other2"));
2696 TEST_F(FunctionAttachmentTest
, getAll
) {
2697 Function
*F
= getFunction("foo");
2699 MDTuple
*T1
= getTuple();
2700 MDTuple
*T2
= getTuple();
2701 MDTuple
*P
= getTuple();
2702 DISubprogram
*SP
= getSubprogram();
2704 F
->setMetadata("other1", T2
);
2705 F
->setMetadata(LLVMContext::MD_dbg
, SP
);
2706 F
->setMetadata("other2", T1
);
2707 F
->setMetadata(LLVMContext::MD_prof
, P
);
2708 F
->setMetadata("other2", T2
);
2709 F
->setMetadata("other1", T1
);
2711 SmallVector
<std::pair
<unsigned, MDNode
*>, 4> MDs
;
2712 F
->getAllMetadata(MDs
);
2713 ASSERT_EQ(4u, MDs
.size());
2714 EXPECT_EQ(LLVMContext::MD_dbg
, MDs
[0].first
);
2715 EXPECT_EQ(LLVMContext::MD_prof
, MDs
[1].first
);
2716 EXPECT_EQ(Context
.getMDKindID("other1"), MDs
[2].first
);
2717 EXPECT_EQ(Context
.getMDKindID("other2"), MDs
[3].first
);
2718 EXPECT_EQ(SP
, MDs
[0].second
);
2719 EXPECT_EQ(P
, MDs
[1].second
);
2720 EXPECT_EQ(T1
, MDs
[2].second
);
2721 EXPECT_EQ(T2
, MDs
[3].second
);
2724 TEST_F(FunctionAttachmentTest
, Verifier
) {
2725 Function
*F
= getFunction("foo");
2726 F
->setMetadata("attach", getTuple());
2727 F
->setIsMaterializable(true);
2729 // Confirm this is materializable.
2730 ASSERT_TRUE(F
->isMaterializable());
2732 // Materializable functions cannot have metadata attachments.
2733 EXPECT_TRUE(verifyFunction(*F
));
2735 // Function declarations can.
2736 F
->setIsMaterializable(false);
2737 EXPECT_FALSE(verifyModule(*F
->getParent()));
2738 EXPECT_FALSE(verifyFunction(*F
));
2740 // So can definitions.
2741 (void)new UnreachableInst(Context
, BasicBlock::Create(Context
, "bb", F
));
2742 EXPECT_FALSE(verifyModule(*F
->getParent()));
2743 EXPECT_FALSE(verifyFunction(*F
));
2746 TEST_F(FunctionAttachmentTest
, EntryCount
) {
2747 Function
*F
= getFunction("foo");
2748 EXPECT_FALSE(F
->getEntryCount().hasValue());
2749 F
->setEntryCount(12304, Function::PCT_Real
);
2750 auto Count
= F
->getEntryCount();
2751 EXPECT_TRUE(Count
.hasValue());
2752 EXPECT_EQ(12304u, Count
.getCount());
2753 EXPECT_EQ(Function::PCT_Real
, Count
.getType());
2755 // Repeat the same for synthetic counts.
2756 F
= getFunction("bar");
2757 EXPECT_FALSE(F
->getEntryCount().hasValue());
2758 F
->setEntryCount(123, Function::PCT_Synthetic
);
2759 Count
= F
->getEntryCount(true /*allow synthetic*/);
2760 EXPECT_TRUE(Count
.hasValue());
2761 EXPECT_EQ(123u, Count
.getCount());
2762 EXPECT_EQ(Function::PCT_Synthetic
, Count
.getType());
2765 TEST_F(FunctionAttachmentTest
, SubprogramAttachment
) {
2766 Function
*F
= getFunction("foo");
2767 DISubprogram
*SP
= getSubprogram();
2768 F
->setSubprogram(SP
);
2770 // Note that the static_cast confirms that F->getSubprogram() actually
2771 // returns an DISubprogram.
2772 EXPECT_EQ(SP
, static_cast<DISubprogram
*>(F
->getSubprogram()));
2773 EXPECT_EQ(SP
, F
->getMetadata("dbg"));
2774 EXPECT_EQ(SP
, F
->getMetadata(LLVMContext::MD_dbg
));
2777 typedef MetadataTest DistinctMDOperandPlaceholderTest
;
2778 TEST_F(DistinctMDOperandPlaceholderTest
, getID
) {
2779 EXPECT_EQ(7u, DistinctMDOperandPlaceholder(7).getID());
2782 TEST_F(DistinctMDOperandPlaceholderTest
, replaceUseWith
) {
2783 // Set up some placeholders.
2784 DistinctMDOperandPlaceholder
PH0(7);
2785 DistinctMDOperandPlaceholder
PH1(3);
2786 DistinctMDOperandPlaceholder
PH2(0);
2787 Metadata
*Ops
[] = {&PH0
, &PH1
, &PH2
};
2788 auto *D
= MDTuple::getDistinct(Context
, Ops
);
2789 ASSERT_EQ(&PH0
, D
->getOperand(0));
2790 ASSERT_EQ(&PH1
, D
->getOperand(1));
2791 ASSERT_EQ(&PH2
, D
->getOperand(2));
2794 auto *N0
= MDTuple::get(Context
, None
);
2795 auto *N1
= MDTuple::get(Context
, N0
);
2796 PH0
.replaceUseWith(N0
);
2797 PH1
.replaceUseWith(N1
);
2798 PH2
.replaceUseWith(nullptr);
2799 EXPECT_EQ(N0
, D
->getOperand(0));
2800 EXPECT_EQ(N1
, D
->getOperand(1));
2801 EXPECT_EQ(nullptr, D
->getOperand(2));
2804 TEST_F(DistinctMDOperandPlaceholderTest
, replaceUseWithNoUser
) {
2805 // There is no user, but we can still call replace.
2806 DistinctMDOperandPlaceholder(7).replaceUseWith(MDTuple::get(Context
, None
));
2809 // Test various assertions in metadata tracking. Don't run these tests if gtest
2810 // will use SEH to recover from them. Two of these tests get halfway through
2811 // inserting metadata into DenseMaps for tracking purposes, and then they
2812 // assert, and we attempt to destroy an LLVMContext with broken invariants,
2813 // leading to infinite loops.
2814 #if defined(GTEST_HAS_DEATH_TEST) && !defined(NDEBUG) && !defined(GTEST_HAS_SEH)
2815 TEST_F(DistinctMDOperandPlaceholderTest
, MetadataAsValue
) {
2816 // This shouldn't crash.
2817 DistinctMDOperandPlaceholder
PH(7);
2818 EXPECT_DEATH(MetadataAsValue::get(Context
, &PH
),
2819 "Unexpected callback to owner");
2822 TEST_F(DistinctMDOperandPlaceholderTest
, UniquedMDNode
) {
2823 // This shouldn't crash.
2824 DistinctMDOperandPlaceholder
PH(7);
2825 EXPECT_DEATH(MDTuple::get(Context
, &PH
), "Unexpected callback to owner");
2828 TEST_F(DistinctMDOperandPlaceholderTest
, SecondDistinctMDNode
) {
2829 // This shouldn't crash.
2830 DistinctMDOperandPlaceholder
PH(7);
2831 MDTuple::getDistinct(Context
, &PH
);
2832 EXPECT_DEATH(MDTuple::getDistinct(Context
, &PH
),
2833 "Placeholders can only be used once");
2836 TEST_F(DistinctMDOperandPlaceholderTest
, TrackingMDRefAndDistinctMDNode
) {
2837 // TrackingMDRef doesn't install an owner callback, so it can't be detected
2838 // as an invalid use. However, using a placeholder in a TrackingMDRef *and*
2839 // a distinct node isn't possible and we should assert.
2841 // (There's no positive test for using TrackingMDRef because it's not a
2842 // useful thing to do.)
2844 DistinctMDOperandPlaceholder
PH(7);
2845 MDTuple::getDistinct(Context
, &PH
);
2846 EXPECT_DEATH(TrackingMDRef
Ref(&PH
), "Placeholders can only be used once");
2849 DistinctMDOperandPlaceholder
PH(7);
2850 TrackingMDRef
Ref(&PH
);
2851 EXPECT_DEATH(MDTuple::getDistinct(Context
, &PH
),
2852 "Placeholders can only be used once");