📄 tut14.html
字号:
invoke CloseHandle,processInfo.hProcess</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
mov processInfo.hProcess,0</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.endif</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke GetStartupInfo,ADDR startInfo</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke CreateProcess,ADDR programname,NULL,NULL,NULL,FALSE,\</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
NORMAL_PRIORITY_CLASS,\</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
NULL,NULL,ADDR startInfo,ADDR processInfo</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke CloseHandle,processInfo.hThread</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.elseif ax==IDM_TERMINATE</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke GetExitCodeProcess,processInfo.hProcess,ADDR ExitCode</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.if ExitCode==STILL_ACTIVE</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke TerminateProcess,processInfo.hProcess,0</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.endif</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke CloseHandle,processInfo.hProcess</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
mov processInfo.hProcess,0</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.else</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke DestroyWindow,hWnd</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.endif</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.endif</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.ELSE</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke DefWindowProc,hWnd,uMsg,wParam,lParam</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
ret</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.ENDIF</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
xor eax,eax</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
ret</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>WndProc
endp</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>end
start</font></font></font></b>
<h3>
<b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>Analysis:</font></font></font></b></h3>
<font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>The program
creates the main window and retrieves the menu handle for future use. It
then waits for the user to select a command from the menu. When the user
selects "Process" menu item in the main menu, we process WM_INITMENUPOPUP
message to modify the menu items inside the popup menu before it's displayed.</font></font></font><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1></font></font></font>
<p><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.ELSEIF uMsg==WM_INITMENUPOPUP</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke GetExitCodeProcess,processInfo.hProcess,ADDR ExitCode</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.if eax==TRUE</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.if ExitCode==STILL_ACTIVE</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke EnableMenuItem,hMenu,IDM_CREATE_PROCESS,MF_GRAYED</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke EnableMenuItem,hMenu,IDM_TERMINATE,MF_ENABLED</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.else</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke EnableMenuItem,hMenu,IDM_CREATE_PROCESS,MF_ENABLED</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke EnableMenuItem,hMenu,IDM_TERMINATE,MF_GRAYED</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.endif</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.else</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke EnableMenuItem,hMenu,IDM_CREATE_PROCESS,MF_ENABLED</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke EnableMenuItem,hMenu,IDM_TERMINATE,MF_GRAYED</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.endif</font></font></font></b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1></font></font></font>
<p><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>Why
do we want to process this message? Because we want to prepare the menu
items in the popup menu before the user can see them. In our example, if
the new process is not started yet, we want to enable the "start process"
and gray out the "terminate process" menu items. We do the reverse if the
new process is already active.</font></font></font>
<br><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>We
first check if the new process is still running by calling GetExitCodeProcess
function with the process handle that was filled in by CreateProcess function.
If GetExitCodeProcess returns FALSE, it means the process is not started
yet so we gray out the "terminate process" menu item. If GetExitCodeProcess
returns TRUE, we know that a new process has been started, but we have
to check further if it is still running. So we compare the value in ExitCode
to the value <b>STILL_ACTIVE</b>, if they're equal, the process is still
running: we must gray out the "start process" menu item since we don't
want to start several concurrent processes.</font></font></font><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1></font></font></font>
<p><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.if ax==IDM_CREATE_PROCESS</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.if processInfo.hProcess!=0</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke CloseHandle,processInfo.hProcess</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
mov processInfo.hProcess,0</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.endif</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke GetStartupInfo,ADDR startInfo</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke CreateProcess,ADDR programname,NULL,NULL,NULL,FALSE,\</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
NORMAL_PRIORITY_CLASS,\</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
NULL,NULL,ADDR startInfo,ADDR processInfo</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke CloseHandle,processInfo.hThread</font></font></font></b>
<br><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1> </font></font></font>
<br><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>When
the user selects "start process" menu item, we first check if hProcess
member of PROCESS_INFORMATION structure is already closed. If this is the
first time, the value of hProcess will always be zero since we define PROCESS_INFORMATION
structure in .data section. If the value of hProcess member is not 0, it
means the child process has exited but we haven't closed its process handle
yet. So this is the time to do it.</font></font></font>
<br><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>We
call GetStartupInfo function to fill in the startupinfo structure that
we will pass to CreateProcess function. After that we call CreateProcess
function to start the new process. Note that I haven't checked the return
value of CreateProcess because it will make the example more complex. In
real life, you should check the return value of CreateProcess. Immediately
after CreateProcess, we close the primary thread handle returned in processInfo
structure. Closing the handle doesn't mean we terminate the thread, only
that we don't want to use the handle to refer to the thread from our program.
If we don't close it, it will cause a resource leak.</font></font></font><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1></font></font></font>
<p><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.elseif ax==IDM_TERMINATE</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke GetExitCodeProcess,processInfo.hProcess,ADDR ExitCode</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.if ExitCode==STILL_ACTIVE</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke TerminateProcess,processInfo.hProcess,0</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
.endif</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
invoke CloseHandle,processInfo.hProcess</font></font></font></b>
<br><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>
mov processInfo.hProcess,0</font></font></font></b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1></font></font></font>
<p><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>When
the user selects "terminate process" menu item, we check if the new process
is still active by calling GetExitCodeProcess function. If it's still active,
we call TerminateProcess function to kill the process. Also we close the
child process handle since we have no need for it anymore.</font></font></font>
<br>
<hr WIDTH="100%">
<center><b><font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1>[<a href="http://win32asm.cjb.net">Iczelion's
Win32 Assembly HomePage</a>]</font></font></font></b></center>
<font face="Arial,Helvetica"><font color="#CCCCCC"><font size=-1></font></font></font>
</body>
</html>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -