Compartilhar via


aviso do compilador (nível 2) C4412

Mensagem de erro

'função': assinatura de função contém o tipo 'type'; objetos C++ não seguros sejam transmitidas entre código puro e misto ou nativo.

O compilador detectou uma situação potencialmente não seguro pode resultar em um erro em tempo de execução: uma telefonar é feita a partir de um /clr:pure compiland para uma função que foi importada por meio de dllimport e a assinatura de função contém um tipo não seguro. Um tipo não é seguro se ele contém uma função de membro ou tem um membro de dados que é um tipo não seguro ou um caminho indireto a um tipo não seguro.

Isso não é seguro por causa da diferença no padrão convenções entre código pura e nativo de chamada (ou mista nativa e gerenciada).Ao importar (via dllimport) uma função em um /clr:pure compiland, verifique se as declarações de cada tipo na assinatura são idênticas às compiland que exporta a função (tenha cuidado especialmente sobre as diferenças nas convenções de chamada implícitas).

Uma função de membro virtual está especialmente propensa a fornecer resultados inesperados.No entanto, até mesmo uma função não-virtual deve ser testada para garantir que você obtenha os resultados corretos.Se você tiver certeza de que você está obtendo os resultados corretos, você pode ignorar esse aviso.

Para obter mais informações sobre /clr:pure, consulte: Como: Migrar para o / CLR: puro.

C4412 está desativado por padrão.Consulte Avisos do Compilador That Are Off by Padrão e dllexport, DllImport para mais informações.

Para resolver esse aviso, remova todas as funções do tipo.

Exemplo

O exemplo a seguir gera C4412.

// C4412.cpp
// compile with: /c /W2 /clr:pure
#pragma warning (default : 4412)

struct Unsafe {
   virtual void __cdecl Test();
};

struct Safe {
   int i;
};

__declspec(dllimport) Unsafe * __cdecl func();
__declspec(dllimport) Safe * __cdecl func2();

int main() {
   Unsafe *pUnsafe = func();   // C4412
   // pUnsafe->Test();

   Safe *pSafe = func2();   // OK
}

O exemplo a seguir é um arquivo de cabeçalho que declara dois tipos.The Unsafe tipo não é seguro porque tem uma função de membro.

// C4412.h
struct Unsafe {
   // will be __clrcall if #included in pure compilation
   // defaults to __cdecl in native or mixed mode compilation
   virtual void Test(int * pi);

   // try the following line instead
   // virtual void __cdecl Test(int * pi);
};

struct Safe {
   int i;
};

Este exemplo exporta funções com os tipos definidos no arquivo de cabeçalho.

// C4412_2.cpp
// compile with: /LD
#include "C4412.h"

void Unsafe::Test(int * pi) {
   *pi++;
}

__declspec(dllexport) Unsafe * __cdecl func() { return new Unsafe; }
__declspec(dllexport) Safe * __cdecl func2() { return new Safe; }

O padrão de convenção de chamada em um /clr:pure a compilação é diferente de uma compilação nativa. Quando C4412.h está incluído, Test será o padrão para __clrcall. Se você compilar e executar este programa (não use /c), o programa apresentará uma exceção.

O exemplo a seguir gera C4412.

// C4412_3.cpp
// compile with: /W2 /clr:pure /c /link C4412_2.lib
#pragma warning (default : 4412)
#include "C4412.h"

__declspec(dllimport) Unsafe * __cdecl func();
__declspec(dllimport) Safe * __cdecl func2();

int main() {
   int n = 7;
   Unsafe *pUnsafe = func();   // C4412
   pUnsafe->Test(&n);

   Safe *pSafe = func2();   // OK
}