The following list describes changes that must be made to code that was written for the C++ 3.0 compiler before compiling the code with the C++ 5.0 compiler.
K&R-style function definitions are no longer allowed. You must use prototype-style definitions.
int f(a) int a; { ... } // Error in C++ 5.0
You cannot set a global variable _new_handler by assignment. Call function set_new_handler() instead.
Global operator new() is always used when there is no in-class version. C++ 3.0 incorrectly used an outer-class version in preference to the global version. In the following example, C++ 3.0 would incorrectly use Outer::operator new to allocate space.
class Outer {
public:
void* operator new(size_t);
class Inner {
... // No operator new
};
};
Outer::Inner* p = new Outer::Inner; // Which operator new?
Typedef names cannot be used as struct (or class or union) tags. For example:
typedef struct { int x; } S;
struct S b; // OK in C++ 3.0, error in C++ 5.0
S c; // Always OK
typedef struct S { int x; } S;
struct S b; // Always OK
S c; // Always OK
You cannot redefine a name from an outer scope once it has been used in a class. Such redefinition is disallowed by the C++ standard, since it can be disastrous, but the C++ 3.0 compiler did not detect the situation. The C++ 5.0 compiler makes it an error. For example:
typedef int T;
class C {
T iv; // type int
typedef float T; // redefine T -- error in C++ 5.0
T fv; // type float
};
The C++ 3.0 compiler had a bug that allowed a pointer to a function taking unspecified parameters to act in some circumstances as a "universal" pointer-to-function, as in the following example. The C++ rule is that function pointer types must match.
typedef (*pfp)(int,char); typedef (*ufp)(...); int foo(int,char); pfp p = (ufp)foo; // Allowed by 3.0, error in 5.0
Comma-expressions are not allowed in null pointer constants. Although a literal zero is a null pointer constant, an expression such as (anything, 0) is not:
int f();
char* g()
{
return (f(), 0); // OK in 3.0, error in 5.0
// should be:
// return (f(), (char*)0); // OK
// or two statements:
// f();
// return 0;
}
Classes with base classes cannot be initialized with aggregate-initialization syntax. The C++ 3.0 compiler allowed this if no virtual functions were present. You should write a constructor for the class instead.
struct Base { int i; };
struct Derived : Base { int j; };
Derived d = {1, 2}; // OK with 3.0, error in 5.0