summaryrefslogtreecommitdiffstats
path: root/clang-tools-extra/test/clang-tidy/google-explicit-constructor.cpp
blob: a865733da6246ee30bf90251f22d7e571b819488 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
// RUN: $(dirname %s)/check_clang_tidy.sh %s google-explicit-constructor %t
// REQUIRES: shell

namespace std {
  typedef decltype(sizeof(int)) size_t;

  // libc++'s implementation
  template <class _E>
  class initializer_list
  {
    const _E* __begin_;
    size_t    __size_;

    initializer_list(const _E* __b, size_t __s)
      : __begin_(__b),
        __size_(__s)
    {}

  public:
    typedef _E        value_type;
    typedef const _E& reference;
    typedef const _E& const_reference;
    typedef size_t    size_type;

    typedef const _E* iterator;
    typedef const _E* const_iterator;

    initializer_list() : __begin_(nullptr), __size_(0) {}

    size_t    size()  const {return __size_;}
    const _E* begin() const {return __begin_;}
    const _E* end()   const {return __begin_ + __size_;}
  };
}

struct A {
  A() {}
  A(int x, int y) {}

  explicit A(void *x) {}
  explicit A(void *x, void *y) {}

  explicit A(const A& a) {}
  // CHECK-MESSAGES: :[[@LINE-1]]:12: warning: copy constructor should not be declared explicit [google-explicit-constructor]
  // CHECK-FIXES: {{^  }}A(const A& a) {}

  A(int x1) {}
  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: single-argument constructors must be explicit [google-explicit-constructor]
  // CHECK-FIXES: {{^  }}explicit A(int x1) {}

  A(double x2, double y = 3.14) {}
  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: constructors that are callable with a single argument must be marked explicit [google-explicit-constructor]
  // CHECK-FIXES: {{^  }}explicit A(double x2, double y = 3.14) {}

  template <typename... T>
  A(T&&... args);
  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: constructors that are callable with a single argument
  // CHECK-FIXES: {{^  }}explicit A(T&&... args);
};

struct B {
  B(std::initializer_list<int> list1) {}
  B(const std::initializer_list<unsigned> &list2) {}
  B(std::initializer_list<unsigned> &&list3) {}

  explicit B(::std::initializer_list<double> list4) {}
  // CHECK-MESSAGES: :[[@LINE-1]]:12: warning: initializer-list constructor should not be declared explicit [google-explicit-constructor]
  // CHECK-FIXES: {{^  }}B(::std::initializer_list<double> list4) {}

  explicit B(const ::std::initializer_list<char> &list5) {}
  // CHECK-MESSAGES: :[[@LINE-1]]:12: warning: initializer-list constructor
  // CHECK-FIXES: {{^  }}B(const ::std::initializer_list<char> &list5) {}

  explicit B(::std::initializer_list<char> &&list6) {}
  // CHECK-MESSAGES: :[[@LINE-1]]:12: warning: initializer-list constructor
  // CHECK-FIXES: {{^  }}B(::std::initializer_list<char> &&list6) {}
};

using namespace std;

struct C {
  C(initializer_list<int> list1) {}
  C(const initializer_list<unsigned> &list2) {}
  C(initializer_list<unsigned> &&list3) {}
};

template <typename T>
struct C2 {
  C2(initializer_list<int> list1) {}
  C2(const initializer_list<unsigned> &list2) {}
  C2(initializer_list<unsigned> &&list3) {}

  explicit C2(initializer_list<double> list4) {}
  // CHECK-MESSAGES: :[[@LINE-1]]:12: warning: initializer-list constructor
  // CHECK-FIXES: {{^  }}C2(initializer_list<double> list4) {}
};

template <typename T>
struct C3 {
  C3(initializer_list<T> list1) {}
  C3(const std::initializer_list<T*> &list2) {}
  C3(::std::initializer_list<T**> &&list3) {}

  template <typename U>
  C3(initializer_list<U> list3) {}
};

struct D {
  template <typename T>
  explicit D(T t) {}
};

template <typename T>
struct E {
  E(T *pt) {}
  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: single-argument constructors
  // CHECK-FIXES: {{^  }}explicit E(T *pt) {}
  template <typename U>
  E(U *pu) {}
  // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: single-argument constructors
  // CHECK-FIXES: {{^  }}explicit E(U *pu) {}

  explicit E(T t) {}
  template <typename U>
  explicit E(U u) {}
};

void f(std::initializer_list<int> list) {
  D d(list);
  E<decltype(list)> e(list);
  E<int> e2(list);
}
OpenPOWER on IntegriCloud