1 // RUN: %check_clang_tidy %s misc-new-delete-overloads %t 2 3 typedef decltype(sizeof(int)) size_t; 4 5 struct S { 6 // CHECK-MESSAGES: :[[@LINE+1]]:9: warning: declaration of 'operator new' has no matching declaration of 'operator delete' at the same scope [misc-new-delete-overloads] 7 void *operator new(size_t size) noexcept; 8 // CHECK-MESSAGES: :[[@LINE+1]]:9: warning: declaration of 'operator new[]' has no matching declaration of 'operator delete[]' at the same scope 9 void *operator new[](size_t size) noexcept; 10 }; 11 12 // CHECK-MESSAGES: :[[@LINE+1]]:7: warning: declaration of 'operator new' has no matching declaration of 'operator delete' at the same scope 13 void *operator new(size_t size) noexcept(false); 14 15 struct T { 16 // Sized deallocations are not enabled by default, and so this new/delete pair 17 // does not match. However, we expect only one warning, for the new, because 18 // the operator delete is a placement delete and we do not warn on mismatching 19 // placement operations. 20 // CHECK-MESSAGES: :[[@LINE+1]]:9: warning: declaration of 'operator new' has no matching declaration of 'operator delete' at the same scope 21 void *operator new(size_t size) noexcept; 22 void operator delete(void *ptr, size_t) noexcept; // ok only if sized deallocation is enabled 23 }; 24 25 struct U { 26 void *operator new(size_t size) noexcept; 27 void operator delete(void *ptr) noexcept; 28 29 void *operator new[](size_t) noexcept; 30 void operator delete[](void *) noexcept; 31 }; 32 33 struct Z { 34 // CHECK-MESSAGES: :[[@LINE+1]]:8: warning: declaration of 'operator delete' has no matching declaration of 'operator new' at the same scope 35 void operator delete(void *ptr) noexcept; 36 // CHECK-MESSAGES: :[[@LINE+1]]:8: warning: declaration of 'operator delete[]' has no matching declaration of 'operator new[]' at the same scope 37 void operator delete[](void *ptr) noexcept; 38 }; 39 40 struct A { 41 void *operator new(size_t size, Z) noexcept; // ok, placement new 42 }; 43 44 struct B { 45 void operator delete(void *ptr, A) noexcept; // ok, placement delete 46 }; 47 48 // It is okay to have a class with an inaccessible free store operator. 49 struct C { 50 void *operator new(size_t, A) noexcept; // ok, placement new 51 private: 52 void operator delete(void *) noexcept; 53 }; 54 55 // It is also okay to have a class with a delete free store operator. 56 struct D { 57 void *operator new(size_t, A) noexcept; // ok, placement new 58 void operator delete(void *) noexcept = delete; 59 }; 60 61 struct E : U { 62 void *operator new(size_t) noexcept; // okay, we inherit operator delete from U 63 }; 64 65 struct F : S { 66 // CHECK-MESSAGES: :[[@LINE+1]]:9: warning: declaration of 'operator new' has no matching declaration of 'operator delete' at the same scope 67 void *operator new(size_t) noexcept; 68 }; 69 70 class G { 71 void operator delete(void *) noexcept; 72 }; 73 74 struct H : G { 75 // CHECK-MESSAGES: :[[@LINE+1]]:9: warning: declaration of 'operator new' has no matching declaration of 'operator delete' at the same scope 76 void *operator new(size_t) noexcept; // base class operator is inaccessible 77 }; 78 79 template <typename Base> struct Derived : Base { 80 void operator delete(void *); 81 }; 82