[R] DllCall et passage d'une chaîne

Aide et conseils concernant AutoIt et ses outils.
Règles du forum
.
Répondre
jlf
Niveau 2
Niveau 2
Messages : 15
Enregistré le : sam. 24 juil. 2010 13:42
Status : Hors ligne

[R] DllCall et passage d'une chaîne

#1

Message par jlf »

Bonjour,

J'essaye de faire appel à une DLL que je développe moi-même. Cette DLL est écrite en C et compilée avec gcc sous Cygwin. Mon problème est que je n'arrive pas à trouver la syntaxe pour transmettre une chaîne de caractères.
Test n°1 (avec func1 dans la DLL) : retour d'un entier => tout ok
Test n°2 (avec func2 dans la DLL) : la DLL attend un "char ifn[256]" et fait un test ultra-basique
Test n°3 (avec func3 dans la DLL) : la DLL attend un "char *ifn" et fait le même test ultra-basique

Je pense que la func3 est à préférer car la taille de la chaîne n'est pas fixée arbitrairement.

J'ai essayé avec "str", "wstr", "char" (avec ou sans "*"), rien n'y fait.

str, str*, wstr, wstr* => AutoIT3.exe ended.rc:-1073741819
char, char* => @error=1

Visiblement, ça fonctionne "moins mal" avec "char", mais dans ce cas je récupère un code d'erreur à 1 (unable to use the DLL file)

Ci-joint, tous les codes sources. Tous les fichiers ont un nom suffisamment explicite. La DLL "cygwin1.dll" est requise et est fournie. Si vous préférez recompiler ma DLL (confiance, sécurité...), le makefile est fourni (attention, fichier au format UNIX impératif chez moi !!)
► Afficher le texteCode de la DLL
► Afficher le texteCode de test1.au3
► Afficher le texteCode de test2.au3
► Afficher le texteCode de test3.au3
Voilà, si quelqu'un peut m'aider à trouver où est l'erreur... :D
Solution fortement appréciée :mrgreen:

Cordialement,


JLF
Fichiers joints
test.zip
(1004.48 Kio) Téléchargé 52 fois
Modifié en dernier par jlf le jeu. 16 févr. 2012 12:54, modifié 1 fois.
Avatar du membre
jchd
AutoIt MVPs (MVP)
AutoIt MVPs (MVP)
Messages : 2284
Enregistré le : lun. 30 mars 2009 22:57
Localisation : Sud-Ouest de la France (43.622788,-1.260864)
Status : Hors ligne

Re: [..] DllCall et passage d'une chaîne

#2

Message par jchd »

Il y a plus d'une erreur.

Dans le code C :
Tes fonctions ont fortement intérêt a être qualifiées __declspec(dllexport)
Ensuite, ta fonction 2 n'a aucun sens : elle déclare un paramètre qu'elle alloue elle-même ???

Maintenant, sous AutoIt :
Tu ne spécifies pas la convention d'appel cdecl (c'est stdcall par défaut)
Tu dois employer le type str. Si ta chaîne contient de l'Unicode, emploie directement wstr, mais exit des fonctions stdio et la fonction en C doit utiliser un paramètre chaîne Unicode.

Une fois ceci fixé :

Code : Tout sélectionner

#include <stdio.h>

__declspec(dllexport) int func1(void) {
    return 1234;
}

__declspec(dllexport) int func3(char *ifn) {
    if (strcmp(ifn, "in.txt")) {
        return 10;
    } else {
        return 11;
    }
}

Code : Tout sélectionner

gcc -O2 -lm -shared test.c -o test.dll

Code : Tout sélectionner

ConsoleWrite("Test func1" & @CRLF)
Local $result1 = DllCall("test.dll", "int:cdecl", "func1")
Local $error1  = @error
ConsoleWrite("$error1     = " & $error1     & @CRLF)
ConsoleWrite("$result1[0] = " & $result1[0] & @CRLF)

ConsoleWrite("Test func3" & @CRLF)
Local $result3 = DllCall("test.dll", "int:cdecl", "func3", "str", "in.txt")
Local $error3  = @error
ConsoleWrite("$error3     = " & $error3 & @CRLF)
If Not $error3 Then
    ConsoleWrite("$result3[0] = " & $result3[0] & @CRLF)
EndIf

Code : Tout sélectionner

Test func1
$error1     = 0
$result1[0] = 1234
Test func3
$error3     = 0
$result3[0] = 11
La cryptographie d'aujourd'hui c'est le taquin plus l'électricité.
jlf
Niveau 2
Niveau 2
Messages : 15
Enregistré le : sam. 24 juil. 2010 13:42
Status : Hors ligne

Re: [..] DllCall et passage d'une chaîne

#3

Message par jlf »

Bonjour,

Merci de l'aide, et effectivement plusieurs erreurs...
J'ai une fonction en C et je pensais que seul l'appel (et le passage d'argument) était en cause. Ma fonction en C doit faire des opérations sur des fichiers, et là ça coince (alors qu'un programme en C appelant cette même DLL est OK). D'où une nouvelle demande d'aide... :mrgreen:

La fonction "func4_1" est OK (preuve que DLL bien compilée). Les fonction "func4" et "func4_2" (qui est encore plus basique) me renvoient "AutoIT3.exe ended.rc:-1073741819"

D'avance merci :D
► Afficher le texteCode de la func4.dll
► Afficher le texteCode du test-case test4.au3
Avatar du membre
jchd
AutoIt MVPs (MVP)
AutoIt MVPs (MVP)
Messages : 2284
Enregistré le : lun. 30 mars 2009 22:57
Localisation : Sud-Ouest de la France (43.622788,-1.260864)
Status : Hors ligne

Re: [..] DllCall et passage d'une chaîne

#4

Message par jchd »

Perso, je n'ai eu aucun problème. Seule différence : j'emploie toujours MinGW car Cygnus impose ses propres DLLs qui causent parfois des soucis dans certains contextes.
► Afficher le texte
► Afficher le texte
► Afficher le texte
La cryptographie d'aujourd'hui c'est le taquin plus l'électricité.
jlf
Niveau 2
Niveau 2
Messages : 15
Enregistré le : sam. 24 juil. 2010 13:42
Status : Hors ligne

Re: [..] DllCall et passage d'une chaîne

#5

Message par jlf »

Bonjour,

Effectivement tout marche mieux avec MinGW. D'ailleurs j'avais remarqué qu'un "printf" dans une fonction C (compilée avec CygWin) bloquait le scripts AU3. Et là, avec MinGW, tout semble OK
Merci encore pour l'aide :)

Cordialement
Répondre