summaryrefslogtreecommitdiff
path: root/test/SemaCXX/linkage-spec.cpp
blob: 1598d0e35a050b1663099e12cd8350dd2b7887b5 (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
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
// RUN: %clang_cc1 -fsyntax-only -verify %s
// RUN: %clang_cc1 -fsyntax-only -verify -Wretained-language-linkage -DW_RETAINED_LANGUAGE_LINKAGE  %s
extern "C" {
  extern "C" void f(int);
}

extern "C++" {
  extern "C++" int& g(int);
  float& g();
}
double& g(double);

void test(int x, double d) {
  f(x);
  float &f1 = g();
  int& i1 = g(x);
  double& d1 = g(d);
}

extern "C" int foo;
extern "C" int foo;

extern "C" const int bar;
extern "C" int const bar;

// <rdar://problem/6895431>
extern "C" struct bar d;
extern struct bar e;

extern "C++" {
  namespace N0 {
    struct X0 {
      int foo(int x) { return x; }
    };
  }
}

// PR5430
namespace pr5430 {
  extern "C" void func(void);
}
using namespace pr5430;
extern "C" void pr5430::func(void) { }

// PR5405
int f2(char *)
{
        return 0;
}

extern "C"
{
    int f2(int)
    {
        return f2((char *)0);
    }
}

namespace PR5405 {
  int f2b(char *) {
    return 0;
  }

  extern "C" {
    int f2b(int) {
      return f2b((char *)0); // ok
    }
  }
}

// PR6991
extern "C" typedef int (*PutcFunc_t)(int);


// PR7859
extern "C" void pr7859_a(int) {} // expected-note {{previous definition}}
extern "C" void pr7859_a(int) {} // expected-error {{redefinition}}

extern "C" void pr7859_b() {} // expected-note {{previous definition}}
extern "C" void pr7859_b(int) {} // expected-error {{conflicting}}

extern "C" void pr7859_c(short) {} // expected-note {{previous definition}}
extern "C" void pr7859_c(int) {} // expected-error {{conflicting}}

// <rdar://problem/8318976>
extern "C" {
  struct s0 {
  private:
    s0();
    s0(const s0 &);
  };
}

//PR7754
extern "C++" template <class T> int pr7754(T param);

namespace N {
  int value;
}

extern "C++" using N::value;

// PR7076
extern "C" const char *Version_string = "2.9";

extern "C" {
  extern const char *Version_string2 = "2.9";
}

namespace PR9162 {
  extern "C" {
    typedef struct _ArtsSink ArtsSink;
    struct _ArtsSink {
      int sink;
    };
  }
  int arts_sink_get_type()
  {
    return sizeof(ArtsSink);
  }
}

namespace pr14958 {
  namespace js { extern int ObjectClass; }
  extern "C" {
    namespace js {}
  }
  int js::ObjectClass;
}

extern "C" void PR16167; // expected-error {{variable has incomplete type 'void'}}
extern void PR16167_0; // expected-error {{variable has incomplete type 'void'}}

// PR7927
enum T_7927 {
  E_7927
};

extern "C" void f_pr7927(int);

namespace {
  extern "C" void f_pr7927(int);

  void foo_pr7927() {
    f_pr7927(E_7927);
    f_pr7927(0);
    ::f_pr7927(E_7927);
    ::f_pr7927(0);
  }
}

void bar_pr7927() {
  f_pr7927(E_7927);
  f_pr7927(0);
  ::f_pr7927(E_7927);
  ::f_pr7927(0);
}

namespace PR17337 {
  extern "C++" {
    class Foo;
    extern "C" int bar3(Foo *y);
    class Foo {
      int x;
      friend int bar3(Foo *y);
#ifdef W_RETAINED_LANGUAGE_LINKAGE
// expected-note@-5 {{previous declaration is here}}
// expected-warning@-3 {{retaining previous language linkage}}
#endif
    };
    extern "C" int bar3(Foo *y) {
      return y->x;
    }
  }
}