2009-12-15 23:14:24 +03:00
// RUN: %clang_cc1 -fsyntax-only -verify %s
2008-11-25 07:08:05 +03:00
2008-12-03 23:26:15 +03:00
# include <stddef.h>
2008-11-21 22:14:01 +03:00
struct S // expected-note {{candidate}}
{
S ( int , int , double ) ; // expected-note {{candidate}}
2009-02-07 22:52:04 +03:00
S ( double , int ) ; // expected-note 2 {{candidate}}
S ( float , int ) ; // expected-note 2 {{candidate}}
2008-11-21 22:14:01 +03:00
} ;
2010-03-10 14:27:22 +03:00
struct T ; // expected-note{{forward declaration of 'T'}}
2008-12-04 20:24:46 +03:00
struct U
{
// A special new, to verify that the global version isn't used.
2009-05-14 22:11:41 +04:00
void * operator new ( size_t , S * ) ; // expected-note {{candidate}}
2008-12-04 20:24:46 +03:00
} ;
2008-12-05 01:20:51 +03:00
struct V : U
{
} ;
2008-11-21 22:14:01 +03:00
2009-12-23 02:42:49 +03:00
// PR5823
void * operator new ( const size_t ) ; // expected-note 2 {{candidate}}
2009-02-07 22:52:04 +03:00
void * operator new ( size_t , int * ) ; // expected-note 3 {{candidate}}
void * operator new ( size_t , float * ) ; // expected-note 3 {{candidate}}
2009-05-31 23:49:47 +04:00
void * operator new ( size_t , S ) ; // expected-note 2 {{candidate}}
2008-12-03 23:26:15 +03:00
2008-11-21 22:14:01 +03:00
void good_news ( )
{
int * pi = new int ;
float * pf = new ( pi ) float ( ) ;
pi = new int ( 1 ) ;
pi = new int ( ' c ' ) ;
const int * pci = new const int ( ) ;
S * ps = new S ( 1 , 2 , 3.4 ) ;
2008-12-02 17:43:59 +03:00
ps = new ( pf ) ( S ) ( 1 , 2 , 3.4 ) ;
2008-11-21 22:14:01 +03:00
S * ( * paps ) [ 2 ] = new S * [ * pi ] [ 2 ] ;
typedef int ia4 [ 4 ] ;
ia4 * pai = new ( int [ 3 ] [ 4 ] ) ;
2008-12-02 19:35:44 +03:00
pi = : : new int ;
2008-12-04 20:24:46 +03:00
U * pu = new ( ps ) U ;
2009-09-30 04:03:47 +04:00
V * pv = new ( ps ) V ;
2009-05-31 23:49:47 +04:00
pi = new ( S ( 1.0f , 2 ) ) int ;
2009-09-23 04:37:25 +04:00
( void ) new int [ true ] ;
2008-11-21 22:14:01 +03:00
}
2009-03-24 22:52:54 +03:00
struct abstract {
virtual ~ abstract ( ) = 0 ;
} ;
2008-11-25 07:08:05 +03:00
void bad_news ( int * ip )
2008-11-21 22:14:01 +03:00
{
int i = 1 ;
( void ) new ; // expected-error {{missing type specifier}}
( void ) new 4 ; // expected-error {{missing type specifier}}
( void ) new ( ) int ; // expected-error {{expected expression}}
2008-12-02 17:43:59 +03:00
( void ) new int [ 1.1 ] ; // expected-error {{array size expression must have integral or enumerated type, not 'double'}}
2008-11-21 22:14:01 +03:00
( void ) new int [ 1 ] [ i ] ; // expected-error {{only the first dimension}}
( void ) new ( int [ 1 ] [ i ] ) ; // expected-error {{only the first dimension}}
2009-10-26 00:45:37 +03:00
( void ) new ( int [ i ] ) ; // expected-error {{when type is in parentheses}}
2010-03-10 14:27:22 +03:00
( void ) new int ( * ( S * ) 0 ) ; // expected-error {{no viable conversion from 'S' to 'int'}}
2009-12-16 04:38:02 +03:00
( void ) new int ( 1 , 2 ) ; // expected-error {{excess elements in scalar initializer}}
2008-11-21 22:14:01 +03:00
( void ) new S ( 1 ) ; // expected-error {{no matching constructor}}
2010-03-10 14:27:22 +03:00
( void ) new S ( 1 , 1 ) ; // expected-error {{call to constructor of 'S' is ambiguous}}
2009-12-16 04:38:02 +03:00
( void ) new const int ; // expected-error {{default initialization of an object of const type 'int const'}}
2010-01-23 08:47:27 +03:00
( void ) new float * ( ip ) ; // expected-error {{cannot initialize a new value of type 'float *' with an lvalue of type 'int *'}}
2008-12-02 17:43:59 +03:00
// Undefined, but clang should reject it directly.
( void ) new int [ - 1 ] ; // expected-error {{array size is negative}}
2010-03-10 14:27:22 +03:00
( void ) new int [ * ( S * ) 0 ] ; // expected-error {{array size expression must have integral or enumerated type, not 'S'}}
2008-12-02 19:35:44 +03:00
( void ) : : S : : new int ; // expected-error {{expected unqualified-id}}
2008-12-03 23:26:15 +03:00
( void ) new ( 0 , 0 ) int ; // expected-error {{no matching function for call to 'operator new'}}
2008-12-05 01:20:51 +03:00
( void ) new ( 0L ) int ; // expected-error {{call to 'operator new' is ambiguous}}
2008-12-04 20:24:46 +03:00
// This must fail, because the member version shouldn't be found.
( void ) : : new ( ( S * ) 0 ) U ; // expected-error {{no matching function for call to 'operator new'}}
2009-05-14 22:11:41 +04:00
// This must fail, because any member version hides all global versions.
( void ) new U ; // expected-error {{no matching function for call to 'operator new'}}
2009-02-09 21:24:27 +03:00
( void ) new ( int [ ] ) ; // expected-error {{array size must be specified in new expressions}}
( void ) new int & ; // expected-error {{cannot allocate reference type 'int &' with new}}
2008-11-21 22:14:01 +03:00
// Some lacking cases due to lack of sema support.
}
void good_deletes ( )
{
delete ( int * ) 0 ;
delete [ ] ( int * ) 0 ;
delete ( S * ) 0 ;
2008-12-02 19:35:44 +03:00
: : delete ( int * ) 0 ;
2008-11-21 22:14:01 +03:00
}
void bad_deletes ( )
{
delete 0 ; // expected-error {{cannot delete expression of type 'int'}}
delete [ 0 ] ( int * ) 0 ; / / expected - error { { expected ' ] ' } } \
2008-11-24 02:17:07 +03:00
// expected-note {{to match this '['}}
2008-11-21 22:14:01 +03:00
delete ( void * ) 0 ; // expected-error {{cannot delete expression}}
delete ( T * ) 0 ; // expected-warning {{deleting pointer to incomplete type}}
2008-12-02 19:35:44 +03:00
: : S : : delete ( int * ) 0 ; // expected-error {{expected unqualified-id}}
2008-11-21 22:14:01 +03:00
}
2009-09-10 03:39:55 +04:00
struct X0 { } ;
struct X1 {
operator int * ( ) ;
operator float ( ) ;
} ;
struct X2 {
2009-09-15 21:21:47 +04:00
operator int * ( ) ; // expected-note {{candidate function}}
operator float * ( ) ; // expected-note {{candidate function}}
2009-09-10 03:39:55 +04:00
} ;
void test_delete_conv ( X0 x0 , X1 x1 , X2 x2 ) {
delete x0 ; // expected-error{{cannot delete}}
delete x1 ;
2010-03-10 14:27:22 +03:00
delete x2 ; // expected-error{{ambiguous conversion of delete expression of type 'X2' to a pointer}}
2009-09-15 21:21:47 +04:00
}
2009-09-29 22:16:17 +04:00
// PR4782
class X3 {
public :
2009-11-16 08:14:40 +03:00
static void operator delete ( void * mem , size_t size ) ;
2009-09-29 22:16:17 +04:00
} ;
class X4 {
public :
static void release ( X3 * x ) ;
2009-11-16 08:14:40 +03:00
static void operator delete ( void * mem , size_t size ) ;
2009-09-29 22:16:17 +04:00
} ;
void X4 : : release ( X3 * x ) {
delete x ;
}
2009-09-30 01:38:53 +04:00
2009-09-30 04:03:47 +04:00
class X5 {
2009-09-30 01:38:53 +04:00
public :
void Destroy ( ) const { delete this ; }
} ;
2009-11-11 02:47:18 +03:00
class Base {
public :
2009-12-13 20:53:43 +03:00
static void * operator new ( signed char ) throw ( ) ; // expected-error {{'operator new' takes type size_t}}
static int operator new [ ] ( size_t ) throw ( ) ; // expected-error {{operator new[]' must return type 'void *'}}
2009-11-11 02:47:18 +03:00
} ;
class Tier { } ;
class Comp : public Tier { } ;
class Thai : public Base {
public :
Thai ( const Tier * adoptDictionary ) ;
} ;
void loadEngineFor ( ) {
const Comp * dict ;
new Thai ( dict ) ;
}
template < class T > struct TBase {
2010-02-16 22:28:15 +03:00
void * operator new ( T size , int ) ; // expected-error {{'operator new' cannot take a dependent type as first parameter; use size_t}}
2009-11-11 02:47:18 +03:00
} ;
2010-02-16 22:28:15 +03:00
TBase < int > t1 ;
2009-11-11 02:47:18 +03:00
2009-11-14 06:17:38 +03:00
class X6 {
public :
static void operator delete ( void * , int ) ; // expected-note {{member found by ambiguous name lookup}}
} ;
class X7 {
public :
static void operator delete ( void * , int ) ; // expected-note {{member found by ambiguous name lookup}}
} ;
class X8 : public X6 , public X7 {
} ;
2009-11-15 19:43:15 +03:00
void f ( X8 * x8 ) {
2009-11-14 06:17:38 +03:00
delete x8 ; // expected-error {{member 'operator delete' found in multiple base classes of different types}}
}
2009-11-15 19:43:15 +03:00
class X9 {
2010-04-09 23:03:51 +04:00
public :
2009-11-15 19:43:15 +03:00
static void operator delete ( void * , int ) ; // expected-note {{'operator delete' declared here}}
static void operator delete ( void * , float ) ; // expected-note {{'operator delete' declared here}}
} ;
void f ( X9 * x9 ) {
delete x9 ; // expected-error {{no suitable member 'operator delete' in 'X9'}}
}
2009-12-01 00:24:50 +03:00
struct X10 {
virtual ~ X10 ( ) ;
} ;
struct X11 : X10 { // expected-error {{no suitable member 'operator delete' in 'X11'}}
void operator delete ( void * , int ) ; // expected-note {{'operator delete' declared here}}
} ;
void f ( ) {
2010-03-10 14:27:22 +03:00
X11 x11 ; // expected-note {{implicit default destructor for 'X11' first required here}}
2009-12-01 00:24:50 +03:00
}
2009-12-09 10:39:44 +03:00
struct X12 {
void * operator new ( size_t , void * ) ;
} ;
struct X13 : X12 {
using X12 : : operator new ;
} ;
static void * f ( void * g )
{
return new ( g ) X13 ( ) ;
}
2010-02-03 14:02:14 +03:00
2010-02-08 21:54:05 +03:00
class X14 {
2010-04-09 23:03:51 +04:00
public :
2010-02-08 21:54:05 +03:00
static void operator delete ( void * , const size_t ) ;
} ;
void f ( X14 * x14a , X14 * x14b ) {
delete x14a ;
}
2010-02-03 14:02:14 +03:00
namespace PR5918 { // Look for template operator new overloads.
struct S { template < typename T > static void * operator new ( size_t , T ) ; } ;
void test ( ) {
( void ) new ( 0 ) S ;
}
}
2010-05-03 19:45:23 +04:00
namespace Test1 {
void f ( ) {
( void ) new int [ 10 ] ( 1 , 2 ) ; // expected-error {{array 'new' cannot have initialization arguments}}
}
template < typename T >
void g ( unsigned i ) {
( void ) new T [ 1 ] ( i ) ; // expected-error {{array 'new' cannot have initialization arguments}}
}
template < typename T >
void h ( unsigned i ) {
( void ) new T ( i ) ; // expected-error {{array 'new' cannot have initialization arguments}}
}
template void h < unsigned > ( unsigned ) ;
template void h < unsigned [ 10 ] > ( unsigned ) ; // expected-note {{in instantiation of function template specialization 'Test1::h<unsigned int [10]>' requested here}}
}