1*b0914e72SArtem Dergachev // RUN: %clang_analyze_cc1 -std=c++14 \
2077f13c6SCsaba Dabis // RUN: -analyzer-checker=core.CallAndMessage \
3077f13c6SCsaba Dabis // RUN: -analyzer-config suppress-null-return-paths=false \
4077f13c6SCsaba Dabis // RUN: -verify %s
5*b0914e72SArtem Dergachev // RUN: %clang_analyze_cc1 -std=c++14 \
6077f13c6SCsaba Dabis // RUN: -analyzer-checker=core.CallAndMessage \
7077f13c6SCsaba Dabis // RUN: -DSUPPRESSED \
8077f13c6SCsaba Dabis // RUN: -verify %s
9077f13c6SCsaba Dabis
10077f13c6SCsaba Dabis #ifdef SUPPRESSED
11077f13c6SCsaba Dabis // expected-no-diagnostics
12077f13c6SCsaba Dabis #endif
13077f13c6SCsaba Dabis
144d4ef2a1SCsaba Dabis #include <stdint.h>
15077f13c6SCsaba Dabis #include "../Inputs/system-header-simulator-cxx.h"
16077f13c6SCsaba Dabis
17077f13c6SCsaba Dabis void error();
18077f13c6SCsaba Dabis void *malloc(size_t);
19077f13c6SCsaba Dabis
20077f13c6SCsaba Dabis
21077f13c6SCsaba Dabis // From llvm/include/llvm/Support/MathExtras.h
alignAddr(const void * Addr,size_t Alignment)22077f13c6SCsaba Dabis inline uintptr_t alignAddr(const void *Addr, size_t Alignment) {
23077f13c6SCsaba Dabis return (((uintptr_t)Addr + Alignment - 1) & ~(uintptr_t)(Alignment - 1));
24077f13c6SCsaba Dabis }
25077f13c6SCsaba Dabis
alignmentAdjustment(const void * Ptr,size_t Alignment)26077f13c6SCsaba Dabis inline size_t alignmentAdjustment(const void *Ptr, size_t Alignment) {
27077f13c6SCsaba Dabis return alignAddr(Ptr, Alignment) - (uintptr_t)Ptr;
28077f13c6SCsaba Dabis }
29077f13c6SCsaba Dabis
30077f13c6SCsaba Dabis
31077f13c6SCsaba Dabis // From llvm/include/llvm/Support/MemAlloc.h
safe_malloc(size_t Sz)32077f13c6SCsaba Dabis inline void *safe_malloc(size_t Sz) {
33077f13c6SCsaba Dabis void *Result = malloc(Sz);
34077f13c6SCsaba Dabis if (Result == nullptr)
35077f13c6SCsaba Dabis error();
36077f13c6SCsaba Dabis
37077f13c6SCsaba Dabis return Result;
38077f13c6SCsaba Dabis }
39077f13c6SCsaba Dabis
40077f13c6SCsaba Dabis
41077f13c6SCsaba Dabis // From llvm/include/llvm/Support/Allocator.h
42077f13c6SCsaba Dabis class MallocAllocator {
43077f13c6SCsaba Dabis public:
Allocate(size_t Size,size_t)44077f13c6SCsaba Dabis void *Allocate(size_t Size, size_t /*Alignment*/) {
45077f13c6SCsaba Dabis return safe_malloc(Size);
46077f13c6SCsaba Dabis }
47077f13c6SCsaba Dabis };
48077f13c6SCsaba Dabis
49077f13c6SCsaba Dabis class BumpPtrAllocator {
50077f13c6SCsaba Dabis public:
Allocate(size_t Size,size_t Alignment)51077f13c6SCsaba Dabis void *Allocate(size_t Size, size_t Alignment) {
52077f13c6SCsaba Dabis BytesAllocated += Size;
53077f13c6SCsaba Dabis size_t Adjustment = alignmentAdjustment(CurPtr, Alignment);
54077f13c6SCsaba Dabis size_t SizeToAllocate = Size;
55077f13c6SCsaba Dabis
56077f13c6SCsaba Dabis size_t PaddedSize = SizeToAllocate + Alignment - 1;
57077f13c6SCsaba Dabis uintptr_t AlignedAddr = alignAddr(Allocator.Allocate(PaddedSize, 0),
58077f13c6SCsaba Dabis Alignment);
59077f13c6SCsaba Dabis char *AlignedPtr = (char*)AlignedAddr;
60077f13c6SCsaba Dabis
61077f13c6SCsaba Dabis return AlignedPtr;
62077f13c6SCsaba Dabis }
63077f13c6SCsaba Dabis
64077f13c6SCsaba Dabis private:
65077f13c6SCsaba Dabis char *CurPtr = nullptr;
66077f13c6SCsaba Dabis size_t BytesAllocated = 0;
67077f13c6SCsaba Dabis MallocAllocator Allocator;
68077f13c6SCsaba Dabis };
69077f13c6SCsaba Dabis
70077f13c6SCsaba Dabis
71077f13c6SCsaba Dabis // From clang/include/clang/AST/ASTContextAllocate.h
72077f13c6SCsaba Dabis class ASTContext;
73077f13c6SCsaba Dabis
74077f13c6SCsaba Dabis void *operator new(size_t Bytes, const ASTContext &C, size_t Alignment = 8);
75077f13c6SCsaba Dabis void *operator new[](size_t Bytes, const ASTContext &C, size_t Alignment = 8);
76077f13c6SCsaba Dabis
77077f13c6SCsaba Dabis
78077f13c6SCsaba Dabis // From clang/include/clang/AST/ASTContext.h
79077f13c6SCsaba Dabis class ASTContext {
80077f13c6SCsaba Dabis public:
Allocate(size_t Size,unsigned Align=8) const81077f13c6SCsaba Dabis void *Allocate(size_t Size, unsigned Align = 8) const {
82077f13c6SCsaba Dabis return BumpAlloc.Allocate(Size, Align);
83077f13c6SCsaba Dabis }
84077f13c6SCsaba Dabis
85077f13c6SCsaba Dabis template <typename T>
Allocate(size_t Num=1) const86077f13c6SCsaba Dabis T *Allocate(size_t Num = 1) const {
87077f13c6SCsaba Dabis return static_cast<T *>(Allocate(Num * sizeof(T), alignof(T)));
88077f13c6SCsaba Dabis }
89077f13c6SCsaba Dabis
90077f13c6SCsaba Dabis private:
91077f13c6SCsaba Dabis mutable BumpPtrAllocator BumpAlloc;
92077f13c6SCsaba Dabis };
93077f13c6SCsaba Dabis
94077f13c6SCsaba Dabis
95077f13c6SCsaba Dabis // From clang/include/clang/AST/ASTContext.h
operator new(size_t Bytes,const ASTContext & C,size_t Alignment)96077f13c6SCsaba Dabis inline void *operator new(size_t Bytes, const ASTContext &C,
97077f13c6SCsaba Dabis size_t Alignment /* = 8 */) {
98077f13c6SCsaba Dabis return C.Allocate(Bytes, Alignment);
99077f13c6SCsaba Dabis }
100077f13c6SCsaba Dabis
operator new[](size_t Bytes,const ASTContext & C,size_t Alignment)101077f13c6SCsaba Dabis inline void *operator new[](size_t Bytes, const ASTContext &C,
102077f13c6SCsaba Dabis size_t Alignment /* = 8 */) {
103077f13c6SCsaba Dabis return C.Allocate(Bytes, Alignment);
104077f13c6SCsaba Dabis }
105077f13c6SCsaba Dabis
106077f13c6SCsaba Dabis
107077f13c6SCsaba Dabis // From clang/include/clang/AST/Attr.h
operator new(size_t Bytes,ASTContext & C,size_t Alignment=8)108077f13c6SCsaba Dabis void *operator new(size_t Bytes, ASTContext &C,
109077f13c6SCsaba Dabis size_t Alignment = 8) noexcept {
110077f13c6SCsaba Dabis return ::operator new(Bytes, C, Alignment);
111077f13c6SCsaba Dabis }
112077f13c6SCsaba Dabis
113077f13c6SCsaba Dabis
114077f13c6SCsaba Dabis class A {
115077f13c6SCsaba Dabis public:
setValue(int value)116077f13c6SCsaba Dabis void setValue(int value) { Value = value; }
117077f13c6SCsaba Dabis private:
118077f13c6SCsaba Dabis int Value;
119077f13c6SCsaba Dabis };
120077f13c6SCsaba Dabis
f(const ASTContext & C)121077f13c6SCsaba Dabis void f(const ASTContext &C) {
122077f13c6SCsaba Dabis A *a = new (C) A;
123077f13c6SCsaba Dabis a->setValue(13);
124077f13c6SCsaba Dabis #ifndef SUPPRESSED
125077f13c6SCsaba Dabis // expected-warning@-2 {{Called C++ object pointer is null}}
126077f13c6SCsaba Dabis #endif
127077f13c6SCsaba Dabis }
128077f13c6SCsaba Dabis
g(const ASTContext & C)129077f13c6SCsaba Dabis void g(const ASTContext &C) {
130077f13c6SCsaba Dabis A *a = new (C) A[1];
131077f13c6SCsaba Dabis a[0].setValue(13);
132077f13c6SCsaba Dabis #ifndef SUPPRESSED
133077f13c6SCsaba Dabis // expected-warning@-2 {{Called C++ object pointer is null}}
134077f13c6SCsaba Dabis #endif
135077f13c6SCsaba Dabis }
136077f13c6SCsaba Dabis
137