48
Processes Processes 井井井井井

Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

Embed Size (px)

Citation preview

Page 1: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

ProcessesProcesses

井民全製作

Page 2: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

IntroductionIntroduction

Process is an instance of running Process is an instance of running programprogram Kernel object:Kernel object:

OS uses to OS uses to managemanage the process and the process and keeps keeps informationinformation about the process about the process

Address space:Address space:

contains all the executable or DLL contains all the executable or DLL module’s module’s code and datacode and data

包含 Heap 配置的空間Thread 使用的 Stack

包含 Heap 配置的空間Thread 使用的 Stack

例如 : ExitCode, STILL ACTIVE 等資訊

例如 : ExitCode, STILL ACTIVE 等資訊

Page 3: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

IntroductionIntroduction

Processes are inert, it must have a Processes are inert, it must have a threadthread that runs in its context that runs in its context

Single process Single process several threads several threads ThreadThread

Own set of CPU registersOwn set of CPU registers Own StackOwn Stack All thread run concurrently by offering All thread run concurrently by offering

time slicestime slices

Create ProcessCreate Process Create Primary thread

Create Primary thread

Thread 1Thread 1

Thread 2Thread 2

靜止不動的靜止不動的

CPU

Thread1

Thread2

Thread3

Thread5

Thread7

Thread4Thread6

Thread8

Page 4: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

Writing Your First Windows Writing Your First Windows ApplicationApplication

Two types of applicationTwo types of application GUI:GUI: based on based on graphicalgraphical user interface user interface

Create window, menuCreate window, menu Could output text string to consoleCould output text string to console the Linker switch: the Linker switch:

/SUBSYSTEM:WINDOWS/SUBSYSTEM:WINDOWS

CUICUI: based on : based on consoleconsole user interface user interface CMD.exe (2k) or COMMAND.COM(98)CMD.exe (2k) or COMMAND.COM(98) could display a graphical dialog box could display a graphical dialog box the Linker switch: the Linker switch: /SUBSYSTEM:CONSOLE/SUBSYSTEM:CONSOLECreate a

consoleWindow

Create a consoleWindow Load the applicationLoad the application

OS’s loader

Load the applicationLoad the applicationOS’s loader

Page 5: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

The entry point function for The entry point function for C/C++C/C++

Application TypeApplication Type Startup FunctionStartup Function Entry PointEntry Point

GUI applicationGUI application

((ANSIANSI characters) characters)WinMainWinMainCRTStartupCRTStartup WinMain(HINSTANCWinMain(HINSTANC

E …)E …)

GUI applicationGUI application

((UNICODEUNICODE characters) characters)wwWinMainWinMainCRTCRTStartupStartup wwWinMain(HINSTANWinMain(HINSTAN

CE …)CE …)

CUI applicationCUI application

((ANSIANSI characters) characters)mainmainCRTCRTStartupStartup main(int argc,char main(int argc,char

*argv[], …)*argv[], …)

CUI applicationCUI application

((UNICODEUNICODE characters) characters)wwmainmainCRTCRTStartupStartup wwmain(int argc, main(int argc,

wchar_t *argv[])wchar_t *argv[])

Operating SystemOperating System Startup FunctionStartup Function int __cdecl main(…){

}

int __cdecl main(…){

}

Entry Point function

Initializes the C/C++run-time library ( 之後你才可以呼叫 malloc, free)

GUI

CUI

C/C++ Run-Time CRT 呼叫的是 WinMain

呼叫的是 main

功用在於

1 2

新增解釋

C/C++ 的起始執行位置執行檔的起始執行位置

位於 crt.0.c 位於你的 project

Page 6: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

Choose the proper C/C++ Choose the proper C/C++ startup functionstartup function

WinMainCRTStartupWinMainCRTStartup

LinkerLinker

mainCRTStartupmainCRTStartup

/SUBSYSTEM:WINDOWS

/SUBSYSTEM:CONSOLE

You can You can removeremove the /SUBSYSTEM the /SUBSYSTEM linker switch linker switch system checksystem check

範例 : RemoveLinkerSwitchDemo

系統會看看你的 source 檔中 , 包含哪一種 entry point function以決定你是哪一個 subsystem

調整不同的選項看看 ( 選錯 => 出現 link 錯誤 )

注意 : .Net 2003 IDE 會向你詢問 entry point function: 請加入 WinMainCRTStartup

Page 7: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

選擇 選擇 SubSystemSubSystem

Page 8: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

What the startup What the startup functions do?functions do?

PointerPointer

Full command lineFull command line

Step 1

PointerPointerEnvironment variables

Environment variables

Initial C/C++ run time’sGlobal variables

Initial C/C++ run time’sGlobal variables

Initial heap malloc / calloc

Initial heap malloc / calloc

Global and static C++ object 呼叫他們的建構子

Global and static C++ object 呼叫他們的建構子

C/C++ Entry functionC/C++ Entry functionthen

int retValue= main(__argc,__argv,_environ);

If you wrote a main function

建立 Heap 結構建立 Heap 結構

main(), wmain(), WinMain(), wWinMain

Step 2

Step 3

Step 4

Step 5

作業系統版本等資訊

Page 9: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

GetStartupInfo(&StartupInfo);int nMainRetVal = wWinMain(GetModuleHandle(NULL), NULL, pszCommandLineUnicode, (StartupInfo.dwFlags & STARTF_USESHOWWINDOW)? StartupInfo.wShowWindow : SW_SHOWDEFAULT);

目前 instance 的 Handle

目前 instance 的 Handle

永遠設為 null永遠設為 null

命令列字串命令列字串

指定視窗該如何秀出來

指定視窗該如何秀出來

int nMainRetVal = WinMain(GetModuleHandle(NULL), NULL, pszCommandLineAnsi , (StartupInfo.dwFlags & STARTF_USESHOWWINDOW)? StartupInfo.wShowWindow : SW_SHOWDEFAULT);

ANSI 版本

ANSI 版本

int nMainRetVal = wmain(__argc, __wargv, __wenviron);

如果你寫了 wmain如果你寫了 wmain

int nMainRetVal = main(__argc, __argv, __environ);

Startup function 如何呼叫你的 entry function ?

ANSI 版本

ANSI 版本

Page 10: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

The C/C++ run-time The C/C++ run-time global global variablevariable

printf(“ 作業系統 build version %d\n",_osver);printf(“ 作業系統 major version %d\n",_winmajor);printf(“ 作業系統 minor version %d\n",_winminor);printf(" 作業系統 win version %d\n",_winver);printf("command line 共有 %d 個參數 \n",__argc);for(int i=0;i<__argc;i++){ if(__argv!=NULL) printf("\tANSI 字串參數 %s\n",__argv[i]); if(__wargv!=NULL) printf("\tUNICODE 字串參數 %s\n",__wargv[i]);}

printf("ANSI 字串 envoronent 指標 %p\n",_environ);printf("UNICODE 字串 envoronent 指標 %p\n",_wenviron);printf("ANSI 目前程式的 full path %s\n",_pgmptr);printf("UNICODE 目前程式的 full path %s\n",_wpgmptr);

printf(“ 作業系統 build version %d\n",_osver);printf(“ 作業系統 major version %d\n",_winmajor);printf(“ 作業系統 minor version %d\n",_winminor);printf(" 作業系統 win version %d\n",_winver);printf("command line 共有 %d 個參數 \n",__argc);for(int i=0;i<__argc;i++){ if(__argv!=NULL) printf("\tANSI 字串參數 %s\n",__argv[i]); if(__wargv!=NULL) printf("\tUNICODE 字串參數 %s\n",__wargv[i]);}

printf("ANSI 字串 envoronent 指標 %p\n",_environ);printf("UNICODE 字串 envoronent 指標 %p\n",_wenviron);printf("ANSI 目前程式的 full path %s\n",_pgmptr);printf("UNICODE 目前程式的 full path %s\n",_wpgmptr);

see: 讀取環境變數範例

請 #include <stdlib.h>

在 Startup function 片段中 ,設定初值

在 Startup function 片段中 ,設定初值

Crt0.c line 155

Page 11: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

When your entry-point function When your entry-point function returnreturn

Call any functions Call any functions registeredregistered by calls by calls to the to the _onexit_onexit function function

Call Call destructordestructor global & static C+ global & static C++ objects+ objects

Call OS’s Call OS’s ExitProcessExitProcess() to kill your () to kill your processprocess

Startup FunctionStartup Function

C/C++ run-time library

exit( main 傳回值 )

Crt0dat.c line 374Crt0dat.c line 374

Page 12: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

Registers a routine to Registers a routine to be be called at exit timecalled at exit time

#include <stdlib.h>#include <stdio.h>int fn1(void), fn2(void); // 定義 prototypes

void main(void){ _onexit( fn1 ); _onexit( fn2 ); printf( "This is executed first.\n" );}

int fn1(){ printf(" 第三號執行 .\n" ); return 0;}int fn2(){ printf(" 第二號執行 "); return 0;}

#include <stdlib.h>#include <stdio.h>int fn1(void), fn2(void); // 定義 prototypes

void main(void){ _onexit( fn1 ); _onexit( fn2 ); printf( "This is executed first.\n" );}

int fn1(){ printf(" 第三號執行 .\n" ); return 0;}int fn2(){ printf(" 第二號執行 "); return 0;}

註冊當 main 結束時 , 要呼叫的 function(LIFO 後進先出 Last In First Out)

註冊當 main 結束時 , 要呼叫的 function(LIFO 後進先出 Last In First Out)

See: 註冊 on_exit 範例參考資料 : http://msdn.microsoft.com/library/default.asp?url=/library/en-us/vccore98/html/_crt__onexit.asp

int fn1(void);int fn2(void);

int fn1(void);int fn2(void);

GDI 程式也可以使用

Page 13: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

A Process’s Instance A Process’s Instance HandleHandle

Needed for load resourcesNeeded for load resources

You can save this handle in You can save this handle in a global a global variablevariable, so that easily accessible to , so that easily accessible to all the code.all the code.

Some functions requires a Some functions requires a parameter of the type parameter of the type HMODULEHMODULE

HICON LoadIcon( HINSTANCE hinst, PCTR pszIcon);HICON LoadIcon( HINSTANCE hinst, PCTR pszIcon);

ex 指定你 resource 的位置指定你 resource 的位置

HINSTANCE = HMODULE

用途 :用途 :

MFC 程式 : 你可以用下面指令 theApp.m_hInstance

Page 14: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

A Process’s Instance A Process’s Instance HandleHandle

int APIENTRY WinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow){}

int APIENTRY WinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow){}is the base memory address where the executable file’s image into the space

hInstancecodecode

0x00400000(default)

virtual space

In Win98, In Win98, 0x00400000 is the 0x00400000 is the lowest addresslowest address where where the executable file the executable file image can be loaded.image can be loaded.

You can change the You can change the base address!base address!Linker option: /BASE: address

Base address

請看範例程式

注意 : 5 個 0

Win2000 沒有這個限制Win2000 沒有這個限制

Page 15: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

更改你的 Module 基底位址更改你的 Module 基底位址

Page 16: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

Get the module handle/base Get the module handle/base addressaddress

HMODULE GetModuleHandle(PCTSTR pszModule);HMODULE GetModuleHandle(PCTSTR pszModule);

要取得位址的 module(.dll or .exe) 名稱 ( 字串 )要取得位址的 module(.dll or .exe) 名稱 ( 字串 )傳回的 handle (base address)傳回的 handle (base address)

傳回 NULL: 表示系統找不到相關的 module ( 可能是目前的 Process 沒有載入 )

int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow){

HMODULE MyHandle=GetModuleHandle(NULL); MessageBoxEx(NULL," 查看 hInstance 的值 "," 查看 hInstance 的值 ",MB_OK);

return 0;}

取得目前 process 的載入位址

也可以察看 Common Control library 被 載入的位址 : HMODULE h=GetModuleHandle(_T("Comctl32.dll"));

也可以察看 Common Control library 被 載入的位址 : HMODULE h=GetModuleHandle(_T("Comctl32.dll"));

Page 17: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

取得 取得 console application console application 的載入的載入位址位址

因為 因為 main/ wmain main/ wmain 沒有參數給你 沒有參數給你 Process Process 的 的 Handle, Handle, 所以你可以使用所以你可以使用

GetModuleHandle(NULL)GetModuleHandle(NULL)

#include <stdlib.h> // for C/C++ global varible definition#include <stdio.h> // for printf#include <windows.h>

int main(){char buffer[100];

sprintf(buffer,"The module base address= %p", GetModuleHandle(NULL) );MessageBox(NULL,buffer," 讀取 module base address",MB_OK);

}

GetModuleHandle 傳回來的 Handle 不會增加該 process 的 usage counter, 故不必 close

GetModuleHandle 傳回來的 Handle 不會增加該 process 的 usage counter, 故不必 close

使用 void* 位址顯示格式 %p使用 void* 位址顯示格式 %p

Page 18: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

A Process’s Command A Process’s Command LineLine

int WINAPI WinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow);

C:\Cmd.exe 1 2 3 4 5 6

PTSTR GetCommandLine(); // 取得全部的參數列PTSTR GetCommandLine(); // 取得全部的參數列

int nNumArgs; PWSTR *ppArgv=CommandLineToArgvW( GetCommandLineW(), &nNumArgs); // 處理 if( *pArgv[1] == L’x’) … HeapFree( GetProcessHeap(), 0, ppArgv);

Parsing ArgumentsParsing Arguments

MessageBox(NULL,ppArgv[1],L"test",MB_OK);MessageBox(NULL,ppArgv[1],L"test",MB_OK);

字串

範例程式 : 剖析你的 commandline範例程式 : 剖析你的 commandline

always NULL

新增圖片說明

IDE 設定 command 參數

自動將 參數解析出來

Page 19: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

環境變數 環境變數 A Process’s Environment A Process’s Environment

VariableVariable Every Process has an environment Every Process has an environment

block associated with itblock associated with it

codecode

JAVA_HOME=C:\j2sdk1.4.1_01\0Name1=Value2\0Name2=Value3\0\0

JAVA_HOME=C:\j2sdk1.4.1_01\0Name1=Value2\0Name2=Value3\0\0

virtual space

Note: 1. ‘=‘ cannot be part of the name 2. XYZ= Windows

ABC =Home空白也算數空白也算數

以 \0 結尾以 \0 結尾

變數名稱變數名稱 值值

最後結束最後結束

Page 20: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

設定環境變數初值設定環境變數初值Create an initial set of Create an initial set of environment variableenvironment variable

Windows 98Windows 98 Autoexec.batAutoexec.bat

SET VarName=VarValueSET VarName=VarValue

Windows 2000Windows 2000

HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\Environment

HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\Environment

HKEY_CURRENT_USER\EnvironmentHKEY_CURRENT_USER\Environment

System 的設定System 的設定

目前 User 的設定目前 User 的設定

JAVA_HOME=C:\j2sdk1.4.1_01\0Name1=Value2\0Name2=Value3\0\0

JAVA_HOME=C:\j2sdk1.4.1_01\0Name1=Value2\0Name2=Value3\0\0

Environment blockEnvironment block

使用 Registry使用 Registry

Regedit.exeRegedit.exe

Page 21: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

讀取環境變數的值讀取環境變數的值Determine the value of an Determine the value of an

environment valueenvironment valueDWORD GetEnvironmentVariable (PCTSTR pszName, PTSTR pszValue, DWORD cchValue);

NameName

ValueValue

Ex:

#include <windows.h> #include <tchar.h>

int APIENTRY WinMain(…){ TCHAR pszValue[100]; DWORD ReadedChar=GetEnvironmentVariable(_T("JAVA_HOME"),pszValue,100); MessageBox(NULL,pszValue,_T("Read Environment Value"),MB_OK);return 0;

}

#include <windows.h> #include <tchar.h>

int APIENTRY WinMain(…){ TCHAR pszValue[100]; DWORD ReadedChar=GetEnvironmentVariable(_T("JAVA_HOME"),pszValue,100); MessageBox(NULL,pszValue,_T("Read Environment Value"),MB_OK);return 0;

}

for TCHAR, _Tfor TCHAR, _T

配置 TCHAR 字元陣列當字串傳回儲存空間配置 TCHAR 字元陣列當字串傳回儲存空間

查詢 環境變數 Java_Home 的內容查詢 環境變數 Java_Home 的內容

注意 : 要夠大 , 否則不會放進來注意 : 要夠大 , 否則不會放進來

範例 : 讀取環境變數的值

空間大小空間大小

Page 22: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

You can modify, delete, add You can modify, delete, add the variable from the the variable from the environment blockenvironment block

BOOL SetEnvironmentVariable (PCTSTR pszName, PTSTR pszValue);

#include <windows.h> #include <tchar.h>

int APIENTRY WinMain(…){ TCHAR pszValue[100]; SetEnvironmentVariable(_T("MyProjectDir"), _T("c:\\test")); MessageBox(NULL, pszValue, _T(“Set Environment Value), MB_OK);return 0;

}

#include <windows.h> #include <tchar.h>

int APIENTRY WinMain(…){ TCHAR pszValue[100]; SetEnvironmentVariable(_T("MyProjectDir"), _T("c:\\test")); MessageBox(NULL, pszValue, _T(“Set Environment Value), MB_OK);return 0;

}

SetEnvironmentVariable(_T(“MyProjectDir“ ), _T(“c:\\test”));設定環境變數 MyProjectDir=c:\test設定環境變數 MyProjectDir=c:\test

SetEnvironmentVariable(_T(“MyProjectDir“ ), NULL);刪除環境變數 MyProjectDir刪除環境變數 MyProjectDir

程式 Demo: 環境變數刪除新增範例注意 : SetEnvironmentVariable 只為反映在目前的 process 的設定上 , 不會影響其他的 process注意 : SetEnvironmentVariable 只為反映在目前的 process 的設定上 , 不會影響其他的 process

Page 23: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

更改 更改 Registry Registry 上的變數值上的變數值 Step 1: Step 1: Open the Key Open the Key

KEY_CURRENT_USER Environment (Sub Key)

Step 2: Set the value

HKEY hKey; LONG lRet = RegOpenKeyEx(HKEY_CURRENT_USER, _T("Environment"), 0, KEY_ALL_ACCESS, &hKey );

HKEY hKey; LONG lRet = RegOpenKeyEx(HKEY_CURRENT_USER, _T("Environment"), 0, KEY_ALL_ACCESS, &hKey );

Opened keyOpened key 要修改的 Sub key要修改的 Sub key

must be 0must be 0Access maskAccess mask Handle to the opened

key

Handle to the openedkey

Succeeds

ERROR_SUCCESS

Succeeds

ERROR_SUCCESS

LPCTSTR pszValue=_T("d:\\test"); lRet=RegSetValueEx(hKey,_T("TestDir"), 0,REG_SZ, (const BYTE*)pszValue, lstrlen(pszValue)*sizeof(TCHAR));

LPCTSTR pszValue=_T("d:\\test"); lRet=RegSetValueEx(hKey,_T("TestDir"), 0,REG_SZ, (const BYTE*)pszValue, lstrlen(pszValue)*sizeof(TCHAR));

新的值新的值 要改的變數要改的變數值為字串值為字串

新字串的位址新字串的位址新字串的長度新字串的長度 程式 Demo: Registry 修改範例

Page 24: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

A Process’s Error ModeA Process’s Error Mode -- -- 自己接手處理嚴重錯誤自己接手處理嚴重錯誤 Tell the system Tell the system how the process how the process

should respondshould respond to serious errors to serious errors Disk media failures, unhandled Disk media failures, unhandled

exception, file-find failures, and data exception, file-find failures, and data misalignmentmisalignment

FlagFlag DescriptionDescription

SEM_FAILSEM_FAILCRITICALCRITICALERRORERRORS S

要求不要產生 要求不要產生 critical-critical-error-handlererror-handler message message boxbox

SEM_NOSEM_NOGPFAULTGPFAULTERRORBERRORBOX OX

不要產生不要產生 general-general-protection-faultprotection-fault message boxmessage box

SEM_NOSEM_NOOPENFILEOPENFILEERRORERRORBOX BOX

當系統找不到檔案時當系統找不到檔案時 ,, 不要秀不要秀出錯誤訊息出錯誤訊息

SEM_NOSEM_NOALIGNMENTALIGNMENTFAULFAULTEXCEPT TEXCEPT

要求系統自動修正 要求系統自動修正 memory memory alignment falutsalignment faluts

Page 25: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

不要秀出 不要秀出 general-protection-general-protection-faultfault

補充

請直接執行 exe 檔 ( 不要在 IDE 中執行 )

自己處理 錯誤自己處理 錯誤

Page 26: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

判斷 判斷 A A 槽是否有磁片槽是否有磁片#include <windows.h> #include <tchar.h>

int APIENTRY WinMain(…){ int OldMode = SetErrorMode (SEM_FAILCRITICALERRORS); SetLastError(-1); WIN32_FIND_DATA fd; FindFirstFile("A:\\*.*", &fd); int error = GetLastError(); switch(error){ case ERROR_FILE_NOT_FOUND: case -1: MessageBox(NULL,” 磁片 OK”,MB_OK); break; default: ShowErrorMessage(error); } SetErrorMode(OldMode);

return 0;}

#include <windows.h> #include <tchar.h>

int APIENTRY WinMain(…){ int OldMode = SetErrorMode (SEM_FAILCRITICALERRORS); SetLastError(-1); WIN32_FIND_DATA fd; FindFirstFile("A:\\*.*", &fd); int error = GetLastError(); switch(error){ case ERROR_FILE_NOT_FOUND: case -1: MessageBox(NULL,” 磁片 OK”,MB_OK); break; default: ShowErrorMessage(error); } SetErrorMode(OldMode);

return 0;}

設定發生問題時 , 系統不要秀出 message box

設定發生問題時 , 系統不要秀出 message box

嘗試的讀取 A 槽的資料嘗試的讀取 A 槽的資料

若沒有 error 發生時 , GetLastError 會傳回 -1 我們藉此判斷是否正常

若沒有 error 發生時 , GetLastError 會傳回 -1 我們藉此判斷是否正常

設定回原來的設定設定回原來的設定

程式 Demo:: 判斷 a 槽是否 ready 範例

Page 27: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

設定與取得預設路徑設定與取得預設路徑 ::Obtain and set the current drive Obtain and set the current drive

and directoryand directoryDWORD GetCurrentDirectory( DWORD nBufferLength, // size, in characters, of directory buffer LPTSTR lpBuffer // pointer to buffer for current directory);

DWORD GetCurrentDirectory( DWORD nBufferLength, // size, in characters, of directory buffer LPTSTR lpBuffer // pointer to buffer for current directory);

#include <windows.h> #include <tchar.h>int APIENTRY WinMain(…){

const DWORD nBufferLength=100;TCHAR lpBuffer[nBufferLength];

DWORD Num=GetCurrentDirectory (nBufferLength , lpBuffer);if(Num==0){

ShowErrorMessage(Num); return -1;}MessageBox(NULL, lpBuffer, _T(" 目前的預設路徑 "), MB_OK);return 0;

}

#include <windows.h> #include <tchar.h>int APIENTRY WinMain(…){

const DWORD nBufferLength=100;TCHAR lpBuffer[nBufferLength];

DWORD Num=GetCurrentDirectory (nBufferLength , lpBuffer);if(Num==0){

ShowErrorMessage(Num); return -1;}MessageBox(NULL, lpBuffer, _T(" 目前的預設路徑 "), MB_OK);return 0;

}程式 Demo: 讀取預設路徑範例

BOOL SetCurrentDirectory( LPCTSTR lpPathName); 會反映到目前 Process 中所有的 threads

BOOL SetCurrentDirectory( LPCTSTR lpPathName); 會反映到目前 Process 中所有的 threads

有多少個字元被讀取有多少個字元被讀取 取得目前目錄的字串 取得目前目錄的字串

Page 28: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

Handling current directories Handling current directories for multiple drives -- for multiple drives -- 更改其他槽更改其他槽的預設路徑的預設路徑

1. 1. 先看 先看 Current DirectoryCurrent Directory 2. If your current directory = C:\, then the 2. If your current directory = C:\, then the

system looks up system looks up 環境 變數 環境 變數 ““ =D:”=D:” 3. If “D:” did not exist 3. If “D:” did not exist open from the root of D open from the root of D

drivedrive

hFile = CreateFile(_T("D:myfile.txt"), …) hFile = CreateFile(_T("D:myfile.txt"), …) D:myfile.txtD:myfile.txt

Where to open the myfile.txt

file ?

Problem

磁碟機 D 的目前目錄 例如 : =D:=D:\Program Files 磁碟機 D 的目前目錄 例如 : =D:=D:\Program Files

You can use _chdir instead the SetCurrentDirect

ory()!

隨著 _chdir 的設定 , 會新增修改每個磁碟機的 Default Directory 的環境變數

_chdir 的好處是

Page 29: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

_chdir _chdir 範例範例#include <direct.h>#include <stdio.h>#include <stdlib.h>

int main( int argc, char *argv[] ){ if( _chdir( argv[1] ) ) printf( "Unable to locate the directory: %s\n", argv[1] ); else system( "dir *.exe");}

列出目前目錄下 , 的所有 exe 檔列出目前目錄下 , 的所有 exe 檔

如果 _chdir(“c:\\”); 則會設定目前目錄為 c:\\並且列出 c:\\ 下所有的 exe 檔

如果 _chdir(“c:\\”); 則會設定目前目錄為 c:\\並且列出 c:\\ 下所有的 exe 檔

Page 30: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

Example: Example: 設定 設定 D D 槽的 槽的 Default Default

DirectoryDirectory#include <windows.h> #include <tchar.h>int APIENTRY WinMain(…){

SetEnvironmentVariable(_T("=D:"),_T("D:\\TEST"));HANDLE hFile; hFile = CreateFile(_T("D:myfile.txt"), // file to create

GENERIC_WRITE, // open for writing 0, // do not share NULL, // default security CREATE_ALWAYS, // overwrite existing FILE_ATTRIBUTE_NORMAL | // normal file FILE_FLAG_OVERLAPPED, // asynchronous I/O NULL); // no attr. template

if (hFile == INVALID_HANDLE_VALUE) {MessageBox(NULL,_T("Could not open file "),_T("Error"),MB_OK);

return 0;}CloseHandle(hFile); // 系統離開時 , 也會自動的 close 所有的 handle return 0;

}

#include <windows.h> #include <tchar.h>int APIENTRY WinMain(…){

SetEnvironmentVariable(_T("=D:"),_T("D:\\TEST"));HANDLE hFile; hFile = CreateFile(_T("D:myfile.txt"), // file to create

GENERIC_WRITE, // open for writing 0, // do not share NULL, // default security CREATE_ALWAYS, // overwrite existing FILE_ATTRIBUTE_NORMAL | // normal file FILE_FLAG_OVERLAPPED, // asynchronous I/O NULL); // no attr. template

if (hFile == INVALID_HANDLE_VALUE) {MessageBox(NULL,_T("Could not open file "),_T("Error"),MB_OK);

return 0;}CloseHandle(hFile); // 系統離開時 , 也會自動的 close 所有的 handle return 0;

}

目前更改了 D 槽的預設路徑目前更改了 D 槽的預設路徑程式 Demo: 更改其他槽的預設路徑範例

Page 31: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

The child process The child process does not inherit does not inherit the parent process’s current the parent process’s current directoriesdirectories Root of every drive (default)Root of every drive (default)

You must create the You must create the drive-letter drive-letter environment variableenvironment variable

=C:=C:\Utility\Bin=D:=D:\Program Files

=C:=C:\Utility\Bin=D:=D:\Program Files

Environment block

=C:=C:\Utility\Bin=D:=D:\Program Files

=C:=C:\Utility\Bin=D:=D:\Program Files

Child A’s environment block

=C:=C:\Utility\Bin=D:=D:\Program Files

=C:=C:\Utility\Bin=D:=D:\Program Files

TCHAR szCurDir[MAX_PATH];DWORD GetFullPathName(_T(“C:”), MAX_PATH, szCurDir, NULL);

TCHAR szCurDir[MAX_PATH];DWORD GetFullPathName(_T(“C:”), MAX_PATH, szCurDir, NULL);

放進指定的檔名 ,傳回 完整的路徑名稱

先建立 Driver-Letter 環境變數先建立 Driver-Letter 環境變數

Child 會繼承 parent的環境變數 , 使得各個Device Default Directory會被複製

Child 會繼承 parent的環境變數 , 使得各個Device Default Directory會被複製

傳回目前 C 槽的Current Directory

傳回目前 C 槽的Current Directory

檔案名稱檔案名稱 Buffer 大小Buffer 大小 Buffer 位置Buffer 位置 Filename 所在位置Filename 所在位置

C 的預設目錄為 c:\Utility\Bin C 的預設目錄為 c:\Utility\Bin

* Current Directory 每個 process 只有一個* Current Directory 每個 process 只有一個

Child B’s environment block

D 的預設目錄為 D:\Program Files D 的預設目錄為 D:\Program Files

Page 32: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

How to determine the Windows How to determine the Windows versionsversions

BOOL GetVersionEx( LPOSVERSIONINFO lpVersionInformation); BOOL GetVersionEx( LPOSVERSIONINFO lpVersionInformation);

MemberMember DescriptionDescription

dwOSVersionInfoSizdwOSVersionInfoSizee

LPOSVERSIONINFO 的大小 .必須使用 sizeof(LPOSVERSIONINFOEX)EX)

dwMajorVersion, dwMajorVersion, dwMinorVersion, dwMinorVersion, dwBuildNumberdwBuildNumber

主要主要 ,, 次要版本號碼與建構號碼次要版本號碼與建構號碼4 4 95, 98 , ME, NT4.0; (Major) 5 95, 98 , ME, NT4.0; (Major) 5 2000, XP, Server 2003 2000, XP, Server 2003

0 10 90 0 (Minor) 0 1 20 10 90 0 (Minor) 0 1 2

dwPlatformId dwPlatformId VER_PLATFORM_WIN32s VER_PLATFORM_WIN32s Win32s on Windows 3.1 Win32s on Windows 3.1

VER_PLATFORM_WIN32_WINDOWS VER_PLATFORM_WIN32_WINDOWS Windows 95 /98 Windows 95 /98

VER_PLATFORM_WIN32_NT VER_PLATFORM_WIN32_NT Windows NT/ Windows NT/Windows2000Windows2000

VER_PLATFORM_WIN32_CEHH VER_PLATFORM_WIN32_CEHH Windows CE Windows CE

… … (( 其他其他 ))

wProductTypewProductType VER_NT_WORKSTATION VER_NT_WORKSTATION W2k XP Professional, XP Home W2k XP Professional, XP Home EditionEdition

VER_NT_DOMAIN_CONTROLLERVER_NT_DOMAIN_CONTROLLER

VER_NT_SERVER VER_NT_SERVER Server Server

Page 33: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

Example: Example: 判斷是否為判斷是否為Win2000Win2000

#include <windows.h> #include <tchar.h>int APIENTRY WinMain(…){

OSVERSIONINFOEX osver={0};osver.dwOSVersionInfoSize=sizeof(OSVERSIONINFOEX);

BOOL bFlag=GetVersionEx((OSVERSIONINFO *) &osver);if(bFlag==FALSE){

MessageBox(NULL,_T("Error"),_T(" 系統資訊 "),MB_OK);ExitProcess(-1);

}if(osver.dwMajorVersion==5 && osver.dwMinorVersion==0)

MessageBox(NULL,_T("Windows2000"),_T(" 系統資訊 "),MB_OK);return 0;

}

#include <windows.h> #include <tchar.h>int APIENTRY WinMain(…){

OSVERSIONINFOEX osver={0};osver.dwOSVersionInfoSize=sizeof(OSVERSIONINFOEX);

BOOL bFlag=GetVersionEx((OSVERSIONINFO *) &osver);if(bFlag==FALSE){

MessageBox(NULL,_T("Error"),_T(" 系統資訊 "),MB_OK);ExitProcess(-1);

}if(osver.dwMajorVersion==5 && osver.dwMinorVersion==0)

MessageBox(NULL,_T("Windows2000"),_T(" 系統資訊 "),MB_OK);return 0;

}

指定大小指定大小

取得版本資訊取得版本資訊

判斷是否為 Win2000 作業系統判斷是否為 Win2000 作業系統

程式 Demo: 判斷是否為 Win2000 範例

Page 34: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

Create the Process:Create the Process: Process Process 建立流程建立流程

Create a Process kernel object

Create a Process kernel objectA thread call CreateProcess 1

管理 Process 的資料結構管理 Process 的資料結構

Create a Virtual address space

Create a Virtual address space

Load the Code ,Data and DLL

Load the Code ,Data and DLL

main{}

Create a Thread kernel object

Create a Thread kernel object1

管理 Thread 的資料結構管理 Thread 的資料結構

建立 primary thread建立 primary thread

main{}

執行 C/C++ run-timeStartup code

執行 C/C++ run-timeStartup code

Page 35: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

Create the Process:Create the Process: The CreateProcess The CreateProcess function function

BOOL CreateProcess( LPCTSTR lpApplicationName, LPTSTR lpCommandLine, LPSECURITY_ATTRIBUTES lpProcessAttributes, LPSECURITY_ATTRIBUTES lpThreadAttributes, BOOL bInheritHandles, DWORD dwCreationFlags, LPVOID lpEnvironment, LPCTSTR lpCurrentDirectory, LPSTARTUPINFO lpStartupInfo, LPPROCESS_INFORMATION lpProcessInformation);

BOOL CreateProcess( LPCTSTR lpApplicationName, LPTSTR lpCommandLine, LPSECURITY_ATTRIBUTES lpProcessAttributes, LPSECURITY_ATTRIBUTES lpThreadAttributes, BOOL bInheritHandles, DWORD dwCreationFlags, LPVOID lpEnvironment, LPCTSTR lpCurrentDirectory, LPSTARTUPINFO lpStartupInfo, LPPROCESS_INFORMATION lpProcessInformation);

執行檔名稱執行檔名稱

命令列命令列新建出來的 process / thread 是否可以被其他 child 繼承新建出來的 process / thread 是否可以被其他 child 繼承

TRUE: 則每個可以被繼承的 Kernel Object 都會被新建立的 process 繼承

TRUE: 則每個可以被繼承的 Kernel Object 都會被新建立的 process 繼承

設定 process 的建立方式 : 1. 是否擁有 console 2. 優先權類別設定

設定 process 的建立方式 : 1. 是否擁有 console 2. 優先權類別設定

指向環境變數區塊的位址 , NULL 使用 parent 的environment.

指向環境變數區塊的位址 , NULL 使用 parent 的environment.

字串 , 指定新建立 process 的目前目錄 .

字串 , 指定新建立 process 的目前目錄 .

一個 STARTUPINFO 結構 : 紀錄 window 位置 , 大小 console 寬度字元數 , 高度字元數 標準輸入輸出與標準錯誤的 handle

一個 STARTUPINFO 結構 : 紀錄 window 位置 , 大小 console 寬度字元數 , 高度字元數 標準輸入輸出與標準錯誤的 handle

一個 PROCESS_INFORMATION 結構 : 紀錄新建立的 Process Handle 與 PID primary thread Handle 與 hID

一個 PROCESS_INFORMATION 結構 : 紀錄新建立的 Process Handle 與 PID primary thread Handle 與 hID

Page 36: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

void main( VOID ){ STARTUPINFO si; PROCESS_INFORMATION pi;

ZeroMemory( &si, sizeof(si) ); si.cb = sizeof(si); ZeroMemory( &pi, sizeof(pi) );

// Start the child process.

if( !CreateProcess( NULL, // No module name (use command line). "MyChildProcess", // Command line. NULL, // Process handle not inheritable. NULL, // Thread handle not inheritable. FALSE, // Set handle inheritance to FALSE. 0, // No creation flags. NULL, // Use parent's environment block. NULL, // Use parent's starting directory. &si, // Pointer to STARTUPINFO structure. &pi ) // Pointer to PROCESS_INFORMATION structure. ) { ErrorExit( "CreateProcess failed." ); }

// Wait until child process exits.

WaitForSingleObject( pi.hProcess, INFINITE );

// Close process and thread handles. CloseHandle( pi.hProcess ); CloseHandle( pi.hThread );}

範例程式範例程式

等待新建出來的 process terminated( 試著把這行拿掉看看 )

等待新建出來的 process terminated( 試著把這行拿掉看看 )

將 reference 到 process 與 thread 的 Handle close 起來

將 reference 到 process 與 thread 的 Handle close 起來

配置 STARTUPINFO 與PROCESS_INFOMATION 給新建的 process 使用

配置 STARTUPINFO 與PROCESS_INFOMATION 給新建的 process 使用

設定初值設定初值

建立新的 process 主要程式碼建立新的 process 主要程式碼

Page 37: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

Terminating a ProcessTerminating a Process Primary thread’s Primary thread’s entry-point function returnsentry-point function returns

WinMain, main, wWinMain and wmainWinMain, main, wWinMain and wmain The thread’s The thread’s resourcesresources will be cleaned up will be cleaned up

properlyproperly C++C++ object will be destroyed properly object will be destroyed properly The The memorymemory used in the thread’s stack will free used in the thread’s stack will free Process’s Process’s exit codeexit code will return will return Process kernel object Process kernel object usage counterusage counter - 1 - 1

ExitProcess()ExitProcess() TerminateProcess()TerminateProcess()

All the threads in the process dieAll the threads in the process die

強烈建議使用強烈建議使用

下列四種情況下 , 會 Terminating 一個 proces下列四種情況下 , 會 Terminating 一個 proces

可以強迫其他 process終止 ( 不會通知 DLL 對應的 detaching function) Process 可能沒有機會 update 狀態資料到 disk 中

可以強迫其他 process終止 ( 不會通知 DLL 對應的 detaching function) Process 可能沒有機會 update 狀態資料到 disk 中

強迫自己終止 ( 會通知 DLL ) C++ 解構子不會被呼叫強迫自己終止 ( 會通知 DLL ) C++ 解構子不會被呼叫

由 main 或 WinMain離開 , 系統幫你做的事情由 main 或 WinMain離開 , 系統幫你做的事情

Page 38: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

ExitProcess() functionExitProcess() function

Any thread that call Any thread that call ExitProcess()ExitProcess() will terminates the processwill terminates the process

All All system resourcesystem resource will be cleaned will be cleaned up perfectlyup perfectly

C/C++ run time policyC/C++ run time policy

VOID ExitProcess(UINT fuExitCode);VOID ExitProcess(UINT fuExitCode);

int APIENTRY WinMain(…){ … return 0;}

int APIENTRY WinMain(…){ … return 0;}

進入 C/C++ run-timeStartup code

進入 C/C++ run-timeStartup code

call ExitProcess(0)call ExitProcess(0)

Any threads running in the process terminate

這裡指的是那些 Handle (Event,File,Process…)這裡指的是那些 Handle (Event,File,Process…)

0 表示正常結束0 表示正常結束

Page 39: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

C/C++ C/C++ 程式應該避免呼叫 程式應該避免呼叫 ExitProcess()ExitProcess()

System resource will be cleaned but System resource will be cleaned but the C++ objects are not.the C++ objects are not.

#include <windows.h>

#include <iostream>using namespace std;

CSomeObj g_GlobalObj; // 宣告全區域變數void main(){

CSomeObj LocalObj;ExitProcess(0);

}

#include <windows.h>

#include <iostream>using namespace std;

CSomeObj g_GlobalObj; // 宣告全區域變數void main(){

CSomeObj LocalObj;ExitProcess(0);

}

class CSomeObj{ public: CSomeObj(){ cout<<" 建構子 " << endl;} ~CSomeObj(){ cout<<" 解構子 "<< endl;}};

class CSomeObj{ public: CSomeObj(){ cout<<" 建構子 " << endl;} ~CSomeObj(){ cout<<" 解構子 "<< endl;}};

執行結果執行結果

建構子建構子

建構子建構子直接呼叫的結果直接呼叫的結果

C++ 物件沒有被解構C++ 物件沒有被解構

程式範例 : 避免呼叫 ExitProcess

導致系統狀態無法更新 有可能的情況是在物件的解構子中 , 針對目標資料庫做結束的動作 , 因為你呼叫了 ExitProcess() 而導致資料庫資訊不正確

Page 40: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

TerminateProcess TerminateProcess function()function()

You can terminate You can terminate another processanother process

BOOL TerminateProcess(HANDLE hProcess,UINT fuExitCode);BOOL TerminateProcess(HANDLE hProcess,UINT fuExitCode);

TerminateProcess(…)TerminateProcess(…)

Process A Process B

根本沒有通知 ,來不及存檔

terminate

OS 會接手把會接手把

ProcessB 的所有資源全部釋

Page 41: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

列出所有目前正在執行列出所有目前正在執行 Processes NameProcesses Name範例範例

BOOL GetProcessList( ){

HANDLE hProcessSnap;hProcessSnap = CreateToolhelp32Snapshot( TH32CS_SNAPPROCESS, 0 );if( hProcessSnap == INVALID_HANDLE_VALUE ) {

printError( "CreateToolhelp32Snapshot (of processes)" );return( FALSE );

}

PROCESSENTRY32 pe32;pe32.dwSize = sizeof( PROCESSENTRY32 );

if( !Process32First( hProcessSnap, &pe32 ) ) {printError( "Process32First" ); CloseHandle( hProcessSnap ); // Must clean up the snapshot object!return( FALSE );

}

do{printf( "\nPROCESS NAME: %s", pe32.szExeFile );

}while( Process32Next( hProcessSnap, &pe32 ) );

// 4. Don't forget to clean up the snapshot object!CloseHandle( hProcessSnap ); return TRUE;

}

BOOL GetProcessList( ){

HANDLE hProcessSnap;hProcessSnap = CreateToolhelp32Snapshot( TH32CS_SNAPPROCESS, 0 );if( hProcessSnap == INVALID_HANDLE_VALUE ) {

printError( "CreateToolhelp32Snapshot (of processes)" );return( FALSE );

}

PROCESSENTRY32 pe32;pe32.dwSize = sizeof( PROCESSENTRY32 );

if( !Process32First( hProcessSnap, &pe32 ) ) {printError( "Process32First" ); CloseHandle( hProcessSnap ); // Must clean up the snapshot object!return( FALSE );

}

do{printf( "\nPROCESS NAME: %s", pe32.szExeFile );

}while( Process32Next( hProcessSnap, &pe32 ) );

// 4. Don't forget to clean up the snapshot object!CloseHandle( hProcessSnap ); return TRUE;

}

1. 取得目前系統中正在執行 Processes 的快照 (snapshot)1. 取得目前系統中正在執行 Processes 的快照 (snapshot)

2. 取出第一個正在執行的 Process2. 取出第一個正在執行的 Process

3. 印出相關 Process 的名稱3. 印出相關 Process 的名稱

#include <windows.h>#include <stdio.h>#include <tlhelp32.h>void main(){ GetProcessList();}

#include <windows.h>#include <stdio.h>#include <tlhelp32.h>void main(){ GetProcessList();}

C/C++ startup

ignoredignored

程式範例 : 列出目前系統正在執行的 Process參考資料 : http://msdn.microsoft.com/library/default.asp?url=/library/en-us/perfmon/base/taking_a_snapshot_and_viewing_processes.asp

列出的是 process列出的是 process

Page 42: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

Terminate Terminate 所有目前正在執行的 所有目前正在執行的 NotepadNotepad

BOOL GetProcessList( ){HANDLE hProcessSnap;hProcessSnap =

CreateToolhelp32Snapshot( TH32CS_SNAPPROCESS, 0 );

< 中間省略>do{ printf( "\nPROCESS NAME: %s", pe32.szExeFile );

}while( Process32Next( hProcessSnap, &pe32 ) );

// 4. Don't forget to clean up the snapshot object!CloseHandle( hProcessSnap ); return TRUE;

}

BOOL GetProcessList( ){HANDLE hProcessSnap;hProcessSnap =

CreateToolhelp32Snapshot( TH32CS_SNAPPROCESS, 0 );

< 中間省略>do{ printf( "\nPROCESS NAME: %s", pe32.szExeFile );

}while( Process32Next( hProcessSnap, &pe32 ) );

// 4. Don't forget to clean up the snapshot object!CloseHandle( hProcessSnap ); return TRUE;

}

if(strcmpi("NotePad.exe",pe32.szExeFile)==0){ printf(" 發現 NotePad.exe 程式 刪除 "); HANDLE hProcess; hProcess = OpenProcess( PROCESS_ALL_ACCESS, FALSE, pe32.th32ProcessID ); if( hProcess == NULL ) printError( "OpenProcess" ); TerminateProcess(hProcess,0); CloseHandle( hProcess ); WaitForSingleObject(hProcess,INFINITE);}

if(strcmpi("NotePad.exe",pe32.szExeFile)==0){ printf(" 發現 NotePad.exe 程式 刪除 "); HANDLE hProcess; hProcess = OpenProcess( PROCESS_ALL_ACCESS, FALSE, pe32.th32ProcessID ); if( hProcess == NULL ) printError( "OpenProcess" ); TerminateProcess(hProcess,0); CloseHandle( hProcess ); WaitForSingleObject(hProcess,INFINITE);}

取得 notepad.exe process 的 Handle取得 notepad.exe process 的 Handle

Terminate notepad processesTerminate notepad processes

程式範例 :TerminateProcess

這個傳回來的 Handle 不需要繼承屬性

這個傳回來的 Handle 不需要繼承屬性

Page 43: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

When a Process TerminatesWhen a Process Terminates當當 ProcessProcess 被終結時被終結時 ,, 系統的動作系統的動作

流程流程Terminate any

remaining thread

Terminate any remaining thread

All User & GDI objectsare freed

All User & GDI objectsare freed

All Kernel objectsare closed

All Kernel objectsare closed

若沒有任何 Process 擁有它 ,則這個 Kernel object 將會被destory

若沒有任何 Process 擁有它 ,則這個 Kernel object 將會被destory

Exit codeSTILL_ACTIVE

Exit codeSTILL_ACTIVE VOID ExitProcess(UINT fuExitCode);VOID ExitProcess(UINT fuExitCode);

釋放如 menu, icon 等資源釋放如 menu, icon 等資源

Signaled the Process kernel object

Signaled the Process kernel object

-1

系統狀態會由 STILL_ACTIVE 改成 fuExitCode

系統狀態會由 STILL_ACTIVE 改成 fuExitCode

Page 44: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

Obtain the process’s exit Obtain the process’s exit codecode

BOOL GetExitCodeProcess(HANDLE hProcess, PDWORD pdwExitCode);BOOL GetExitCodeProcess(HANDLE hProcess, PDWORD pdwExitCode);

Get the process’s handleGet the process’s handle

WaitForSingleObjectWaitForSingleObject

GetExitCodeProcessGetExitCodeProcess

等待該 process terminate等待該 process terminate

You can call this function at any time

若目標 process 沒有 exit 則 1. pdwExitcode

STILL_ACTIVE

(0x103)

回傳的資料

會傳回目標 process 的 kernel objectExitCode

Page 45: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

Appendix (Appendix ( 補充補充 ))

Page 46: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

__cdecl V.S. __stdcall__cdecl V.S. __stdcall __cdecl: __cdecl: defaultdefault calling converting for C/C++ calling converting for C/C++

The stack is cleaned up by the The stack is cleaned up by the callercaller. . (( 可處理不定變數可處理不定變數 ))

__stdcall: is used to call __stdcall: is used to call Win32 APIWin32 API The The calleecallee clean the stack. clean the stack. (( 故不定變數 故不定變數 function function 由 由 __cdecl __cdecl

處理處理 ))

ElementElement Startup FunctionStartup Function

Argument-passing Argument-passing orderorder

Right to LeftRight to Left

Stack-maintenance Stack-maintenance responsibilityresponsibility

Calling functionCalling function pop the pop the arguments from the arguments from the stackstack

ElementElement Startup FunctionStartup Function

Argument-passing Argument-passing orderorder

Right to LeftRight to Left

Stack-maintenance Stack-maintenance responsibilityresponsibility

Called functionCalled function pop its pop its own argument from the own argument from the stackstack

Microsoft Specific Microsoft Specific

參考資料 : http://msdn.microsoft.com/library/default.asp?url=/library/en-us/vccelng/htm/msmod_6.asp

被呼叫的 function被呼叫的 function

因為只有 caller 才知道 push 了多少參數給 callee function

因為只有 caller 才知道 push 了多少參數給 callee function

Page 47: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

__fastcall__fastcall

__fastcall:__fastcall: arguments to functions are to be arguments to functions are to be

passed in passed in registersregisters, when , when possiblepossible..

ElementElement Startup FunctionStartup Function

Argument-passing Argument-passing orderorder ECX & EDXECX & EDX 前兩個 前兩個 DWORD DWORD 或較小的或較小的 argumentargument

剩下的剩下的 are passed right to leftare passed right to left

Stack-maintenance Stack-maintenance responsibilityresponsibility

Called functionCalled function pop the pop the arguments from the stackarguments from the stack

參考資料 : http://msdn.microsoft.com/library/default.asp?url=/library/en-us/vclang/html/_core___fastcall.asp

Page 48: Processes 井民全製作. Introduction Process is an instance of running program Process is an instance of running program Kernel object: Kernel object: OS uses

EndEnd