CreateProcess, Nom du processus.

Messages postés
97
Date d'inscription
vendredi 19 octobre 2007
Statut
Membre
Dernière intervention
18 décembre 2013
- - Dernière réponse : grandyaka54
Messages postés
97
Date d'inscription
vendredi 19 octobre 2007
Statut
Membre
Dernière intervention
18 décembre 2013
- 6 janv. 2012 à 11:35
Bonjour à tous,

J'utilise dans mon programme la fonction CreateProcess() pour lancer une autre application.

Quand je lance cette application manuellement, je vois dans l'onglet Processus du Gestionnaire des tâches, le nom complet de mon application qui s'appelle EBICSMoteur.exe or quand je le lance depuis le CreateProcess(), le nom de mon application est tronqué en EBISCM~1.exe ou EBISCM~2.exe

Je souhaiterai, quand je lance mon application par la fonction CreateProcess(), le nom reste en entier.

Voici mon code :

function TFonctions.LanceComEBICS(DossierAppli: String): Byte;
var
  StartInfo : TStartupInfo;
  ProcInfo  : TProcessInformation;
  CreateOK  : Boolean;
  Commande  : String;
  NomUtil   : String;
  cExe      : array [0..255] of Char;
  sExe      : String;
  fnFile    : TFileName;
  ProcEbics : Dword;
Begin

  NomUtil := '"Standard"';

  fnFile := ExtractFilePath(Application.ExeName) + 'EBICSMoteur.exe';
  FindExecutable(PChar(ExtractFileName(fnFile)), PChar(ExtractFilePath(fnFile)), cExe);
  sExe := String(cExe);

  FillChar(StartInfo,SizeOf(TStartupInfo), #0);  // Mise à zéro de la structure StartInfo

  //Seule la taille est renseignée, toutes les autres options laissées à zéro prendront les valeurs par défaut
  ZeroMemory(@StartInfo, SizeOf(StartInfo));
  StartInfo.cb          := SizeOf(StartInfo);      
  StartInfo.dwFlags     := STARTF_USESHOWWINDOW;   
  StartInfo.wShowWindow := SW_NORMAL;              

  FillChar(ProcInfo,SizeOf(TProcessInformation), #0);

  Commande := '"' + fnfile + '" "' + DossierAppli + '" '+ NomUtil;

  CreateOK := CreateProcess(PChar(sExe), 
                            PChar(Commande), 
                            nil, 
                            nil, 
                            False,
                            CREATE_NEW_CONSOLE + NORMAL_PRIORITY_CLASS + CREATE_DEFAULT_ERROR_MODE,
                            nil, 
                            PChar(ExtractFilePath(fnFile)), 
                            StartInfo, 
                            ProcInfo);

  if CreateOK then  //CreateOK est à True si le process est bien créé.
  begin

    ProcEbics := ProcInfo.dwProcessId;

    //Tant que mon EBICS tourne , on traite les messages pour ne pas figer l'application
    repeat
      Application.ProcessMessages;
      EnumWindows(@EbicsAuPremierPlan, ProcEbics);
    until WaitForSingleObject(ProcInfo.hProcess, 100) = WAIT_OBJECT_0 ;

    try
      CloseHandle(ProcInfo.hThread);   //On Close le Thread
      CloseHandle(ProcInfo.hProcess);  //On Close le Process
    except;
    end;

    Result := 0; //Ici, la télétrans a bien fonctionné. On met donc RESULT à 0.

  end
  else begin  
    //Si on a pas pu lancer le process de la télétrans.
    Result := 13;
    ShowMessage(SysErrorMessage(GetLastError));
  end;

end;


Merci pour votre aide.

Cordialement.
Afficher la suite 

12 réponses

Messages postés
1270
Date d'inscription
samedi 14 août 2004
Statut
Membre
Dernière intervention
5 avril 2012
0
Merci
Bonjour

A tout hasard, as-tu essayé en encadrant le nom de ton exécutable avec des guillemets "" ?
sExe := '"' + String(cExe) + '"' ;


N.B. Cela devrait être fait pour les paramètres lpApplicationName, lpCommandLine et lpCurrentDirectory de la fonction CreateProcess.

Cordialement.[hr]"L'imagination est plus importante que le savoir." Albert Einstein
Commenter la réponse de WhiteHippo
Messages postés
97
Date d'inscription
vendredi 19 octobre 2007
Statut
Membre
Dernière intervention
18 décembre 2013
5
0
Merci
Bonjour WhiteHippo,

Merci de m'apporter ton aide. Je me suis empressé de mettre en place ton idée.
Mais hélas, le CreateProcess plante et me donne comme message d'erreur : Syntaxe du nom de fichier, de répertoire ou de volume incorrecte.

Je continu à chercher...

Merci.
Commenter la réponse de grandyaka54
Messages postés
1270
Date d'inscription
samedi 14 août 2004
Statut
Membre
Dernière intervention
5 avril 2012
0
Merci
J'ai fait un test avec l'executable XNResourceditor.exe sous XP avec le code suivant compilé sous Delphi XE2 :

function LancerExe(const ExeAvecChemin : String): Byte;
var
  StartInfo : TStartupInfo;
  ProcInfo  : TProcessInformation;
  CreateOK  : Boolean;
  Commande  : String;
  NomUtil   : String;
  cExe      : array [0..255] of Char;
  sExe      : String;
  fnFile    : TFileName;
  ProcEbics : Dword;
Begin
  FillChar(StartInfo,SizeOf(TStartupInfo), #0);  // Mise à zéro de la structure StartInfo

  //Seule la taille est renseignée, toutes les autres options laissées à zéro prendront les valeurs par défaut
  ZeroMemory(@StartInfo, SizeOf(StartInfo));
  StartInfo.cb          := SizeOf(StartInfo);
  StartInfo.dwFlags     := STARTF_USESHOWWINDOW;
  StartInfo.wShowWindow := SW_NORMAL;

  FillChar(ProcInfo,SizeOf(TProcessInformation), #0);

  Commande := PChar(ExeAvecChemin) +' "' + PChar(ExeAvecChemin) + '"';

  CreateOK := CreateProcess(NIL,
                            PChar(Commande),
                            nil,
                            nil,
                            False,
                            CREATE_NEW_CONSOLE + NORMAL_PRIORITY_CLASS + CREATE_DEFAULT_ERROR_MODE,
                            nil,
                            nil,
                            StartInfo,
                            ProcInfo);

  if CreateOK then  //CreateOK est à True si le process est bien créé.
  begin

    ProcEbics := ProcInfo.dwProcessId;

    //Tant que mon EBICS tourne , on traite les messages pour ne pas figer l'application
    repeat
      Application.ProcessMessages;
//      EnumWindows(@EbicsAuPremierPlan, ProcEbics);
    until WaitForSingleObject(ProcInfo.hProcess, 100) = WAIT_OBJECT_0 ;

    try
      CloseHandle(ProcInfo.hThread);   //On Close le Thread
      CloseHandle(ProcInfo.hProcess);  //On Close le Process
    except;
    end;

    Result := 0; //Ici, la télétrans a bien fonctionné. On met donc RESULT à 0.

  end
  else begin
    //Si on a pas pu lancer le process de la télétrans.
    Result := 13;
    ShowMessage(SysErrorMessage(GetLastError));
  end;

end;

// Code d'appel
LancerExe( 'D:\utilitaires\XN Resource Editor\XNResourceEditor.exe' ) ;


A priori, pas de souci de nom long.

N.B. Attention les chaines sous Delphi XE2 sont de l'UNICODE et non de l'ANSI.

Cordialement.[hr]"L'imagination est plus importante que le savoir." Albert Einstein
Commenter la réponse de WhiteHippo
Messages postés
97
Date d'inscription
vendredi 19 octobre 2007
Statut
Membre
Dernière intervention
18 décembre 2013
5
0
Merci
Merci pour ton aide.

J'ai repris exactement ton code et j'ai le même problème.

De mon côté je développe sous Delphi2010.

Cordialement.
Commenter la réponse de grandyaka54
Messages postés
1270
Date d'inscription
samedi 14 août 2004
Statut
Membre
Dernière intervention
5 avril 2012
0
Merci
Donc, le problème vient de chez toi.

Quelques questions :
[list] Tu as essayé avec "XNRexourceEditor.exe" (disponible ici) ?
Ton système d'exploitation ?
Ton exécutable est une application 16 bits, une application maison ?/listCordialement.[hr]"L'imagination est plus importante que le savoir." Albert Einstein
Commenter la réponse de WhiteHippo
Messages postés
97
Date d'inscription
vendredi 19 octobre 2007
Statut
Membre
Dernière intervention
18 décembre 2013
5
0
Merci
J'ai essayé de lancer XNRexourceEditor.exe via ton code ci-dessus et mon code, je n'ai effectivement pas eu le problème.

Je suis sur un XP Pro SP3.
C'est une application maison 32bits.

Je vais regarder du côté de mon application dans ses propriétés de compilation.

Cordialement.
Commenter la réponse de grandyaka54
Messages postés
1270
Date d'inscription
samedi 14 août 2004
Statut
Membre
Dernière intervention
5 avril 2012
0
Merci
Dernière idée, après je sèche .
Aurais-tu des ressources en 16 bits dans un .res intégré au projet qui a généré l’exécutable ?

Cordialement.[hr]"L'imagination est plus importante que le savoir." Albert Einstein
Commenter la réponse de WhiteHippo
Messages postés
97
Date d'inscription
vendredi 19 octobre 2007
Statut
Membre
Dernière intervention
18 décembre 2013
5
0
Merci
Autant pour moi, je suis en Delphi2009, je me suis trompé d'une année.

J'ai regardé le fichier .res et je trouve la mention win32.

En tout cas merci pour ton aide et tes idées. Ce n'est pas handicapant pour l'exécution du programme.

Cordialement.
Commenter la réponse de grandyaka54
Messages postés
3809
Date d'inscription
vendredi 23 juillet 2004
Statut
Modérateur
Dernière intervention
1 septembre 2019
32
0
Merci
Salut à tous et meilleurs voeux,

Delphi 2009 est aussi en unicode donc le problème ne vient pas de là.

mais je serais curieux de savoir ce que te retourne la variable : "sExe" ???

je pense que le problème se situ ici

@WhiteHippo:

content de te voir à nouveau parmi nous ...
c'est toujours un plaisir et un enrichissement, pour tous, de lire.


[hr]@+Cirec
[hr]
Commenter la réponse de Cirec
Messages postés
97
Date d'inscription
vendredi 19 octobre 2007
Statut
Membre
Dernière intervention
18 décembre 2013
5
0
Merci
Bonjour Cirec,

Pour ta curiosité, la variable sExe retournée par la fonction FindExecutable donne un nom court en l’occurrence pour moi EBICSM~1.exe ou EBICSM~2.exe

  
  FindExecutable(PChar(ExtractFileName(fnFile)), PChar(ExtractFilePath(fnFile)), cExe);
  sExe := String(cExe);


Mais si dans le CreateProcess, je mets ''Nil'' a la place de ''sExe'', le résultat reste le même.

  
  CreateOK := CreateProcess(NIL,
                            PChar(Commande),
                            ...

  CreateOK := CreateProcess(sExe,
                            PChar(Commande),
                            ...


Cordialement,

Merci.
Commenter la réponse de grandyaka54
Messages postés
3809
Date d'inscription
vendredi 23 juillet 2004
Statut
Modérateur
Dernière intervention
1 septembre 2019
32
0
Merci
ah ... je m'en doutais ...

[quote=grandyaka54]Mais si dans le CreateProcess, je mets ''Nil'' a la place de ''sExe'', le résultat reste le même.
/quote

et c'est normal ... si tu lui donnes un nom court en entrée tu auras un nom court dans le Gestionnaire des tâches.
Fais le teste avec le nom long.
voir "GetLongPathName"

si tu utilise les deux premier paramètres:
  CreateOK := CreateProcess(PChar(sExe), 
                            PChar(Commande), 
pas besoin de guillemets.

en revanche si tu mets nil
il faut séparer le Chemin+nom de l'application des paramètres par des guillemets sinon il sera mal interprété.


[hr]@+Cirec
[hr]
Commenter la réponse de Cirec
Messages postés
97
Date d'inscription
vendredi 19 octobre 2007
Statut
Membre
Dernière intervention
18 décembre 2013
5
0
Merci
Merci Cirec pour ton aide...
Dès que possible, je mets en place tes conseils.
Commenter la réponse de grandyaka54