Home | History | Annotate | Download | only in CodeGenCXX
      1 // RUN: %clang_cc1 -emit-llvm -triple x86_64-apple-darwin10 -o - %s | FileCheck %s
      2 
      3 // PR6024
      4 extern int i;
      5 
      6 // CHECK: define dereferenceable({{[0-9]+}}) i32* @_Z16lvalue_noop_castv() [[NUW:#[0-9]+]]
      7 const int &lvalue_noop_cast() {
      8   if (i == 0)
      9     // CHECK: store i32 17, i32*
     10     return (const int&)17;
     11   else if (i == 1)
     12     // CHECK: store i32 17, i32*
     13     return static_cast<const int&>(17);
     14     // CHECK: store i32 17, i32*
     15   return 17;
     16 }
     17 
     18 // CHECK-LABEL: define dereferenceable({{[0-9]+}}) i16* @_Z20lvalue_integral_castv()
     19 const short &lvalue_integral_cast() {
     20   if (i == 0)
     21     // CHECK: store i16 17, i16*
     22     return (const short&)17;
     23   else if (i == 1)
     24     // CHECK: store i16 17, i16*
     25     return static_cast<const short&>(17);
     26   // CHECK: store i16 17, i16*
     27   return 17;
     28 }
     29 
     30 // CHECK-LABEL: define dereferenceable({{[0-9]+}}) i16* @_Z29lvalue_floating_integral_castv()
     31 const short &lvalue_floating_integral_cast() {
     32   if (i == 0)
     33     // CHECK: store i16 17, i16*
     34     return (const short&)17.5;
     35   else if (i == 1)
     36     // CHECK: store i16 17, i16*
     37     return static_cast<const short&>(17.5);
     38   // CHECK: store i16 17, i16*
     39   return 17.5;
     40 }
     41 
     42 // CHECK-LABEL: define dereferenceable({{[0-9]+}}) float* @_Z29lvalue_integral_floating_castv()
     43 const float &lvalue_integral_floating_cast() {
     44   if (i == 0)
     45     // CHECK: store float 1.700000e+{{0*}}1, float*
     46     return (const float&)17;
     47   else if (i == 1)
     48     // CHECK: store float 1.700000e+{{0*}}1, float*
     49     return static_cast<const float&>(17);
     50   // CHECK: store float 1.700000e+{{0*}}1, float*
     51   return 17;
     52 }
     53 
     54 // CHECK-LABEL: define dereferenceable({{[0-9]+}}) float* @_Z20lvalue_floating_castv()
     55 const float &lvalue_floating_cast() {
     56   if (i == 0)
     57     // CHECK: store float 1.700000e+{{0*}}1, float*
     58     return (const float&)17.0;
     59   else if (i == 1)
     60     // CHECK: store float 1.700000e+{{0*}}1, float*
     61     return static_cast<const float&>(17.0);
     62   // CHECK: store float 1.700000e+{{0*}}1, float*
     63   return 17.0;
     64 }
     65 
     66 int get_int();
     67 
     68 // CHECK-LABEL: define dereferenceable({{[0-9]+}}) i8* @_Z24lvalue_integer_bool_castv()
     69 const bool &lvalue_integer_bool_cast() {
     70   if (i == 0)
     71     // CHECK: call i32 @_Z7get_intv()
     72     // CHECK: store i8
     73     return (const bool&)get_int();
     74   else if (i == 1)
     75     // CHECK: call i32 @_Z7get_intv()
     76     // CHECK: store i8
     77     return static_cast<const bool&>(get_int());
     78   // CHECK: call i32 @_Z7get_intv()
     79   // CHECK: store i8
     80   return get_int();
     81 }
     82 
     83 float get_float();
     84 
     85 // CHECK-LABEL: define dereferenceable({{[0-9]+}}) i8* @_Z25lvalue_floating_bool_castv()
     86 const bool &lvalue_floating_bool_cast() {
     87   if (i == 0)
     88     // CHECK: call float @_Z9get_floatv()
     89     // CHECK: fcmp une float
     90     // CHECK: store i8
     91     return (const bool&)get_float();
     92   else if (i == 1)
     93     // CHECK: call float @_Z9get_floatv()
     94     // CHECK: fcmp une float
     95     // CHECK: store i8
     96     return static_cast<const bool&>(get_float());
     97   // CHECK: call float @_Z9get_floatv()
     98   // CHECK: fcmp une float
     99   // CHECK: store i8
    100   return get_float();
    101 }
    102 
    103 struct X { };
    104 typedef int X::*pm;
    105 typedef int (X::*pmf)(int);
    106 
    107 pm get_pointer_to_member_data();
    108 pmf get_pointer_to_member_function();
    109 
    110 // CHECK-LABEL: define dereferenceable({{[0-9]+}}) i8* @_Z26lvalue_ptrmem_to_bool_castv()
    111 const bool &lvalue_ptrmem_to_bool_cast() {
    112   if (i == 0)
    113     // CHECK: call i64 @_Z26get_pointer_to_member_datav()
    114     // CHECK: store i8
    115     // CHECK: store i8*
    116     return (const bool&)get_pointer_to_member_data();
    117   else if (i == 1)
    118     // CHECK: call i64 @_Z26get_pointer_to_member_datav()
    119     // CHECK: store i8
    120     // CHECK: store i8*
    121     return static_cast<const bool&>(get_pointer_to_member_data());
    122   // CHECK: call i64 @_Z26get_pointer_to_member_datav()
    123   // CHECK: store i8
    124   // CHECK: store i8*
    125   return get_pointer_to_member_data();
    126 }
    127 
    128 // CHECK-LABEL: define dereferenceable({{[0-9]+}}) i8* @_Z27lvalue_ptrmem_to_bool_cast2v
    129 const bool &lvalue_ptrmem_to_bool_cast2() {
    130   if (i == 0)
    131     // CHECK: {{call.*_Z30get_pointer_to_member_functionv}}
    132     // CHECK: store i8
    133     // CHECK: store i8*
    134     return (const bool&)get_pointer_to_member_function();
    135   else if (i == 1)
    136     // CHECK: {{call.*_Z30get_pointer_to_member_functionv}}
    137     // CHECK: store i8
    138     // CHECK: store i8*
    139     return static_cast<const bool&>(get_pointer_to_member_function());
    140   // CHECK: {{call.*_Z30get_pointer_to_member_functionv}}
    141   // CHECK: store i8
    142   // CHECK: store i8*
    143   return get_pointer_to_member_function();
    144 }
    145 
    146 _Complex double get_complex_double();
    147 
    148 // CHECK: {{define.*_Z2f1v}}
    149 const _Complex float &f1() {
    150   if (i == 0)
    151     // CHECK: {{call.*_Z18get_complex_doublev}}
    152     // CHECK: fptrunc
    153     // CHECK: fptrunc
    154     // CHECK: store float
    155     // CHECK: store float
    156     return (const _Complex float&)get_complex_double();
    157   else if (i == 1)
    158     // CHECK: {{call.*_Z18get_complex_doublev}}
    159     // CHECK: fptrunc
    160     // CHECK: fptrunc
    161     // CHECK: store float
    162     // CHECK: store float
    163     return static_cast<const _Complex float&>(get_complex_double());
    164   // CHECK: {{call.*_Z18get_complex_doublev}}
    165   // CHECK: fptrunc
    166   // CHECK: fptrunc
    167   // CHECK: store float
    168   // CHECK: store float
    169   return get_complex_double();
    170 }
    171 
    172 // CHECK-LABEL: define i32 @_Z7pr10592RKi(i32*
    173 unsigned pr10592(const int &v) {
    174   // CHECK: [[VADDR:%[a-zA-Z0-9.]+]] = alloca i32*
    175   // CHECK-NEXT: [[REFTMP:%[a-zA-Z0-9.]+]] = alloca i32
    176   // CHECK-NEXT: store i32* [[V:%[a-zA-Z0-9.]+]], i32** [[VADDR]]
    177   // CHECK-NEXT: [[VADDR_1:%[a-zA-Z0-9.]+]] = load i32*, i32** [[VADDR]]
    178   // CHECK-NEXT: [[VVAL:%[a-zA-Z0-9.]+]] = load i32, i32* [[VADDR_1]]
    179   // CHECK-NEXT: store i32 [[VVAL]], i32* [[REFTMP]]
    180   // CHECK-NEXT: [[VVAL_I:%[a-zA-Z0-9.]+]] = load i32, i32* [[REFTMP]]
    181   // CHECK-NEXT: ret i32 [[VVAL_I]]
    182   return static_cast<const unsigned &>(v);
    183 }
    184 
    185 namespace PR10650 {
    186   struct Helper {
    187     unsigned long long id();
    188   };
    189   unsigned long long test(Helper *obj) {
    190     return static_cast<const unsigned long long&>(obj->id());
    191   }
    192   // CHECK-LABEL: define i64 @_ZN7PR106504testEPNS_6HelperE
    193   // CHECK: store i64
    194 }
    195 
    196 // CHECK: attributes [[NUW]] = { nounwind{{.*}} }
    197