Valeur de sortie d'une programme

Résolu
Oniria Messages postés 292 Date d'inscription dimanche 14 mars 2004 Statut Membre Dernière intervention 18 décembre 2014 - 27 août 2007 à 16:52
Oniria Messages postés 292 Date d'inscription dimanche 14 mars 2004 Statut Membre Dernière intervention 18 décembre 2014 - 31 août 2007 à 09:02
Bonjour,

J'aimerais savoir comment faire pour assigner une valeur de sortie à un programme et la récupérer dans un autre.
Pour mieux comprendre, j'ai un programme de gestion de compte bancaire qui utilise un TProcess pour executer un autre programme qui permet d'imprimer un relevé de compte. J'ai séparé les deux car le programme de gestion est enorme, et windows a du mal à gérer la mémoire.
Donc j'aimerais que mon programme d'impression puisse renvoyer une valeur comme en C ( int main(void) ) désolé pour l'exemple en C. Le programme de gestion récupére cette valeur pour l'utiliser : savoir si l'impression s'est bien passé, si l'utilisateur a annuler l'impression, etc...

Merci

A bientot

12 réponses

cs_rt15 Messages postés 3874 Date d'inscription mardi 8 mars 2005 Statut Modérateur Dernière intervention 7 novembre 2014 13
29 août 2007 à 13:44
Salut,

Si tu veux vraiment faire un deuxième programme qui renvoie une valeure de retour, c'est tout à fait possible. Il faut créer le processus avec CreateProcess. Le programme appelé peut par exemple utiliser ExitProcess pour renvoyer un code d'erreur. Il faut ensuite que le créateur attende le deuxième processus, avec WaitForSingleObject par exemple (Peut être sur un thread pour ne pas le figer...).

Finalement, un appel à GetExitCodeProcess permet de récupérer le code renvoyé (En lui passant le hanlde récupéré dans le CreateProcess).

Pour avoir un dépassement de pile sous Windows sans faire de récursif, il faut y aller vraiment (très) (très) très fort sur les variables locales. Et un processus doit pouvoir allouer au moins 1Go de mémoire globale sans trops de soucis.

Là je suis sous FireFox qui consomme 216Mo de RAM + 213Mo de mémoire virtuelle (Mémoire virtuelle -> Windows met des données sensées être dans la RAM sur le dur pour que le PC est en apparence beaucoup de mémoire RAM).

Donc tes 25Mo....

Si ton programme rame au moment de l'impression, c'est certainement au niveau du dialogue avec l'imprimante qu'il y a un problème, ou que les fichiers à imprimer sont très gros. Tu peux éventellement essayer de réaliser l'impression sur un thread si ton programme ne répond pas pendant l'impression.
3
cs_Delphiprog Messages postés 4297 Date d'inscription samedi 19 janvier 2002 Statut Membre Dernière intervention 9 janvier 2013 32
30 août 2007 à 09:43
Bonjour,

Pour indiquer un code de retour d'un programme, il y a l'instruction suivante (et méconnue) :
Unité : System



Catégorie : routines de contrôle de flux



Syntaxe Delphi :


procedureHalt [(Exitcode:Integer)];



Description :


La procédure Halt exécute une fin anormale d'un programme et renvoie le contrôle au système d'exploitation.


Pour exécuter une fin normale d'une application Delphi,appelez la méthode Terminate sur l'objet global Application.Si l'application n'utilise aucune unitéfournissant un objet Application,appelez la procédure Exit àpartir du bloc de programme principal.


Exitcode est une expression facultative qui indique le code de sortie du programme.

Qui n'a jamais utilisé, dans des fichiers batch, un test du genre :
if errorlevel == ...
Eh bien, c'est ce genre de code que retournera l'application si l'on utilise l'instruction Halt.

Mais les remarques concernant l'optimisation du code s'appliquent toujours. Cette solution ne serait être qu'un pis-aller.

May Delphi be with you !





<hr color="#008000" />
Pensez à cliquer sur Réponse acceptée lorsque la réponse vous convient.
http://www.afipa.net/
3
Utilisateur anonyme
27 août 2007 à 17:30
Salut Oniria,

Moi à ta place je serai plus préoccupé par le fait que mon application pédale . En général c'est le signe que le projet a été mal codé ou mal pensé : style des variables globales plutot que des variables locales, libération d'objets à des moments non opportuns(d'ou l'interet des variables locales) ou pas du tout, mauvaise gestion des tableaux ect ect.

Je pense pas que d'inclure la procédure d'impréssion  dans ton premier soft change grand chose en terme de ressources .

Une solution qui n'est pas des plus jolies mais qui est simple et efficace est d'utiliser les fichiers Ini pour faire une telle chose : ca te permettra de comparer facilement la valeur assigné à ta variable. L'avantage aussi c'est que l'acces à ces fichiers est rapide et peu gourmand.

Pour revenir à ton probleme : j'essayerai plutot de l'optimiser à ta place. Imagine Delphi fait 500Mo et il rame pas :meme sur un 486 (Si si j'ai essayé ). Je pense pas que ton soft soit aussi conséquent que notre IDE favoris .
0
f0xi Messages postés 4205 Date d'inscription samedi 16 octobre 2004 Statut Modérateur Dernière intervention 12 mars 2022 35
27 août 2007 à 18:07
"J'ai séparé les deux car le programme de gestion est enorme, et windows a du mal à gérer la mémoire."






Haaa elle est pas mal celle la ... genre c'est la faute a wouindoz...

j'imagine bien si Adobe ou Discreet venaient a dire "c'est la faute a windows".

lol
0

Vous n’avez pas trouvé la réponse que vous recherchez ?

Posez votre question
Oniria Messages postés 292 Date d'inscription dimanche 14 mars 2004 Statut Membre Dernière intervention 18 décembre 2014 3
27 août 2007 à 20:36
bonjour,

Peut-etre que vous avez raison, le probléme est que en effet,  le programme tout compilé fait 15 Mo, en execution, en regardant le gestionnaire de tache, on passe à 25 Mo, Il y a 40 fiches différentes que je ne peut pas assembler entre elles car elles sont différentes. Il existe surement des méthodes permettant d'optimiser le programme mais je ne les maitrise pas . Le phénoméne qui se produit est simple, lorsque j'ai ajouté une fiche suplémentaire avec toutes les fonctions associées (dans mon cas, une fiche avec des statistiques), mon programme s'est mis à planter sur les autres fiches alors que celle-ci n'avaient pas été touché. Dans les fiches, j'utilise des variables globales directement dans la section VAR, ces variables sont souvent utilisées par d'autres fiches. Sinon, j'utilise des  variables déclarées dans  la partie  public de la classe TForm de la fiche. Il arrive aussi que le programme plante à l'initialisation des fiches (Application.createForm()).

Mais l'option d'un fonctionnement déporté à beaucoup d'avantage : Un code beaucoup plus simple : chaque fonction élémentaire est dans un process à part.
Lors de la mise au point, la concentration n'est que sur un bout de code. Le Nouveau process dispose de plus de mémoire (au niveau de la pile).
Et dans mon cas, je peut archiver les impressions avant de les faire réellement.

Je ne suis pas un pro de delphi, avant je travaillait sur Turbo pascal 7 et j'ai quelque lacune sur la programmation Windows.

Mais si l'option du fichier ini entre les deux applis est la solution, je vais faire de plus ample recherche sur le partage de zone mémoire entre deux process.

Merci de vous interresser à mon probléme.
0
Utilisateur anonyme
27 août 2007 à 22:02
Oniria :

Ton fichier fait 15 Mo et c'est ca que tu appelles une grosse application ? . Moi j'appelle cela une petite application .

Si tu vends un soft non optimisé, tot ou tard tu vas payer la facture : il faudrait mieux que tu optimises ton source maintenant pluot que d'aller au devant de sacrés problèmes juridiques (les proces ce n'est pas qu'à la télé ). En plus si tu dois retoucher ton probleme dans 6 mois ca va etre dur de s'y remettre et une sacrée perte de temps.

Tu parles d'optimisation en utilisant différents process : tu fais erreur sur toute la ligne car ce n'est pas aussi simple que cela. Appeler 2 programmes demandent plus en ressource que d'en appeler un seul qui contient les deux . Ensuite si tu as utilisés des variables globales c'est qu'effectivement mal codé : il est tres souvent possible de créer des unités contenant des fonctions et des procédures appelant des Variables globales.

Procedure TForm1.Alert;
Var
str:string;
Begin
Str : = 'WARNING, WINDOWS IS EXPLOSED';
Form2.ShowText(Str);
End;

Procedure TForm2.ShowAlert(AText:String);
Begin
ShowMessage(AText);

End;

Plutot que de faire de la bidouille, optimise ton code .
0
Utilisateur anonyme
27 août 2007 à 22:04
Pardon pour la boulette : il est tres souvent possible de créer des unités contenant des fonctions et des procédures appelant des Variables locales.
0
Oniria Messages postés 292 Date d'inscription dimanche 14 mars 2004 Statut Membre Dernière intervention 18 décembre 2014 3
28 août 2007 à 08:59
Bonjour,

C'est vrai, mais si windows travaille comme le dos, les variables globales sont alouées dans l'espace mémoire des données alors que les variables locale sont dans l'espace de la pile.  Si je ne dis pas de bétise,  l'espace de la pile  n'est  pas  infini,  au contraire,  il est limité.  Le fait  d'avoir  plein  de  procedure  et  de fonction  à appeler,  la pile va se remplir rapidement et déborder (on y arrive très facilement sous dos).
Sinon, FRANCKY, je ne comprend pas bien pourquoi tu me dis que l'utilisation de variable globale est mauvais.  Pourquoi  ?  Lorsque  je  crées  un objet contenant une variable, celui ci prend bien plus de place qu'une simple variable globale. De même pour une procedure par rapport à une variable.

Si je pose toutes ces questions, c'est pour justement optimiser mon prog car je suis justement pour l'optimisation de taille qui a beaucoup de vertu, Et il faut vraiment que je m'améliore dans la programmation Windows pour réussir à tenir cet objectif. J'essaye de mieux comprendre la gestion de la mémoire car je ne comprend pas très bien ce que fait windows.

En tout cas, merci pour l'intérêt.

Oniria
0
Caribensila Messages postés 2527 Date d'inscription jeudi 15 janvier 2004 Statut Membre Dernière intervention 16 octobre 2019 18
28 août 2007 à 10:44
Salut Oniria,

Peut-être une voie de recherche qui pourrait te rendre service :
utiliser la même technique que Windows, à savoir les DLL.

En utilisant des liaisons dynamiques, les DLL ne sont chargées en mémoire que lorsque c'est nécessaire.
Ca répondrait bien à ton souci de morceler ton code et en faciliterait la maintenance(?).

Mais la gestion de la mémoire reste toujours délicate avec les DLL, et Borland recommande l'utilisation des fichiers projetés en mémoire.

En tout cas, la 1ère chose à faire, comme dit Francky, c'est d'optimiser ton code. DLL ou pas, c'est incontournable.

@+
0
Oniria Messages postés 292 Date d'inscription dimanche 14 mars 2004 Statut Membre Dernière intervention 18 décembre 2014 3
28 août 2007 à 14:21
Bonjour,

Caribensila, tu parle des fichiers projetés en mémoire, qu'est ce que c'est ? Ce sont des TMemoryStream ?

Par contre, je suis en train d'optimiser à fond, d'ailleur, je vais poster une autre question pour me premettre de mettre la gestion d'impression dans mon soft principal.

Merci
0
Utilisateur anonyme
28 août 2007 à 15:41
Salut,

Comme tu viens de le dire une variable est stockée en mémoire. Après utilisation la mémoire est libérée : Donc en globale la libération a lieu à la fermeture de l'application alors qu'en globale à la fin de la procédure qui l'utilise.
0
Oniria Messages postés 292 Date d'inscription dimanche 14 mars 2004 Statut Membre Dernière intervention 18 décembre 2014 3
31 août 2007 à 09:02
Bonjour,

Merci à vous tous pour votre aide, justement, je vais travailler sur tout ca... Ca m'a vraiment aidé....

Oniria
0
Rejoignez-nous