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 :

Exemple de la Faq sur les services ne fonctionne pas


Sujet :

Langage Delphi

  1. #1
    Membre habitué
    Profil pro
    Inscrit en
    Février 2007
    Messages
    341
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 341
    Points : 150
    Points
    150
    Par défaut Exemple de la Faq sur les services ne fonctionne pas
    Bonsoir,

    J'essaye d'utiliser l'exemple des faq concernant les services https://delphi.developpez.com/faq/?p...es-services-NT:

    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
    Type
      PNTServices = ^TNTServices ;
      TNTServices = array[0..4096] of TEnumServiceStatus;
    
    ................
    
    
    Procedure TMainForm.Refresh_Liste_Services(AHandle_SCM : SC_Handle;List : TStringList);
    Var
     Mes_Services : PNTServices;
     ResumeHandle,
     OctetsNecessaires,
     Nombre_Srv : DWord;
     i : Integer;
    begin
     List.Clear;
    
    try
     New(Mes_Services);
     Nombre_Srv := 0;
     OctetsNecessaires:=0;
     ResumeHandle := 0;
     if EnumServicesStatus(AHandle_SCM,
                           SERVICE_WIN32, //Uniquement les services, pas les drivers
                           SERVICE_STATE_ALL, // Peut importe l'état
                           Mes_Services^[0],
                           SizeOf(Mes_Services^),
                           OctetsNecessaires,
                           Nombre_Srv,
                           ResumeHandle)
      then
       For i := 0 to Nombre_Srv-1 do
        //List.Add(Mes_Services^[i].lpServiceName);
        List.Add(Mes_Services^[i].lpDisplayName);
      //else GetlastErrorCode
    
     finally
      Dispose(Mes_Services);
     end;
    end;
    Mais j'ai un message d'erreur à la ligne 19 que j'ai mise en rouge :
    E2010 Types incompatibles : LPENUM_SERVICE_STATUSW et _ENUM_SERVICE_STATUSW

    J'ai regardé dans Winapi.WinSvc, la fonction est :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    function EnumServicesStatus(hSCManager: SC_HANDLE; dwServiceType,
      dwServiceState: DWORD; lpServices: LPENUM_SERVICE_STATUS; cbBufSize: DWORD;
      var pcbBytesNeeded, lpServicesReturned, lpResumeHandle: DWORD): BOOL; stdcall;
    donc, j'ai essayé de comprendre ce qu'était MesServices, mais je doit m'embrouiller dans les pointeurs et les pchar car j'ai essayé plusieurs modifications, mais sans grand résultat.

    Quelqu'un peut-il m'expliquer ce qui ne va pas dans l'exemple de la FAQ ?

    Merci d'avance.

  2. #2
    Membre actif
    Homme Profil pro
    Ingénieur systèmes et réseaux
    Inscrit en
    Décembre 2003
    Messages
    167
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Ingénieur systèmes et réseaux
    Secteur : Distribution

    Informations forums :
    Inscription : Décembre 2003
    Messages : 167
    Points : 208
    Points
    208
    Par défaut
    Bonjour

    perso ce que j'utilise
    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
    Var
      ResumeHandle      : DWORD;
      OctetsNecessaires : DWORD;
      Nombre_Service    : DWORD;
      i                 : Integer;
      err               : integer;
      Mes_Services      : LPENUM_SERVICE_STATUS;
    begin
      fHServiceManager  := OpenSCManager( PChar ( strHostname ), nil, SC_MANAGER_ALL_ACCESS );
      err               := GetLastError ;
      Nombre_Service    := 0;
      OctetsNecessaires := 0;
      ResumeHandle      := 0;
      Mes_Services      := nil;
      if fHServiceManager <> 0 then
      try
        EnumServicesStatus ( fHServiceManager, SERVICE_WIN32, SERVICE_STATE_ALL, Mes_Services, 0, OctetsNecessaires, Nombre_Service, ResumeHandle );
        Mes_Services := AllocMem(OctetsNecessaires);
        if EnumServicesStatus ( fHServiceManager, SERVICE_WIN32, SERVICE_STATE_ALL , Mes_Services, OctetsNecessaires, OctetsNecessaires, Nombre_Service, ResumeHandle ) then
        begin
          For i := 0 to Nombre_Service - 1 do
          begin
            List.Add ( Mes_Services.lpServiceName );
            end;
            inc(Mes_Services);
          end;
        end 
      except
      end;
      if Assigned(Mes_Services) then
      begin
        FreeMem(Mes_Services,OctetsNecessaires);
      end;
    end;

  3. #3
    Expert éminent sénior
    Avatar de ShaiLeTroll
    Homme Profil pro
    Développeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    13 563
    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 563
    Points : 25 165
    Points
    25 165
    Par défaut
    Voir ce sujet Position du Try qui explique la mauvaise utilisation de EnumServicesStatus dans la FAQ

  4. #4
    Membre habitué
    Profil pro
    Inscrit en
    Février 2007
    Messages
    341
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 341
    Points : 150
    Points
    150
    Par défaut
    @fbalien : ton code doit bien fonctionner mais j'ai essayé de modifier l'exemple de la faq pour comprendre.

    Après correction de l'histoire de @ au lieu de ^, le code de la faq fonctionne ... à condition, et c'est pour ça que j'ai galéré, de compiler, puis de le lancer comme administrateur !
    Est-il possible de lancer l'appli depuis delphi en tant qu'administrateur ?

    @shai : merci pour le lien. j'ai cherché hier pendant une heure avant de poster, mais je n'avais rien trouvé ... je suis définitivement nul :o(

    Maintenant que j'ai vu la subtilité entre Mes_Services^[0] et @Mes_Services[0] .... je me doutais bien qu'il y avait un truc de ce genre, mais je me trompe toujours de syntaxe avec ces histoires de pointeurs. J'y travaille, j'essaye de comprendre, je crois avoir compris, et puis quand j'en ai de nouveau besoin ... je m'aperçois que j'ai pas compris ;o)

  5. #5
    Membre habitué
    Profil pro
    Inscrit en
    Février 2007
    Messages
    341
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 341
    Points : 150
    Points
    150
    Par défaut
    Citation Envoyé par navyg Voir le message
    Après correction de l'histoire de @ au lieu de ^, le code de la faq fonctionne ... à condition, et c'est pour ça que j'ai galéré, de compiler, puis de le lancer comme administrateur !
    Est-il possible de lancer l'appli depuis delphi en tant qu'administrateur ?
    Bon, après moults tâtonnements, jai cru qu'il fallait faire quelque chose sur manifeste, mais la solution toute simple est : ... exécuter delphi en tant qu'administrateur ... tout bête

  6. #6
    Expert éminent sénior
    Avatar de ShaiLeTroll
    Homme Profil pro
    Développeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    13 563
    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 563
    Points : 25 165
    Points
    25 165
    Par défaut
    SC_MANAGER_ENUMERATE_SERVICE suffit à la place de SC_MANAGER_ALL_ACCESS
    Cela ne requiert pas de droit d'administration

  7. #7
    Membre habitué
    Profil pro
    Inscrit en
    Février 2007
    Messages
    341
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 341
    Points : 150
    Points
    150
    Par défaut
    Encore une précision absolument géniale ! Merci Shai

  8. #8
    Membre habitué
    Profil pro
    Inscrit en
    Février 2007
    Messages
    341
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 341
    Points : 150
    Points
    150
    Par défaut
    Citation Envoyé par ShaiLeTroll Voir le message
    SC_MANAGER_ENUMERATE_SERVICE suffit à la place de SC_MANAGER_ALL_ACCESS
    Cela ne requiert pas de droit d'administration
    pour cette instruction ça fonctionne :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    AHandle_SCM:= OpenSCManager(PChar(Computer_Name), nil, SC_MANAGER_ENUMERATE_SERVICE);
    mais après j'ai besoin quand même d'être admin pour ces deux instructions (je n'ai pas trouvé d'arguments qui passent en lançant le programme en "normal"

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Handle_Service := OpenService(Handle_SCM, Pchar(ServiceGetKeyName(NomService)), SERVICE_ALL_ACCESS
    J'arrive à avoir le handle du service en utilisant SERVICE_INTERROGATE, mais après à l'instruction :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    QueryServiceStatus(Handle_Service, Status_Service);
    j'ai toujours un résultat 0 pour Status_Service.dwCurrentState

    Une autre astuce ?

  9. #9
    Membre actif
    Homme Profil pro
    Ingénieur systèmes et réseaux
    Inscrit en
    Décembre 2003
    Messages
    167
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Ingénieur systèmes et réseaux
    Secteur : Distribution

    Informations forums :
    Inscription : Décembre 2003
    Messages : 167
    Points : 208
    Points
    208
    Par défaut
    Bonjour

    utilise GENERIC_READ a la place de SERVICE_ALL_ACCESS
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Handle_Service := OpenService(Handle_SCM, Pchar(ServiceGetKeyName(NomService)), GENERIC_READ)

  10. #10
    Rédacteur/Modérateur

    Avatar de SergioMaster
    Homme Profil pro
    Développeur informatique retraité
    Inscrit en
    Janvier 2007
    Messages
    15 097
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 68
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique retraité
    Secteur : Industrie

    Informations forums :
    Inscription : Janvier 2007
    Messages : 15 097
    Points : 41 081
    Points
    41 081
    Billets dans le blog
    62
    Par défaut
    Citation Envoyé par navyg Voir le message
    Une autre astuce ?
    Même si je sais que c'est utiliser le marteau et l'enclume il y a toujours la possibilité des WMI qui, à ma connaissance, ne sont pas limités par le "système de sécurité" windows

  11. #11
    Expert éminent sénior
    Avatar de ShaiLeTroll
    Homme Profil pro
    Développeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    13 563
    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 563
    Points : 25 165
    Points
    25 165
    Par défaut
    Je ne peux pas répondre mieux que SergioMaster, je dois être administrateur en partie sur mon poste de développeur

    Sinon pourquoi OpenService ?
    Ce n'est pas utile pour la liste !

    OpenSCManager + EnumServicesStatus

  12. #12
    Membre habitué
    Profil pro
    Inscrit en
    Février 2007
    Messages
    341
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 341
    Points : 150
    Points
    150
    Par défaut
    Bonjour,

    Je reprends cet aspect car je n'arrive pas à tout simplement obtenir le status du service mariadb

    Si je ne suis pas administrateur, je n'arrive même pas à exécuter cette instruction

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    QueryServiceStatus(Handle_Service, Status_Service);
    j'ai toujours un résultat 0 pour le résultat dans Status_Service.dwCurrentState

    Si j'indique d'exécuter le programme en tant qu'administrateur, ça fonctionne ...
    Je pensais que juste pour lire le status d'un service il ne fallait pas de privilège particulier ...

    @shai
    Sinon pourquoi OpenService ?
    Ce n'est pas utile pour la liste !

    OpenSCManager + EnumServicesStatus
    Malgré toute ma bonne volonté, je n'arrive pas à configurer correctement tous les paramètres de EnumServicesStatus, que je n'ai trouvé que comme EnumServicesStatusA ou W ou EnumServicesStatusExA ou W.
    Serait-il possible d'avoir un exemple ?
    Merci d'avance.

  13. #13
    Membre habitué
    Profil pro
    Inscrit en
    Février 2007
    Messages
    341
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 341
    Points : 150
    Points
    150
    Par défaut
    Citation Envoyé par navyg Voir le message
    Bonjour,

    Je reprends cet aspect car je n'arrive pas à tout simplement obtenir le status du service mariadb

    Si je ne suis pas administrateur, je n'arrive même pas à exécuter cette instruction

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    QueryServiceStatus(Handle_Service, Status_Service);
    j'ai toujours un résultat 0 pour le résultat dans Status_Service.dwCurrentState

    Si j'indique d'exécuter le programme en tant qu'administrateur, ça fonctionne ...
    Je pensais que juste pour lire le status d'un service il ne fallait pas de privilège particulier ...

    @shai


    Malgré toute ma bonne volonté, je n'arrive pas à configurer correctement tous les paramètres de EnumServicesStatus, que je n'ai trouvé que comme EnumServicesStatusA ou W ou EnumServicesStatusExA ou W.
    Serait-il possible d'avoir un exemple ?
    Merci d'avance.
    Au temps pour moi ! Désolé, c'est le début du post ... bon je me rassemble et je vous dis ...

  14. #14
    Expert éminent sénior
    Avatar de ShaiLeTroll
    Homme Profil pro
    Développeur C++\Delphi
    Inscrit en
    Juillet 2006
    Messages
    13 563
    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 563
    Points : 25 165
    Points
    25 165
    Par défaut
    Le lien fourni dans ma première contient un code qui me semblait simple à reprendre pour la partie EnumServicesStatus
    EnumServicesStatusA c'est la même chose de D3 à D2007 car Char = AnsiChar
    EnumServicesStatusW c'est la même chose à parti de D2009 car Char = WideChar

    Citation Envoyé par ShaiLeTroll Voir le message
    Voir ce sujet Position du Try qui explique la mauvaise utilisation de EnumServicesStatus dans la FAQ

  15. #15
    Membre habitué
    Profil pro
    Inscrit en
    Février 2007
    Messages
    341
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 341
    Points : 150
    Points
    150
    Par défaut
    Oui tu as été très clair ... c'est moi qui ne le suis pas ...

  16. #16
    Membre habitué
    Profil pro
    Inscrit en
    Février 2007
    Messages
    341
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 341
    Points : 150
    Points
    150
    Par défaut
    Bon, j'arrive à trouver l'état du service avec EnumServicesStatus, mais si je trouve qu'il est arrêté, j'ai une erreur "Accès refusé" lorsque je veux le relancer ... sauf si je suis administrateur.

    Je suppose que la seule manière de lancer un service c'est d'exécuter le programme en tant qu'administrateur ?

  17. #17
    Membre habitué
    Profil pro
    Inscrit en
    Février 2007
    Messages
    341
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 341
    Points : 150
    Points
    150
    Par défaut
    Alors l'affaire est plus compliquée qu'elle ne semblait.

    Même lorsque je suis administrateur, tout dépend de la façon dont j'exécute certaines instructions.
    L'unité ressemble à ç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
    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
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
    112
    113
    114
    115
    116
    117
    118
    119
    120
    121
    122
    123
    124
    125
    126
    127
    128
    129
    130
    131
    132
    133
    134
    135
    136
    137
    138
    139
    140
    141
    142
    143
    144
    145
    146
    147
    148
    149
    150
    151
    152
    153
    154
    155
    156
    157
    158
    159
    160
    161
    162
    163
    164
    165
    166
    167
    168
    169
    170
    171
    172
    173
    174
    unit utils_services;
    
    interface
    uses
       system.classes, system.types, system.sysutils, messages, windows,
       vcl.forms, vcl.dialogs, winsvc;
    
    type
       DisplayService=(Key,Display);
       PNTServices = ^TNTServices ;
       TNTServices = array[0..4096] of TEnumServiceStatus;
    
    var
       Handle_SCM: SC_Handle; // handle du manager de control des services
       Handle_Service: SC_Handle; // handle d'un service
       TypeDemarrageSrvCourant : DWord;
    
       Function ConnectToServicesManager(Computer_Name : String;Var AHandle_SCM: SC_Handle):Boolean;
       function  ServiceGetName(AServiceName : string ;ATypeAffichage:DisplayService) : string;
       function  ServiceGetKeyName(AServiceDisplayName : string ) : string;
       function  ServiceGetDisplayName(AServiceKeyName : string ) : string;
       Procedure Pause_No_Bloc_Application(Millisenconde : Cardinal);
       Function etat_service(AHandle_SCM : SC_Handle; Nom_Service: string): integer;
       function lance_service(NomService: string): boolean;
    
    
    implementation
    
    function lance_service(NomService: string): boolean;
    var
       NomPC : String;
       index: integer;
       Status_Service : TServiceStatus;
       EtatDuService : Word;
       ArrayOfArguments : PChar;
       lpBuffer: array[0..MAX_COMPUTERNAME_LENGTH] of char;
       nSize: dword;
       etat_serv: integer;
    
    begin
    Result:=false;
    NSize := Length(LpBuffer);
    if GetComputerName(lpBuffer,NSize)
    then
       begin
       NomPC :=  LpBuffer;
       if ConnectToServicesManager(NomPC,Handle_SCM)
       then
          begin
          etat_serv:=etat_service(Handle_SCM, NomService);
          if etat_serv=-1 then
             begin
             MessageDlg('Le service n''existe pas', mtError, [mbOK], 0);
             Exit;
             end;
             Case etat_serv of
             SERVICE_STOPPED,
             SERVICE_PAUSED :
                Begin
                ArrayOfArguments := nil;
                
                Handle_Service := OpenService(Handle_SCM, Pchar(ServiceGetKeyName(NomService)), SERVICE_INTERROGATE );
                Handle_Service := OpenService(Handle_SCM, Pchar(ServiceGetKeyName(NomService)), SERVICE_ALL_ACCESS);
                
                if StartService(Handle_Service, 0, ArrayOfArguments) = false then
                   MessageDlg(SysErrorMessage(GetLastError), mtError, [mbOK], 0)
                else
                   MessageDlg('Service MariaDB démarré.', mtInformation, [mbOK], 0);
                Pause_No_Bloc_Application(1000);
                end;
             SERVICE_RUNNING :
                Begin
                Result:=true;
                exit;
                end;
             end; // case of
          if etat_service(Handle_SCM, NomService)=SERVICE_RUNNING
          then
             begin
             Result:=true;
             end;
          end
       else
          showmessage('Service '+nomservice+' non trouvé');
       end
    else
       showmessage('Nom du PC non trouvé');
    end;
    
    Function etat_service(AHandle_SCM : SC_Handle; Nom_Service: string): integer;
    Var
     Mes_Services : PNTServices;
     ResumeHandle,
     OctetsNecessaires,
     Nombre_Srv : DWord;
     i, etat_serv : Integer;
    begin
    Result:=-1;
    Mes_Services:=nil;
       try
       New(Mes_Services);
       Nombre_Srv := 0;
       OctetsNecessaires:=0;
       ResumeHandle := 0;
       if EnumServicesStatus(AHandle_SCM,
                             SERVICE_WIN32, //Uniquement les services, pas les drivers
                             SERVICE_STATE_ALL, // Peut importe l'état
                             @Mes_Services[0],
                             SizeOf(Mes_Services^),
                             OctetsNecessaires,
                             Nombre_Srv,
                             ResumeHandle)
       then
          For i := 0 to Nombre_Srv-1 do
             begin
             if Mes_Services^[i].lpDisplayName=Nom_Service then
                begin
                result:=Mes_Services^[i].ServiceStatus.dwCurrentState;
                exit;
                end;
             end;
       finally
         Dispose(Mes_Services);
       end;
    end;
    
    
    Procedure Pause_No_Bloc_Application(Millisenconde : Cardinal);
    Var  H : Cardinal;
    Begin
    H := GetTickCount;
    WHile H+Millisenconde >= GetTickCount do
       Application.ProcessMessages;
    end;
    
    Function ConnectToServicesManager(Computer_Name : String;Var AHandle_SCM: SC_Handle):Boolean;
    Begin
    AHandle_SCM:= OpenSCManager(PChar(Computer_Name), nil, SC_MANAGER_ENUMERATE_SERVICE);
    //AHandle_SCM:= OpenSCManager(PChar(Computer_Name), nil, SC_MANAGER_ALL_ACCESS);
    Result :=AHandle_SCM <> 0;
    end;
    
    
    function ServiceGetName(AServiceName : string ;ATypeAffichage:DisplayService) : string;
    Const LongueurMaxNomSvr = 255;
    
    var NomService : Array[0..LongueurMaxNomSvr+1] of Char;
        TailleBuffer: DWord;
        Erreur: Boolean;
    
    begin
    FillChar(NomService,SizeOf(NomService),#0);
    TailleBuffer:=LongueurMaxNomSvr+1;
    
       Case ATypeAffichage of
       Key : Erreur:=GetServiceKeyName(Handle_SCM,PChar(AServiceName),NomService,TailleBuffer)=False;
       Display: Erreur:=GetServiceDisplayName(Handle_SCM,PChar(AServiceName),NomService,TailleBuffer)=False;
       end;
    
    if Erreur
    then MessageDlg(SysErrorMessage(GetLastError), mtError, [mbOK], 0);
    Result :=NomService;
    end;
    
    function ServiceGetKeyName(AServiceDisplayName : string ) : string;
    begin
    Result:=ServiceGetName(AServiceDisplayName,Key);
    end;
    
    function ServiceGetDisplayName(AServiceKeyName : string ) : string;
    begin
    Result:=ServiceGetName(AServiceKeyName,Display);
    end;
    Tout se joue sur les lignes en rouge dans le code (62 et 63).
    Si je vais chercher le handle du service avec un paramètre SERVICE_INTERROGATE j'obtiens une valeur, et si je vais chercher le handle avec SERVICE_ALL_ACCESS, j'obtiens une autre valeur pour le handle.
    Et en fonction de la valeur de ce handle, l'instruction suivante StartService(Handle_Service, 0, ArrayOfArguments) ne réagit pas de la même manière, même si je suis administrateur.
    Il faut absolument le handle rendu par SERVICE_ALL_ACCESS pour que je puisse lancer le service.

  18. #18
    Modérateur
    Avatar de tourlourou
    Homme Profil pro
    Biologiste ; Progr(amateur)
    Inscrit en
    Mars 2005
    Messages
    3 871
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 61
    Localisation : France, Yvelines (Île de France)

    Informations professionnelles :
    Activité : Biologiste ; Progr(amateur)

    Informations forums :
    Inscription : Mars 2005
    Messages : 3 871
    Points : 11 361
    Points
    11 361
    Billets dans le blog
    6
    Par défaut
    Bonjour,
    L'aide msdn nous dit qu'OpenService retourne un handle sur le service, valable pour le seul processus appelant, et non le handle du service.
    Je ne sais pas si ce handle lui-même contient une info de privilège ou (et ?) si ce qu'on demande ensuite sur ce handle fait l'objet d'une vérification des privilèges.
    Ce pourrait être un élément d'explication. Du coup, un handle renvoyé par une demande "pour info" ne permettrait à bon droit pas les mêmes choses qu'un autre demandé "pour action", quelque soit le niveau de privilèges du demandeur.

  19. #19
    Rédacteur/Modérateur

    Avatar de SergioMaster
    Homme Profil pro
    Développeur informatique retraité
    Inscrit en
    Janvier 2007
    Messages
    15 097
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 68
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique retraité
    Secteur : Industrie

    Informations forums :
    Inscription : Janvier 2007
    Messages : 15 097
    Points : 41 081
    Points
    41 081
    Billets dans le blog
    62
    Par défaut
    En tout cas, s'il s'agit de lancer des services, ce qui n'était pas indiqué au début, ma suggestion d'utiliser les WMI tombe à l'eau, car ce n'est qu'un moyen d'interrogation (uniquement des SELECT)

  20. #20
    Membre habitué
    Profil pro
    Inscrit en
    Février 2007
    Messages
    341
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 341
    Points : 150
    Points
    150
    Par défaut
    Merci tourlourou, j'ai pensé la même chose.
    Je croyais bêtement depuis des années qu'un handle était seulement un pointeur vers l'adresse de l'objet, mais peut-être que le type thandle cache d'autres choses ... En tout cas, ça m'a permis de retourner vers les api de windows, qui sont clairement conçues pour être attaquées en C ;o)
    C'est vraiment compliqué à utiliser avec des paramètres qui sont des pointeurs, des adresses, des buffer .... enfin que des trucs compliqués.
    Ca serait plus simple de passer des paramètres string, integer, etc ... enfin que des types simples.

Discussions similaires

  1. [FAQ] Pourquoi les signaux ne fonctionnent pas ?
    Par Rachel dans le forum Contribuez
    Réponses: 0
    Dernier message: 01/11/2012, 12h18
  2. 2007 : onclick sur les onglets ne fonctionnent pas
    Par charliejo dans le forum IHM
    Réponses: 5
    Dernier message: 16/02/2009, 10h35
  3. Suggestion sur les services offertent sur un site intranet!
    Par ghyosmik dans le forum Général Conception Web
    Réponses: 3
    Dernier message: 30/01/2006, 16h14
  4. Question sur les services windows
    Par bilb0t dans le forum Windows
    Réponses: 8
    Dernier message: 09/11/2005, 15h31

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