2017-09-19 2 views
0

je la structure suivante dans mon fichier cpp:passer un struct C++ à l'application aC#

struct EntityData 
{ 
    char globalId[512]; 
    int mySpeed; 
    double x; 
    double y; 
    double z; 
    double h; 
    double p; 
    double r; 
}; 

J'ai une méthode qui obtient un # index et retourne la structure correcte:

extern "C" { __declspec(dllexport) getDataStruct(int index) 

cette méthode est exposée afin que je puisse utiliser cette méthode dans mon application C# et je continue à obtenir une erreur:

marshal directive exception.

mon code C#:

[DllImport("my64.dll")] 
[return: MarshalAs(UnmanagedType.LPStruct)] 
public static extern EntityDataRx getDataStruct(int index); 

[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi, Pack = 1)] 
public struct EntityDataRx 
{ 
    [MarshalAs(UnmanagedType.LPStr, SizeConst = 512)] 
    StringBuilder globalId; 
    int mySpeed; 
    double x; 
    double y; 
    double z; 
    double h; 
    double p; 
    double r; 
} 

Que manque-t-il?

+1

Avez-vous essayé 'char []' ou 'CHAINE' au lieu de 'StringBuilder'? –

+0

Essayé les deux mais cela n'a pas fonctionné, même exception – KBE

+0

Essayez avec 'UnmanagedType.ByValArray' ou' ByValTStr' et 'char []'. 'LPStr' devrait être utilisé avec' char * 'alors peut-être que cela va résoudre le problème. –

Répondre

0

Enfin résolu. La question est que de la structure de cpp je retourne un pointeur vers la structure:

struct EntityData 
{ 
    char globalId[512]; 
    int mySpeed; 
    double x; 
    double y; 
    double z; 
    double h; 
    double p; 
    double r; 
}; 

et dans mon application C#:

[DllImport("listenHLA1516e_64.dll")] 
    //[return: MarshalAs(UnmanagedType.Struct)] **cancelled not necessary** 
    public static extern IntPtr getDataStruct(int index); 

    [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)] 
    public struct EntityDataRx 
    { 
     [MarshalAs(UnmanagedType.ByValArray, SizeConst = 512)] 
     char[] globalId; 
     int mySpeed; 
     double x; 
     double y; 
     double z; 
     double h; 
     double p; 
     double r; 
    } 

    IntPtr a = getDataStruct(i); 
    EntityDataRx ent = (EntityDataRx)Marshal.PtrToStructure(a, typeof(EntityDataRx)); 
4

De l'msdn documentation page il dit:

The ByValTStr type is used for inline, fixed-length character arrays that appear within a structure. Other types apply to string references contained within structures that contain pointers to strings.

juger donc par votre structure de

struct EntityData 
{ 
    char globalId[512]; 
    // ... 
} 

Vous devez définir votre structure C# comme tel:

[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi, Pack = 1)] 
public struct EntityDataRx 
{ 
    [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 512)] 
    char[] globalId; 
    // ... 
} 

LPStr est utilisé lorsque vous avez "un pointeur vers un tableau à terminaison nulle de caractères ANSI" mais ce que vous avez à la place est un tableau de longueur fixe.