IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Langage Delphi Discussion :

Pb traduction C en Delphi


Sujet :

Langage Delphi

  1. #1
    Membre à l'essai
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Avril 2009
    Messages
    13
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 55
    Localisation : France, Isère (Rhône Alpes)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2009
    Messages : 13
    Points : 20
    Points
    20
    Par défaut Pb traduction C en Delphi
    Bonjour,

    J'ai un souci de traduction de C vers Delphi:

    Voici le code en C (qui marche):
    Code c : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    ...
    typedef char           *IScan_String;
    ....
     
    typedef struct _IScan_ResultConsts
    {
        IScan_String IFC_OK;
        IScan_String IFC_OK_NOT_EXECUTED;
        IScan_String IFC_OK_DONT_SELL;
        IScan_String IFC_ERROR_ITEM_UNKNOWN;
        IScan_String IFC_ERROR_NOT_AN_ITEM;
        IScan_String IFC_ERROR_IS_COUPON;
        IScan_String IFC_ERROR_IS_VOUCHER;
        IScan_String IFC_ERROR_IS_REFUND;
        IScan_String IFC_ERROR_IS_CUSTOMERCARD;
        IScan_String IFC_ERROR_IS_GIFTCARD;
        IScan_String IFC_ERROR_IS_ETOPUP;
        IScan_String IFC_ERROR_TRY_ALTERNATIVE;
        IScan_String IFC_ERROR_ILLEGAL_CALL;
        IScan_String IFC_ERROR_OTHER;
        IScan_String IFC_PRINT_REPRINT;
        IScan_String IFC_PRINT_RETRY;
        IScan_String IFC_PRINT_ABORT;
        IScan_String IFC_SIGNATURE_ACCEPTED;
        IScan_String IFC_SIGNATURE_DECLINED;
    }
    IScan_ResultConsts;
     
    ....
     
    LIB_EXPORT const IScan_TextEntryConsts *iscan_constsTextEntry;
     
     
    ....
     
    memset (&g_result, 0, sizeof g_result);
     
    ....
     
    g_result.id = iscan_constsResult->IFC_OK;
    ...

    voici ce que j'ai traduit: (qui ne marche pas):
    type

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    IScan_String=PChar;
     
     _IScan_ResultConsts = packed record
          IFC_OK : IScan_String;
          IFC_OK_NOT_EXECUTED : IScan_String;
          IFC_OK_DONT_SELL : IScan_String;
          IFC_ERROR_ITEM_UNKNOWN : IScan_String;
          IFC_ERROR_NOT_AN_ITEM : IScan_String;
          IFC_ERROR_IS_COUPON : IScan_String;
          IFC_ERROR_IS_VOUCHER : IScan_String;
          IFC_ERROR_IS_REFUND : IScan_String;
          IFC_ERROR_IS_CUSTOMERCARD : IScan_String;
          IFC_ERROR_IS_GIFTCARD : IScan_String;
          IFC_ERROR_IS_ETOPUP : IScan_String;
          IFC_ERROR_TRY_ALTERNATIVE : IScan_String;
          IFC_ERROR_ILLEGAL_CALL : IScan_String;
          IFC_ERROR_OTHER : IScan_String;
          IFC_PRINT_REPRINT : IScan_String;
          IFC_PRINT_RETRY : IScan_String;
          IFC_PRINT_ABORT : IScan_String;
          IFC_SIGNATURE_ACCEPTED : IScan_String;
          IFC_SIGNATURE_DECLINED : IScan_String;
       end;
     IScan_ResultConsts = _IScan_ResultConsts;
     PIScan_ResultConsts = ^IScan_ResultConsts; 
     
      Tiscan_constsResult=function : PIScan_ResultConsts; cdecl;
     
    var
      iscan_constsResult:Tiscan_constsResult;
     
    begin
    // fonction iscan_constsResult appelé dynamiquement
     
      getmem(g_result,sizeof(g_result)); 
      FillChar(g_result^, sizeof(g_result), 0); 
      try
        g_result^.Id:=iscan_constsResult^.IFC_OK;
    	...
      finally
        FreeMem(g_result);
      end;
      ...
     end;
    la fonction "iscan_constsResult" me retourne une violation d'accès...

    Quelqu'un peut il m'aider ?

  2. #2
    Expert éminent sénior
    Avatar de ShaiLeTroll
    Homme Profil pro
    Développeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    13 518
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Seine Saint Denis (Île de France)

    Informations professionnelles :
    Activité : Développeur C++\Delphi
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juillet 2006
    Messages : 13 518
    Points : 25 036
    Points
    25 036
    Par défaut
    manque un peu de code en delphi, tu aurais pu mettre l'unité complète



    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    getmem(g_result,sizeof(g_result));
    ...
    g_result^....
    je suppose que g_result est un PIScan_ResultConsts donc sizeof(g_result) renvoie 4, utilise à la place sizeof(g_result^));
    tu as oublié le & du code C qui devait être inversé pour le Delphi ...



    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    g_result^.Id:=iscan_constsResult^.IFC_OK
    ;

    attention, cela ne copiera RIEN, cela ne fait que faire pointer ID sur IFC_OK, cela n'est qu'un pointeur !

    une Structure de constante ??? mais elles sont bien initalisé quelques part, sinon tout est à nil, ou pire à une valeur indéterminée !
    Aide via F1 - FAQ - Guide du développeur Delphi devant un problème - Pensez-y !
    Attention Troll Méchant !
    "Quand un homme a faim, mieux vaut lui apprendre à pêcher que de lui donner un poisson" Confucius
    Mieux vaut se taire et paraître idiot, Que l'ouvrir et de le confirmer !
    L'ignorance n'excuse pas la médiocrité !

    L'expérience, c'est le nom que chacun donne à ses erreurs. (Oscar Wilde)
    Il faut avoir le courage de se tromper et d'apprendre de ses erreurs

  3. #3
    Membre à l'essai
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Avril 2009
    Messages
    13
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 55
    Localisation : France, Isère (Rhône Alpes)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2009
    Messages : 13
    Points : 20
    Points
    20
    Par défaut
    Désolé pour le manque de code, j'ai voulu résumé (un peu trop) mon problème.
    Par contre, je ne peux pas mettre tout le code, l'unité est trop grande
    En plus je me suis trompé dans le copier/coller du code.
    Je vais essayer d'être plus précis.

    La dll que j'essaie de lire est s'appelle: iscan.dll

    La première unité (iscan_md.h) en C:

    Code c : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    #ifndef ISCAN_MD_H_INCLUDED
    #define ISCAN_MD_H_INCLUDED
     
    #if !(defined(_MSC_VER) && defined(_M_IX86))
        #error Microsoft C Compiler on Windows Intel x86 platform required.
    #endif
     
    #define ISCAN_ADAPTER_VERSION       "1.5"
     
    typedef int             IScan_Integer;
    typedef double          IScan_Double;
    typedef char           *IScan_String;
    typedef __int64         IScan_Amount;
    typedef char           *IScan_Date;
    typedef char           *IScan_Time;
    typedef void           *IScan_Heap;
    typedef unsigned        IScan_Size;
     
    typedef enum { ISCAN_FALSE, ISCAN_TRUE } IScan_Boolean;
     
    #if defined(__SYSISCAN__)
        #define LIB_EXPORT      __declspec(dllexport)
    #else
        #define LIB_EXPORT      __declspec(dllimport)
    #endif
     
    /* make sure we have the proper default alignment */
    #pragma pack(push, 8)
     
    #endif

    la 2ème unité (iscan.h) en C (que je resume):

    Code c : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    ...
    #include "iscan_md.h"
    ...
    typedef struct _IScan_POSStatusConsts
    {
        IScan_String STATUS_OPERATOR_SIGNED_OFF;
        IScan_String STATUS_OPERATOR_SIGNED_ON;
        IScan_String STATUS_TRANSACTION_ACTIVE;
        IScan_String STATUS_ERROR;
    }
    IScan_POSStatusConsts;
     
    typedef struct _IScan_Result
    {
        IScan_String id;    // error or success identifier
    }
    IScan_Result;
    ...
    LIB_EXPORT const IScan_POSStatusConsts *iscan_constsPOSStatus;
    ...

    la 3ème unité (iscandemo.c) en C que je résume aussi:
    Code c : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    ...
    #include "iscan.h"
    ...
    static IScan_Result      g_result;
    ...
    int main(int argc, char *argv[])
    {
        // les 2 fonction ci-dessous sont là à titre
        // indicatif et ne sont pas l'objet du problème
        iscan = iscan_connect(...
        g_heap = iscan_heapCreate(...
     
        memset (&g_result, 0, sizeof g_result);
        g_result.id = iscan_constsResult->IFC_OK;
        ...
    }
    ...

    Voici mon code en Delphi un peu plus détaillé mais résumé tout de même:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    type
      ...
      IScan_String = Pchar;
      ...
      _IScan_POSStatusConsts = record
        STATUS_OPERATOR_SIGNED_OFF : IScan_String;
        STATUS_OPERATOR_SIGNED_ON : IScan_String;
        STATUS_TRANSACTION_ACTIVE : IScan_String;
        STATUS_ERROR : IScan_String;
      end;
      IScan_POSStatusConsts = _IScan_POSStatusConsts;
      PIScan_POSStatusConsts = ^IScan_POSStatusConsts;
     
      _IScan_Result = record
        id : IScan_String;
      end;
      IScan_Result = _IScan_Result;
      PIScan_Result = ^IScan_Result;
      ...
      Tiscan_constsPOSStatus=function : PIScan_POSStatusConsts; cdecl;
      ...
    var
      g_result : PIScan_Result;
      HLibDLL:THandle;
      ...
      iscan_constsPOSStatus:Tiscan_constsPOSStatus;
      ...
    procedure InitDll;
    procedure Commence;
     
    implementation
     
    procedure InitDll;
    begin
      HLibDLL:=LoadLibrary(PChar('iscan.dll'));
      ...
      iscan_constsPOSStatus:=Tiscan_constsPOSStatus(getprocaddress(HLibDLL,'iscan_constsPOSStatus'));
      ...
    end;
     
    procedure Commence;
    begin
      InitDll;
      // les 2 fonction ci-dessous sont là à titre
      // indicatif et ne sont pas l'objet du problème
      iscan := iscan_connect(...
      g_heap := iscan_heapCreate (...
     
      getmem(g_result,sizeof(IScan_Result));
      FillChar(g_result^, sizeof(IScan_Result), 0);   
      g_result^.id:=iscan_constsResult^.IFC_OK;
      ...
    end;
    Mon problème est dans la fonction Commence quand je fais
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    g_result^.id:=iscan_constsResult^.IFC_OK;
    J'ai essayé avec ceci:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    MessageBox(Handle,iscan_constsResult^.IFC_OK,'Test',MB_OK);
    juste avant "GetMem", mais j'ai la même erreur:
    Violation d'accès dans le module iscan.dll
    J'espère avoir été plus clair

  4. #4
    Membre à l'essai
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Avril 2009
    Messages
    13
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 55
    Localisation : France, Isère (Rhône Alpes)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2009
    Messages : 13
    Points : 20
    Points
    20
    Par défaut
    J'ai fait un autre test si ça peut éclairé:

    j'ai changé:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
      Tiscan_constsPOSStatus=function : PIScan_POSStatusConsts; cdecl;
    en
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
      Tiscan_constsPOSStatus=function : IScan_POSStatusConsts; cdecl;
    j'ai déclaré la variable:
    j'ai mis:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
      toto:=@iscan_constsResult;
      MessageBox(Handle,PChar(PIScan_ResultConsts(toto)^.IFC_OK),'Test',MB_OK);
    à la place de:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
      g_result^.id:=iscan_constsResult^.IFC_OK;
    lorsque je mets un point d'arrêt sur messageBox,
    puis en faisant Evaluer/Modifier (Ctrl+F7),
    le résultat est étonnant: tout est décalé sur un autre record !!
    comme si il y avait un problème d'alignement des champs

  5. #5
    Expert éminent sénior
    Avatar de ShaiLeTroll
    Homme Profil pro
    Développeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    13 518
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Seine Saint Denis (Île de France)

    Informations professionnelles :
    Activité : Développeur C++\Delphi
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juillet 2006
    Messages : 13 518
    Points : 25 036
    Points
    25 036
    Par défaut
    Euh, tu as essayé de remplacer cdecl par stdcall ?
    j'ai toujours eu des DLL en stdcall

    vérifie aussi que g_result est à nil si il n'est pas alloué !
    Aide via F1 - FAQ - Guide du développeur Delphi devant un problème - Pensez-y !
    Attention Troll Méchant !
    "Quand un homme a faim, mieux vaut lui apprendre à pêcher que de lui donner un poisson" Confucius
    Mieux vaut se taire et paraître idiot, Que l'ouvrir et de le confirmer !
    L'ignorance n'excuse pas la médiocrité !

    L'expérience, c'est le nom que chacun donne à ses erreurs. (Oscar Wilde)
    Il faut avoir le courage de se tromper et d'apprendre de ses erreurs

  6. #6
    Membre à l'essai
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Avril 2009
    Messages
    13
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 55
    Localisation : France, Isère (Rhône Alpes)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2009
    Messages : 13
    Points : 20
    Points
    20
    Par défaut
    J'ai tout essayé:
    cdecl, stdcall, pascal, register, safecall avec et sans far

    le résultat est toujours le même, mais par contre, il a toujours la même valeur !!

  7. #7
    Membre confirmé
    Avatar de gb_68
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Août 2006
    Messages
    232
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Haut Rhin (Alsace)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Août 2006
    Messages : 232
    Points : 546
    Points
    546
    Par défaut
    Bonjour,
    Citation Envoyé par chrisgood Voir le message
    Code c : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    #include "iscan_md.h"
    ...
    typedef struct _IScan_POSStatusConsts
    {
        IScan_String STATUS_OPERATOR_SIGNED_OFF;
        IScan_String STATUS_OPERATOR_SIGNED_ON;
        IScan_String STATUS_TRANSACTION_ACTIVE;
        IScan_String STATUS_ERROR;
    }
    IScan_POSStatusConsts;
     
    LIB_EXPORT const IScan_POSStatusConsts *iscan_constsPOSStatus;
    [...]
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    type
      ...
      _IScan_POSStatusConsts = record
        STATUS_OPERATOR_SIGNED_OFF : IScan_String;
        STATUS_OPERATOR_SIGNED_ON : IScan_String;
        STATUS_TRANSACTION_ACTIVE : IScan_String;
        STATUS_ERROR : IScan_String;
      end;
      IScan_POSStatusConsts = _IScan_POSStatusConsts;
      PIScan_POSStatusConsts = ^IScan_POSStatusConsts;
      ...
      Tiscan_constsPOSStatus=function : PIScan_POSStatusConsts; cdecl;
    var
      iscan_constsPOSStatus:Tiscan_constsPOSStatus;
    Dans le code C fourni, iscan_constsPOSStatus n'est pas une fonction, mais une variable globale .
    As-tu essayé :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    iscan_constsPOSStatus:PIScan_POSStatusConsts;
    implementation
     
    procedure InitDll;
    begin
      HLibDLL:=LoadLibrary(PChar('iscan.dll'));
      ...  iscan_constsPOSStatus:=PIScan_POSStatusConsts(getprocaddress(HLibDLL,'iscan_constsPOSStatus'));
      ...
    end;

  8. #8
    Membre à l'essai
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Avril 2009
    Messages
    13
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 55
    Localisation : France, Isère (Rhône Alpes)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2009
    Messages : 13
    Points : 20
    Points
    20
    Par défaut
    Bonjour,

    et merci à ceux qui essayent de me répondre (ce n'est pas facile comme question )

    Pour gb_68,

    pour moi, déclarer une variable en fonction (qui renvoie un pointeur de record) ou en pointeur de record, en local ou en global renvoie toujours la même valeur (en delphi).

    J'ai tout de même essayer ta suggestion, et effectivement, la valeur renvoyée est la même:
    PChar(iscan_constsPOSStatus^.IFC_OK) est égale à "|s°" pour les 2 cas.

    Pour info, j'ai remplacé tous mes "record" par "packed record" et j'ai toujours la même valeur ("|s°").

    J'ai la sensation d'être décalé dans mes appels dll, comme s'il y avait un décalage d'adressage !!

  9. #9
    Membre confirmé
    Avatar de gb_68
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Août 2006
    Messages
    232
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Haut Rhin (Alsace)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Août 2006
    Messages : 232
    Points : 546
    Points
    546
    Par défaut

    J'ai oublié une chose : GetProcAddress renvoie un pointeur vers le symbole exporté - ici sur la variable. Or celle-ci étant déjà un pointeur, c'est un pointeur de pointeur qui devrait être renvoyé.
    Il faudrait essayer quelque chose comme ça :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
     
    type 
      ...
      PIScan_POSStatusConsts = ^IScan_POSStatusConsts;
      PPIScan_POSStatusConsts = ^PIScan_POSStatusConsts;
    implementation
    var 
      iscan_constsPOSStatus:PIScan_POSStatusConsts;
    procedure InitDll;
    begin
      HLibDLL:=LoadLibrary(PChar('iscan.dll'));
      ...
      iscan_constsPOSStatus:=PPIScan_POSStatusConsts(
        GetProcAddress(HLibDLL,'iscan_constsPOSStatus') )^;
      ...
    end;

  10. #10
    Membre à l'essai
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Avril 2009
    Messages
    13
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 55
    Localisation : France, Isère (Rhône Alpes)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Avril 2009
    Messages : 13
    Points : 20
    Points
    20
    Par défaut
    Alors là,

    profile bas

    Bravo, super et merci 500000 fois de ta réponse !!!

    mon problème est maintenant résolu

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Aide pour traduction C++ vers Delphi
    Par BobaL dans le forum Langage
    Réponses: 8
    Dernier message: 25/01/2011, 18h47
  2. Problème de traduction C vers Delphi
    Par BobaL dans le forum API, COM et SDKs
    Réponses: 2
    Dernier message: 23/02/2009, 14h15
  3. traduction structure en Delphi (suite)
    Par skywaukers dans le forum Delphi
    Réponses: 10
    Dernier message: 15/06/2007, 22h41
  4. Traduction C++ vers Delphi
    Par lil_jam63 dans le forum Langage
    Réponses: 6
    Dernier message: 05/07/2004, 13h10
  5. probleme traduction C vers Delphi
    Par zinaif dans le forum Langage
    Réponses: 3
    Dernier message: 27/06/2003, 08h51

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo