[docs] Add LICENSE.txt to the root of the mono-repo
[llvm-project.git] / clang / unittests / CodeGen / TBAAMetadataTest.cpp
blob2919a35c8cedfb7084441f2b3f5bec6f75ffe3f1
1 //=== unittests/CodeGen/TBAAMetadataTest.cpp - Checks metadata generation -===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
9 #include "IRMatchers.h"
10 #include "TestCompiler.h"
11 #include "clang/AST/ASTConsumer.h"
12 #include "clang/AST/ASTContext.h"
13 #include "clang/Basic/SourceManager.h"
14 #include "clang/Basic/TargetInfo.h"
15 #include "llvm/IR/Constants.h"
16 #include "llvm/Support/MemoryBuffer.h"
17 #include "gtest/gtest.h"
18 #include <memory>
20 using namespace llvm;
22 namespace {
24 struct TBAATestCompiler : public TestCompiler {
25 TBAATestCompiler(clang::LangOptions LO, clang::CodeGenOptions CGO)
26 : TestCompiler(LO, CGO) {}
27 static clang::CodeGenOptions getCommonCodeGenOpts() {
28 clang::CodeGenOptions CGOpts;
29 CGOpts.StructPathTBAA = 1;
30 CGOpts.OptimizationLevel = 1;
31 return CGOpts;
35 auto OmnipotentCharC = MMTuple(
36 MMString("omnipotent char"),
37 MMTuple(
38 MMString("Simple C/C++ TBAA")),
39 MConstInt(0, 64)
43 auto OmnipotentCharCXX = MMTuple(
44 MMString("omnipotent char"),
45 MMTuple(
46 MMString("Simple C++ TBAA")),
47 MConstInt(0, 64)
51 TEST(TBAAMetadataTest, BasicTypes) {
52 const char TestProgram[] = R"**(
53 void func(char *CP, short *SP, int *IP, long long *LP, void **VPP,
54 int **IPP) {
55 *CP = 4;
56 *SP = 11;
57 *IP = 601;
58 *LP = 604;
59 *VPP = CP;
60 *IPP = IP;
62 )**";
64 clang::LangOptions LO;
65 TBAATestCompiler Compiler(LO, TBAATestCompiler::getCommonCodeGenOpts());
66 Compiler.init(TestProgram);
67 const BasicBlock *BB = Compiler.compile();
69 const Instruction *I = match(BB,
70 MInstruction(Instruction::Store,
71 MConstInt(4, 8),
72 MMTuple(
73 OmnipotentCharC,
74 MSameAs(0),
75 MConstInt(0))));
76 ASSERT_TRUE(I);
78 I = matchNext(I,
79 MInstruction(Instruction::Store,
80 MConstInt(11, 16),
81 MMTuple(
82 MMTuple(
83 MMString("short"),
84 OmnipotentCharC,
85 MConstInt(0)),
86 MSameAs(0),
87 MConstInt(0))));
88 ASSERT_TRUE(I);
90 I = matchNext(I,
91 MInstruction(Instruction::Store,
92 MConstInt(601, 32),
93 MMTuple(
94 MMTuple(
95 MMString("int"),
96 OmnipotentCharC,
97 MConstInt(0)),
98 MSameAs(0),
99 MConstInt(0))));
100 ASSERT_TRUE(I);
102 I = matchNext(I,
103 MInstruction(Instruction::Store,
104 MConstInt(604, 64),
105 MMTuple(
106 MMTuple(
107 MMString("long long"),
108 OmnipotentCharC,
109 MConstInt(0)),
110 MSameAs(0),
111 MConstInt(0))));
112 ASSERT_TRUE(I);
114 I = matchNext(I,
115 MInstruction(Instruction::Store,
116 MValType(Type::getInt8PtrTy(Compiler.Context)),
117 MMTuple(
118 MMTuple(
119 MMString("any pointer"),
120 OmnipotentCharC,
121 MConstInt(0)),
122 MSameAs(0),
123 MConstInt(0))));
124 ASSERT_TRUE(I);
126 I = matchNext(I,
127 MInstruction(Instruction::Store,
128 MValType(Type::getInt32PtrTy(Compiler.Context)),
129 MMTuple(
130 MMTuple(
131 MMString("any pointer"),
132 OmnipotentCharC,
133 MConstInt(0)),
134 MSameAs(0),
135 MConstInt(0))));
136 ASSERT_TRUE(I);
139 TEST(TBAAMetadataTest, CFields) {
140 const char TestProgram[] = R"**(
141 struct ABC {
142 short f16;
143 int f32;
144 long long f64;
145 unsigned short f16_2;
146 unsigned f32_2;
147 unsigned long long f64_2;
150 void func(struct ABC *A) {
151 A->f32 = 4;
152 A->f16 = 11;
153 A->f64 = 601;
154 A->f16_2 = 22;
155 A->f32_2 = 77;
156 A->f64_2 = 604;
158 )**";
160 clang::LangOptions LO;
161 LO.C11 = 1;
162 TBAATestCompiler Compiler(LO, TBAATestCompiler::getCommonCodeGenOpts());
163 Compiler.init(TestProgram);
164 const BasicBlock *BB = Compiler.compile();
166 auto StructABC = MMTuple(
167 MMString("ABC"),
168 MMTuple(
169 MMString("short"),
170 OmnipotentCharC,
171 MConstInt(0)),
172 MConstInt(0),
173 MMTuple(
174 MMString("int"),
175 OmnipotentCharC,
176 MConstInt(0)),
177 MConstInt(4),
178 MMTuple(
179 MMString("long long"),
180 OmnipotentCharC,
181 MConstInt(0)),
182 MConstInt(8),
183 MSameAs(1),
184 MConstInt(16),
185 MSameAs(3),
186 MConstInt(20),
187 MSameAs(5),
188 MConstInt(24));
190 const Instruction *I = match(BB,
191 MInstruction(Instruction::Store,
192 MConstInt(4, 32),
193 MMTuple(
194 StructABC,
195 MMTuple(
196 MMString("int"),
197 OmnipotentCharC,
198 MConstInt(0)),
199 MConstInt(4))));
200 ASSERT_TRUE(I);
202 I = matchNext(I,
203 MInstruction(Instruction::Store,
204 MConstInt(11, 16),
205 MMTuple(
206 StructABC,
207 MMTuple(
208 MMString("short"),
209 OmnipotentCharC,
210 MConstInt(0)),
211 MConstInt(0))));
212 ASSERT_TRUE(I);
214 I = matchNext(I,
215 MInstruction(Instruction::Store,
216 MConstInt(601, 64),
217 MMTuple(
218 StructABC,
219 MMTuple(
220 MMString("long long"),
221 OmnipotentCharC,
222 MConstInt(0)),
223 MConstInt(8))));
224 ASSERT_TRUE(I);
226 I = matchNext(I,
227 MInstruction(Instruction::Store,
228 MConstInt(22, 16),
229 MMTuple(
230 StructABC,
231 MMTuple(
232 MMString("short"),
233 OmnipotentCharC,
234 MConstInt(0)),
235 MConstInt(16))));
236 ASSERT_TRUE(I);
238 I = matchNext(I,
239 MInstruction(Instruction::Store,
240 MConstInt(77, 32),
241 MMTuple(
242 StructABC,
243 MMTuple(
244 MMString("int"),
245 OmnipotentCharC,
246 MConstInt(0)),
247 MConstInt(20))));
248 ASSERT_TRUE(I);
250 I = matchNext(I,
251 MInstruction(Instruction::Store,
252 MConstInt(604, 64),
253 MMTuple(
254 StructABC,
255 MMTuple(
256 MMString("long long"),
257 OmnipotentCharC,
258 MConstInt(0)),
259 MConstInt(24))));
260 ASSERT_TRUE(I);
263 TEST(TBAAMetadataTest, CTypedefFields) {
264 const char TestProgram[] = R"**(
265 typedef struct {
266 short f16;
267 int f32;
268 } ABC;
269 typedef struct {
270 short value_f16;
271 int value_f32;
272 } CDE;
274 void func(ABC *A, CDE *B) {
275 A->f32 = 4;
276 A->f16 = 11;
277 B->value_f32 = 44;
278 B->value_f16 = 111;
280 )**";
282 clang::LangOptions LO;
283 LO.C11 = 1;
284 TBAATestCompiler Compiler(LO, TBAATestCompiler::getCommonCodeGenOpts());
285 Compiler.init(TestProgram);
286 const BasicBlock *BB = Compiler.compile();
288 auto NamelessStruct = MMTuple(
289 MMString(""),
290 MMTuple(
291 MMString("short"),
292 OmnipotentCharC,
293 MConstInt(0)),
294 MConstInt(0),
295 MMTuple(
296 MMString("int"),
297 OmnipotentCharC,
298 MConstInt(0)),
299 MConstInt(4));
301 const Metadata *MetaABC = nullptr;
302 const Instruction *I = match(BB,
303 MInstruction(Instruction::Store,
304 MConstInt(4, 32),
305 MMTuple(
306 MMSave(MetaABC, NamelessStruct),
307 MMTuple(
308 MMString("int"),
309 OmnipotentCharC,
310 MConstInt(0)),
311 MConstInt(4))));
312 ASSERT_TRUE(I);
314 I = matchNext(I,
315 MInstruction(Instruction::Store,
316 MConstInt(11, 16),
317 MMTuple(
318 NamelessStruct,
319 MMTuple(
320 MMString("short"),
321 OmnipotentCharC,
322 MConstInt(0)),
323 MConstInt(0))));
324 ASSERT_TRUE(I);
326 const Metadata *MetaCDE = nullptr;
327 I = matchNext(I,
328 MInstruction(Instruction::Store,
329 MConstInt(44, 32),
330 MMTuple(
331 MMSave(MetaCDE, NamelessStruct),
332 MMTuple(
333 MMString("int"),
334 OmnipotentCharC,
335 MConstInt(0)),
336 MConstInt(4))));
337 ASSERT_TRUE(I);
339 I = matchNext(I,
340 MInstruction(Instruction::Store,
341 MConstInt(111, 16),
342 MMTuple(
343 NamelessStruct,
344 MMTuple(
345 MMString("short"),
346 OmnipotentCharC,
347 MConstInt(0)),
348 MConstInt(0))));
349 ASSERT_TRUE(I);
351 // FIXME: Nameless structures used in definitions of 'ABC' and 'CDE' are
352 // different structures and must be described by different descriptors.
353 //ASSERT_TRUE(MetaABC != MetaCDE);
356 TEST(TBAAMetadataTest, CTypedefFields2) {
357 const char TestProgram[] = R"**(
358 typedef struct {
359 short f16;
360 int f32;
361 } ABC;
362 typedef struct {
363 short f16;
364 int f32;
365 } CDE;
367 void func(ABC *A, CDE *B) {
368 A->f32 = 4;
369 A->f16 = 11;
370 B->f32 = 44;
371 B->f16 = 111;
373 )**";
375 clang::LangOptions LO;
376 LO.C11 = 1;
377 TBAATestCompiler Compiler(LO, TBAATestCompiler::getCommonCodeGenOpts());
378 Compiler.init(TestProgram);
379 const BasicBlock *BB = Compiler.compile();
381 auto NamelessStruct = MMTuple(
382 MMString(""),
383 MMTuple(
384 MMString("short"),
385 OmnipotentCharC,
386 MConstInt(0)),
387 MConstInt(0),
388 MMTuple(
389 MMString("int"),
390 OmnipotentCharC,
391 MConstInt(0)),
392 MConstInt(4));
394 const Metadata *MetaABC = nullptr;
395 const Instruction *I = match(BB,
396 MInstruction(Instruction::Store,
397 MConstInt(4, 32),
398 MMTuple(
399 MMSave(MetaABC, NamelessStruct),
400 MMTuple(
401 MMString("int"),
402 OmnipotentCharC,
403 MConstInt(0)),
404 MConstInt(4))));
405 ASSERT_TRUE(I);
407 I = matchNext(I,
408 MInstruction(Instruction::Store,
409 MConstInt(11, 16),
410 MMTuple(
411 NamelessStruct,
412 MMTuple(
413 MMString("short"),
414 OmnipotentCharC,
415 MConstInt(0)),
416 MConstInt(0))));
417 ASSERT_TRUE(I);
419 const Metadata *MetaCDE = nullptr;
420 I = matchNext(I,
421 MInstruction(Instruction::Store,
422 MConstInt(44, 32),
423 MMTuple(
424 MMSave(MetaCDE, NamelessStruct),
425 MMTuple(
426 MMString("int"),
427 OmnipotentCharC,
428 MConstInt(0)),
429 MConstInt(4))));
430 ASSERT_TRUE(I);
432 I = matchNext(I,
433 MInstruction(Instruction::Store,
434 MConstInt(111, 16),
435 MMTuple(
436 NamelessStruct,
437 MMTuple(
438 MMString("short"),
439 OmnipotentCharC,
440 MConstInt(0)),
441 MConstInt(0))));
442 ASSERT_TRUE(I);
444 // FIXME: Nameless structures used in definitions of 'ABC' and 'CDE' are
445 // different structures, although they have the same field sequence. They must
446 // be described by different descriptors.
447 //ASSERT_TRUE(MetaABC != MetaCDE);
450 TEST(TBAAMetadataTest, CTypedefFields3) {
451 const char TestProgram[] = R"**(
452 typedef struct {
453 short f16;
454 int f32;
455 } ABC;
456 typedef struct {
457 int f32;
458 short f16;
459 } CDE;
461 void func(ABC *A, CDE *B) {
462 A->f32 = 4;
463 A->f16 = 11;
464 B->f32 = 44;
465 B->f16 = 111;
467 )**";
469 clang::LangOptions LO;
470 LO.C11 = 1;
471 TBAATestCompiler Compiler(LO, TBAATestCompiler::getCommonCodeGenOpts());
472 Compiler.init(TestProgram);
473 const BasicBlock *BB = Compiler.compile();
475 auto NamelessStruct1 = MMTuple(
476 MMString(""),
477 MMTuple(
478 MMString("short"),
479 OmnipotentCharC,
480 MConstInt(0)),
481 MConstInt(0),
482 MMTuple(
483 MMString("int"),
484 OmnipotentCharC,
485 MConstInt(0)),
486 MConstInt(4));
488 auto NamelessStruct2 = MMTuple(
489 MMString(""),
490 MMTuple(
491 MMString("int"),
492 OmnipotentCharC,
493 MConstInt(0)),
494 MConstInt(0),
495 MMTuple(
496 MMString("short"),
497 OmnipotentCharC,
498 MConstInt(0)),
499 MConstInt(4));
501 const Instruction *I = match(BB,
502 MInstruction(Instruction::Store,
503 MConstInt(4, 32),
504 MMTuple(
505 NamelessStruct1,
506 MMTuple(
507 MMString("int"),
508 OmnipotentCharC,
509 MConstInt(0)),
510 MConstInt(4))));
511 ASSERT_TRUE(I);
513 I = matchNext(I,
514 MInstruction(Instruction::Store,
515 MConstInt(11, 16),
516 MMTuple(
517 NamelessStruct1,
518 MMTuple(
519 MMString("short"),
520 OmnipotentCharC,
521 MConstInt(0)),
522 MConstInt(0))));
523 ASSERT_TRUE(I);
525 I = matchNext(I,
526 MInstruction(Instruction::Store,
527 MConstInt(44, 32),
528 MMTuple(
529 NamelessStruct2,
530 MMTuple(
531 MMString("int"),
532 OmnipotentCharC,
533 MConstInt(0)),
534 MConstInt(0))));
535 ASSERT_TRUE(I);
537 I = matchNext(I,
538 MInstruction(Instruction::Store,
539 MConstInt(111, 16),
540 MMTuple(
541 NamelessStruct2,
542 MMTuple(
543 MMString("short"),
544 OmnipotentCharC,
545 MConstInt(0)),
546 MConstInt(4))));
547 ASSERT_TRUE(I);
550 TEST(TBAAMetadataTest, CXXFields) {
551 const char TestProgram[] = R"**(
552 struct ABC {
553 short f16;
554 int f32;
555 long long f64;
556 unsigned short f16_2;
557 unsigned f32_2;
558 unsigned long long f64_2;
561 void func(struct ABC *A) {
562 A->f32 = 4;
563 A->f16 = 11;
564 A->f64 = 601;
565 A->f16_2 = 22;
566 A->f32_2 = 77;
567 A->f64_2 = 604;
569 )**";
571 clang::LangOptions LO;
572 LO.CPlusPlus = 1;
573 LO.CPlusPlus11 = 1;
574 TBAATestCompiler Compiler(LO, TBAATestCompiler::getCommonCodeGenOpts());
575 Compiler.init(TestProgram);
576 const BasicBlock *BB = Compiler.compile();
578 auto StructABC = MMTuple(
579 MMString("_ZTS3ABC"),
580 MMTuple(
581 MMString("short"),
582 OmnipotentCharCXX,
583 MConstInt(0)),
584 MConstInt(0),
585 MMTuple(
586 MMString("int"),
587 OmnipotentCharCXX,
588 MConstInt(0)),
589 MConstInt(4),
590 MMTuple(
591 MMString("long long"),
592 OmnipotentCharCXX,
593 MConstInt(0)),
594 MConstInt(8),
595 MSameAs(1),
596 MConstInt(16),
597 MSameAs(3),
598 MConstInt(20),
599 MSameAs(5),
600 MConstInt(24));
602 const Instruction *I = match(BB,
603 MInstruction(Instruction::Store,
604 MConstInt(4, 32),
605 MMTuple(
606 StructABC,
607 MMTuple(
608 MMString("int"),
609 OmnipotentCharCXX,
610 MConstInt(0)),
611 MConstInt(4))));
612 ASSERT_TRUE(I);
614 I = matchNext(I,
615 MInstruction(Instruction::Store,
616 MConstInt(11, 16),
617 MMTuple(
618 StructABC,
619 MMTuple(
620 MMString("short"),
621 OmnipotentCharCXX,
622 MConstInt(0)),
623 MConstInt(0))));
624 ASSERT_TRUE(I);
626 I = matchNext(I,
627 MInstruction(Instruction::Store,
628 MConstInt(601, 64),
629 MMTuple(
630 StructABC,
631 MMTuple(
632 MMString("long long"),
633 OmnipotentCharCXX,
634 MConstInt(0)),
635 MConstInt(8))));
636 ASSERT_TRUE(I);
638 I = matchNext(I,
639 MInstruction(Instruction::Store,
640 MConstInt(22, 16),
641 MMTuple(
642 StructABC,
643 MMTuple(
644 MMString("short"),
645 OmnipotentCharCXX,
646 MConstInt(0)),
647 MConstInt(16))));
648 ASSERT_TRUE(I);
650 I = matchNext(I,
651 MInstruction(Instruction::Store,
652 MConstInt(77, 32),
653 MMTuple(
654 StructABC,
655 MMTuple(
656 MMString("int"),
657 OmnipotentCharCXX,
658 MConstInt(0)),
659 MConstInt(20))));
660 ASSERT_TRUE(I);
662 I = matchNext(I,
663 MInstruction(Instruction::Store,
664 MConstInt(604, 64),
665 MMTuple(
666 StructABC,
667 MMTuple(
668 MMString("long long"),
669 OmnipotentCharCXX,
670 MConstInt(0)),
671 MConstInt(24))));
672 ASSERT_TRUE(I);
675 TEST(TBAAMetadataTest, CXXTypedefFields) {
676 const char TestProgram[] = R"**(
677 typedef struct {
678 short f16;
679 int f32;
680 } ABC;
681 typedef struct {
682 short value_f16;
683 int value_f32;
684 } CDE;
686 void func(ABC *A, CDE *B) {
687 A->f32 = 4;
688 A->f16 = 11;
689 B->value_f32 = 44;
690 B->value_f16 = 111;
692 )**";
694 clang::LangOptions LO;
695 LO.CPlusPlus = 1;
696 LO.CPlusPlus11 = 1;
697 TBAATestCompiler Compiler(LO, TBAATestCompiler::getCommonCodeGenOpts());
698 Compiler.init(TestProgram);
699 const BasicBlock *BB = Compiler.compile();
701 auto StructABC = MMTuple(
702 MMString("_ZTS3ABC"),
703 MMTuple(
704 MMString("short"),
705 OmnipotentCharCXX,
706 MConstInt(0)),
707 MConstInt(0),
708 MMTuple(
709 MMString("int"),
710 OmnipotentCharCXX,
711 MConstInt(0)),
712 MConstInt(4));
714 auto StructCDE = MMTuple(
715 MMString("_ZTS3CDE"),
716 MMTuple(
717 MMString("short"),
718 OmnipotentCharCXX,
719 MConstInt(0)),
720 MConstInt(0),
721 MMTuple(
722 MMString("int"),
723 OmnipotentCharCXX,
724 MConstInt(0)),
725 MConstInt(4));
727 const Instruction *I = match(BB,
728 MInstruction(Instruction::Store,
729 MConstInt(4, 32),
730 MMTuple(
731 StructABC,
732 MMTuple(
733 MMString("int"),
734 OmnipotentCharCXX,
735 MConstInt(0)),
736 MConstInt(4))));
737 ASSERT_TRUE(I);
739 I = matchNext(I,
740 MInstruction(Instruction::Store,
741 MConstInt(11, 16),
742 MMTuple(
743 StructABC,
744 MMTuple(
745 MMString("short"),
746 OmnipotentCharCXX,
747 MConstInt(0)),
748 MConstInt(0))));
749 ASSERT_TRUE(I);
751 I = matchNext(I,
752 MInstruction(Instruction::Store,
753 MConstInt(44, 32),
754 MMTuple(
755 StructCDE,
756 MMTuple(
757 MMString("int"),
758 OmnipotentCharCXX,
759 MConstInt(0)),
760 MConstInt(4))));
761 ASSERT_TRUE(I);
763 I = matchNext(I,
764 MInstruction(Instruction::Store,
765 MConstInt(111, 16),
766 MMTuple(
767 StructCDE,
768 MMTuple(
769 MMString("short"),
770 OmnipotentCharCXX,
771 MConstInt(0)),
772 MConstInt(0))));
773 ASSERT_TRUE(I);
776 TEST(TBAAMetadataTest, StructureFields) {
777 const char TestProgram[] = R"**(
778 struct Inner {
779 int f32;
782 struct Outer {
783 short f16;
784 Inner b1;
785 Inner b2;
788 void func(Outer *S) {
789 S->f16 = 14;
790 S->b1.f32 = 35;
791 S->b2.f32 = 77;
793 )**";
795 clang::LangOptions LO;
796 LO.CPlusPlus = 1;
797 LO.CPlusPlus11 = 1;
798 TBAATestCompiler Compiler(LO, TBAATestCompiler::getCommonCodeGenOpts());
799 Compiler.init(TestProgram);
800 const BasicBlock *BB = Compiler.compile();
802 auto StructInner = MMTuple(
803 MMString("_ZTS5Inner"),
804 MMTuple(
805 MMString("int"),
806 OmnipotentCharCXX,
807 MConstInt(0)),
808 MConstInt(0));
810 auto StructOuter = MMTuple(
811 MMString("_ZTS5Outer"),
812 MMTuple(
813 MMString("short"),
814 OmnipotentCharCXX,
815 MConstInt(0)),
816 MConstInt(0),
817 StructInner,
818 MConstInt(4),
819 MSameAs(3),
820 MConstInt(8));
822 const Instruction *I = match(BB,
823 MInstruction(Instruction::Store,
824 MConstInt(14, 16),
825 MMTuple(
826 StructOuter,
827 MMTuple(
828 MMString("short"),
829 OmnipotentCharCXX,
830 MConstInt(0)),
831 MConstInt(0))));
832 ASSERT_TRUE(I);
834 I = matchNext(I,
835 MInstruction(Instruction::Store,
836 MConstInt(35, 32),
837 MMTuple(
838 StructOuter,
839 MMTuple(
840 MMString("int"),
841 OmnipotentCharCXX,
842 MConstInt(0)),
843 MConstInt(4))));
844 ASSERT_TRUE(I);
846 I = matchNext(I,
847 MInstruction(Instruction::Store,
848 MConstInt(77, 32),
849 MMTuple(
850 StructOuter,
851 MMTuple(
852 MMString("int"),
853 OmnipotentCharCXX,
854 MConstInt(0)),
855 MConstInt(8))));
856 ASSERT_TRUE(I);
859 TEST(TBAAMetadataTest, ArrayFields) {
860 const char TestProgram[] = R"**(
861 struct Inner {
862 int f32;
865 struct Outer {
866 short f16;
867 Inner b1[2];
870 void func(Outer *S) {
871 S->f16 = 14;
872 S->b1[0].f32 = 35;
873 S->b1[1].f32 = 77;
875 )**";
877 clang::LangOptions LO;
878 LO.CPlusPlus = 1;
879 LO.CPlusPlus11 = 1;
880 TBAATestCompiler Compiler(LO, TBAATestCompiler::getCommonCodeGenOpts());
881 Compiler.init(TestProgram);
882 const BasicBlock *BB = Compiler.compile();
884 auto StructInner = MMTuple(
885 MMString("_ZTS5Inner"),
886 MMTuple(
887 MMString("int"),
888 OmnipotentCharCXX,
889 MConstInt(0)),
890 MConstInt(0));
892 auto StructOuter = MMTuple(
893 MMString("_ZTS5Outer"),
894 MMTuple(
895 MMString("short"),
896 OmnipotentCharCXX,
897 MConstInt(0)),
898 MConstInt(0),
899 OmnipotentCharCXX, // FIXME: Info about array field is lost.
900 MConstInt(4));
902 const Instruction *I = match(BB,
903 MInstruction(Instruction::Store,
904 MConstInt(14, 16),
905 MMTuple(
906 StructOuter,
907 MMTuple(
908 MMString("short"),
909 OmnipotentCharCXX,
910 MConstInt(0)),
911 MConstInt(0))));
912 ASSERT_TRUE(I);
914 I = matchNext(I,
915 MInstruction(Instruction::Store,
916 MConstInt(35, 32),
917 MMTuple(
918 StructInner,
919 MMTuple(
920 MMString("int"),
921 OmnipotentCharCXX,
922 MConstInt(0)),
923 MConstInt(0))));
924 ASSERT_TRUE(I);
926 I = matchNext(I,
927 MInstruction(Instruction::Store,
928 MConstInt(77, 32),
929 MMTuple(
930 StructInner,
931 MMTuple(
932 MMString("int"),
933 OmnipotentCharCXX,
934 MConstInt(0)),
935 MConstInt(0))));
936 ASSERT_TRUE(I);
939 TEST(TBAAMetadataTest, BaseClass) {
940 const char TestProgram[] = R"**(
941 struct Base {
942 int f32;
945 struct Derived : public Base {
946 short f16;
949 void func(Base *B, Derived *D) {
950 B->f32 = 14;
951 D->f16 = 35;
952 D->f32 = 77;
954 )**";
956 clang::LangOptions LO;
957 LO.CPlusPlus = 1;
958 LO.CPlusPlus11 = 1;
959 TBAATestCompiler Compiler(LO, TBAATestCompiler::getCommonCodeGenOpts());
960 Compiler.init(TestProgram);
961 const BasicBlock *BB = Compiler.compile();
963 auto ClassBase = MMTuple(
964 MMString("_ZTS4Base"),
965 MMTuple(
966 MMString("int"),
967 OmnipotentCharCXX,
968 MConstInt(0)),
969 MConstInt(0));
971 auto ClassDerived =
972 MMTuple(MMString("_ZTS7Derived"), ClassBase, MConstInt(0),
973 MMTuple(MMString("short"), OmnipotentCharCXX, MConstInt(0)),
974 MConstInt(4));
976 const Instruction *I = match(BB,
977 MInstruction(Instruction::Store,
978 MConstInt(14, 32),
979 MMTuple(
980 ClassBase,
981 MMTuple(
982 MMString("int"),
983 OmnipotentCharCXX,
984 MConstInt(0)),
985 MConstInt(0))));
986 ASSERT_TRUE(I);
988 I = matchNext(I,
989 MInstruction(Instruction::Store,
990 MConstInt(35, 16),
991 MMTuple(
992 ClassDerived,
993 MMTuple(
994 MMString("short"),
995 OmnipotentCharCXX,
996 MConstInt(0)),
997 MConstInt(4))));
998 ASSERT_TRUE(I);
1000 I = matchNext(I,
1001 MInstruction(Instruction::Store,
1002 MConstInt(77, 32),
1003 MMTuple(
1004 ClassBase,
1005 MMTuple(
1006 MMString("int"),
1007 OmnipotentCharCXX,
1008 MConstInt(0)),
1009 MConstInt(0))));
1010 ASSERT_TRUE(I);
1013 TEST(TBAAMetadataTest, PolymorphicClass) {
1014 const char TestProgram[] = R"**(
1015 struct Base {
1016 virtual void m1(int *) = 0;
1017 int f32;
1020 struct Derived : public Base {
1021 virtual void m1(int *) override;
1022 short f16;
1025 void func(Base *B, Derived *D) {
1026 B->f32 = 14;
1027 D->f16 = 35;
1028 D->f32 = 77;
1030 )**";
1032 clang::LangOptions LO;
1033 LO.CPlusPlus = 1;
1034 LO.CPlusPlus11 = 1;
1035 TBAATestCompiler Compiler(LO, TBAATestCompiler::getCommonCodeGenOpts());
1036 Compiler.init(TestProgram);
1037 const BasicBlock *BB = Compiler.compile();
1039 auto ClassBase = MMTuple(
1040 MMString("_ZTS4Base"),
1041 MMTuple(
1042 MMString("int"),
1043 OmnipotentCharCXX,
1044 MConstInt(0)),
1045 MConstInt(Compiler.PtrSize));
1047 auto ClassDerived =
1048 MMTuple(MMString("_ZTS7Derived"), ClassBase, MConstInt(0),
1049 MMTuple(MMString("short"), OmnipotentCharCXX, MConstInt(0)),
1050 MConstInt(Compiler.PtrSize + 4));
1052 const Instruction *I = match(BB,
1053 MInstruction(Instruction::Store,
1054 MConstInt(14, 32),
1055 MMTuple(
1056 ClassBase,
1057 MMTuple(
1058 MMString("int"),
1059 OmnipotentCharCXX,
1060 MConstInt(0)),
1061 MConstInt(Compiler.PtrSize))));
1062 ASSERT_TRUE(I);
1064 I = matchNext(I,
1065 MInstruction(Instruction::Store,
1066 MConstInt(35, 16),
1067 MMTuple(
1068 ClassDerived,
1069 MMTuple(
1070 MMString("short"),
1071 OmnipotentCharCXX,
1072 MConstInt(0)),
1073 MConstInt(Compiler.PtrSize + 4))));
1074 ASSERT_TRUE(I);
1076 I = matchNext(I,
1077 MInstruction(Instruction::Store,
1078 MConstInt(77, 32),
1079 MMTuple(
1080 ClassBase,
1081 MMTuple(
1082 MMString("int"),
1083 OmnipotentCharCXX,
1084 MConstInt(0)),
1085 MConstInt(Compiler.PtrSize))));
1086 ASSERT_TRUE(I);
1089 TEST(TBAAMetadataTest, VirtualBase) {
1090 const char TestProgram[] = R"**(
1091 struct Base {
1092 int f32;
1095 struct Derived : public virtual Base {
1096 short f16;
1099 void func(Base *B, Derived *D) {
1100 B->f32 = 14;
1101 D->f16 = 35;
1102 D->f32 = 77;
1104 )**";
1106 clang::LangOptions LO;
1107 LO.CPlusPlus = 1;
1108 LO.CPlusPlus11 = 1;
1109 TBAATestCompiler Compiler(LO, TBAATestCompiler::getCommonCodeGenOpts());
1110 Compiler.init(TestProgram);
1111 const BasicBlock *BB = Compiler.compile();
1113 auto ClassBase = MMTuple(
1114 MMString("_ZTS4Base"),
1115 MMTuple(
1116 MMString("int"),
1117 OmnipotentCharCXX,
1118 MConstInt(0)),
1119 MConstInt(0));
1121 auto ClassDerived = MMTuple(
1122 MMString("_ZTS7Derived"),
1123 MMTuple(
1124 MMString("short"),
1125 OmnipotentCharCXX,
1126 MConstInt(0)),
1127 MConstInt(Compiler.PtrSize));
1129 const Instruction *I = match(BB,
1130 MInstruction(Instruction::Store,
1131 MConstInt(14, 32),
1132 MMTuple(
1133 ClassBase,
1134 MMTuple(
1135 MMString("int"),
1136 OmnipotentCharCXX,
1137 MConstInt(0)),
1138 MConstInt(0))));
1139 ASSERT_TRUE(I);
1141 I = matchNext(I,
1142 MInstruction(Instruction::Store,
1143 MConstInt(35, 16),
1144 MMTuple(
1145 ClassDerived,
1146 MMTuple(
1147 MMString("short"),
1148 OmnipotentCharCXX,
1149 MConstInt(0)),
1150 MConstInt(Compiler.PtrSize))));
1151 ASSERT_TRUE(I);
1153 I = matchNext(I,
1154 MInstruction(Instruction::Load,
1155 MMTuple(
1156 MMTuple(
1157 MMString("vtable pointer"),
1158 MMTuple(
1159 MMString("Simple C++ TBAA")),
1160 MConstInt(0)),
1161 MSameAs(0),
1162 MConstInt(0))));
1163 ASSERT_TRUE(I);
1165 I = matchNext(I,
1166 MInstruction(Instruction::Store,
1167 MConstInt(77, 32),
1168 MMTuple(
1169 ClassBase,
1170 MMTuple(
1171 MMString("int"),
1172 OmnipotentCharCXX,
1173 MConstInt(0)),
1174 MConstInt(0))));
1175 ASSERT_TRUE(I);
1178 TEST(TBAAMetadataTest, TemplSpec) {
1179 const char TestProgram[] = R"**(
1180 template<typename T1, typename T2>
1181 struct ABC {
1182 T1 f1;
1183 T2 f2;
1186 void func(ABC<double, int> *p) {
1187 p->f1 = 12.1;
1188 p->f2 = 44;
1190 )**";
1192 clang::LangOptions LO;
1193 LO.CPlusPlus = 1;
1194 LO.CPlusPlus11 = 1;
1195 TBAATestCompiler Compiler(LO, TBAATestCompiler::getCommonCodeGenOpts());
1196 Compiler.init(TestProgram);
1197 const BasicBlock *BB = Compiler.compile();
1199 auto SpecABC = MMTuple(
1200 MMString("_ZTS3ABCIdiE"),
1201 MMTuple(
1202 MMString("double"),
1203 OmnipotentCharCXX,
1204 MConstInt(0)),
1205 MConstInt(0),
1206 MMTuple(
1207 MMString("int"),
1208 OmnipotentCharCXX,
1209 MConstInt(0)),
1210 MConstInt(8));
1212 const Instruction *I = match(BB,
1213 MInstruction(Instruction::Store,
1214 MValType(MType([](const Type &T)->bool { return T.isDoubleTy(); })),
1215 MMTuple(
1216 SpecABC,
1217 MMTuple(
1218 MMString("double"),
1219 OmnipotentCharCXX,
1220 MConstInt(0)),
1221 MConstInt(0))));
1222 ASSERT_TRUE(I);
1224 I = matchNext(I,
1225 MInstruction(Instruction::Store,
1226 MConstInt(44, 32),
1227 MMTuple(
1228 SpecABC,
1229 MMTuple(
1230 MMString("int"),
1231 OmnipotentCharCXX,
1232 MConstInt(0)),
1233 MConstInt(8))));
1234 ASSERT_TRUE(I);