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

Delphi Discussion :

[D5] Handle de DLL identique pour tout les threads


Sujet :

Delphi

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre averti
    Inscrit en
    Mai 2002
    Messages
    24
    Détails du profil
    Informations forums :
    Inscription : Mai 2002
    Messages : 24
    Par défaut [D5] Handle de DLL identique pour tout les threads
    Bonjour,

    Dans le cadre d'un petit service d'impression, je lance mes éditions dans des threads (fonctionnement multitache).

    Chaque thread effectue un loadlibrary (chargement dynamique) de ma dll qui s'occupe de l'édition.

    Mais le handle de la dll est toujours le même dans chaque thread.

    Est-ce normal ?

    L'appel à GetProcAddress me donne donc certainement la même adresse pour la fonction 'imprimer'.

    Au final, je me retrouve avec des violations d'accès lorsque 2 threads tournent en même temps. Ils doivent se mélanger les pinceaux.

    N'est il pas possible d'avoir 2 instances bien séparées de la dll ?

    Voici la structure principale de mon thread (code épuré)

    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
     
    unit SIEDIL01;
    interface
    uses
      Windows, Classes, Sysutils, sinlibl01, forms, dbtables;
    type
      Tthread_edit = class(TThread)
      private
        { Déclarations privées }
     
        ch : string;
     
        ImprimerThread : TImprimerThread; 
     
      protected
        procedure Execute; override;
      public
        property Terminated;
        constructor create(pserial, pch, pnompr : string);
      end;
     
    implementation
     
    //-------------------------------------------------------------------------
    constructor Tthread_edit.create(pserial, pch, pnompr: string);
    begin
      UHandle := 0;
      FreeOnTerminate := true;
      Priority := tpNormal;
      ch := pch;
      inherited create(false);
    end;
    //-------------------------------------------------------------------------
    procedure Tthread_edit.Execute;
    begin
      try
        try
            retour := '';
            UHandle := LoadLibrary('siimpd00.dll');
            if UHandle <> 0 then begin
              @ImprimerThread := GetProcAddress(UHandle, 'Imprimer');
              if @ImprimerThread <> nil then begin
                ImprimerThread(ch, retour) ;
              end; 
            end;
        except
        end;
      finally
        FreeLibrary(UHandle); 
      end;
    end;
    //-------------------------------------------------------------------------

  2. #2
    Expert confirmé
    Avatar de Jipété
    Profil pro
    Inscrit en
    Juillet 2006
    Messages
    11 148
    Détails du profil
    Informations personnelles :
    Localisation : France, Hérault (Languedoc Roussillon)

    Informations forums :
    Inscription : Juillet 2006
    Messages : 11 148
    Par défaut
    Yep !

    Vais encore dire des grosses bêtises et me faire enguirlander, mais bon, je te jette en pâture deux/trois idées comme ça :
    Mais le handle de la dll est toujours le même dans chaque thread.

    Est-ce normal ?
    J'aurais tendance à dire oui : d'un point de vue multitâche un thread c'est jamais qu'un process, avec son propre espace d'adressage, alors.
    Mais relatif à lui, comme tout process.
    Donc, en supposant qu'il démarre à *son* adresse 1000 et qu'il charge l'adresse de la fonction qui t'intéresse à *son* adresse 2000, ben si d'un niveau supérieur tu clones ce process, tu en crées un second qui fonctionne avec les mêmes paramètres.
    Non ?
    Chacun de tes threads va bricoler avec *son* adresse 2000 mais physiquement il s'agit de 2 emplacements mémoire différents gérés par l'OS.


    J'ai regardé ton code, il semble normal, à première vue.
    Et si le problème était dans le dll ?
    Qu'elle soit pas capable de gérer une seconde demande pendant qu'elle en meule une première ?
    Gamberge là-dessus !

    Mes 2 cts,
    JP

  3. #3
    Membre averti
    Inscrit en
    Mai 2002
    Messages
    24
    Détails du profil
    Informations forums :
    Inscription : Mai 2002
    Messages : 24
    Par défaut
    Citation Envoyé par Jipété
    Et si le problème était dans le dll ?
    Qu'elle soit pas capable de gérer une seconde demande pendant qu'elle en meule une première ?
    C'est bien là le problème : 1 thread à la fois ça fonctionne .
    Mais dès qu'il y en a plusieurs, il n'y en a qu'un qui aboutit.

    Cela veut bien dire qu'il y a des conflits lors de l'exécution de la dll mais ces conflits ne se produisent pas lorsque je lance 2 exe séparés.
    Ils ont chacun un handle différent pour la dll et ça marche.

    Ne peut-on pas isoler parfaitement les threads en amont comme si on lancait 2 exécutables séparés ?

  4. #4
    Membre émérite Avatar de slimjoe
    Homme Profil pro
    Inscrit en
    Juin 2005
    Messages
    647
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : Canada

    Informations forums :
    Inscription : Juin 2005
    Messages : 647
    Par défaut
    Peut-être est-ce que ça peut t'aider :

    http://www.experts-exchange.com/Prog..._20323003.html

  5. #5
    Membre averti
    Inscrit en
    Mai 2002
    Messages
    24
    Détails du profil
    Informations forums :
    Inscription : Mai 2002
    Messages : 24
    Par défaut
    La proposition qu'ils donnent est celle que j'emploie.
    Dans ce cas, le handle de la dll est unique pour chaque thread.

    Désolé mais ça ne m'avance pas.

    En plus, il faut s'inscrire pour voir la solution de leur topics.
    Je n'ai vu qu'une fois leur réponse et depuis elle est cachée !!

  6. #6
    Membre émérite Avatar de slimjoe
    Homme Profil pro
    Inscrit en
    Juin 2005
    Messages
    647
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : Canada

    Informations forums :
    Inscription : Juin 2005
    Messages : 647
    Par défaut
    J'y suis inscrit mais je ne crois pas que la réponse puisse t'aider d'avantage (sauf peut-être le lien vers MSDN). La voici quand même :

    Citation Envoyé par Experts Exchange
    Accepted Answer from Lee_Nover
    Date: 07/16/2002 05:35AM MDT
    Grade: B
    Accepted Answer

    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
    type
      TFunction = function(x: Integer): Integer; stdcall;
     
    ...
    var
      Func: TFunction;
      hLib: Cardinal;
      param, result: Integer;
    begin
      hLib:=LoadLibrary('mylib.dll'); // load the dll dynamically
      if hLib = 0 then exit;
      try
        // now get our functions entry point
        @Func:=GetProcAddress(hLib, 'TheFunctionName');
        if @Func <> nil then
          result:=Func(param);// simply call out function var as we would any other function
      finally
        FreeLibrary(hLib);
      end;
    end;
    this will call the Func in the calling thread
    this way the library is always loaded in the calling processes memory !

    a more exact explanation here :
    http://msdn.microsoft.com/library/de...c/dll_1o8p.asp
    P.S.
    Je ne sais pas si la citation contrevient à un quelconque copyright. Si c'est le cas, dites-le moi et j'effacerai le tout.

Discussions similaires

  1. Réponses: 1
    Dernier message: 06/03/2006, 14h16
  2. Ma requête ne calcul pas pour tout les champs
    Par leloup84 dans le forum Requêtes
    Réponses: 10
    Dernier message: 01/03/2006, 12h59
  3. Ma requête ne calcul pas pour tout les champs
    Par leloup84 dans le forum Langage SQL
    Réponses: 2
    Dernier message: 01/03/2006, 10h11
  4. Site pour toutes les résolutions...
    Par Angeldu74 dans le forum Balisage (X)HTML et validation W3C
    Réponses: 13
    Dernier message: 24/02/2006, 23h14
  5. Réponses: 6
    Dernier message: 06/10/2004, 10h41

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