Beefy Boxes and Bandwidth Generously Provided by pair Networks
Think about Loose Coupling

Windows process suspend

by gautamparimoo (Beadle)
on Apr 24, 2013 at 09:05 UTC ( #1030305=perlquestion: print w/replies, xml ) Need Help??
gautamparimoo has asked for the wisdom of the Perl Monks concerning the following question:

I am trying to run the following code without much results:

use Win32::Process::Kill; my $pids = $ARGV[0]; $handles = GetHandle($pids); SuspendProcess($handles); INPUT: perl 5568 OUTPUT: AppCrash

When I run the above code the perl.exe crashes and gives command line interpreter has stopped working. Anybody knows how this module works?

One machine can do the work of fifty ordinary men. No machine can do the work of one extraordinary man. -Elbert Hubbard

Replies are listed 'Best First'.
Re: Windows process suspend
by kcott (Chancellor) on Apr 24, 2013 at 09:19 UTC

    G'day gautamparimoo,

    According to the Win32::Process::Kill documentation, GetHandle returns an array. I expect that calling it in scalar context will return 1 (in your code here). Subsequently, you call "SuspendProcess(1);" which is probably responsible for the crash. The documentation has the code you need.

    -- Ken

      the documentation has given this line:

      Suspend(@Handles); or Suspend($Handle);

      So what am I exactly doing wrong?

      One machine can do the work of fifty ordinary men. No machine can do the work of one extraordinary man. -Elbert Hubbard


        You want to kill specific processes. Each process ID is a number referring to a job. So you need to determine which process number you want to kill. It looks like you have things in hand to that point. But when you get the handles for the threads, you've got a bug. Since GetHandles returns a *list* of handles, you'll need to do something like:

        use strict; use warnings; use Win32::Process::Kill; my $pids = $ARGV[0]; # Get *all* the handles returned my @handles = GetHandle($pids); print scalar(@handles), " handles returned\n"; # We'll just suspend the first one: my $handle = $handles[0]; SuspendProcess($handle);

        Note: I'm on a linux box right now, so I can't test things out at the moment, but after reviewing the docs, that's what I'm expecting.


        When your only tool is a hammer, all problems look like your thumb.

Re: Windows process suspend
by bulk88 (Priest) on Apr 25, 2013 at 04:08 UTC
    The module is broken and is guaranteed to crash in 32 bit mode on most compilers.
    12: HMODULE ntdll = LoadLibrary( "ntdll.dll" ); 003C1002 68 3C 22 3C 00 push offset string "ntdll.dll" (3C223 +Ch) 003C1007 FF 15 04 20 3C 00 call dword ptr [__imp__LoadLibraryA@ +4 (3C2004h)] 003C100D 8B F8 mov edi,eax 13: if (!ntdll) 003C100F 85 FF test edi,edi 003C1011 74 61 je Import+74h (3C1074h) 003C1013 56 push esi 14: return 0; 15: RtlAdjPriv = (pRtlAdjustPrivilege) GetProcAddress(ntdll,"R +tlAdjustPrivilege"); 003C1014 8B 35 08 20 3C 00 mov esi,dword ptr [__imp__GetProcAd +dress@8 (3C2008h)] 003C101A 68 28 22 3C 00 push offset string "RtlAdjustPrivileg +e" (3C2228h) 003C101F 57 push edi 003C1020 FF D6 call esi 16: NtTerminateProcess = (pNtTerminateProcess)GetProcAddress( +ntdll, "NtTerminateProcess"); 003C1022 68 14 22 3C 00 push offset string "NtTerminateProces +s" (3C2214h) 003C1027 57 push edi 003C1028 A3 18 30 3C 00 mov dword ptr [_RtlAdjPriv (3C3018h) +],eax 003C102D FF D6 call esi 17: NtSuspendProcess = (pNtSuspendProcess)GetProcAddress(ntdll +, "NtSuspendProcess" ); 003C102F 68 00 22 3C 00 push offset string "NtSuspendProcess" + (3C2200h) 003C1034 57 push edi 003C1035 A3 34 30 3C 00 mov dword ptr [_NtTerminateProcess ( +3C3034h)],eax 003C103A FF D6 call esi 18: NtResumeProcess = (pNtResumeProcess)GetProcAddress(ntdll, +"NtResumeProcess" ); 003C103C 68 F0 21 3C 00 push offset string "NtResumeProcess" +(3C21F0h) 003C1041 57 push edi 003C1042 A3 1C 30 3C 00 mov dword ptr [_NtSuspendProcess (3C +301Ch)],eax 003C1047 FF D6 call esi 19: FreeLibrary(ntdll); 003C1049 57 push edi 003C104A A3 20 30 3C 00 mov dword ptr [_NtResumeProcess (3C3 +020h)],eax 003C104F FF 15 14 20 3C 00 call dword ptr [__imp__FreeLibrary@4 + (3C2014h)] 20: { 21: int prtn; 22: RtlAdjPriv(20,TRUE,FALSE,&prtn); 003C1055 8D 44 24 08 lea eax,[esp+8] 003C1059 50 push eax 003C105A 6A 00 push 0 003C105C 6A 01 push 1 003C105E 6A 14 push 14h 003C1060 FF 15 18 30 3C 00 call dword ptr [_RtlAdjPriv (3C3018h +)] 23: } 24: RtlAdjPriv = NULL; 003C1066 83 25 18 30 3C 00 00 and dword ptr [_RtlAdjPriv (3C30 +18h)],0 003C106D 83 C4 10 add esp,10h ; HUH? this isn't a CDEC +L 25: return 1; 003C1070 33 C0 xor eax,eax 003C1072 40 inc eax 003C1073 5E pop esi 003C1074 5F pop edi 26: } 003C1075 59 pop ecx 003C1076 C3 ret
    created callstack,
    > Kill.dll!Import() Line 25 C perl517.dll!Perl_pp_entersub(interpreter * my_perl=0x00000002) L +ine 2877 C perl517.dll!Perl_runops_standard(interpreter * my_perl=0x00346014 +) Line 42 + 0x4 C perl517.dll!Perl_call_sv(interpreter * my_perl=0xffffffff, sv * s +v=0x7c91005d, volatile long flags=2083927443) Line 2759 + 0xc C perl517.dll!Perl_call_list(interpreter * my_perl=0x00346014, long + oldscope=2, av * paramList=0x008fd4ec) Line 4856 C perl517.dll!S_process_special_blocks(interpreter * my_perl=0x0007 +0023, long floor=31144, const char * const fullname=0x009069c8, gv * +const gv=0x008fd56c, cv * const cv=0x008fd50c) Line 7680 C perl517.dll!Perl_newATTRSUB_flags(interpreter * my_perl=0x000079a +8, long floor=38, op * o=0x00a4649c, op * proto=0x00000000, void * at +trs=0x2802a411, op * block=0x00a464bc, unsigned long flags=16777216) + Line 7642 + 0x13 C perl517.dll!Perl_newATTRSUB(interpreter * my_perl=0x00346014, lon +g floor=38, op * o=0x00a4649c, op * proto=0x00000000, op * attrs=0x00 +000000, op * block=0x00a464bc) Line 7315 + 0x19 C perl517.dll!Perl_utilize(interpreter * my_perl=0x000079a8, int av +er=1, long floor=38, op * version=0x00000000, op * idop=0x00000000, o +p * arg=0x00000000) Line 5111 + 0x7a C perl517.dll!Perl_yyparse(interpreter * my_perl=0x00346014, int gr +amtype=1) Line 397 + 0x16 C perl517.dll!S_parse_body(interpreter * my_perl=0x000079a8, char * + * env=0x00345230, void (interpreter *)* xsinit=0x280b2bb3) Line 230 +2 + 0xd C perl517.dll!perl_parse(interpreter * my_perl=0x00346014, void (in +terpreter *)* xsinit=0x280b2bb3, int argc=2, char * * argv=0x00342478 +, char * * env=0x00345230) Line 1661 C perl517.dll!RunPerl(int argc=2, char * * argv=0x01342478, char * +* env=0x00342dc8) Line 263 + 0x10 C perl.exe!mainCRTStartup() Line 398 + 0xe C kernel32.dll!_BaseProcessStart@4() + 0x23
    which means the C stack is now corrupt since the XSUB disappeared. There is a __stdcall or WINAPI missing in "typedef LONG (*pRtlAdjustPrivilege)(int,BOOL,BOOL,int*);". I like to declare my func ptrs as "ULONG (WINAPI * pRtlNtStatusToDosError) (NTSTATUS);" for example. The module also needs "#define PERL_NO_GET_CONTEXT".

    We all know ntdll.dll will never be unloaded from the process, but can we atleast play along that it is a normal DLL? The Module does a LoadLibrary, then a FreeLibrary, then uses funcs from that DLL. It should use GetModuleHandle and never call FreeLibrary.

      Any alternatives ? I need to suspend and resume a process using its pid in Windows.

      One machine can do the work of fifty ordinary men. No machine can do the work of one extraordinary man. -Elbert Hubbard

        Have you tried Win32::Process?

        With the rise and rise of 'Social' network sites: 'Computers are making people easier to use everyday'
        Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
        "Science is about questioning the status quo. Questioning authority".
        In the absence of evidence, opinion is indistinguishable from prejudice.

      The module is broken ... incomprehensible ...

      If you're proposing a patch, please make it stand out (make it clear), cause otherwise what is the point?

        If you're proposing a patch, please make it stand out (make it clear), cause otherwise what is the point?
        Since you are complaining so much, patch made,, although I dont think the API of this module can ever be completely fixed regarding handle leaking without breaking changes.
        A patch with no comments is useless for fixing a bug. Heck, you wouldn't even know if there was a bug, or the patch is a backdoor from CIA or MSS.

Log In?

What's my password?
Create A New User
Node Status?
node history
Node Type: perlquestion [id://1030305]
Approved by kcott
and all is quiet...

How do I use this? | Other CB clients
Other Users?
Others scrutinizing the Monastery: (6)
As of 2018-03-21 10:02 GMT
Find Nodes?
    Voting Booth?
    When I think of a mole I think of:

    Results (265 votes). Check out past polls.