Nota
L'accesso a questa pagina richiede l'autorizzazione. È possibile provare ad accedere o modificare le directory.
L'accesso a questa pagina richiede l'autorizzazione. È possibile provare a modificare le directory.
Questa pagina raccoglie tutte le pagine "Novità" per tutte le versioni di Visual C++ da Visual Studio 2015 al 2003. Queste informazioni vengono fornite come praticità nel caso in cui sia utile quando si esegue l'aggiornamento da versioni precedenti di Visual Studio.
Annotazioni
Per informazioni sulla versione corrente di Visual Studio, vedere Novità di Visual C++ in Visual Studio e Miglioramenti della conformità in Visual C++ in Visual Studio.
Novità di C++ in Visual Studio 2015
In Visual Studio 2015 e versioni successive, i miglioramenti continui alla conformità del compilatore possono talvolta modificare il modo in cui il compilatore riconosce il codice sorgente esistente. In questo caso, è possibile che si verifichino errori nuovi o diversi durante la compilazione o anche differenze comportamentali nel codice creato in precedenza e che sembravano essere eseguiti correttamente.
Fortunatamente, queste differenze hanno poco o nessun impatto sulla maggior parte del codice sorgente e quando sono necessarie codice sorgente o altre modifiche per risolvere queste differenze, le correzioni sono in genere piccole e semplici. Sono stati inclusi molti esempi di codice sorgente accettabile in precedenza che potrebbero essere modificati (prima) e le correzioni per correggerle (dopo).
Anche se queste differenze possono influire sul codice sorgente o su altri artefatti di compilazione, non influiscono sulla compatibilità binaria tra gli aggiornamenti delle versioni di Visual C++. Un tipo di modifica più grave, la modifica di rilievo può influire sulla compatibilità binaria, ma questi tipi di interruzioni di compatibilità binaria si verificano solo tra le versioni principali di Visual C++. Ad esempio, tra Visual C++ 2013 e Visual C++ 2015. Per informazioni sulle modifiche di rilievo apportate tra Visual C++ 2013 e Visual C++ 2015, vedere Cronologia modifiche di Visual C++ 2003 - 2015.
Miglioramenti della conformità in Visual Studio 2015 Update 1
Miglioramenti della conformità in Visual Studio 2015 Update 2
Miglioramenti della conformità in Visual Studio 2015 Update 3
Miglioramenti della conformità in Visual Studio 2015
Opzione /Zc:forScope-
L'opzione del compilatore
/Zc:forScope-
è stata deprecata e verrà rimossa in una futura versione.Command line warning D9035: option 'Zc:forScope-' has been deprecated and will be removed in a future release
L'opzione è stata in genere usata per consentire il codice non standard che usa variabili di ciclo dopo il punto in cui, in base allo standard, dovrebbero uscire dall'ambito. È necessario solo quando si compila con l'opzione
/Za
, poiché senza/Za
, usare una variabile del ciclo for dopo la fine del ciclo è sempre consentito. Se non è rilevante la conformità agli standard, ad esempio se il codice non è destinato a essere portabile in altri compilatori, è possibile disattivare l'opzione/Za
o impostare la proprietà Disabilita estensioni linguaggio su No. Se si vuole scrivere codice portatile conforme agli standard, è necessario riscrivere il codice in modo che sia conforme allo standard spostando la dichiarazione di tali variabili in un punto esterno al ciclo.// zc_forScope.cpp // compile with: /Zc:forScope- /Za // C2065 expected int main() { // Uncomment the following line to resolve. // int i; for (int i =0; i < 1; i++) ; i = 20; // i has already gone out of scope under /Za }
Opzione del compilatore Zg.
L'opzione del compilatore
/Zg
, che consente di generare i prototipi delle funzioni, non è più disponibile. Questa opzione del compilatore è stata precedentemente deprecata.Non è più possibile eseguire unit test con C++/CLI dalla riga di comando con mstest.exe. Usare invece vstest.console.exe
Parola chiave mutable.
L'identificatore di classi di archiviazione
mutable
non è più consentito in posizioni dove in precedenza eseguiva compilazioni senza errori. Ora il compilatore genera l'errore C2071 (classe di archiviazione non valida). In base allo standard, l'identificatore modificabile può essere applicato solo ai nomi dei membri dati della classe e non può essere applicato ai nomi dichiarati const o statici e non può essere applicato ai membri di riferimento.Si consideri ad esempio il codice seguente:
struct S { mutable int &r; };
Le versioni precedenti del compilatore Microsoft C++ accettano questa operazione, ma ora il compilatore restituisce l'errore seguente:
error C2071: 'S::r': illegal storage class
Per correggere l'errore, rimuovere semplicemente la parola chiave ridondante
mutable
.char_16_t e char32_t
Non è più possibile usare
char16_t
ochar32_t
come alias in un typedef, perché questi tipi vengono ora considerati incorporati. Era normale per gli utenti e gli autori di librerie definirechar16_t
echar32_t
rispettivamente come alias diuint16_t
euint32_t
.#include <cstdint> typedef uint16_t char16_t; //C2628 typedef uint32_t char32_t; //C2628 int main(int argc, char* argv[]) { uint16_t x = 1; uint32_t y = 2; char16_t a = x; char32_t b = y; return 0; }
Per aggiornare il codice, rimuovere le
typedef
dichiarazioni e rinominare eventuali altri identificatori che si scontrano con questi nomi.Parametri di modello non di tipo
Determinato codice che prevede parametri di modello non di tipo viene ora verificato correttamente per la compatibilità del tipo quando vengono forniti gli argomenti di modello espliciti. Ad esempio, il codice seguente compilato senza errori nelle versioni precedenti di Visual C++.
struct S1 { void f(int); void f(int, int); }; struct S2 { template <class C, void (C::*Function)(int) const> void f() {} }; void f() { S2 s2; s2.f<S1, &S1::f>(); }
Il compilatore corrente restituisce correttamente un errore, perché il tipo di parametro del modello non corrisponde all'argomento del modello (il parametro è un puntatore a un membro const, ma la funzione f non è const):
error C2893: Failed to specialize function template 'void S2::f(void)'note: With the following template arguments:note: 'C=S1'note: 'Function=S1::f'
Per risolvere questo errore nel codice, verificare che il tipo di argomento del modello usato corrisponda al tipo dichiarato del parametro di modello.
__declspec(align)
Il compilatore non accetta più
__declspec(align)
sulle funzioni. Questa operazione è sempre stata ignorata, ma ora genera un errore del compilatore.error C3323: 'alignas' and '__declspec(align)' are not allowed on function declarations
Per risolvere questo problema, rimuovere
__declspec(align)
dalla dichiarazione di funzione. Poiché non ha avuto alcun effetto, la rimozione non cambia nulla.Gestione delle eccezioni
Sono state apportate alcune modifiche alla gestione delle eccezioni. In primo luogo, gli oggetti eccezione devono poter essere copiati o spostati. Il codice seguente compilato in Visual Studio 2013, ma non viene compilato in Visual Studio 2015:
struct S { public: S(); private: S(const S &); }; int main() { throw S(); // error }
Il problema è che il costruttore di copia è privato, quindi l'oggetto non può essere copiato come avviene nel normale corso della gestione di un'eccezione. Lo stesso vale quando il costruttore di copia viene dichiarato
explicit
.struct S { S(); explicit S(const S &); }; int main() { throw S(); // error }
Per aggiornare il codice, assicurarsi che il costruttore di copia per l'oggetto eccezione sia pubblico e non contrassegnato.
explicit
L'individuazione di un'eccezione in base al valore richiede anche che sia possibile copiare l'oggetto eccezione. Il codice seguente compilato in Visual Studio 2013, ma non viene compilato in Visual Studio 2015:
struct B { public: B(); private: B(const B &); }; struct D : public B { }; int main() { try { } catch (D d) // error { } }
Per risolvere questo problema, è possibile modificare il tipo di parametro per
catch
in un riferimento.catch(D& d) { }
Valori letterali stringa seguiti da macro
Il compilatore supporta ora valori letterali definiti dall'utente. Di conseguenza, i valori letterali stringa seguiti da macro senza eventuali spazi intermedi vengono interpretati come valori letterali definiti dall'utente, che potrebbero produrre errori o risultati imprevisti. Nei compilatori precedenti, ad esempio, il codice seguente veniva compilato correttamente:
#define _x "there" char* func() { return "hello"_x; } int main() { char * p = func(); return 0; }
Il compilatore ha interpretato questo come una stringa letterale "hello" seguita da una macro espansa in "there", e quindi le due stringhe letterali sono state concatenate in una sola. In Visual Studio 2015 il compilatore interpreta questo valore come valore letterale definito dall'utente, ma poiché non esiste un valore letterale definito dall'utente corrispondente _x definito, viene generato un errore.
error C3688: invalid literal suffix '_x'; literal operator or literal operator template 'operator ""_x' not found note: Did you forget a space between the string literal and the prefix of the following string literal?
Per risolvere questo problema, aggiungere uno spazio tra il valore letterale stringa e la macro.
Valori letterali stringa adiacenti
Analogamente al precedente, a causa di modifiche correlate all'analisi delle stringhe, i valori letterali stringa adiacenti (valori letterali stringa di caratteri wide o narrow) senza spazi vuoti sono stati interpretati come una singola stringa concatenata nelle versioni precedenti di Visual C++. In Visual Studio 2015 è necessario aggiungere spazi vuoti tra le due stringhe. Ad esempio, il codice seguente deve essere modificato:
char * str = "abc""def";
È sufficiente aggiungere uno spazio tra le due stringhe.
char * str = "abc" "def";
Operatore new e delete di posizionamento
È stata apportata una modifica all'operatore
delete
per renderla conforme allo standard C++14. Per informazioni dettagliate sulla modifica agli standard, vedere Deallocazione con dimensione C++. Le modifiche aggiungono una forma dell'operatore globaledelete
che accetta un parametro size. La modifica che causa un'interruzione è che se in precedenza si usasse un operatore con la stessa firma (per corrispondere a un nuovo operatoredelete
di posizionamento ), si riceverà un errore del compilatore (C2956, che si verifica nel punto in cui viene usato il nuovo posizionamento , poiché si tratta della posizione nel codice in cui il compilatore tenta di identificare un operatore di corrispondenzadelete
appropriato).La funzione
void operator delete(void *, size_t)
era un operatore delete di posizionamento corrispondente alla funzione new di posizionamentovoid * operator new(size_t, size_t)
in C++11. Con la deallocazione di dimensioni C++14, questadelete
funzione è ora una funzione di deallocazione consueta (operatore globaledelete
). Lo standard richiede che se l'uso di un placement new cerca una funzione corrispondentedelete
e trova una normale funzione di deallocazione, il programma è malformato.Si supponga, ad esempio, che il codice definisca un operatore new e delete di posizionamento:
void * operator new(std::size_t, std::size_t); void operator delete(void*, std::size_t) noexcept;
Il problema si verifica a causa della corrispondenza nelle firme di funzione tra un operatore delete di posizionamento definito e il nuovo operatore di dimensioni
delete
globali. Valutare se è possibile usare un tipo diverso dasize_t
per qualsiasi . Si noti che il tipo disize_t
typedef
è dipendente dal compilatore; è untypedef
perunsigned int
in Visual C++. Una buona soluzione consiste nell'usare un tipo enumerato, ad esempio:enum class my_type : size_t {};
Successivamente, modificare la definizione di posizionamento di
new
edelete
, utilizzando questo tipo come secondo argomento al posto disize_t
. Sarà anche necessario aggiornare le chiamate al posizionamento nuovo per passare il nuovo tipo (ad esempio, usandostatic_cast<my_type>
per eseguire la conversione dal valore intero) e aggiornare la definizione dinew
edelete
per eseguire il cast al tipo integer. Non è necessario usare un oggettoenum
per questo. Anche un tipo di classe con unsize_t
membro funziona.Una soluzione alternativa potrebbe essere l'eliminazione totale dell'operatore new di posizionamento. Se il codice usa il posizionamento nuovo per implementare un pool di memoria in cui l'argomento di posizionamento è la dimensione dell'oggetto allocato o eliminato, la funzionalità deallocazione ridimensionata potrebbe essere adatta per sostituire il codice del pool di memoria personalizzato ed è possibile eliminare le funzioni di posizionamento e usare semplicemente l'operatore a due argomenti
delete
anziché le funzioni di posizionamento.Se non si intende aggiornare immediatamente il codice, è possibile ripristinare il comportamento precedente usando l'opzione del compilatore
/Zc:sizedDealloc-
. Se si usa questa opzione, le funzioni a due argomentidelete
non esistono e non causeranno un conflitto con l'operatore di eliminazione del posizionamento .Membri dati di unioni
I membri dati di unioni non possono avere tipi di riferimento. Il codice seguente viene compilato correttamente in Visual Studio 2013 ma genera un errore in Visual Studio 2015.
union U1 { const int i; }; union U2 { int &i; }; union U3 { struct {int &i;}; };
Il codice precedente produce gli errori seguenti:
test.cpp(67): error C2625: 'U2::i': illegal union member; type 'int &' is reference type test.cpp(70): error C2625: 'U3::i': illegal union member; type 'int &' is reference type
Per risolvere questo problema, modificare i tipi di riferimento in un puntatore o un valore. La modifica del tipo in un puntatore richiede modifiche al codice che usa il campo di unione. La modifica del codice in un valore modificherebbe i dati archiviati nell'unione, che influiscono su altri campi, poiché i campi in tipi di unione condividono la stessa memoria. A seconda delle dimensioni del valore, è possibile anche modificare le dimensioni dell'unione.
Unioni anonime
sono ora più conformi allo standard. Le versioni precedenti del compilatore hanno generato un costruttore e distruttore esplicito per unioni anonime. Questi vengono eliminati in Visual Studio 2015.
struct S { S(); }; union { struct { S s; }; } u; // C2280
Il codice precedente genera l'errore seguente in Visual Studio 2015:
error C2280: '<unnamed-type-u>::<unnamed-type-u>(void)': attempting to reference a deleted function note: compiler has generated '<unnamed-type-u>::<unnamed-type-u>' here
Per risolvere questo problema, specificare definizioni personalizzate del costruttore e/o del distruttore.
struct S { // Provide a default constructor by adding an empty function body. S() {} }; union { struct { S s; }; } u;
Unioni con strutture anonime
Per la conformità allo standard, il comportamento di runtime è stato modificato per i membri di strutture anonime nelle unioni. Il costruttore per i membri di strutture anonime in un'unione non viene più chiamato in modo implicito quando viene creato questo tipo di unione. Il distruttore per i membri di strutture anonime in un'unione non viene più chiamato in modo implicito quando l'unione è esterna all'ambito. Si consideri il codice seguente, in cui un'unione U contiene una struttura anonima che contiene un membro che è una struttura denominata S con un distruttore.
#include <stdio.h> struct S { S() { printf("Creating S\n"); } ~S(){ printf("Destroying S\n"); } }; union U { struct { S s; }; U() {} ~U(){} }; void f() { U u; // Destructor implicitly called here. } int main() { f(); char s[1024]; printf("Press any key.\n"); gets_s(s); return 0; }
In Visual Studio 2013 il costruttore per S viene chiamato quando viene creata l'unione e il distruttore per S viene chiamato durante la pulitura dello stack per la funzione f. In Visual Studio 2015, tuttavia, il costruttore e il distruttore non vengono chiamati. Il compilatore visualizza un avviso relativo a questa modifica del comportamento.
warning C4587: 'U::s': behavior change: constructor is no longer implicitly calledwarning C4588: 'U::s': behavior change: destructor is no longer implicitly called
Per ripristinare il comportamento originale, assegnare alla struttura anonima un nome. Il comportamento di runtime di strutture non anonime è lo stesso, indipendentemente dalla versione del compilatore.
#include <stdio.h> struct S { S() { printf("Creating S.\n"); } ~S() { printf("Destroying S\n"); } }; union U { struct { S s; } namedStruct; U() {} ~U() {} }; void f() { U u; } int main() { f(); char s[1024]; printf("Press any key.\n"); gets_s(s); return 0; }
In alternativa, provare a spostare il codice del costruttore e del distruttore in nuove funzioni e aggiungere chiamate a queste funzioni provenienti dal costruttore e distruttore per l'unione.
#include <stdio.h> struct S { void Create() { printf("Creating S.\n"); } void Destroy() { printf("Destroying S\n"); } }; union U { struct { S s; }; U() { s.Create(); } ~U() { s.Destroy(); } }; void f() { U u; } int main() { f(); char s[1024]; printf("Press any key.\n"); gets_s(s); return 0; }
Risoluzione per il modello
Sono state apportate modifiche alla risoluzione dei nomi per i modelli. In C++, quando si considerano i candidati per la risoluzione di un nome, può accadere che uno o più nomi presi in considerazione come corrispondenze potenziali producano un'istanza del modello non valida. Queste istanze non valide in genere non causano errori del compilatore, un principio noto come SFINAE (l'errore di sostituzione non è un errore).
A questo punto, se SFINAE richiede al compilatore di creare un'istanza di specializzazione del modello di classe, eventuali errori verificatisi durante questo processo sono errori del compilatore. Nelle versioni precedenti il compilatore potrebbe ignorare tali errori. Si consideri ad esempio il codice seguente:
#include <type_traits> template<typename T> struct S { S() = default; S(const S&); S(S&&); template<typename U, typename = typename std::enable_if<std::is_base_of<T, U>::value>::type> S(S<U>&&); }; struct D; void f1() { S<D> s1; S<D> s2(s1); } struct B { }; struct D : public B { }; void f2() { S<D> s1; S<D> s2(s1); }
Se si compila con il compilatore corrente, viene visualizzato l'errore seguente:
type_traits(1110): error C2139: 'D': an undefined class is not allowed as an argument to compiler intrinsic type trait '__is_base_of' ..\t331.cpp(14): note: see declaration of 'D' ..\t331.cpp(10): note: see reference to class template instantiation 'std::is_base_of<T,U>' being compiled with [ T=D, U=D ]
Ciò è dovuto al fatto che al momento della prima chiamata del is_base_of la classe 'D' non è ancora stata definita.
In questo caso, la correzione non prevede l'uso di tali tratti di tipo fino a quando la classe non è stata definita. Se si spostano le definizioni di B e D all'inizio del file di codice, l'errore viene risolto. Se le definizioni sono nei file di intestazione, controllare l'ordine delle istruzioni include per i file di intestazione per verificare che tutte le definizioni di classe vengano compilate prima di usare modelli problematici.
Costruttori di copia
Sia in Visual Studio 2013 che in Visual Studio 2015 il compilatore genera un costruttore di copia per una classe se tale classe ha un costruttore di spostamento definito dall'utente, ma nessun costruttore di copia definito dall'utente. In Dev14, questo costruttore di copia generato in modo implicito è contrassegnato come "= delete".
Miglioramenti della conformità in Visual Studio 2015 Update 1
Classi base virtuali private ed ereditarietà indiretta
Le versioni precedenti del compilatore hanno consentito a una classe derivata di chiamare le funzioni membro delle classi di base derivate
private virtual
. Questo comportamento precedente non è corretto e non è conforme allo standard C++. Il compilatore non accetta più il codice scritto in questo modo e genera l'errore del compilatore C2280 di conseguenza.error C2280: 'void *S3::__delDtor(unsigned int)': attempting to reference a deleted function
Esempio (prima)
class base { protected: base(); ~base(); }; class middle: private virtual base {};class top: public virtual middle {}; void destroy(top *p) { delete p; // }
Esempio (dopo)
class base; // as above class middle: protected virtual base {}; class top: public virtual middle {}; void destroy(top *p) { delete p; }
oppure
class base; // as above class middle: private virtual base {}; class top: public virtual middle, private virtual bottom {}; void destroy(top *p) { delete p; }
Funzioni operator new e operator delete in overload
Le versioni precedenti del compilatore consentivano di dichiarare statiche le funzioni non membro operator new e non membro operator delete e di dichiararle in spazi dei nomi diversi dallo spazio dei nomi globale. Questo comportamento precedente creava il rischio che il programma non chiamasse l'implementazione dell'operator
new
odelete
prevista dal programmatore, determinando un comportamento errato in fase di esecuzione senza avvisare. Il compilatore non accetta più il codice scritto in questo modo e genera invece l'errore del compilatore C2323.error C2323: 'operator new': non-member operator new or delete functions may not be declared static or in a namespace other than the global namespace.
Esempio (prima)
static inline void * __cdecl operator new(size_t cb, const std::nothrow_t&) // error C2323
Esempio (dopo)
void * __cdecl operator new(size_t cb, const std::nothrow_t&) // removed 'static inline'
Inoltre, anche se il compilatore non offre una diagnostica specifica, l'operatore inline new viene considerato malformato.
Chiamando 'operator type()' (conversione definita dall'utente) su tipi non di classe Nelle versioni precedenti del compilatore era consentito chiamare 'operator type()' su tipi non di classe ignorandolo silenziosamente. Questo comportamento precedente creava un rischio di generazione di codice errato senza avvisare, determinando un comportamento imprevedibile in fase di esecuzione. Il compilatore non accetta più il codice scritto in questo modo e genera invece l'errore del compilatore C2228.
error C2228: left of '.operator type' must have class/struct/union
Esempio (prima)
typedef int index_t; void bounds_check(index_t index); void login(int column) { bounds_check(column.operator index_t()); // error C2228 }
Esempio (dopo)
typedef int index_t; void bounds_check(index_t index); void login(int column) { bounds_check(column); // removed cast to 'index_t', 'index_t' is an alias of 'int' }
Typename ridondante nei specificatori di tipo elaborato Le versioni precedenti del compilatore consentivano
typename
nei specificatori di tipo elaborato; il codice scritto in questo modo non è semanticamente corretto. Il compilatore non accetta più il codice scritto in questo modo e genera invece l'errore del compilatore C3406.error C3406: 'typename' cannot be used in an elaborated type specifier
Esempio (prima)
template <typename class T> class container;
Esempio (dopo)
template <class T> // alternatively, could be 'template <typename T>'; 'typename' is not elaborating a type specifier in this case class container;
Deduzione dei tipi di matrici da un elenco di inizializzatori Le versioni precedenti del compilatore non supportavano la deduzione dei tipi di matrici da un elenco di inizializzatori. Il compilatore supporta ora questa forma di deduzione del tipo e, di conseguenza, le chiamate a modelli di funzione con gli elenchi di inizializzatori potrebbero essere ambigue o potrebbe essere scelto un altro overload rispetto alle versioni precedenti del compilatore. Per risolvere questi problemi, il programma deve ora specificare in modo esplicito l'overload previsto dal programmatore.
Quando questo nuovo comportamento fa sì che la risoluzione dell'overload consideri un candidato aggiuntivo altrettanto valido come candidato storico, la chiamata diventa ambigua e il compilatore genera l'errore del compilatore C2668 di conseguenza.
error C2668: 'function' : ambiguous call to overloaded function.
Esempio 1: chiamata ambigua a funzione in overload (prima)
// In previous versions of the compiler, code written in this way would unambiguously call f(int, Args...) template <typename... Args> void f(int, Args...); // template <int N, typename... Args> void f(const int (&)[N], Args...); int main() { // The compiler now considers this call ambiguous, and issues a compiler error f({3}); error C2668: 'f' ambiguous call to overloaded function }
Esempio 1: chiamata ambigua a funzione in overload (dopo)
template <typename... Args> void f(int, Args...); // template <int N, typename... Args> void f(const int (&)[N], Args...); int main() { // To call f(int, Args...) when there is just one expression in the initializer list, remove the braces from it. f(3); }
Quando questo nuovo comportamento fa sì che la risoluzione dell'overload consideri un candidato aggiuntivo che sia una corrispondenza migliore rispetto al candidato storico, la chiamata viene risolta in modo univoco al nuovo candidato, causando una modifica del comportamento del programma probabilmente diverso da quanto previsto dal programmatore.
Esempio 2: modifica nella risoluzione dell'overload (prima)
// In previous versions of the compiler, code written in this way would unambiguously call f(S, Args...) struct S { int i; int j; }; template <typename... Args> void f(S, Args...); template <int N, typename... Args> void f(const int *&)[N], Args...); int main() { // The compiler now resolves this call to f(const int (&)[N], Args...) instead f({1, 2}); }
Esempio 2: modifica nella risoluzione dell'overload (dopo)
struct S; // as before template <typename... Args> void f(S, Args...); template <int N, typename... Args> void f(const int *&)[N], Args...); int main() { // To call f(S, Args...), perform an explicit cast to S on the initializer list. f(S{1, 2}); }
Ripristino di avvisi di istruzione switch
Una versione precedente del compilatore ha rimosso avvisi esistenti in precedenza correlati alle
switch
istruzioni. Questi avvisi sono stati ripristinati. Il compilatore genera ora gli avvisi ripristinati e gli avvisi correlati a casi specifici (incluso il caso predefinito) sono ora rilasciati sulla riga contenente il caso che causa l'errore, anziché l'ultima riga dell'istruzione switch. Dal momento che gli avvisi vengono ora emessi su diverse righe rispetto al passato, di conseguenza gli avvisi precedentemente eliminato con#pragma warning(disable:####)
non potranno più essere eliminati come previsto. Per eliminare intenzionalmente questi avvisi, potrebbe essere necessario spostare la direttiva#pragma warning(disable:####)
a una riga sopra il primo caso potenzialmente offensivo. Di seguito sono riportati gli avvisi ripristinati.warning C4060: switch statement contains no 'case' or 'default' labels
warning C4061: enumerator 'bit1' in switch of enum 'flags' is not explicitly handled by a case label
warning C4062: enumerator 'bit1' in switch of enum 'flags' is not handled
warning C4063: case 'bit32' is not a valid value for switch of enum 'flags'
warning C4064: switch of incomplete enum 'flags'
warning C4065: switch statement contains 'default' but no 'case' labels
warning C4808: case 'value' is not a valid value for switch condition of type 'bool'
Warning C4809: switch statement has redundant 'default' label; all possible 'case' labels are given
Esempio di C4063 (prima)
class settings { public: enum flags { bit0 = 0x1, bit1 = 0x2, ... }; ... }; int main() { auto val = settings::bit1; switch (val) { case settings::bit0: break; case settings::bit1: break; case settings::bit0 | settings::bit1: // warning C4063 break; } };
Esempio di C4063 (dopo)
class settings {...}; // as above int main() { // since C++11, use std::underlying_type to determine the underlying type of an enum typedef std::underlying_type<settings::flags>::type flags_t; auto val = settings::bit1; switch (static_cast<flags_t>(val)) { case settings::bit0: break; case settings::bit1: break; case settings::bit0 | settings::bit1: // ok break; } };
Gli esempi di altri avvisi ripristinati vengono forniti nella relativa documentazione.
#include: uso dell'identificatore di directory padre '.'. nel percorso di file (influisce solo su
/Wall
/WX
)Le versioni precedenti del compilatore non è stato rilevato l’utilizzo dell’identificatore di directory padre ‘... ‘ nel percorso delle direttive
#include
. Il codice scritto in questo modo è in genere usato in modo da includere le intestazioni che esistono di fuori del progetto usando in modo non corretto percorsi relativi al progetto. Questo comportamento precedente creava il rischio che il programma potesse essere compilato con l'inclusione di un file di origine diversa rispetto a quello previsto dal programmatore, o che i percorsi relativi non sarebbero stati portabili in altri ambienti di compilazione. Il compilatore ora rileva e invia una notifica al programmatore riguardo il codice scritto in questo modo e genera un avviso del compilatore C4464 facoltativo, se abilitato.warning C4464: relative include path contains '..'
Esempio (prima)
#include "..\headers\C4426.h" // emits warning C4464
Esempio (dopo)
#include "C4426.h" // add absolute path to 'headers\' to your project's include directories
Inoltre, anche se il compilatore non offre una diagnostica specifica, è consigliabile usare anche l'identificatore di directory padre ".." per specificare le directory di inclusione del progetto.
#pragma optimize() estende oltre la fine del file di intestazione (influisce solo su
/Wall
/WX
)Le versioni precedenti del compilatore non rilevavano le modifiche alle impostazioni del flag di ottimizzazione non incluse in un file di intestazione all'interno di un'unità di conversione. Il compilatore ora rileva e invia una notifica al programmatore riguardo il codice scritto in questo modo e genera un avviso del compilatore C4426 facoltativo nella posizione della direttiva
#include
danneggiata, se abilitata. Questo avviso viene generato solo se le modifiche sono in conflitto con i flag di ottimizzazione impostati dagli argomenti della riga di comando nel compilatore.warning C4426: optimization flags changed after including header, may be due to #pragma optimize()
Esempio (prima)
// C4426.h #pragma optimize("g", off) ... // C4426.h ends // C4426.cpp #include "C4426.h" // warning C4426
Esempio (dopo)
// C4426.h #pragma optimize("g", off) ... #pragma optimize("", on) // restores optimization flags set via command-line arguments // C4426.h ends // C4426.cpp #include "C4426.h"
Avviso #pragma non corrispondente (push) e avviso(pop)
Le versioni precedenti del compilatore non rilevavano l'abbinamento delle modifiche di stato
#pragma warning(push)
con le modifiche di stato#pragma warning(pop)
in un file di origine differente e questo raramente rappresenta lo scopo previsto. Questo comportamento precedente creava il rischio che il programma fosse compilato con un set di avvisi abilitato diverso da quello previsto dal programmatore, determinando un probabile comportamento errato in fase di esecuzione senza avvisare. Il compilatore ora rileva e invia una notifica al programmatore riguardo al codice scritto in questo modo e genera un avviso del compilatore C5031 facoltativo nella posizione della direttiva#pragma warning(pop)
corrispondente, se abilitata. Questo avviso include una nota che fa riferimento alla posizione del corrispondente#pragma warning(push)
.warning C5031: #pragma warning(pop): likely mismatch, popping warning state pushed in different file
Esempio (prima)
// C5031_part1.h #pragma warning(push) #pragma warning(disable:####) ... // C5031_part1.h ends without #pragma warning(pop) // C5031_part2.h ... #pragma warning(pop) // pops a warning state not pushed in this source file ... // C5031_part1.h ends // C5031.cpp #include "C5031_part1.h" // leaves #pragma warning(push) 'dangling' ... #include "C5031_part2.h" // matches 'dangling' #pragma warning(push), resulting in warning C5031 ...
Esempio (dopo)
// C5031_part1.h #pragma warning(push) #pragma warning(disable:####) ... #pragma warning(pop) // pops the warning state pushed in this source file // C5031_part1.h ends without #pragma warning(pop) // C5031_part2.h #pragma warning(push) // pushes the warning state pushed in this source file #pragma warning(disable:####) ... #pragma warning(pop) // C5031_part1.h ends // C5031.cpp #include "C5031_part1.h" // #pragma warning state changes are self-contained and independent of other source files or their #include order. ... #include "C5031_part2.h" ...
Benché sia un fatto insolito, a volte il codice scritto in questo modo è intenzionale. Il codice scritto in questo modo è sensibile alle modifiche nell'ordine
#include
. Se possibile, è consigliabile che i file del codice sorgente gestiscano lo stato di avviso in modo autonomo.Avviso di #pragma non corrispondente (push) (influisce solo su
/Wall
/WX
)Le versioni precedenti del compilatore non rilevavano modifiche di stato
#pragma warning(push)
senza corrispondenza alla fine di un'unità di conversione. Il compilatore ora rileva e invia una notifica al programmatore riguardo al codice scritto in questo modo e genera un avviso del compilatore C5032 facoltativo nella posizione di#pragma warning(push)
non corrispondente, se abilitata. Questo avviso viene generato solo se non sono presenti errori di compilazione nell'unità di conversione.warning C5032: detected #pragma warning(push) with no corresponding #pragma warning(pop)
Esempio (prima)
// C5032.h #pragma warning(push) #pragma warning(disable:####) ... // C5032.h ends without #pragma warning(pop) // C5032.cpp #include "C5032.h" ... // C5032.cpp ends -- the translation unit is completed without #pragma warning(pop), resulting in warning C5032 on line 1 of C5032.h
Esempio (dopo)
// C5032.h #pragma warning(push) #pragma warning(disable:####) ... #pragma warning(pop) // matches #pragma warning (push) on line 1 // C5032.h ends // C5032.cpp #include "C5032.h" ... // C5032.cpp ends -- the translation unit is completed without unmatched #pragma warning(push)
Potrebbero essere generati avvisi aggiuntivi in seguito al migliorato rilevamento dello stato della direttiva #pragma warning
Le versioni precedenti del compilatore hanno rilevato
#pragma warning
le modifiche dello stato in modo insufficiente per generare tutti gli avvisi previsti. Questo comportamento comportava il rischio che alcuni avvisi sarebbero stati eliminati in modo efficace in circostanze diverse rispetto a quelle previste dal programmatore. Il compilatore ora tiene traccia#pragma warning
dello stato in modo più affidabile, specialmente in relazione alle modifiche di stato#pragma warning
all'interno dei modelli, e, facoltativamente, genera nuovi avvisi C5031 e C5032 che aiutano il programmatore a rilevare utilizzi imprevisti di#pragma warning(push)
e#pragma warning(pop)
.In seguito al migliorato rilevamento delle modifiche di stato di
#pragma warning
, è ora possibile generare gli avvisi in precedenza eliminati in modo errato oppure quelli relativi ai problemi in precedenza diagnosticati in modo errato.Identificazione del codice non eseguibile migliorata
Le modifiche della Libreria standard C++ e la migliorata capacità di incorporare le chiamate di funzione inline rispetto alle versioni precedenti del compilatore potrebbero consentire al compilatore di dimostrare che determinato codice è ora non eseguibile. Questo nuovo comportamento può comportare nuove e più frequenti visualizzazioni dell'avviso C4720.
warning C4720: unreachable code
In molti casi, l'avviso potrebbe essere generato solo durante la compilazione con ottimizzazioni abilitate, dal momento che le ottimizzazioni potrebbero incorporare più chiamate di funzione, eliminare il codice ridondante o altrimenti consentire di determinare che determinato codice non è eseguibile. Si è osservato che le nuove istanze dell'avviso C4720 si sono verificate di frequente nei blocchi try/catch, in special modo in relazione all'uso di std::find.
Esempio (prima)
try { auto iter = std::find(v.begin(), v.end(), 5); } catch(...) { do_something(); // ok }
Esempio (dopo)
try { auto iter = std::find(v.begin(), v.end(), 5); } catch(...) { do_something(); // warning C4702: unreachable code }
Rimozione dell'ottimizzazione
pow(T, int)
del loop unrollingLe versioni precedenti della libreria standard C++ definivano un modello di funzione
pow(T, int)
che espandeva una chiamata di funzionepow
in una serie di operazioni di moltiplicazione. Questa tecnica accumula un elevato grado di imprecisione a causa della natura delle operazioni a virgola mobile, portando a risultati finali che potrebbero essere significativamente imprecisi. In Visual Studio 2015 Update 1 questo comportamento è stato rimosso per evitare la perdita involontaria di accuratezza quando si usa lapow
funzione . Tuttavia, questa versione dipow
era molto più veloce del calcolo corretto. Se questa modifica causa una regressione significativa delle prestazioni e il progetto non richiede risultati precisi a virgola mobile (ad esempio, il progetto già compilato con /fp:fast), è consigliabile sostituire le chiamate apow
con questa funzione alternativa:template <class T> inline T pow_int(T x, int y) throw() { unsigned int n; if (y >= 0) { n = (unsigned int)(y); } else { n = (unsigned int)(-y); } for (T z = T(1); ; x *= x) { if ((n & 1) != 0) { z *= x; } if ((n >>= 1) == 0) { return (y < 0 ? T(1) / z : z); } } }
Questa implementazione è identica a quella inclusa nelle versioni precedenti di Visual Studio.
Miglioramenti della conformità in Visual Studio 2015 Update 2
Errori e avvisi aggiuntivi potrebbero essere generati in seguito a un supporto parziale per l'espressione SFINAE
Le versioni precedenti del compilatore non analizzavano alcuni tipi di espressioni negli identificatori
decltype
a causa della mancanza di supporto per l'espressione SFINAE. Questo comportamento precedente non è corretto e non è conforme allo standard C++. Grazie ai costanti miglioramenti alla conformità, ora il compilatore analizza le espressioni e ha un supporto parziale per l'espressione SFINAE. Di conseguenza, ora vengono visualizzati avvisi ed errori rilevati nelle espressioni non analizzati dalle versioni precedenti del compilatore.Quando questo nuovo comportamento analizza un'espressione
decltype
che include un tipo che non è ancora stato dichiarato, il compilatore genera l'errore del compilatore C2039 di conseguenza.error C2039: 'type': is not a member of 'global namespace'
Esempio 1: uso di un tipo non dichiarato (prima)
struct s1 { template <typename T> auto f() -> decltype(s2<T>::type::f()); // error C2039 template<typename> struct s2 {}; }
Esempio 1 (dopo)
struct s1 { template <typename> // forward declare s2struct s2; template <typename T> auto f() -> decltype(s2<T>::type::f()); template<typename> struct s2 {}; }
Quando questo nuovo comportamento analizza un'espressione che non include l'uso necessario della parola chiave
decltype
per specificare che un nome associato è un tipo, il compilatore emette l'avviso del compilatore C4346 insieme all'errore del compilatore C2923.warning C4346: 'S2<T>::Type': dependent name is not a type
error C2923: 's1': 'S2<T>::Type' is not a valid template type argument for parameter 'T'
Esempio 2: il nome dipendente non è un tipo (prima)
template <typename T> struct s1 { typedef T type; }; template <typename T> struct s2 { typedef T type; }; template <typename T> T declval(); struct s { template <typename T> auto f(T t) -> decltype(t(declval<S1<S2<T>::type>::type>())); // warning C4346, error C2923 };
Esempio 2 (dopo)
template <typename T> struct s1 {...}; // as above template <typename T> struct s2 {...}; // as above template <typename T> T declval(); struct s { template <typename T> auto f(T t) -> decltype(t(declval<S1<typename S2<T>::type>::type>())); };
volatile
Le variabili membro impediscono costruttori e operatori di assegnazione definiti in modo implicito Le versioni precedenti del compilatore hanno consentito a una classe convolatile
variabili membro di avere costruttori di copia/spostamento predefiniti e gli operatori di assegnazione di copia/spostamento predefiniti generati automaticamente. Questo comportamento precedente non è corretto e non è conforme allo standard C++. Il compilatore considera ora una classe con variabili membro volatili per avere operatori di costruzione e assegnazione non semplici che impediscono la generazione automatica delle implementazioni predefinite di questi operatori. Quando una classe di questo tipo è un membro di un'unione (o un'unione anonima all'interno di una classe), i costruttori di copia/spostamento e gli operatori di assegnazione di copia/spostamento dell'unione (o della classe contenente l'unione non anonima) verranno definiti in modo implicito come eliminati. Il tentativo di costruire o copiare l'unione, o la classe che contiene l'unione anonima, senza definirli in modo esplicito è un errore e, di conseguenza, il compilatore genera l'errore C2280.error C2280: 'B::B(const B &)': attempting to reference a deleted function
Esempio (prima)
struct A { volatile int i; volatile int j; }; extern A* pa; struct B { union { A a; int i; }; }; B b1 {*pa}; B b2 (b1); // error C2280
Esempio (dopo)
struct A { int i;int j; }; extern volatile A* pa; A getA() // returns an A instance copied from contents of pa { A a; a.i = pa->i; a.j = pa->j; return a; } struct B; // as above B b1 {GetA()}; B b2 (b1); // error C2280
Le funzioni membro statiche non supportano i qualificatori CV.
Le versioni precedenti di Visual C++ 2015 consentivano alle funzioni membro statiche di avere qualificatori cv. Questo comportamento è dovuto a una regressione in Visual C++ 2015 e Visual C++ 2015 Update 1; Visual C++ 2013 e versioni precedenti di Visual C++ rifiutano il codice scritto in questo modo. Il comportamento di Visual C++ 2015 e Visual C++ 2015 Update 1 non è corretto e non è conforme allo standard C++. Visual Studio 2015 Update 2 non accetta il codice scritto in questo modo e genera l'errore del compilatore C2511.
error C2511: 'void A::func(void) const': overloaded member function not found in 'A'
Esempio (prima)
struct A { static void func(); }; void A::func() const {} // C2511
Esempio (dopo)
struct A { static void func(); }; void A::func() {} // removed const
La dichiarazione anticipata dell'enumerazione non è consentita nel codice WinRT (influisce solo su
/ZW
)Il codice compilato per Windows Runtime (WinRT) non consente
enum
tipi da dichiarare anticipatamente, in modo analogo a quando il codice C++ gestito viene compilato per .Net Framework usando l'opzione del compilatore/clr
. Questo comportamento garantisce che le dimensioni di un'enumerazione siano sempre note e possano essere proiettate correttamente nel sistema di tipi WinRT. Il compilatore non accetta il codice scritto in questo modo e genera gli errori C2599 e C3197.error C2599: 'CustomEnum': the forward declaration of a WinRT enum is not allowed
error C3197: 'public': can only be used in definitions
Esempio (prima)
namespace A { public enum class CustomEnum: int32; // forward declaration; error C2599, error C3197 } namespace A { public enum class CustomEnum: int32 { Value1 }; } public ref class Component sealed { public: CustomEnum f() { return CustomEnum::Value1; } };
Esempio (dopo)
// forward declaration of CustomEnum removed namespace A { public enum class CustomEnum: int32 { Value1 }; } public ref class Component sealed { public: CustomEnum f() { return CustomEnum::Value1; } };
È possibile che le funzioni new o delete dell'operatore non membro in overload non siano dichiarate come inline (livello 1 (
/W1
) attivato per impostazione predefinita)Le versioni precedenti del compilatore non generano un avviso quando le funzioni di eliminazione dell'operatore non membro new e operator delete vengono dichiarate inline. Il codice scritto in questo modo non è valido, la diagnostica non è necessaria, e può causare problemi di memoria difficili da diagnosticare derivanti dalla mancata corrispondenza degli operatori new e delete, in particolare quando sono usati insieme con la deallocazione dimensionata. Ora il compilatore genera l'avviso C4595 per identificare il codice scritto in questo modo.
warning C4595: 'operator new': non-member operator new or delete functions may not be declared inline
Esempio (prima)
inline void* operator new(size_t sz) // warning C4595 { ... }
Esempio (dopo)
void* operator new(size_t sz) // removed inline { ... }
La correzione del codice scritto in questo modo potrebbe richiedere lo spostamento delle definizioni dell'operatore da un file di intestazione a un file di origine corrispondente.
Miglioramenti della conformità in Visual Studio 2015 Update 3
std::is_convertable ora rileva l'auto assegnazione (libreria standard) Le versioni precedenti del
std::is_convertable
tipo tratto non rilevavano correttamente l'auto assegnazione di un tipo di classe se il suo costruttore di copia viene eliminato o reso privato. Orastd::is_convertable<>::value
è impostato correttamente sufalse
quando è applicato a un tipo di classe con costruttore di copia privato o eliminato.A questa modifica non è associata alcuna diagnostica del compilatore.
Esempio
#include <type_traits> class X1 { public: X1(const X1&) = delete; }; class X2 { private: X2(const X2&); }; static_assert(std::is_convertible<X1&, X1>::value, "BOOM");static_assert(std::is_convertible<X2&, X2>::value, "BOOM");
Nelle versioni precedenti di Visual C++, le asserzioni statiche nella parte inferiore di questo esempio passano perché
std::is_convertable<>::value
non è stato impostato correttamente sutrue
. Orastd::is_convertable<>::value
è impostato correttamente sufalse
causando l'esito negativo delle asserzioni statiche.I costruttori di copia e di spostamento semplici impostati come predefiniti o eliminati rispettano gli identificatori di accesso
Le versioni precedenti del compilatore non verificavano l'identificatore di accesso dei costruttori di copia o spostamento semplici impostati come predefiniti o eliminati prima di consentirne la chiamata. Questo comportamento precedente non è corretto e non è conforme allo standard C++. In alcuni casi questo comportamento precedente creava un rischio di generazione silenziosa di codice errato, determinando un comportamento imprevedibile in fase di runtime. Il compilatore ora controlla l'identificatore di accesso dei costruttori di copia e spostamento semplici impostati come predefiniti o eliminati per determinare se può essere effettuata la chiamata e, se non è possibile, genera di conseguenza un avviso del compilatore C2248.
error C2248: 'S::S' cannot access private member declared in class 'S'
Esempio (prima)
class S { public: S() = default; private: S(const S&) = default; }; void f(S); // pass S by value int main() { S s; f(s); // error C2248, can't invoke private copy constructor }
Esempio (dopo)
class S { public: S() = default; private: S(const S&) = default; }; void f(const S&); // pass S by reference int main() { S s; f(s); }
Deprecazione del supporto per il codice ATL con attributi (livello 1 (
/W1
) attivato per impostazione predefinita)Le versioni precedenti del compilatore supportavano il codice ATL con attributi. Come fase successiva della rimozione del supporto per il codice ATL con attributi iniziato in Visual C++ 2008, il codice ATL con attributi è stato deprecato. Ora il compilatore genera l'avviso C4467 per consentire l'identificazione di questo tipo di codice deprecato.
warning C4467: Usage of ATL attributes is deprecated
Se si vuole continuare a usare il codice ATL con attributi fino a quando il supporto non viene rimosso dal compilatore, è possibile disabilitare questo avviso passando gli argomenti della
/Wv:18
riga di comando o/wd4467
al compilatore o aggiungendo#pragma warning(disable:4467)
nel codice sorgente.Esempio 1 (prima)
[uuid("594382D9-44B0-461A-8DE3-E06A3E73C5EB")] class A {};
Esempio 1 (dopo)
__declspec(uuid("594382D9-44B0-461A-8DE3-E06A3E73C5EB")) A {};
In alcuni casi potrebbe essere necessario o preferibile creare un file IDL file per evitare l'uso degli attributi ATL deprecati, come nell'esempio di codice riportato di seguito
Esempio 2 (prima)
[emitidl]; [module(name="Foo")]; [object, local, uuid("9e66a290-4365-11d2-a997-00c04fa37ddb")] __interface ICustom { HRESULT Custom([in] long l, [out, retval] long *pLong); [local] HRESULT CustomLocal([in] long l, [out, retval] long *pLong); }; [coclass, appobject, uuid("9e66a294-4365-11d2-a997-00c04fa37ddb")] class CFoo : public ICustom { // ... };
Creare innanzitutto il file *.idl; Il file generato da vc140.idl può essere usato per ottenere un file *.idl contenente le interfacce e le annotazioni.
Quindi, aggiungere una fase MIDL alla compilazione per assicurarsi che le definizioni dell'interfaccia di C++ vengano generate.
Esempio 2 IDL (dopo)
import "docobj.idl"; [ object,local,uuid(9e66a290-4365-11d2-a997-00c04fa37ddb) ] interface ICustom : IUnknown { HRESULT Custom([in] long l, [out,retval] long *pLong); [local] HRESULT CustomLocal([in] long l, [out,retval] long *pLong); }; [ version(1.0), uuid(29079a2c-5f3f-3325-99a1-3ec9c40988bb) ] library Foo { importlib("stdole2.tlb"); importlib("olepro32.dll"); [ version(1.0), appobject,uuid(9e66a294-4365-11d2-a997-00c04fa37ddb) ] coclass CFoo { interface ICustom; }; }
Usare quindi ATL direttamente nel file di implementazione, come illustrato nell'esempio di codice che segue.
Esempio 2 Implementazione (dopo)
#include <idl.header.h> #include <atlbase.h> class ATL_NO_VTABLE CFooImpl : public ICustom, public ATL::CComObjectRootEx<CComMultiThreadModel> { public: BEGIN_COM_MAP(CFooImpl) COM_INTERFACE_ENTRY(ICustom) END_COM_MAP() };
File di intestazione precompilata (PCH) e direttive di #include non corrispondenti (influisce solo su
/Wall
/WX
)Le versioni precedenti del compilatore accettavano le direttive
#include
non corrispondenti nei file di origine tra le compilazioni-Yc
e-Yu
quando venivano usati file di intestazione precompilata (PCH). Il codice scritto in questo modo non è più accettato dal compilatore. Il compilatore ora genera un avviso CC4598 per consentire l'identificazione delle direttive#include
non corrispondenti quando si usano i file PCH.warning C4598: 'b.h': included header file specified for Ycc.h at position 2 does not match Yuc.h at that position
Esempio (prima):
X.cpp (-Ycc.h)
#include "a.h" #include "b.h" #include "c.h"
Z.cpp (-Yuc.h)
#include "b.h" #include "a.h" // mismatched order relative to X.cpp #include "c.h"
Esempio (dopo)
X.cpp (-Ycc.h)
#include "a.h" #include "b.h" #include "c.h"
Z.cpp (-Yuc.h)
#include "a.h" #include "b.h" // matched order relative to X.cpp #include "c.h"
File di intestazione precompilata (PCH) e directory di inclusione non corrispondenti (influisce solo su
/Wall
/WX
)Le versioni precedenti del compilatore accettavano argomenti della riga di comando con directory di inclusione non corrispondenti tra le compilazioni
-I
e-Yc
quando si utilizzavano file di intestazione precompilati (PCH). Il codice scritto in questo modo non è più accettato dal compilatore. Il compilatore ora genera un avviso CC4599 per consentire l'identificazione degli argomenti della riga di comando delle directory di inclusione non corrispondenti (-I
) quando si usano i file PCH.warning C4599: '-I..' : specified for Ycc.h at position 1 does not match Yuc.h at that position
Esempio (prima)
cl /c /Wall /Ycc.h -I.. X.cpp cl /c /Wall /Yuc.h Z.cpp
Esempio (dopo)
cl /c /Wall /Ycc.h -I.. X.cpp cl /c /Wall /Yuc.h -I.. Z.cpp
Novità di C++ in Visual Studio 2013
Supporto migliorato degli standard ISO C/C++
Compilatore
MSVC supporta queste funzionalità del linguaggio ISO C++11:
- Argomenti di modello predefiniti per i modelli di funzione.
- Costruttori deleganti
- Operatori di conversione espliciti.
- Elenchi di inizializzatori e inizializzazione uniforme.
- Stringhe letterali grezze.
- Modelli variadic.
- Modelli di alias.
- Funzioni eliminate.
- Inizializzatori di membri dati non statici (NSDMI).
- Funzioni predefinite. *
- Supporta queste funzionalità del linguaggio ISO C99:
- _Bool
- Letterali composti.
- Inizializzatori designati.
- Combinazione di dichiarazioni con codice.
- La conversione di valori letterali stringa in valori modificabili può essere disabilitata usando la nuova opzione
/Zc:strictStrings
del compilatore . In C++98, la conversione dai letterali di stringa achar*
(e dai letterali di stringhe ampie awchar_t*
) è stata deprecata. In C++11 la conversione è stata rimossa completamente. Sebbene il compilatore possa conformarsi strettamente allo standard, offre invece l'opzione/Zc:strictStrings
per consentire di controllare la conversione. Per impostazione predefinita, l'opzione è disattivata. Si noti che quando si usa questa opzione in modalità di debug, la libreria STL non verrà compilata. - I cast di riferimento rvalue/lvalue. Con i riferimenti rvalue, C++11 può distinguere chiaramente tra lvalues e rvalues. In precedenza, il compilatore non forniva questa funzionalità in scenari di cast specifici. È stata aggiunta una nuova opzione del compilatore per
/Zc:rvalueCast
rendere il compilatore conforme al Working Paper del linguaggio C++(vedere la sezione 5.4, [expr.cast]/1). Il comportamento predefinito quando questa opzione non viene specificata è identica a quella di Visual Studio 2012.
Annotazioni
Per le funzioni predefinite, l'uso di =default per richiedere costruttori di spostamento per membro e operatori di assegnazione per spostamento non è supportato.
Librerie C99
Le dichiarazioni e le implementazioni vengono aggiunte per le funzioni mancanti in queste intestazioni: math.h, ctype.h, wctype.h, stdio.h, stdlib.h e wchar.h. Vengono aggiunte anche le nuove intestazioni complex.h, stdbool.h, fenv.h e inttypes.h e le implementazioni per tutte le funzioni dichiarate. Sono disponibili nuove intestazioni wrapper C++ (ccomplex, cfenv, cinttypes, ctgmath) e diverse altre vengono aggiornate (ccomplex, cctype, clocale, cmath, cstdint, cstdio, cstring, cwchar e cwctype).
Libreria di modelli standard
Supporto per gli operatori di conversione espliciti C++11, elenchi di inizializzatori, enumerazioni con ambito e modelli variadic. Tutti i contenitori supportano ora i requisiti degli elementi con granularità fine C++11. Supporto per queste funzionalità di C++14:
- "Funtori di operatori trasparenti" minore<>, maggiore<>, più<>, moltiplica<> e così via.
- make_unique<T>(args...) e make_unique<T[]>(n)
- cbegin()/cend(), rbegin()/rend() e crbegin()/crend() funzioni non membro.
- <atomic> ha ricevuto numerosi miglioramenti delle prestazioni.
- < > type_traits ricevuto importanti correzioni di stabilizzazione e codice.
Modifiche radicali
Questo supporto migliorato per gli standard ISO C/C++ potrebbe richiedere modifiche al codice esistente in modo che sia conforme a C++11 e venga compilato correttamente in Visual C++ in Visual Studio 2013.
Miglioramenti della libreria Visual C++
- È stato aggiunto L'SDK REST C++. Ha un'implementazione C++ moderna dei servizi REST.
- Il supporto delle trame AMP C++ è migliorato. Include ora il supporto per mipmap e nuove modalità di campionamento.
- Le attività PPL supportano più tecnologie di pianificazione e debug asincrono. Le nuove API consentono la creazione di attività PPL sia per i risultati normali che per le condizioni di eccezione.
Prestazioni dell'applicazione C++
- Auto-Vectorizer ora riconosce e ottimizza più modelli C++ per velocizzare l'esecuzione del codice.
- Miglioramenti della qualità del codice della piattaforma ARM e della microarchitettura Atom.
- __vectorcall convenzione di chiamata viene aggiunta. Passare argomenti di tipo vettore usando la convenzione di chiamata __vectorcall per usare i registri vettoriali.
- Nuove opzioni del linker. I
/Gw
commutatori (compilatore) e/Gy
(assembler) consentono di ottimizzare il linker per produrre file binari più snella. - Supporto della memoria condivisa C++ AMP per ridurre o eliminare la copia dei dati tra CPU e GPU.
Miglioramenti di Ottimizzazione pgo (Profile Guided Optimization)
- Miglioramenti delle prestazioni derivanti da una riduzione del working set di app ottimizzate tramite PGO.
- Nuovo PGO per lo sviluppo di app di Windows Runtime.
Supporto per lo sviluppo di app di Windows Runtime
Supporto per i tipi boxed negli struct valore.
È ora possibile definire tipi di valore usando campi che possono essere Null, ad esempio anziché
IBox<int>^
int
. Ciò significa che i campi possono avere un valore o essere uguali anullptr
.Informazioni più dettagliate sulle eccezioni.
C++/CX supporta il nuovo modello di errore di Windows che consente l'acquisizione e la propagazione di informazioni dettagliate sulle eccezioni nell'interfaccia binaria dell'applicazione (ABI); sono inclusi stack di chiamate e stringhe di messaggi personalizzate.
Object::ToString() è ora virtuale.
È ora possibile eseguire l'override di ToString nei tipi di riferimento di Windows Runtime definiti dall'utente.
Supporto per le API deprecate.
Le API pubbliche di Windows Runtime possono ora essere contrassegnate come deprecate e date un messaggio personalizzato visualizzato come avviso di compilazione e possono fornire indicazioni sulla migrazione.
Miglioramenti del debugger.
Supporto per il debug di interoperabilità native/JavaScript, la diagnosi delle eccezioni di Windows Runtime e il debug del codice asincrono (sia Windows Runtime che PPL).
Annotazioni
Oltre alle funzionalità e ai miglioramenti specifici di C++descritti in questa sezione, altri miglioramenti in Visual Studio consentono anche di scrivere app di Windows Runtime migliori.
Miglioramenti della diagnostica
- Miglioramenti del debugger. Supporto per il debug asincrono e il debug Just My Code.
- Categorie di analisi del codice. È ora possibile visualizzare l'output classificato dell'analizzatore del codice per individuare e correggere i difetti del codice.
- Diagnostica XAML. È ora possibile diagnosticare i problemi di velocità di risposta dell'interfaccia utente e di utilizzo della batteria nel codice XAML.
- Miglioramenti del debug della grafica e della GPU.
- Acquisizione remota e riproduzione su dispositivi reali.
- Debug simultaneo di C++ AMP e CPU.
- Diagnostica del runtime C++ AMP migliorata.
- Debug di traccia dello shader di calcolo HLSL.
Miglioramenti della grafica 3D
- Supporto della pipeline di contenuto immagine per il formato DDS alfa pre-moltiplicato.
- L'editor di immagini utilizza internamente l'alfa pre-moltiplicato per il rendering, evitando così artefatti di rendering come gli aloni scuri.
- Editor di immagini e modelli. La creazione di filtri definiti dall'utente è ora supportata in Progettazione shader nell'editor di immagini e nell'editor di modelli.
IDE e produttività
Miglioramento della formattazione del codice. È possibile applicare altre impostazioni di formattazione al codice C++. Usando queste impostazioni, è possibile controllare il posizionamento di nuove righe di parentesi graffe e parole chiave, rientro, spaziatura e ritorno a capo riga. Il codice viene formattato automaticamente quando si completano istruzioni e blocchi e quando si incolla il codice in un file.
Completamento parentesi graffa. Il codice C++ completa ora automaticamente i caratteri di chiusura che corrispondono a questi caratteri di apertura:
- { (parentesi graffa)
- [ (parentesi quadrata)
- ( (parentesi)
- ' (virgoletta singola)
- " (virgolette doppie)
Funzionalità di completamento automatico di C++ aggiuntive.
- Aggiunge punto e virgola per i tipi di classe.
- Completa le parentesi per i valori letterali stringa non elaborati.
- Completa i commenti su più righe (/* */)
Trova tutti i riferimenti ora risolve automaticamente e filtra i riferimenti in background dopo aver visualizzato l'elenco di corrispondenze testuali.
Context-Based Filtraggio elenco dei membri. I membri inaccessibili vengono filtrati dagli elenchi di membri di IntelliSense. Ad esempio, i membri privati non vengono visualizzati nell'elenco dei membri, a meno che non si modifichi il codice che implementa il tipo. Mentre l'elenco dei membri è aperto, è possibile premere CTRL+J per rimuovere un livello di filtro (si applica solo alla finestra dell'elenco dei membri corrente). È possibile premere di nuovo CTRL+J per rimuovere il filtro testuale e visualizzare ogni membro.
Scorrimento della Guida dei parametri. La firma della funzione visualizzata nel tooltip della guida sui parametri ora cambia in base al numero di parametri che hai effettivamente digitato, invece di mostrare semplicemente una firma arbitraria e non aggiornarla in base al contesto attuale. La Guida ai parametri funziona correttamente anche quando viene visualizzata nelle funzioni annidate.
Attiva/Disattiva il file di intestazione o codice. È ora possibile alternare un'intestazione e il file di codice corrispondente usando un comando nel menu di scelta rapida o una scelta rapida da tastiera.
Finestra ridimensionabile delle proprietà del progetto C++
Generazione automatica del codice del gestore eventi in C++/CX e C++/CLI. Quando si digita codice per aggiungere un gestore eventi in un file di codice C++/CX o C++/CLI, l'editor può generare automaticamente l'istanza del delegato e la definizione del gestore eventi. Viene visualizzata una finestra di suggerimento quando è possibile generare automaticamente il codice del gestore di eventi.
Miglioramento della consapevolezza DPI. L'impostazione di Riconoscimento DPI per i file manifest dell'applicazione adesso supporta l'impostazione "Per Monitor High DPI Aware".
Cambio di configurazione più veloce. Per le applicazioni di grandi dimensioni, il cambio delle configurazioni, in particolare le successive operazioni di cambio, viene eseguito molto più rapidamente.
Efficienza del tempo di costruzione. Numerose ottimizzazioni e utilizzo multicore rendono le compilazioni più veloci, soprattutto per progetti di grandi dimensioni. Anche le compilazioni incrementali per le applicazioni C++ con riferimenti a WinMD C++ sono molto più veloci.
Novità di C++ in Visual Studio 2012
Supporto migliorato degli standard C++11
Libreria di modelli standard
- Supporto per le nuove intestazioni STL: <atomic>, <chrono>, <condition_variable>, <filesystem>, <future>, <mutex>, <ratio> e <thread>.
- Per ottimizzare l'utilizzo delle risorse di memoria, i contenitori sono ora più piccoli. Ad esempio, in modalità di versione x86 con le impostazioni predefinite,
std::vector
è stato ridotto da 16 byte in Visual Studio 2010 a 12 byte in Visual Studio 2012 edstd::map
è stato ridotto da 16 byte in Visual Studio 2010 a 8 byte in Visual Studio 2012. - Come consentito ma non richiesto dallo standard C++11, sono stati implementati iteratori SCARY.
Altri miglioramenti di C++11
Ciclo for che utilizza intervalli. È possibile scrivere cicli più affidabili che funzionano con matrici, contenitori STL e raccolte di Windows Runtime nel formato per ( for-range-declaration : expression ). Questo fa parte del supporto del linguaggio principale.
Le espressioni lambda senza stato, ovvero blocchi di codice che iniziano con un introducer lambda vuoto [] e non acquisiscono variabili locali, sono ora convertibili in modo implicito in puntatori a funzione come richiesto dallo standard C++11.
Supporto delle enumerazioni con ambito. Ora è supportata la enum class di C++ enum-key. Il codice seguente illustra come questa chiave dell'enumerazione differisce dal precedente comportamento dell'enumerazione.
enum class Element { Hydrogen, Helium, Lithium, Beryllium }; void func1(Element e); func1(Hydrogen); // error C2065: 'Hydrogen' : undeclared identifier func1(Element::Helium); // OK
Supporto per lo sviluppo di app di Windows Runtime
- Modello di interfaccia utente basato su XAML nativo. Per le app di Windows Runtime, puoi usare il nuovo modello di interfaccia utente basato su XAML nativo.
- Estensioni del componente Visual C++. Queste estensioni semplificano l'utilizzo di oggetti Windows Runtime, che sono una parte necessaria delle app di Windows Runtime. Per altre informazioni, vedere Roadmap for Windows Runtime apps using C++ and Visual C++ language reference (C++/CX) (Guida di orientamento per le app Windows Runtime con C++ e Riferimenti al linguaggio Visual C++ (C++/CX)
- Giochi DirectX. Puoi sviluppare giochi coinvolgenti usando il nuovo supporto DirectX per le app di Windows Runtime.
- Interoperabilità XAML/DirectX. Le app di Windows Runtime che usano sia XAML che DirectX ora interagiscono in modo efficiente.
- Sviluppo di DLL del componente Windows Runtime. Lo sviluppo di DLL dei componenti rende estendibile l'ambiente Windows Runtime.
Compilatore e Linker
- Vettore automatico. Il compilatore analizza i cicli nel codice e, ove possibile, genera istruzioni che usano i registri vettoriali e le istruzioni presenti in tutti i processori moderni. In questo modo i cicli vengono eseguiti più velocemente. Le istruzioni del processore sono note come SSE, per le estensioni SIMD di streaming. Non è necessario abilitare o richiedere questa ottimizzazione perché viene applicata automaticamente.
-
Parallelizzatore automatico. Il compilatore può analizzare i cicli nel codice e generare istruzioni che distribuiscono i calcoli tra più core o processori. In questo modo i cicli possono essere eseguiti più velocemente. È necessario richiedere questa ottimizzazione perché non è abilitata per impostazione predefinita. In molti casi, consente di includere un oggetto
#pragma loop(hint_parallel(N))
nel codice immediatamente prima dei cicli che si desidera parallelizzare. - Il vettore automatico e il parallelizzatore automatico possono interagire in modo che i calcoli vengano distribuiti tra più core e il codice in ogni core usi i registri vettoriali.
Novità di Visual Studio 2012 Update 1
Usare Windows XP come destinazione quando si compila il codice C++. È possibile utilizzare il compilatore e le librerie Microsoft C++ per mirare a Windows XP e Windows Server 2003.
Supporto per la programmazione parallela
C++ Parallelismo Massivo Accelerato (AMP)
C++ AMP accelera l'esecuzione del codice C++ sfruttando l'hardware parallelo dei dati che normalmente è presente come GPU in una scheda grafica discreta. Il modello di programmazione C++ AMP include matrici multidimensionali, indicizzazione, trasferimento di memoria, tiling e una libreria di funzioni matematiche. Usando le estensioni del linguaggio C++ AMP e le restrizioni del compilatore, è possibile controllare il modo in cui i dati vengono spostati dalla CPU alla GPU e indietro.
Risoluzione dei problemi di sistema. L'esperienza di debug per le app che usano C++ AMP per definire come destinazione la GPU è simile al debug per altre app C++. Sono incluse le nuove aggiunte di debug parallele menzionate in precedenza.
Profilatura. È ora disponibile il supporto della profilatura per l'attività GPU basata su C++ AMP e altri modelli di programmazione basati su Direct3D.
Miglioramenti generali della programmazione parallela
Con il passaggio dell'hardware alle architetture multi-core e molti core, gli sviluppatori non possono più affidarsi a velocità di clock sempre crescenti da singoli core. Il supporto della programmazione parallela nel runtime di concorrenza consente agli sviluppatori di sfruttare queste nuove architetture. In Visual Studio 2010 sono state introdotte potenti librerie di parallelizzazione C++ come la libreria parallel patterns, insieme alle funzionalità per sfruttare i vantaggi della concorrenza esprimendo pipeline sofisticate del flusso di dati. In Visual Studio 2012 queste librerie sono state estese per offrire prestazioni migliori, maggiore controllo e supporto più avanzato per i modelli paralleli più necessari per gli sviluppatori. L'ampiezza dell'offerta include ora:
- Modello di programmazione avanzato basato su attività che supporta asincronia e continuazioni.
- Algoritmi paralleli, che supportano il parallelismo fork-join (parallel_for, parallel_for con affinità, parallel_for_each, parallel_sort, parallel_reduce, parallel_transform).
- Contenitori sicuri per la concorrenza, che forniscono versioni thread-safe di strutture dati std, come priority_queue, queue, vector e map.
- Libreria di agenti asincroni, che gli sviluppatori possono usare per esprimere le pipeline di flussi di dati che naturalmente scomponeno in unità simultanee.
- Un'utilità di pianificazione personalizzabile e un gestore di risorse per facilitare la composizione uniforme dei modelli in questo elenco.
Miglioramenti generali del debug parallelo
Oltre alla finestra Attività parallele e Stack paralleli, Visual Studio 2012 offre una nuova finestra Osservazione parallela in modo da poter esaminare i valori di un'espressione in tutti i thread e i processi ed eseguire l'ordinamento e il filtro sul risultato. È anche possibile usare i propri visualizzatori per estendere la finestra ed è possibile sfruttare il nuovo supporto multiprocesso in tutte le finestre degli strumenti.
IDE
Supporto dei modelli di Visual Studio. È ora possibile usare la tecnologia Modelli di Visual Studio per creare modelli di progetto e di elemento C++.
Caricamento asincrono della soluzione. I progetti vengono ora caricati in modo asincrono, ovvero le parti chiave della soluzione, in modo da poter iniziare a lavorare più velocemente.
Distribuzione automatica per il debug remoto. La distribuzione di file per il debug remoto in Visual C++ è stata semplificata. L'opzione Distribuisci nel menu di scelta rapida del progetto copia automaticamente nel computer remoto i file specificati nelle proprietà di configurazione del debug. La copia manuale dei file nel computer remoto non è più necessaria.
IntelliSense C++/CLI. C++/CLI include ora il supporto completo di IntelliSense. Le funzionalità di IntelliSense, ad esempio Informazioni rapide, Guida parametri, Elenca membri e Completamento automatico funzionano ora per C++/CLI. Inoltre, gli altri miglioramenti di IntelliSense e IDE elencati in questo documento funzionano anche per C++/CLI.
Descrizioni comando di IntelliSense più avanzate. Le descrizioni rapide di IntelliSense per C++ ora mostrano informazioni sullo stile dei commenti della documentazione XML più ricche. Se si utilizza un'API da una libreria, ad esempio C++ AMP, che include commenti di documentazione XML, il fumetto descrittivo di IntelliSense mostra ulteriori informazioni oltre alla semplice dichiarazione. Inoltre, se il codice contiene i commenti di documentazione XML, le informazioni nei tooltip di IntelliSense visualizzeranno le informazioni più complete.
Costrutti di codice C++. La struttura di codice è disponibile per switch, if-else, ciclo for e altri costrutti di codice di base, nell'elenco a discesa Elenco Membri. Selezionare un frammento di codice dall'elenco per inserirlo nel codice e quindi compilare la logica richiesta. È anche possibile creare parti di codice personalizzate da usare nell'editor.
Miglioramenti dei membri dell'elenco L'elenco a discesa Elenca membri viene visualizzato automaticamente durante la digitazione del codice nell'editor di codice. I risultati vengono filtrati, in modo che vengano visualizzati solo i membri pertinenti durante la digitazione. È possibile controllare il tipo di logica di filtro usata dall'Elenco Membri, nella finestra di dialogo Opzioni in Editor di testo>C/C++>Avanzati.
Colorazione semantica. Per impostazione predefinita, i tipi, le enumerazioni, le macro e altri token C++hanno la colorazione.
Evidenziazione dei riferimenti. La selezione di un simbolo evidenzia ora tutte le istanze del simbolo nel file corrente. Premere Ctrl+Shift+Freccia su o Ctrl+Shift+Freccia giù per spostarsi tra i riferimenti evidenziati. È possibile disattivare questa funzionalità nella finestra di dialogo Opzioni, in Editor> di testoC/C++>Avanzate.
Strumenti di gestione del ciclo di vita delle applicazioni
Analisi statica del codice
L'analisi statica per C++ è stata aggiornata per fornire informazioni più dettagliate sul contesto degli errori, più regole di analisi e risultati di analisi migliori. Nella nuova finestra Analisi codice è possibile filtrare i messaggi in base a parole chiave, progetto e gravità. Quando si seleziona un messaggio nella finestra, la riga nel codice in cui è stato attivato il messaggio viene evidenziata nell'editor di codice. Per determinati avvisi C++, il messaggio elenca le righe di origine che mostrano il percorso di esecuzione che porta all'avviso; sono evidenziati i punti decisionali e i motivi per l'esecuzione di tale percorso specifico. L'analisi del codice è inclusa nella maggior parte delle edizioni di Visual Studio 2012. Nelle edizioni Professional, Premium e Ultimate sono incluse tutte le regole. Nelle edizioni Express per Windows 8 e Windows Phone sono inclusi solo gli avvisi più critici. L'analisi del codice non è inclusa nell'edizione Express per Il Web. Ecco alcuni altri miglioramenti dell'analisi del codice:
- I nuovi avvisi di concorrenza consentono di evitare bug di concorrenza assicurandosi di usare le discipline di blocco corrette nei programmi C/C++ multithreading. L'analizzatore rileva potenziali condizioni di gara, inversioni degli ordini di blocco, violazioni del contratto di blocco tra chiamante e chiamato, errori di operazioni di sincronizzazione non corrispondenti e altri bug di concorrenza.
- È possibile specificare le regole C++ da applicare alle esecuzioni di analisi del codice usando i set di regole.
- Nella finestra Analisi codice è possibile inserire nel codice sorgente un pragma che elimina un avviso selezionato.
- È possibile migliorare l'accuratezza e la completezza dell'analisi statica del codice usando la nuova versione del linguaggio di annotazione del codice sorgente Microsoft (SAL) per descrivere come una funzione usa i relativi parametri, i presupposti su di essi e le garanzie che fa al termine.
- Supporto per progetti C++ a 64 bit.
Framework aggiornato di unit test
Usare il nuovo framework di unit test C++ in Visual Studio per scrivere unit test C++. Aggiungere un nuovo progetto di unit test alla soluzione C++ esistente individuando il modello Progetto unit test C++ nella categoria Visual C++ nella finestra di dialogo Nuovo progetto. Iniziare a scrivere gli unit test nello stub di codice TEST_METHOD generato nel file Unittest1.cpp. Quando il codice di test è scritto, compila la soluzione. Quando si desidera eseguire i test, aprire una finestra di Esplora Test unitari scegliendo Visualizza>Altre finestre>Esplora Test unitari, e quindi scegliere Esegui test selezionato dal menu di scelta rapida per il test selezionato. Al termine dell'esecuzione del test, è possibile visualizzare i risultati dei test e informazioni aggiuntive sull'analisi dello stack nella stessa finestra.
Grafici delle dipendenze dell'architettura
Per comprendere meglio il codice, è ora possibile generare grafici delle dipendenze per il file binario, la classe, lo spazio dei nomi e includere i file in una soluzione. Sulla barra dei menu scegliere Architettura>Genera grafo delle dipendenze e quindi Per soluzione o Per Includi file per generare un grafico delle dipendenze. Al termine della generazione del grafo, è possibile esplorarlo espandendo ogni nodo, apprendendo le relazioni di dipendenza spostandosi tra nodi e sfogliando il codice sorgente scegliendo Visualizza contenuto nel menu di scelta rapida per un nodo. Per generare un grafico delle dipendenze per i file di inclusione, scegliere Genera grafico dei file di inclusione nel menu di scelta rapida per un file di codice sorgente *.cpp o un file di intestazione *.h.
Esploratore di architettura
Usando Esplora architetture, è possibile esplorare gli asset nella soluzione, nei progetti o nei file C++. Sulla barra dei menu scegliere Architettura>Windows>Esplora Architettura. È possibile selezionare un nodo a cui si è interessati, ad esempio Visualizzazione classi. In questo caso, il lato destro della finestra degli strumenti viene espanso con un elenco di namespace. Se si seleziona uno spazio dei nomi, una nuova colonna mostra un elenco di classi, strutture ed enumerazioni in questo spazio dei nomi. È possibile continuare a esplorare questi asset o tornare alla colonna all'estrema sinistra per avviare un'altra query. Vedere Trovare codice con Esplora architetture.
Copertura del codice
Il code coverage è stato aggiornato per instrumentare in modo dinamico i file binari in fase di esecuzione. Ciò riduce il sovraccarico della configurazione e offre prestazioni migliori. È anche possibile raccogliere dati di code coverage dagli unit test per le app C++. Dopo aver creato unit test C++, è possibile usare Esplora unit test per individuare i test nella soluzione. Per eseguire gli unit test e raccogliere i dati di code coverage, in Esplora unit test scegliere Analizza code coverage. È possibile esaminare i risultati della copertura del codice nella finestra Risultati della copertura del codice—nella barra dei menu, scegliere Test>Windows>Risultati della copertura del codice.
Novità di C++ in Visual Studio 2010
Compilatore e linker C++
Auto parola chiave. La auto
parola chiave ha un nuovo scopo. Usare il significato predefinito della auto
parola chiave per dichiarare una variabile il cui tipo viene dedotto dall'espressione di inizializzazione nella dichiarazione della variabile. L'opzione /Zc:auto
del compilatore richiama il significato nuovo o precedente della auto
parola chiave .
identificatore di tipo decltype. L'identificatore decltype
di tipo restituisce il tipo di un'espressione specificata. Usare l'identificatore decltype
di tipo in combinazione con la auto
parola chiave per dichiarare un tipo complesso o noto solo al compilatore. Ad esempio, usare la combinazione per dichiarare una funzione modello il cui tipo restituito dipende dai tipi degli argomenti del modello. In alternativa, dichiarare una funzione modello che chiama un'altra funzione e quindi restituisce il tipo restituito della funzione chiamata.
Espressioni lambda. Le funzioni lambda hanno un corpo della funzione, ma non un nome. Le funzioni lambda combinano le migliori caratteristiche dei puntatori a funzione e degli oggetti di funzioni. Usare una funzione lambda da sola, come parametro di funzione template anziché come oggetto funzione, oppure insieme alla parola chiave auto
per dichiarare una variabile il cui tipo è una lambda.
Riferimento Rvalue. Il dichiaratore di riferimento rvalue (&&) dichiara un riferimento a un rvalue. Un riferimento rvalue consente di usare la semantica di spostamento e il forwarding perfetto per scrivere costruttori, funzioni e modelli più efficienti.
static_assert Dichiarazione. Una static_assert
dichiarazione testa un'asserzione software in fase di compilazione, a differenza di altri meccanismi di asserzione che eseguono il test in fase di esecuzione. Se l'asserzione ha esito negativo, la compilazione ha esito negativo e viene generato un messaggio di errore specificato.
parole chiave nullptr e __nullptr. MSVC consente di usare la nullptr
parola chiave con codice nativo o con codice gestito. La nullptr
parola chiave indica che un handle di oggetto, un puntatore interno o un tipo di puntatore nativo non punta a un oggetto. Il compilatore interpreta nullptr
come codice gestito quando si usa l'opzione del /clr
compilatore e il codice nativo quando non si usa l'opzione /clr
.
La parola chiave __nullptr specifica di Microsoft ha lo stesso significato di nullptr
, ma si applica solo al codice nativo. Se si compila codice C/C++ nativo usando l'opzione del /clr
compilatore, il compilatore non può determinare se la nullptr
parola chiave è un termine nativo o gestito. Per chiarire l'intenzione al compilatore, usare la parola chiave nullptr per specificare il termine gestito e __nullptr per specificare il termine nativo.
/Zc:trigraphs
Opzione del compilatore. Per impostazione predefinita, il supporto per i trigrammi è disabilitato. Usare l'opzione del compilatore /Zc:trigraphs
per abilitare il supporto dei trigrammi.
Un trigrafo è costituito da due punti interrogativi consecutivi (??) seguiti da un terzo carattere univoco. Il compilatore sostituisce un trigrafo con il carattere di punteggiatura corrispondente. Ad esempio, il compilatore sostituisce ?? = trigrafo con il carattere # (segno di numero). Usare i trigrammi nei file di origine C che usano un set di caratteri che non contiene determinati caratteri di punteggiatura.
Nuova opzione di ottimizzazione Profile-Guided. PogoSafeMode è una nuova opzione di ottimizzazione guidata dal profilo che consente di specificare se usare la modalità provvisoria o la modalità rapida quando si ottimizza l'applicazione. La modalità sicura è thread-safe, ma è più lenta rispetto alla modalità rapida. La modalità rapida è il comportamento predefinito.
Nuova opzione CLR (Common Language Runtime) /clr:nostdlib. Viene aggiunta una nuova opzione per /clr
(Compilazione Common Language Runtime). Se vengono incluse versioni diverse delle stesse librerie, viene generato un errore di compilazione. La nuova opzione consente di escludere le librerie CLR predefinite in modo che il programma possa usare una versione specificata.
Nuova direttiva pragma detect_mismatch. La direttiva pragma detect_mismatch consente di inserire un tag nei tuoi file che viene confrontato con altri tag che hanno lo stesso nome. Se sono presenti più valori per lo stesso nome, il linker genera un errore.
Intrinsechi XOP, Intrinsechi FMA4 e Intrinsechi LWP. Sono state aggiunte nuove funzioni intrinseche per supportare le funzioni intrinseche XOP aggiunte per Visual Studio 2010 SP1, le funzioni intrinseche FMA4 aggiunte per Visual Studio 2010 SP1 e le funzioni intrinseche LWP aggiunte per le tecnologie del processore Visual Studio 2010 SP1. Usare __cpuid, __cpuidex per determinare quali tecnologie del processore sono supportate in un determinato computer.
Progetti di Visual Studio C++ e sistema di compilazione
MSBuild. Le soluzioni e i progetti Visual C++ vengono ora compilati usando MSBuild.exe, che sostituisce VCBuild.exe. MSBuild è lo stesso strumento di compilazione flessibile, estendibile e basato su XML usato dagli altri linguaggi e tipi di progetto di Visual Studio. A causa di questa modifica, i file di progetto di Visual Studio C++ ora usano un formato di file XML e hanno l'estensione del nome file .vcxproj. I file di progetto C++ di Visual Studio delle versioni precedenti di Visual Studio vengono convertiti automaticamente nel nuovo formato di file.
Directory di VC++. L'impostazione delle directory di VC++ si trova ora in due posizioni. Usare le pagine delle proprietà del progetto per impostare i valori per progetto per le directory VC++. Usare Gestione proprietà e una finestra delle proprietà per impostare i valori globali per ogni configurazione per le directory VC++.
Dipendenze da progetto a progetto. Nelle versioni precedenti le dipendenze definite tra i progetti sono state archiviate nel file della soluzione. Quando queste soluzioni vengono convertite nel nuovo formato di file di progetto, le dipendenze vengono convertite in riferimenti da progetto a progetto. Questa modifica può influire sulle applicazioni perché i concetti relativi alle dipendenze della soluzione e ai riferimenti da progetto a progetto sono diversi.
Macro e variabili di ambiente. La nuova macro _ITERATOR_DEBUG_LEVEL richiama il supporto del debug per gli iteratori. Utilizzare questa macro anziché le macro _SECURE_SCL e _HAS_ITERATOR_DEBUGGING precedenti.
Librerie di Visual C++
Librerie di runtime di concorrenza. Il framework runtime di concorrenza supporta applicazioni e componenti eseguiti contemporaneamente ed è il framework per la programmazione di applicazioni simultanee in Visual C++. Per supportare la programmazione di applicazioni simultanee, la libreria PPL (Parallel Patterns Library) fornisce contenitori e algoritmi per utilizzo generico per l'esecuzione di parallelismo con granularità fine. La libreria degli agenti asincroni fornisce un modello di programmazione basato su attore e interfacce di passaggio di messaggi per attività di pipelining e flusso di dati con granularità grossolana.
Libreria C++ standard. L'elenco seguente descrive molte delle modifiche apportate alla libreria C++ Standard.
- La nuova funzionalità del linguaggio C++ di riferimento rvalue è stata usata per implementare la semantica di spostamento e l'inoltro perfetto per molte funzioni nella libreria dei modelli standard. La semantica di spostamento e l'inoltro perfetto migliorano notevolmente le prestazioni delle operazioni che allocano o assegnano variabili o parametri.
- I riferimenti Rvalue vengono usati anche per implementare la nuova
unique_ptr
classe, ovvero un tipo di puntatore intelligente più sicuro rispetto allaauto_ptr
classe . Launique_ptr
classe è mobile ma non copiabile, implementa una semantica di proprietà rigorosa senza influire sulla sicurezza e funziona bene con i contenitori che conoscono i riferimenti rvalue. Laauto_ptr
classe è deprecata. - Quindici nuove funzioni, ad esempio
find_if_not
,copy_if
eis_sorted
, sono state aggiunte all'header <algorithm>. - Nell'intestazione <memory>, la nuova funzione make_shared è un modo pratico, affidabile ed efficiente per creare un puntatore condiviso a un oggetto nello stesso momento in cui l'oggetto viene costruito.
- Le liste collegate singolarmente sono supportate dall'intestazione <forward_list>.
- Le nuove funzioni membro
cbegin
,cend
,crbegin
ecrend
forniscono unconst_iterator
che può spostarsi avanti o indietro attraverso un contenitore. - L'intestazione <system_error> e i modelli correlati supportano l'elaborazione di errori di sistema di basso livello. I membri della
exception_ptr
classe possono essere utilizzati per il trasporto di eccezioni tra thread. - L'intestazione <codecvt> supporta la conversione di varie codifiche di caratteri Unicode in altre codifiche.
- L'intestazione <allocatori> definisce diversi modelli che consentono di allocare e liberare blocchi di memoria per i contenitori basati su nodi.
- Sono disponibili numerosi aggiornamenti per l'intestazione <random>.
Libreria Microsoft Foundation Class (MFC)
Funzionalità di Windows 7. MFC supporta molte funzionalità di Windows 7, ad esempio l'interfaccia utente Ribbon, la barra delle applicazioni, le jump list, le anteprime a schede, le anteprime delle miniature, la barra di avanzamento, l'overlay delle icone e l'indicizzazione della ricerca. Poiché MFC supporta automaticamente molte funzionalità di Windows 7, potrebbe non essere necessario modificare l'applicazione esistente. Per supportare altre funzionalità nelle nuove applicazioni, utilizzare la Creazione guidata dell'applicazione MFC per specificare le funzionalità da usare.
Riconoscimento multitocco. MFC supporta applicazioni con un'interfaccia utente multitocco, ad esempio applicazioni scritte per il sistema operativo Microsoft Surface. Un'applicazione multitocco può gestire messaggi di tocco e messaggi di movimento di Windows, che sono combinazioni di messaggi di tocco. È sufficiente registrare l'applicazione per eventi di tocco e movimento e il sistema operativo instrada gli eventi multitocco ai gestori eventi.
High-DPI consapevolezza. Per impostazione predefinita, le applicazioni MFC sono ora compatibili con valori DPI elevati. Se un'applicazione è consapevole di High-DPI (alta densità di punti per pollice), il sistema operativo può ridimensionare finestre, testo e altri elementi dell'interfaccia utente per adattarsi alla risoluzione dello schermo corrente. Ciò significa che è più probabile che un'immagine ridimensionata sia disposta correttamente e non ritagliata o pixelata.
Riavviare Manager. Il gestore di riavvio salva automaticamente i documenti e riavvia l'applicazione in caso di chiusura o riavvio imprevisti. Ad esempio, è possibile usare il gestore di riavvio per avviare l'applicazione dopo che è stata chiusa da un aggiornamento automatico. Per altre informazioni su come configurare l'applicazione per l'uso del gestore di riavvio, vedere Procedura: Aggiungere il supporto di Restart Manager.
CTaskDialog. La CTaskDialog
classe può essere usata invece della finestra di messaggio standard AfxMessageBox
. La CTaskDialog
classe visualizza e raccoglie più informazioni rispetto alla finestra di messaggio standard.
Libreria SafeInt
La nuova libreria SafeInt esegue operazioni aritmetiche sicure che tengono conto dell'overflow di interi. Questa libreria confronta anche diversi tipi di numeri interi.
Nuove macro ATL (Active Template Library)
Sono state aggiunte nuove macro ad ATL per espandere la funzionalità di PROP_ENTRY_TYPE e PROP_ENTRY_TYPE_EX. PROP_ENTRY_INTERFACE e PROP_ENTRY_INTERFACE_EX consentono di aggiungere un elenco di CLSID validi. PROP_ENTRY_INTERFACE_CALLBACK e PROP_ENTRY_INTERFACE_CALLBACK_EX consentono di specificare una funzione di callback per determinare se un CLSID è valido.
/avviso di analisi
La maggior parte degli avvisi di /analyze
(Enterprise Code Analysis) sono stati rimossi dalle librerie C Run-Time (CRT), MFC e ATL.
Animazione e supporto D2D
MFC supporta ora animazioni e grafica Direct2D. La libreria MFC include diverse nuove classi e funzioni MFC per supportare questa funzionalità. Sono disponibili anche due nuove procedure dettagliate per illustrare come aggiungere un oggetto D2D e un oggetto animazione a un progetto. Queste procedure dettagliate sono Procedura dettagliata: aggiunta di un oggetto D2D a un progetto MFC e procedura dettagliata: aggiunta di animazioni a un progetto MFC.
IDE
IntelliSense migliorato. IntelliSense per Visual C++ è stato completamente riprogettato per essere più veloce, più accurato e in grado di gestire progetti più grandi. Per ottenere questo miglioramento, l'IDE distingue il modo in cui uno sviluppatore visualizza e modifica il codice sorgente e il modo in cui l'IDE usa il codice sorgente e le impostazioni del progetto per compilare una soluzione. A causa di questa separazione dei compiti, le funzionalità di esplorazione, ad esempio Visualizzazione classi e la nuova finestra di dialogo Passa a , vengono gestite da un sistema basato su un nuovo file di database desktop di SQL Server (con estensione sdf) che sostituisce il vecchio file di esplorazione senza compilazione (con estensione ncb). Le funzionalità di IntelliSense, ad esempio Informazioni rapide, Completamento automatico e Guida parametri analizzano le unità di conversione solo quando necessario. Le funzionalità ibride, ad esempio la nuova finestra Gerarchia di chiamate , usano una combinazione delle funzionalità di esplorazione e IntelliSense. Poiché IntelliSense elabora solo le informazioni necessarie al momento, l'IDE è più reattivo. Inoltre, poiché le informazioni sono più aggiornate, le visualizzazioni e le finestre dell'IDE sono più accurate. Infine, poiché l'infrastruttura dell'IDE è meglio organizzata, più capace e più scalabile, può gestire progetti di dimensioni maggiori.
Migliorati gli errori di IntelliSense. L'IDE rileva meglio gli errori che potrebbero causare una perdita di IntelliSense e visualizza sottolineature ondulate rosse sotto di esse. Inoltre, l'IDE segnala errori intelliSense alla finestra Elenco errori. Per visualizzare il codice che causa il problema, fare doppio clic sull'errore nella finestra Elenco errori.
#include funzionalità di completamento automatico. L'IDE supporta il completamento automatico per la #include
parola chiave . Quando si digita #include
, l'IDE crea un menu a tendina di file header validi. Continuando a digitare il nome del file, l'IDE filtra l'elenco in base alla tua digitazione. In qualsiasi momento, è possibile selezionare dall'elenco il file che si desidera includere. In questo modo è possibile includere rapidamente i file senza conoscere il nome di file esatto.
Naviga a. La finestra di dialogo Passa a consente di cercare tutti i simboli e i file nel progetto che corrispondono a una stringa specificata. I risultati della ricerca vengono immediatamente modificati durante la digitazione di caratteri aggiuntivi nella stringa di ricerca. Il campo Feedback risultati indica il numero di elementi trovati e consente di decidere se vincolare la ricerca. I campi Kind/Scope, Location e Preview feedback consentono di disambiguare gli elementi con nomi simili. Inoltre, è possibile estendere questa funzionalità per supportare altri linguaggi di programmazione.
Debugging e profilazione parallela. Il debugger di Visual Studio è a conoscenza del runtime di concorrenza e consente di risolvere i problemi relativi alle applicazioni di elaborazione parallela. È possibile usare il nuovo strumento profiler di concorrenza per visualizzare il comportamento complessivo dell'applicazione. Inoltre, è possibile usare nuove finestre degli strumenti per visualizzare lo stato delle attività e i relativi stack di chiamate.
Progettazione barra multifunzione. Il Ribbon Designer è un editor grafico che consente di creare e modificare un'interfaccia utente a barra multifunzione MFC. L'interfaccia utente finale della barra multifunzione è rappresentata da un file di risorse basato su XML (.mfcribbon-ms). Per le applicazioni esistenti, è possibile acquisire l'interfaccia utente della barra multifunzione corrente aggiungendo temporaneamente alcune righe di codice e quindi richiamando la finestra di progettazione della barra multifunzione. Dopo aver creato il file di risorse della barra multifunzione, è possibile sostituire il codice dell'interfaccia utente della barra multifunzione scritto a mano con alcune istruzioni che caricano la risorsa della barra multifunzione.
Gerarchia di chiamata. La finestra Gerarchia chiamate consente di passare a tutte le funzioni chiamate da una determinata funzione o a tutte le funzioni che chiamano una determinata funzione.
Attrezzi
Creazione guidata classe MFC. Visual C++ 2010 reintroduce il ben noto strumento MFC Class Wizard. La Creazione guidata di classe MFC è un modo pratico per aggiungere classi, messaggi e variabili a un progetto senza dover modificare manualmente gli insiemi di file di origine.
Assistente controllo ATL. La Creazione guidata controllo ATL non popola più automaticamente il campo ProgID
. Se un controllo ATL non dispone di un ProgID
, altri strumenti potrebbero non funzionare con esso. Un esempio di strumento che richiede che i controlli dispongano di un ProgID
è la finestra di dialogo Inserisci Controllo Attivo. Per altre informazioni sulla finestra di dialogo, vedere Inserire controlli ActiveX.
Riferimento a Microsoft Macro Assembler
L'aggiunta del tipo di dati YMMWORD supporta gli operandi multimediali a 256 bit inclusi nelle istruzioni Intel Advanced Vector Extensions (AVX).
Novità di C++ in Visual Studio 2008
Visual C++ Integrated Development Environment (IDE)
Le finestre di dialogo create nelle applicazioni ATL, MFC e Win32 sono ora conformi alle linee guida per lo stile di Windows Vista. Quando si crea un nuovo progetto usando Visual Studio 2008, tutte le finestre di dialogo inserite nell'applicazione saranno conformi alle linee guida per lo stile di Windows Vista. Se si ricompila un progetto creato con una versione precedente di Visual Studio, le finestre di dialogo esistenti manterranno lo stesso aspetto di cui in precedenza avevano. Per altre informazioni su come inserire finestre di dialogo nell'applicazione, vedere Editor di dialoghi.
La procedura guidata progetto ATL include ora un'opzione per registrare i componenti per tutti gli utenti. A partire da Visual Studio 2008, i componenti COM e le librerie dei tipi creati dalla creazione guidata del progetto ATL vengono registrati nel nodo HKEY_CURRENT_USER del Registro di sistema, a meno che non si selezioni Registra componente per tutti gli utenti.
La procedura guidata progetto ATL non offre più un'opzione per creare progetti ATL con attributi. A partire da Visual Studio 2008, la procedura guidata progetto ATL non dispone di un'opzione per modificare lo stato con attributi di un nuovo progetto. Tutti i nuovi progetti ATL creati dalla procedura guidata sono ora senza attribuzione.
La scrittura nel Registro di sistema può essere reindirizzata. Con l'introduzione di Windows Vista, la scrittura in determinate aree del Registro di sistema richiede l'esecuzione di un programma in modalità con privilegi elevati. Non è consigliabile eseguire sempre Visual Studio in modalità con privilegi elevati. Il reindirizzamento per utente reindirizza automaticamente le scritture del Registro di sistema da HKEY_CLASSES_ROOT a HKEY_CURRENT_USER senza modifiche di programmazione.
Il Class Designer ha ora un supporto limitato per il codice C++ nativo. Nelle versioni precedenti di Visual Studio, la Progettazione Classi funzionava solo con Visual C# e Visual Basic. Gli utenti C++ possono ora usare Progettazione classi, ma solo in modalità di sola lettura. Per altre informazioni su come usare Progettazione classi con C++, vedere Uso del codice Visual C++ in Progettazione classi.
La procedura guidata del progetto non dispone più di un'opzione per creare un progetto SQL Server C++. A partire da Visual Studio 2008, la creazione guidata del nuovo progetto non offre un'opzione per creare un progetto SQL Server C++. I progetti SQL Server creati usando una versione precedente di Visual Studio verranno comunque compilati e funzioneranno correttamente.
Librerie di Visual C++
Generale
- Le applicazioni possono essere associate a versioni specifiche delle librerie di Visual C++. A volte un'applicazione dipende dagli aggiornamenti apportati alle librerie di Visual C++ dopo una versione. In questo caso, l'esecuzione dell'applicazione in un computer con versioni precedenti delle librerie può causare un comportamento imprevisto. È ora possibile associare un'applicazione a una versione specifica delle librerie in modo che non venga eseguita in un computer con una versione precedente delle librerie.
Libreria STL/CLR
- Visual C++ include ora la libreria STL/CLR. La libreria STL/CLR è un pacchetto della libreria di modelli standard (STL), un subset della libreria C++ standard, da usare con C++ e Common Language Runtime (CLR) di .NET Framework. Con STL/CLR è ora possibile usare tutti i contenitori, gli iteratori e gli algoritmi di STL in un ambiente gestito.
Libreria MFC
- Windows Vista supporta i controlli comuni. Oltre 150 metodi in 18 classi nuove o esistenti sono stati aggiunti per supportare le funzionalità in Windows Vista o per migliorare le funzionalità nelle classi MFC correnti.
- La nuova
CNetAddressCtrl
classe consente di immettere e convalidare indirizzi IPv4 e IPv6 o nomi DNS. - La nuova
CPagerCtrl
classe semplifica l'uso del controllo cercapersone di Windows. - La nuova
CSplitButton
classe semplifica l'uso del controllo splitbutton di Windows per selezionare un'azione predefinita o facoltativa.
Libreria di supporto C++
- C++ introduce una libreria di incapsulamento. La libreria di marshalling offre un modo semplice e ottimizzato per effettuare il marshalling dei dati tra ambienti nativi e gestiti. La libreria è un'alternativa a approcci più complessi e meno efficienti, ad esempio l'uso di PInvoke. Per ulteriori informazioni, vedere Panoramica del marshalling in C++.
ATL Server
- ATL Server viene rilasciato come progetto di origine condiviso.
- La maggior parte della codebase di ATL Server è stata rilasciata come progetto di origine condivisa in CodePlex e non è installata come parte di Visual Studio 2008. Alcuni dei file associati ad ATL Server non fanno più parte di Visual Studio. Per l'elenco dei file rimossi, vedere Rimozione dei file del server ATL.
- Le classi di codifica e decodifica dei dati da atlenc.h e funzioni di utilità e classi da atlutil.h e atlpath.h fanno ora parte della libreria ATL.
- Microsoft continuerà a supportare le versioni di ATL Server incluse nelle versioni precedenti di Visual Studio, purché tali versioni di Visual Studio siano supportate. CodePlex continuerà lo sviluppo del codice ATL Server come progetto della community. Microsoft non supporta una versione CodePlex di ATL Server.
Compilatore e linker di Visual C++
Modifiche del compilatore
- Il compilatore supporta compilazioni incrementali gestite. Quando si specifica questa opzione, il compilatore non ricompila il codice quando viene modificato un assembly a cui si fa riferimento. Eseguirà invece una compilazione incrementale. I file vengono ricompilati solo se le modifiche influiscono sul codice dipendente.
- Gli attributi correlati al server ATL non sono più supportati. Il compilatore non supporta più diversi attributi direttamente correlati a ATL Server. Per un elenco completo degli attributi rimossi, vedere Modifiche di rilievo.
- Il compilatore supporta la microarchitectura Intel Core. Il compilatore contiene l'ottimizzazione per la microarchitectura Intel Core durante la generazione del codice. Per impostazione predefinita, questa ottimizzazione è attivata e non può essere disabilitata perché aiuta anche Il Processor 4 e altri processori.
- Gli intrinseci supportano i più recenti processori AMD e Intel. Diverse nuove istruzioni intrinseche supportano la maggiore funzionalità nei processori AMD e Intel più recenti. Per altre informazioni sui nuovi intrinseci, vedere Istruzioni supplementari sulle estensioni SIMD streaming 3, Istruzioni sulle estensioni SIMD streaming 4, Istruzioni SSE4A e intrinseci avanzati per la manipolazione dei bit, Intrinseci AES, _mm_clmulepi64_si128 e __rdtscp.
- La
__cpuid
funzione viene aggiornata. Le__cpuid
funzioni ,__cpuidex
ora supportano diverse nuove funzionalità delle revisioni più recenti dei processori AMD e Intel. L'intrinseco__cpuidex
è nuovo e raccoglie altre informazioni dai processori recenti. - L'opzione
/MP
del compilatore riduce il tempo di compilazione totale. L'opzione/MP
può ridurre significativamente il tempo totale per compilare diversi file di origine creando diversi processi che compilano i file contemporaneamente. Questa opzione è particolarmente utile nei computer che supportano l'hyperthreading, più processori o più core. - L'opzione del compilatore
/Wp64
e la parola chiave__w64
sono deprecate. L'opzione/Wp64
e la parola chiave__w64
del compilatore, che rilevano problemi di portabilità a 64 bit, sono deprecati e verranno rimossi in una versione futura del compilatore. Anziché questa opzione e parola chiave del compilatore, usare un MSVC destinato a una piattaforma a 64 bit. -
/Qfast_transcendentals
genera codice inline per le funzioni trascendentali. -
/Qimprecise_fwaits
rimuove i comandi fwait interni per provare blocchi quando si usa l'opzione del/fp:except
compilatore.
Modifiche del linker
- Le informazioni sul controllo dell'account utente sono ora incorporate nei file manifesto degli eseguibili dal linker di Visual C++ (link.exe). Questa funzionalità è abilitata per impostazione predefinita. Per altre informazioni su come disabilitare questa funzionalità o su come modificare il comportamento predefinito, vedere
/MANIFESTUAC
(Incorpora informazioni sull'account utente nel manifesto). - Il linker dispone ora dell'opzione
/DYNAMICBASE
per abilitare la funzionalità di Randomizzazione del layout dello spazio degli indirizzi di Windows Vista. Questa opzione modifica l'intestazione di un eseguibile per indicare se l'applicazione deve essere ribasata casualmente in fase di caricamento.
Novità di C++ in Visual Studio 2005
Le funzionalità seguenti sono state nuove in Visual C++ 2005 Service Pack 1:
Intrinseci per x86 e x64
- __fermare
- __lidt
- __Nop
- __readcr8
- __sidt
- __svm_clgi
- __svm_invlpga
- __svm_skinit
- __svm_stgi
- __svm_vmload
- __svm_vmrun
- __svm_vmsave
- __ud2
- __vmx_off
- __vmx_vmptrst
- __writecr8
Intrinseci solo per x64
- __vmx_on
- __vmx_vmclear
- __vmx_vmlaunch
- __vmx_vmptrld
- __vmx_vmread
- __vmx_vmresume
- __vmx_vmwrite
Nuove parole chiave del linguaggio
__sptr, __uptr
Nuove funzionalità del compilatore
Il compilatore presenta modifiche che causano un'interruzione in questa versione.
- Compilatori nativi e incrociati a 64 bit.
-
/analyze
È stata aggiunta l'opzione del compilatore (Enterprise Code Analysis). -
/bigobj
opzione del compilatore è stata aggiunta. -
/clr:pure
,/clr:safe
e/clr:oldSyntax
sono stati aggiunti. In seguito deprecato in Visual Studio 2015 e rimosso in Visual Studio 2017. - Opzioni del compilatore deprecate: molte opzioni del compilatore sono state deprecate in questa versione; Per altre informazioni, vedere Opzioni del compilatore deprecate .
- La doppia delega nel codice
/clr
è ridotta; consultare Double Thunking (C++) per maggiori informazioni. -
/EH
(Modello di gestione delle eccezioni) o/EHs
non può più essere usato per intercettare un'eccezione sollevata con qualcosa di diverso da un throw; utilizza/EHa
. -
/errorReport
Aggiunta l'opzione del compilatore (Segnala errori interni del compilatore). - È stata aggiunta l'opzione del compilatore "Ottimizza per 64".
-
/FA
, è stata aggiunta l'opzione del compilatore/Fa
(Elenco file). -
/FC
È stata aggiunta l'opzione del compilatore "Percorso completo del file di codice sorgente nella diagnostica". -
/fp
È stata aggiunta l'opzione del compilatore "Specifica comportamento Floating-Point". -
/G
(Ottimizza per processore) È stata aggiunta l'opzione del compilatore Options. -
/G
(Ottimizza per processore) È stata aggiunta l'opzione del compilatore Options. -
/G3
,/G4
,/G5
,/G6
,/G7
e/GB
opzioni del compilatore sono state rimosse. Il compilatore usa ora un "modello misto" che tenta di creare il file di output migliore per tutte le architetture. -
/Gf
è stato rimosso. In alternativa, usare/GF
(elimina stringhe duplicate). -
/GL
L'ottimizzazione dell'intero programma è ora compatibile con/CLRHEADER
. -
/GR
è ora attivo per impostazione predefinita. -
/GS
(Controllo sicurezza buffer) fornisce ora protezione di sicurezza per i parametri del puntatore vulnerabili./GS
è ora attivo per impostazione predefinita./GS
ora funziona anche sulle funzioni compilate in MSIL con/clr
(Compilazione Common Language Runtime). -
/homeparams
Aggiunta l'opzione del compilatore Copy Register Parameters to Stack (Copia parametri registro nello stack). -
/hotpatch
Aggiunta l'opzione del compilatore Create Hotpatchable Image (Crea immagine hotpatchable). - L'euristica delle funzioni inline è stata aggiornata; per altre informazioni, vedere
inline
,__inline
__forceinline
e inline_depth - Sono state aggiunte molte nuove funzioni intrinseche e molte funzioni intrinseche non documentate in precedenza sono ora documentate.
- Per impostazione predefinita, qualsiasi chiamata a new che non riesce genererà un'eccezione.
-
/ML
Le opzioni del compilatore e/MLd
sono state rimosse. Visual C++ non supporta più il supporto della libreria CRT a thread singolo collegato in modo statico. - Il compilatore ha implementato l'Ottimizzazione dei Valori di Ritorno Denominati, che viene abilitata durante la compilazione con
/O1
,/O2
(Minimizza le dimensioni, Massimizza la velocità),/Og
(Ottimizzazioni globali) e/Ox
(Ottimizzazione completa). -
/Oa
l'opzione del compilatore è stata rimossa, ma verrà ignorata senza avviso; utilizzarenoalias
orestrict__declspec
modificatori per specificare il modo in cui il compilatore esegue l'aliasing. -
/Op
l'opzione del compilatore è stata rimossa. Usare/fp
(Specifica comportamento Floating-Point) invece. - OpenMP è ora supportato da Visual C++.
-
/openmp
Aggiunta l'opzione del compilatore Enable OpenMP 2.0 Support (Abilita supporto OpenMP 2.0). -
/Ow
L'opzione del compilatore è stata rimossa, ma verrà ignorata automaticamente. Utilizzare i modificatorinoalias
orestrict__declspec
per specificare come il compilatore gestisce l'aliasing.
Profile-Guided Ottimizzazioni
-
/QI0f
è stato rimosso. -
/QIfdiv
è stato rimosso. -
/QIPF_B
È stata aggiunta l'opzione del compilatore per Errata B CPU Stepping. -
/QIPF_C
È stata aggiunta l'opzione del compilatore Errata per il C CPU Stepping. -
/QIPF_fr32
Aggiunta l'opzione del compilatore "Non utilizzare i registri a virgola mobile dei 96 superiori". -
/QIPF_noPIC
È stata aggiunta l'opzione del compilatore "Genera codice dipendente dalla posizione". -
/QIPF_restrict_plabels
Si supponga che sia stata aggiunta l'opzione del compilatore Nessuna funzione creata in fase di esecuzione.
Supporto Unicode nel compilatore e nel linker
-
/vd
(Disabilita spostamenti costruzione) consente ora di usare l'operatore dynamic_cast su un oggetto in fase di costruzione (/vd2) -
/YX
l'opzione del compilatore è stata rimossa. Usare/Yc
(Crea file di intestazione precompilato) o/Yu
(Usa file di intestazione precompilato). Se si rimuove/YX
dalle configurazioni di compilazione e non si sostituisce con nulla, può comportare compilazioni più veloci. -
/Zc:forScope
è ora attivo per impostazione predefinita. -
/Zc:wchar_t
è ora attivo per impostazione predefinita. -
/Zd
l'opzione del compilatore è stata rimossa. Le informazioni di debug che contengono solo numeri di riga non sono più supportate. Usare/Zi
invece (per altre informazioni , vedere /Z7, /Zi, /ZI (Formato informazioni di debug ). -
/Zg
è ora valido solo nei file di codice sorgente C e non nei file di codice sorgente C++. -
/Zx
Aggiunta l'opzione del compilatore Debug Optimized Itanium Code.
Nuove funzionalità del linguaggio
- L'attributo è ora deprecato.
-
appdomain__declspec
è stato aggiunto il modificatore. -
__clrcall
è stata aggiunta la convenzione di chiamata. - Il modificatore declspec deprecato (C++) consente ora di specificare una stringa che verrà visualizzata in fase di compilazione, quando un utente tenta di accedere a una classe o a una funzione deprecata.
-
dynamic_cast
L'operatore presenta modifiche radicali. - Le enumerazioni native consentono ora di specificare il tipo sottostante.
-
jitintrinsicdeclspec
è stato aggiunto il modificatore. -
noaliasdeclspec
è stato aggiunto il modificatore. -
process__declspec
è stato aggiunto il modificatore. - abstract, override e sealed sono validi per le compilazioni native.
-
__restrict
parola chiave è stata aggiunta. -
restrictdeclspec
è stato aggiunto il modificatore. -
__thiscall
è ora una parola chiave. -
__unaligned
parola chiave è ora documentata. -
volatile
(C++) ha aggiornato il comportamento rispetto alle ottimizzazioni.
Nuove funzionalità del preprocessore
- __CLR_VER macro predefinita aggiunta.
- Il pragma del commento (C/C++) ora accetta
/MANIFESTDEPENDENCY
come commento del linker. L'opzione exestr per commentare è ora deprecata. -
embedded_idl
attribute (Direttiva#import
) accetta ora un parametro facoltativo. -
fenv_access
pragma -
float_control
pragma -
fp_contract
pragma - Le variabili globali non verranno inizializzate nell'ordine in cui vengono dichiarate se sono presenti variabili globali nelle sezioni pragma gestite, non gestite e non gestite. Si tratta di una potenziale modifica che causa un'interruzione se, ad esempio, una variabile globale non gestita viene inizializzata con variabili globali gestite ed è necessario un oggetto gestito completamente costruito.
- Le sezioni specificate con init_seg sono ora di sola lettura e non di lettura/scrittura come nelle versioni precedenti.
- inline_depth valore predefinito è ora 16. Un valore predefinito di 16 è stato applicato anche in Visual C++ .NET 2003.
- "_INTEGRAL_MAX_BITS" macro predefinita aggiunta, vedere Macro predefinite.
- _M_CEE, _M_CEE_PURE e _M_CEE_SAFE macro predefinite aggiunte, vedere Macro predefinite.
- È stata aggiunta la macro predefinita _M_IX86_FP.
- _M_X64 macro predefinita aggiunta.
-
make_public
pragma -
managed
,unmanaged
sintassi pragma aggiornata (ora hapush
epop
) - mscorlib.dll è ora implicitamente riferito dalla Direttiva
#using
in tutte le compilazioni/clr
. - _OPENMP macro predefinita aggiunta.
- optimize pragma è stato aggiornato, a e w non sono più parametri validi.
- aggiunta dell'attributo no_registry#import.
-
region
,endregion
pragmas aggiunti - _VC_NODEFAULTLIB macro predefinita aggiunta.
- Le macro variadic sono ora implementate.
-
vtordisp
è deprecato e verrà rimosso in una versione futura di Visual C++. - Il
warning
pragma ha ora l'identificatore di eliminazione.
Nuove funzionalità del linker
- I moduli (file di output MSIL non assembly) sono ora consentiti come input per il linker.
-
/ALLOWISOLATION
È stata aggiunta l'opzione del linker (Ricerca manifesto). -
/ASSEMBLYRESOURCE
(Incorpora una risorsa gestita) è stato aggiornato per consentire ora di specificare il nome della risorsa nell'assembly e di specificare che la risorsa è privata nell'assembly. -
/CLRIMAGETYPE
È stata aggiunta l'opzione del linker (Specificare il tipo di immagine CLR). -
/CLRSUPPORTLASTERROR
È stata aggiunta l'opzione linker Preserva ultimo codice di errore per le chiamate PInvoke. -
/CLRTHREADATTRIBUTE
Aggiunta l'opzione del linker Set CLR Thread Attribute (Imposta attributo thread CLR). -
/CLRUNMANAGEDCODECHECK
È stata aggiunta l'opzione del linker SuppressUnmanagedCodeSecurityAttribute. -
/ERRORREPORT
(Segnala errori interni del linker) è stata aggiunta l'opzione del linker. -
/EXETYPE
l'opzione del linker è stata rimossa. Il linker non supporta più la creazione di driver di dispositivo Windows 95 e Windows 98. Usare un DDK appropriato per creare questi driver di dispositivo. La parola chiave EXETYPE non è più valida per i file di definizione del modulo. -
/FUNCTIONPADMIN
Aggiunta l'opzione del linker Create Hotpatchable Image (Crea immagine hotpatchable). -
/LTCG
L'opzione del linker è ora supportata nei moduli compilati con/clr
./LTCG
è stato aggiornato anche per supportare le ottimizzazioni guidate dal profilo. -
/MANIFEST
Aggiunta l'opzione del linker Create Side-by-Side Assembly Manifest (Crea manifesto assembly side-by-side). -
/MANIFESTDEPENDENCY
È stata aggiunta l'opzione del linker (Specifica dipendenze manifesto). -
/MANIFESTFILE
è stata aggiunta l'opzione linker (Nome file manifesto). -
/MAPINFO:LINES
l'opzione del linker è stata rimossa. -
/NXCOMPAT
Aggiunta l'opzione del linker compatibile con la prevenzione dell'esecuzione dei dati. -
/PGD
È stata aggiunta l'opzione del linker Specificare database per ottimizzazioni Profile-Guided. -
/PROFILE
È stata aggiunta l'opzione del linker (Profiler degli strumenti di performance). -
/SECTION
L'opzione del linker (Specifica attributi sezione) ora supporta la negazione degli attributi e non supporta più gli attributi L o D correlati a VxD. - Supporto Unicode nel compilatore e nel linker
-
/VERBOSE
L'opzione del linker Print Progress Messages (Stampa i messaggi di avanzamento) ora accetta anche ICF e REF. -
/VXD
l'opzione del linker è stata rimossa. Il linker non supporta più la creazione di driver di dispositivo Windows 95 e Windows 98. Usare un DDK appropriato per creare questi driver di dispositivo. La parola chiave VXD non è più valida per i file di definizione del modulo. -
/WS
l'opzione del linker è stata rimossa./WS
è stato usato per modificare le immagini destinate a Windows NT 4.0. IMAGECFG.exe -R nome file può essere usato invece di/WS
. IMAGECFG.exe si trova in Windows NT 4.0 CD-ROM in SUPPORT\DEBUG\I386\IMAGECFG.EXE. - L'opzione di linker
/WX
(Tratta gli avvisi del linker come errori) è ora documentata.
Le nuove funzionalità dell'utilità linker
-
/ALLOWISOLATION
L'opzione editbin è stata aggiunta - L'istruzione del file di definizione del modulo DESCRIPTION viene rimossa. Il linker non supporta più la creazione di driver di dispositivo virtuali.
-
/ERRORREPORT
l'opzione è stata aggiunta a bscmake.exe, dumpbin.exe, editbin.exee lib.exe. -
/LTCG
È stata aggiunta l'opzione lib. -
/NXCOMPAT
È stata aggiunta l'opzione editbin. -
/RANGE
L'opzione dumpbin è stata aggiunta. -
/TLS
L'opzione dumpbin è stata aggiunta. -
/WS
L'opzione editbin è stata rimossa./WS
è stato usato per modificare le immagini destinate a Windows NT 4.0. IMAGECFG.exe -R nome file può essere usato invece di/WS
. IMAGECFG.exe si trova in Windows NT 4.0 CD-ROM in SUPPORT\DEBUG\I386\IMAGECFG.EXE. - L'opzione lib /WX[:NO] è stata aggiunta.
Nuove funzionalità di NMAKE
-
/ERRORREPORT
è stato aggiunto. -
/G
è stato aggiunto. - Le regole predefinite sono state aggiornate.
- La macro $(MAKE), documentata in Macro di ricorsione, fornisce adesso il percorso completo di nmake.exe.
Nuove funzionalità MASM
- Le espressioni MASM sono ora valori a 64 bit. Nelle versioni precedenti le espressioni MASM erano valori a 32 bit.
- L'istruzione __asm int 3 fa ora in modo che una funzione venga compilata in modo nativo.
- ALIAS (MASM) è ora documentato.
-
/ERRORREPORT
Aggiunte le opzioni ml.exe e ml64.exe. - . FPO è ora documentato.
- H2INC.exe non verrà fornito in Visual C++ 2005. Se è necessario continuare a usare H2INC, usare H2INC.exe da una versione precedente di Visual C++.
- è stato aggiunto l'operatore IMAGEREL.
- è stato aggiunto l'operatore HIGH32.
- è stato aggiunto l'operatore LOW32.
- ml64.exe è una versione di MASM per l'architettura x64. Assembla i file con estensione asm x64 in file di oggetto x64. Il linguaggio assembly inline non è supportato nel compilatore x64. Sono state aggiunte le direttive MASM seguenti per ml64.exe (x64):
- . ALLOCSTACK
- . ENDPROLOG
- . PUSHFRAME
- . PUSHREG
- . SAVEREG
- . SAVEXMM128
- .SETFRAME Inoltre, la direttiva PROC è stata aggiornata con solo sintassi x64.
- È stata aggiunta la direttiva MMWORD
-
/omf
(opzione della riga di comandoML.exe) ora implica/c
. ML.exe non supporta il collegamento di oggetti di formato OMF. - La direttiva SEGMENT supporta ora attributi aggiuntivi.
- è stato aggiunto l'operatore SECTIONREL.
- È stata aggiunta la direttiva XMMWORD
Nuove funzionalità CRT
- Sono state aggiunte versioni sicure di diverse funzioni. Queste funzioni gestiscono gli errori in modo migliore e applicano controlli più rigorosi sui buffer per evitare errori di sicurezza comuni. Le nuove versioni sicure sono identificate dal suffisso _s .
- Le versioni meno sicure esistenti di molte funzioni sono state deprecate. Per disabilitare gli avvisi di deprecazione, definire _CRT_SECURE_NO_WARNINGS.
- Molte funzioni esistenti convalidano ora i relativi parametri e richiamano il gestore di parametri non validi quando viene passato un parametro non valido.
- Molte funzioni esistenti ora impostano
errno
dove non lo erano prima. - È stato aggiunto il typedef
errno_t
con tipo integer.errno_t
viene utilizzato ogni volta che il tipo restituito di una funzione o un parametro gestisce i codici di errore dierrno
.errno_t
sostituisceerrcode
. - Le funzioni dipendenti dalle impostazioni locali hanno ora versioni che accettano le impostazioni locali come parametro anziché usare le impostazioni locali correnti. Queste nuove funzioni hanno il suffisso _l . Sono state aggiunte diverse nuove funzioni per lavorare con gli oggetti delle impostazioni locali. Le nuove funzioni includono
_get_current_locale
,_create_locale
e_free_locale
. - Sono state aggiunte nuove funzioni per supportare il blocco e lo sblocco degli handle di file.
- La
_spawn
famiglia di funzioni non reimposta errno su zero in caso di esito positivo, come nelle versioni precedenti. - Le versioni della famiglia di funzioni
printf
che consentono di specificare l'ordine in cui vengono utilizzati gli argomenti sono disponibili. - Unicode è ora un formato di testo supportato. La funzione
_open
supporta gli attributi _O_TEXTW, _O_UTF8 e _O_UTF16. Lafopen
funzione supporta il metodo "ccs=ENCODING" per specificare un formato Unicode. - È ora disponibile una nuova versione delle librerie CRT compilate in codice gestito (MSIL) e viene usata durante la compilazione con l'opzione
/clr
(Compilazione Common Language Runtime). - _fileinfo è stato rimosso.
- La dimensione predefinita per
time_t
è ora 64 bit, il che espande l'intervallo ditime_t
e diverse funzioni temporali fino all'anno 3000. - CRT supporta ora l'impostazione delle impostazioni locali per ogni thread. La funzione
_configthreadlocale
è stata aggiunta per supportare questa funzionalità. - Le funzioni
_statusfp2
e__control87_2
sono state aggiunte per consentire l'accesso e il controllo della parola di controllo del punto mobile sui processori per calcoli in virgola mobile x87 e SSE2. - Le funzioni
_mkgmtime
e_mkgmtime64
sono state aggiunte per fornire supporto per la conversione delle ore (struct tm) in Ora di Greenwich (GMT). - Sono state apportate modifiche a
swprintf
evswprintf
per migliorare la conformità allo standard. - Nuovo file di intestazione, INTRIN. H, fornisce prototipi per alcune funzioni intrinseche.
- La
fopen
funzione ha ora un attributo N. - La
_open
funzione ha ora un attributo _O_NOINHERIT. - La
atoi
funzione restituisce ora INT_MAX e impostaerrno
su ERANGE in caso di overflow. Nelle versioni precedenti il comportamento di overflow non è definito. - La
printf
famiglia di funzioni supporta l'output a virgola mobile esadecimale implementato in base allo standard ANSI C99 usando gli identificatori di tipo di formato %a e %A. - La famiglia
printf
ora supporta il prefisso di dimensione "ll" (long long). - La
_controlfp
funzione è stata ottimizzata per migliorare le prestazioni. - Sono state aggiunte versioni di debug di alcune funzioni.
- Aggiunti
_chgsignl
e_cpysignl
(versioni in formato long double). - Aggiunto tipo
_locale_t
alla tabella dei tipi. - Nuova macro
_countof
Macro aggiunta per il calcolo del numero di elementi in una matrice. - In ogni argomento della funzione è stata aggiunta una sezione sugli equivalenti di .NET Framework.
- Diverse funzioni stringa ora hanno la possibilità di troncare le stringhe invece di avere esito negativo quando i buffer di output sono troppo piccoli; vedere _TRUNCATE.
-
_set_se_translator
richiede ora l'uso dell'opzione del/EHa
compilatore. -
fpos_t
è ora__int64
in/Za
(per il codice C) e quando__STDC__
viene impostato manualmente (per il codice C++). Era unstruct
. - _CRT_DISABLE_PERFCRIT_LOCKS può migliorare le prestazioni di I/O dei programmi a thread singolo.
- I nomi POSIX sono stati deprecati a favore dei nomi conformi a ISO C++ (ad esempio, usare
_getch
anzichégetch
). - Sono disponibili nuove opzioni di collegamento .obj file per la modalità pura
-
_recalloc
combina le caratteristiche direalloc
ecalloc
.
Novità di C++ in Visual Studio 2003
Compilatore
- Informazioni su come eseguire un'applicazione Managed Extensions per C++ compilata con il compilatore della versione corrente in una versione precedente del runtime.
- Domande frequenti sulle estensioni gestite per C++.
- È stata aggiunta una procedura dettagliata che illustra come convertire un'applicazione nativa esistente per usare le estensioni gestite per C++: Procedura dettagliata: Conversione di un'applicazione C++ nativa esistente per interagire con i componenti di .NET Framework.
- È ora possibile creare un delegato su un metodo di un tipo valore.
- La conformità del compilatore allo standard C++ è stata notevolmente migliorata per Visual C++ .NET 2003.
-
/arch
viene aggiunta l'opzione del compilatore. -
/Gf
è deprecato e verrà rimosso nella versione successiva di Visual C++. -
/G7
viene aggiunta l'opzione del compilatore. - L'opzione
/GS
del compilatore è stata migliorata per proteggere le variabili locali da sovraccarichi diretti del buffer. - L'opzione
/noBool
del compilatore è stata rimossa. Il compilatore ora consente dibool
apparire solo come parola chiave (e non come identificatore) in un file di codice sorgente C++. - Il tipo
long long
è ora disponibile cometypedef
di__int64
. Nota che il supporto perlong long
nel CRT non è ancora disponibile. - L'opzione
/Zm
del compilatore specifica ora il limite di allocazione della memoria dell'intestazione precompilata. - "_InterlockedCompareExchange istruzione intrinseca è ora documentata."
- _InterlockedDecrement funzione intrinseca ora documentata.
- _InterlockedExchange funzione intrinseca ora documentata.
- _InterlockedExchangeAdd ora è documentato come intrinseco.
- _InterlockedIncrement funzione intrinseca ora documentata.
- Funzione intrinseca _ReadWriteBarrier aggiunta.
Attributi
-
implements
l'attributo è ora documentato.
Funzionalità del linker
Sono state aggiunte le opzioni del linker seguenti:
- /ASSEMBLYDEBUG
- /ASSEMBLYLINKRESOURCE
- Firma Ritardata
- /KEYFILE
- /KEYCONTAINER
- /SAFESEH
MASM
La direttiva .SAFESEH e l'opzione /safeseh
ml.exe sono state aggiunte.