Forum |  HardWare.fr | News | Articles | PC | Prix | S'identifier | S'inscrire | Shop Recherche
1775 connectés 

  FORUM HardWare.fr
  Programmation
  C#/.NET managed

  [resolut]passage d'un tableau de structure à une DLL C

 



 Mot :   Pseudo :  
 
Bas de page
Auteur Sujet :

[resolut]passage d'un tableau de structure à une DLL C

n°2371701
jungledede
Posté le 16-12-2020 à 10:43:11  profilanswer
 

Hello,
 
 
J'ai un soucis que je ne comprends pas encore très bien.
Je débute en c#, ça fait 2 ans que je suis sur du dev en C.
 
J'ai une lib codé en C qui est exporté en DLL.
Une des fonctions de la DLL attends un pointer de structure. Le pointer est là car c'est un tableau à passer.
 
la structure est celle-ci:

Code :
  1. typedef struct
  2. {
  3.    char Channel_Name[32];
  4.    int Channel_Index;
  5.    double Channel_Range;
  6.    eTermination Channel_Configuration;
  7.    eUnit Channel_Unit;
  8.    stSensors Sensor_Description;
  9. }Type_Channels_Description;


 
le prototype de la fonction C est la suivante:

Code :
  1. int DLLEXPORT Drv_AIBoard_Config(int Module, Type_Channels_Description *Channels_Description, int Channel_Number)


 
ça marche très bien sur mes autres appli codés en C.
 
Maintenant j'ai une autre app que je fait en C#, mais je réutilise la DLL en C.
 
j'ai chargé la dll et le prototype coté c# comme ça:

Code :
  1. [DllImport("C:/Applications/bin/NationalInstruments_NVH.dll", CharSet = CharSet.Unicode, CallingConvention = CallingConvention.Cdecl)]
  2. public static extern int Drv_AIBoard_Config(int Module,  StructType_Channels_Description[] Channels_Description, int Channel_Number);


Au début j'avais ajouté le mot ref, mais au vus des printfs coté C j'avais une salade de pointer  [:jungledede]  
 
La structure coté c# est comme ça:

Code :
  1. [StructLayout(LayoutKind.Sequential)]
  2.     public unsafe struct StructType_Channels_Description
  3.     {
  4.         // public string Channel_Name; //marche pas a cause de  taille non définit et de mémoire non managé.
  5.         public fixed char Channel_Name[32];//32 bytes max !  
  6.         public int Channel_Index;
  7.         public double Channel_Range;
  8.         public Termination Channel_Configuration;
  9.         public Unit Channel_Unit;
  10.         public StructSensors Sensor_Description;
  11.     }


 
D'après msdn je suis obligé d'utiliser le unsafe pour fixer la taille de la chaine de caractère.
Par contre j'ai un doute sur le layout sequential au vus de mon soucis.
 
 
Du coup ça semble bien compiler et tout, sauf que  :o , quand je fait un printf coté C pour lire contenu, j'ai que le premier caractère de la chaine qui est bon, tout les autres champs de la struct sont à 0..   :pt1cable:  
 
Des idées?
 
 
 
ps: une astuce pour que le déboguer puisse aller dans ma dll c?
Le code en C est fait avec National Instrument Labwindows/CVI


Message édité par jungledede le 16-12-2020 à 14:45:15

---------------
Monde de merde | Restez curieux
mood
Publicité
Posté le 16-12-2020 à 10:43:11  profilanswer
 

n°2371710
TotalRecal​l
Posté le 16-12-2020 à 11:02:54  profilanswer
 

Il ne faut pas faire des bricoles comme ajouter un [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 32)]
au dessus de ton string, et/ou spécifier CharSet dans le StructLayout ?

 

C'est juste des pistes à creuser, mais la solution exacte. Je n'ai pas souvent recours à des DLL en C donc je dois pondre moi même les appels.


Message édité par TotalRecall le 16-12-2020 à 11:04:02

---------------
Réalisation amplis classe D / T      Topic .Net - C# @ Prog
n°2371715
jungledede
Posté le 16-12-2020 à 11:07:33  profilanswer
 

au début j'avais trouver une page sur msdn qui faisait le lien entre les type de ptr et les équivalents c#, mais impossible de la retrouver, et pas mis en favoris xD
 
je vais voir ce que je trouve avec Marshal


---------------
Monde de merde | Restez curieux
n°2371717
TotalRecal​l
Posté le 16-12-2020 à 11:12:46  profilanswer
 

Pas UnmanagedType justement ? C'est l'énum qui contient les différents types.

 

Sinon pour éviter d'avoir à écrire à la main tout le code pour appeler des lib unmanaged, il y a des projets comme https://github.com/mono/CppSharp qui peuvent peut être (?) aider, si tu as beaucoup d'appels à faire. On en trouve d'autres aussi.


Message édité par TotalRecall le 16-12-2020 à 11:16:05

---------------
Réalisation amplis classe D / T      Topic .Net - C# @ Prog
n°2371726
jungledede
Posté le 16-12-2020 à 11:53:37  profilanswer
 

mouhah ça marche  [:bultom:1]  
 
merci à toi pour la piste.
 
Du coup la struct deviens :
 

Code :
  1. [StructLayout(LayoutKind.Sequential)]
  2.     public unsafe struct StructType_Channels_Description
  3.     {
  4.         [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 32)]
  5.         public string Channel_Name;
  6.         public int Channel_Index;
  7.         public double Channel_Range;
  8.         public Termination Channel_Configuration;
  9.         public Unit Channel_Unit;
  10.         public StructSensors Sensor_Description;
  11.     }


 
et c'est maintenant biens plus simple pour remplir le champs name sans faire de copie de char à base de boucle for.
 
et coté déclaration du prototype de la DLL, j'ai ajouté un marshal mais qui spécifie que c'est un tableau.
 

Code :
  1. [DllImport("C:/Application/bin/NationalInstruments_NVH.dll", CharSet = CharSet.Unicode, CallingConvention = CallingConvention.Cdecl)]
  2. public static extern int Drv_AIBoard_Config(int Module, [MarshalAs(UnmanagedType.LPArray)] StructType_Channels_Description[] Channels_Description, int Channel_Number);


 
 
c'est bien le c#  [:aqualung]


---------------
Monde de merde | Restez curieux

Aller à :
Ajouter une réponse
  FORUM HardWare.fr
  Programmation
  C#/.NET managed

  [resolut]passage d'un tableau de structure à une DLL C

 

Sujets relatifs
[resolu] [C] [GCC] static volatile variable et warning (ou pas)Programme tri à bulle C++
soucis pour paramétrer un tableau html[RESOLU]formulaires imbriqués dans un tableau
Passage de paramètres du JQUERY au PHPEnvoie et réception d'un tableau d'entier(socket
Récupérer résultat d'une réquête dans un tableau en shell (ksh)[C] Problème de pointeur
extraire dans une variable le contenu d'une structureCompter le nombre de caractères en C
Plus de sujets relatifs à : [resolut]passage d'un tableau de structure à une DLL C


Copyright © 1997-2018 Hardware.fr SARL (Signaler un contenu illicite / Données personnelles) / Groupe LDLC / Shop HFR