1// RUN: %check_clang_tidy %s readability-implicit-bool-conversion %t \
2// RUN: -config='{CheckOptions: \
3// RUN: {readability-implicit-bool-conversion.AllowIntegerConditions: true, \
4// RUN: readability-implicit-bool-conversion.AllowPointerConditions: true}}'
5
6template<typename T>
7void functionTaking(T);
8
9int functionReturningInt();
10int* functionReturningPointer();
11
12struct Struct {
13 int member;
14 unsigned bitfield : 1;
15 bool boolfield : 1;
16};
17
18
19void regularImplicitConversionIntegerToBoolIsNotIgnored() {
20 int integer = 0;
21 functionTaking<bool>(integer);
22 // CHECK-MESSAGES: :[[@LINE-1]]:24: warning: implicit conversion 'int' -> 'bool' [readability-implicit-bool-conversion]
23 // CHECK-FIXES: functionTaking<bool>(integer != 0);
24}
25
26void implicitConversionIntegerToBoolInConditionalsIsAllowed() {
27 Struct s = {};
28 if (s.member) {}
29 if (!s.member) {}
30 if (s.bitfield) {}
31 if (!s.bitfield) {}
32 if (s.boolfield == true) {}
33 if (s.boolfield != true) {}
34 if (functionReturningInt()) {}
35 if (!functionReturningInt()) {}
36 if (functionReturningInt() && functionReturningPointer()) {}
37 if (!functionReturningInt() && !functionReturningPointer()) {}
38 for (; functionReturningInt(); ) {}
39 for (; functionReturningPointer(); ) {}
40 for (; functionReturningInt() && !functionReturningPointer() || (!functionReturningInt() && functionReturningPointer()); ) {}
41 while (functionReturningInt()) {}
42 while (functionReturningPointer()) {}
43 while (functionReturningInt() && !functionReturningPointer() || (!functionReturningInt() && functionReturningPointer())) {}
44 do {} while (functionReturningInt());
45 do {} while (functionReturningPointer());
46 do {} while (functionReturningInt() && !functionReturningPointer() || (!functionReturningInt() && functionReturningPointer()));
47 int value1 = functionReturningInt() ? 1 : 2;
48 int value2 = !functionReturningInt() ? 1 : 2;
49 int value3 = (functionReturningInt() && functionReturningPointer() || !functionReturningInt()) ? 1 : 2;
50 int value4 = functionReturningInt() ?: value3;
51 int *p1 = functionReturningPointer() ?: &value3;
52}
53
54void regularImplicitConversionPointerToBoolIsNotIgnored() {
55 int* pointer = nullptr;
56 functionTaking<bool>(pointer);
57 // CHECK-MESSAGES: :[[@LINE-1]]:24: warning: implicit conversion 'int *' -> 'bool'
58 // CHECK-FIXES: functionTaking<bool>(pointer != nullptr);
59
60 int Struct::* memberPointer = &Struct::member;
61 functionTaking<bool>(memberPointer);
62 // CHECK-MESSAGES: :[[@LINE-1]]:24: warning: implicit conversion 'int Struct::*' -> 'bool'
63 // CHECK-FIXES: functionTaking<bool>(memberPointer != nullptr);
64}
65
66void implicitConversionPointerToBoolInConditionalsIsAllowed() {
67 if (functionReturningPointer()) {}
68 if (not functionReturningPointer()) {}
69 int value1 = functionReturningPointer() ? 1 : 2;
70 int value2 = (not functionReturningPointer()) ? 1 : 2;
71
72 int Struct::* memberPointer = &Struct::member;
73 if (memberPointer) {}
74 if (memberPointer) {}
75 int value3 = memberPointer ? 1 : 2;
76 int value4 = (not memberPointer) ? 1 : 2;
77}
78

source code of clang-tools-extra/test/clang-tidy/checkers/readability/implicit-bool-conversion-allow-in-conditions.cpp