Dites que j'ai un programme qui portait le processeur et / ou le disque dur au point qu'il fait presque impossible de faire autre chose sur cet ordinateur. Maintenant, je ne veux pas tuer ce programme car ce qu'il fait est utile (c'est un travail de lot qui est vraiment que la CPU ou le disque lourd, par exemple, il pourrait poser quelques gigaoctets de fichiers de données), mais pour une courte période, je dois faire quelque chose d'autre sur cet ordinateur. Y a-t-il une manière qu'un programme externe pourrait faire pour geler ce tueur de performance pendant un moment? P>
C'est comme si l'option Old DOS de basculer entre les programmes sans avoir en réalité avoir multitâche. P>
Supposons que le programme hypothétique en question est un produit tiers pour lequel je n'ai pas le code source et il n'ya aucun moyen de le dire de faire une pause. P>
Je sais que je peux changer la classe prioritaire du programme par ex. Dans TaskManager mais ça ne suffit pas, je veux le geler. P>
Je parle de Windows XP comme système d'exploitation et souhaitez programmer une solution avec Delphi. J'ai tous les droits sur la machine. Je pourrais donc commencer quelque chose en tant qu'administrateur, remplacer les fichiers et je pourrais également installer un service si cela est nécessaire. P>
4 Réponses :
Vous pouvez le geler avec Explorateur de processus : cliquez avec le bouton droit de la souris sur Votre programme et sélectionnez Voici quelques échantillons de code pour le gel programmatique de http://www.c-plusplus.de/forum/viewtopic-var-p-is-1460293.html , erreur édité et omise vérification de la brièveté: p> suspendre code>.
Ah oui, mais quel appelle API utilise-t-il? Suspendthread sur tous les threads de processus? msdn.microsoft.com/en-us/library /ms686345(V=VS.85).aspx
Connaissant Russinovich et sa connaissance du noyau, il utilise probablement NtsuspendProcess directement.
Ici, le texte en anglais TECHNET.MICROSSOFT.COM/EN-US/SYSITINERNALS/BB896653 .aspx
@Runner merci, a ajouté un exemple de code pour NtsuspendProcess, @Belisarius merci, a été édité mon lien à pointer vers la version anglaise.
Si vous voulez le faire de manière programmative, vous pouvez utiliser l'approche décrite ici . P>
Qu'est-ce que c'est, consiste à énumérer tous les threads dans un processus, puis à les suspendre. Il n'y a pas d'API de suspension de suspension, il s'agit donc d'une simulation d'un tel appel. P>
méfiez-vous que cela peut potentiellement avoir des effets secondaires mauvais. Cela dépend du processus et de la façon dont il est écrit. P>
Je ne sais pas d'autre façon de le faire dans le monde de l'API Win32 / 64. Si vous allez bas sur la terre du noyau et utilisez les API NT *, vous avez une API «NtsuspendProcess» disponible. Mais cela est sans papiers afin qu'il puisse changer avec n'importe quelle version de Windows ou même avec n'importe quel service de service (pas très probablement). P>
La déclaration de "ntsuspendprocess" peut être trouvée dans les ports Jedi des API Windows. P>
function OpenThread(dwDesiredAccess: DWORD; InheritHandle: Boolean; dwThreadID: DWORD): THandle; stdcall; external 'kernel32.dll'; function ResumeProcess(PID: DWORD):Boolean; var tid, snap: THandle; TE32: TThreadEntry32; begin Result := False; snap := CreateToolHelp32SnapShot(TH32CS_SNAPTHREAD, 0); TE32.dwSize := SizeOf(TThreadEntry32); Thread32First(snap, TE32); repeat if TE32.th32OwnerProcessID = PID then begin tid := OpenThread($0002, FALSE, TE32.th32ThreadID); ResumeThread(tid); Result := TRUE; CloseHandle(tid); end; until Thread32Next(snap, TE32) = false; CloseHandle(snap); end; function SuspendProcess(PID: DWORD): Boolean; var tid, snap: THandle; TE32: TThreadEntry32; begin Result := False; snap := CreateToolHelp32SnapShot(TH32CS_SNAPTHREAD, 0); TE32.dwSize := SizeOf(TThreadEntry32); Thread32First(snap, TE32); repeat if TE32.th32OwnerProcessID = PID then begin tid := OpenThread($0002, FALSE, TE32.th32ThreadID); SuspendThread(tid); Result := TRUE; CloseHandle(tid); end; until Thread32Next(snap, TE32) = false; CloseHandle(snap); end; Hope this helps
utilise tlhelp32; (Ajoutez ceci dans votre clause utilisée)
Vous pouvez utiliser mon composant processInfo pour suspendre toutes les threads appartenant à la traiter. L'approche est similaire à ce que Runner vous a expliqué. Le code serait quelque chose comme ceci:
var Process : TProcessItem; AThread: TThreadItem; begin Process := ProcessInfo1.RunningProcesses.FindByName('notepad.exe'); if Assigned(Process) then begin for AThread in Process.Threads do AThread.SuspendThread; end; end;
J'accepte votre réponse même si les autres sont également correctes et contiennent plus d'informations sur les détails, mais je suis paresseux, donc j'aime utiliser un composant.
@VCLDEveloper, comment est-ce différent de Resmon Stackoverflow.com/a/21649539/632951 ?
Pour une solution alternative utilisant à l'aide de débogActiveProcess: Stackoverflow.com/Questtions/11010165/...