Clang Project

clang_source_code/test/Analysis/casts.cpp
1// RUN: %clang_analyze_cc1 -std=c++14 -analyzer-checker=core,debug.ExprInspection -analyzer-store=region -verify %s
2
3void clang_analyzer_eval(bool);
4
5bool PR14634(int x) {
6  double y = (double)x;
7  return !y;
8}
9
10bool PR14634_implicit(int x) {
11  double y = (double)x;
12  return y;
13}
14
15void intAsBoolAsSwitchCondition(int c) {
16  switch ((bool)c) { // expected-warning {{switch condition has boolean value}}
17  case 0:
18    break;
19  }
20
21  switch ((int)(bool)c) { // no-warning
22    case 0:
23      break;
24  }
25}
26
27int *&castToIntPtrLValueRef(char *p) {
28  return (int *&)*(int *)p;
29}
30bool testCastToIntPtrLValueRef(char *p, int *s) {
31  return castToIntPtrLValueRef(p) != s; // no-crash
32}
33
34int *&&castToIntPtrRValueRef(char *p) {
35  return (int *&&)*(int *)p;
36}
37bool testCastToIntPtrRValueRef(char *p, int *s) {
38  return castToIntPtrRValueRef(p) != s; // no-crash
39}
40
41bool retrievePointerFromBoolean(int *p) {
42  bool q;
43  *reinterpret_cast<int **>(&q) = p;
44  return q;
45}
46
47namespace base_to_derived {
48struct A {};
49struct B : public A{};
50
51void foo(A* a) {
52  B* b = (B* ) a;
53  A* a2 = (A *) b;
54  clang_analyzer_eval(a2 == a); // expected-warning{{TRUE}}
55}
56}
57
58namespace base_to_derived_double_inheritance {
59struct A {
60  int x;
61};
62struct B {
63  int y;
64};
65struct C : A, B {};
66
67void foo(B *b) {
68  C *c = (C *)b;
69  b->y = 1;
70  clang_analyzer_eval(c->x); // expected-warning{{UNKNOWN}}
71  clang_analyzer_eval(c->y); // expected-warning{{TRUE}}
72}
73} // namespace base_to_derived_double_inheritance
74
75namespace base_to_derived_opaque_class {
76class NotInt {
77public:
78  operator int() { return !x; } // no-crash
79  int x;
80};
81
82typedef struct Opaque *OpaqueRef;
83typedef void *VeryOpaqueRef;
84
85class Transparent {
86public:
87  int getNotInt() { return NI; }
88  NotInt NI;
89};
90
91class SubTransparent : public Transparent {};
92
93SubTransparent *castToDerived(Transparent *TRef) {
94  return (SubTransparent *)TRef;
95}
96
97void foo(OpaqueRef ORef) {
98  castToDerived(reinterpret_cast<Transparent *>(ORef))->getNotInt();
99}
100
101void foo(VeryOpaqueRef ORef) {
102  castToDerived(reinterpret_cast<Transparent *>(ORef))->getNotInt();
103}
104} // namespace base_to_derived_opaque_class
105
106namespace bool_to_nullptr {
107struct S {
108  int *a[1];
109  bool b;
110};
111void foo(S s) {
112  s.b = true;
113  for (int i = 0; i < 2; ++i)
114    (void)(s.a[i] != nullptr); // no-crash
115}
116} // namespace bool_to_nullptr
117