2012년 8월 23일 목요일

Create Process 함수의 이해


AdderProcess.cpp   자식 프로세스 코드

1:  #include <stdio.h>  
2:  #include <tchar.h>  
3:  #include <Windows.h>  
4:    
5:  int _tmain(int argc, TCHAR* argv[]) {  
6:       DWORD val1, val2;  
7:       val1=_ttoi(argv[1]);   
8:       // 문자열 데이터를 정수형 데이터로 변경하는 atoi 함수와 유니코드 기반의 _wtoi를 동시 지원하는 매크로 함수  
9:       val2=_ttoi(argv[2]);  
10:    
11:       _tprintf(_T("%d + %d = %d \n"), val1, val2, val1+val2);  
12:    
13:       _gettchar();  // 프로그램의 실행을 잠시 멈추기 위해, getchar과 getwchar 함수를 동시 지원하는 매크로 함수  
14:       return 0;  
15:  }  



CreateProcess.cpp   부모 프로세스 코드

1:  #include <stdint.h>  
2:  #include <tchar.h>  
3:  #include <windows.h>  
4:    
5:  #define DIR_LEN MAX_PATH+1  // MAX_PATH, windef.h에 선언되어 있음. 윈도우에서 허용하는 완전경로의 최대 길이  
6:    
7:  int _tmain(int argc, TCHAR* argv[]) {  
8:       STARTUPINFO si={0, };  // 선언과 동시에 초기화. CreateProcess 함수의 9번째 인자요소. 프로세스의 속성을 지정  
9:       // 0으로 초기화 해야함.  
10:       PROCESS_INFORMATION pi;  // PROCESS_INFORMATION 구조체 변수는 새로 생성되는 프로세스 관련 정보를 얻기 위해 사용  
11:    
12:       si.cb=sizeof(si);  // 구조체 변수 si의 바이트 단위 크기, 형식적인 측면이 강함  
13:       si.dwFlags=STARTF_USEPOSITION | STARTF_USESIZE;  
14:       // si 구조체 변수에 설정된 값중에 반영하고자 하는 멤버들에 대한 정보 설정  
15:       // STARTF_USEPOSITION은 dwX와 dwY를 참조해 창의 위치를 결정  
16:       // sTARTF_USESIZE는 dwXSize와 dwYSize를 참조해 윈도우의 크기를 결정  
17:       si.dwX=100;  
18:       si.dwY=200;  
19:       si.dwXSize=300;  
20:       si.dwYSize=200;  
21:       si.lpTitle=_T("I am a boy!"); // 윈도우의 타이틀 바 제목을 지정  
22:       // 콘솔 프로세스가 아닌, 노트패드와 같은 윈도우 프로세스일 경우 아무런 의미가 없음  
23:    
24:       TCHAR command[]=_T("AdderProcess.exe 10 20");  // 실행 파일의 이름과 함께 전달할 인자  
25:       TCHAR cDir[DIR_LEN];  // 디렉토리 정보가 저장될 버퍼 포인터  
26:       BOOL state;  
27:    
28:       GetCurrentDirectory(DIR_LEN, cDir);  
29:       // cDir 디렉토리 정보가 저장될 버퍼 포인터, DIR_LEN 디렉토리 정보가 저장될 메모리 버퍼의 크기  
30:       _fputts(cDir, stdout);  // 현재 디렉토리 정보를 추출해서 출력
31:       _fputts(_T("\n"), stdout);  
32:    
33:       SetCurrentDirectory(_T("C:\\WinSystem"));  
34:       // 현재 디렉토리 경로명을 지정할 수 있음  
35:    
36:       GetCurrentDirectory(DIR_LEN, cDir);  // 현재 디렉토리를 다시 확인  
37:       _fputts(cDir, stdout);  // 현재 디렉토리 경로명을 다시 출력. C:\\WinSystem이 있어야 변경됨.
38:       _fputts(_T("\n"), stdout);  
39:    
40:       state = CreateProcess (  
41:            NULL,  // 첫번째 인자로 NULL을 전달하고  
42:            command,  // 두번째 인자를 통해 생성하려는 프로세스 이름 정보와 함께 전달 인자까지 함께 전달할 수 있음.  
43:            //  전달 인자는 반드시 변수 형태여야 함. _T("AdderProcess.exe 10 20"),을 직접 파라미터에 쓰면 안됨.  
44:            NULL, NULL, TRUE,  
45:            CREATE_NEW_CONSOLE,  // 프로세스의 특성을 결정지을 때 사용.  
46:            // CREATE_NEW_CONSOLE은 프로세스를 위한 콘솔 윈도우가 독립적으로 생성됨.  
47:            // CREATE_NEW_CONSOLE을 전달하지 않으면 부모 프로세스의 콘솔 윈도우를 자식 프로세스가 공유하게 됨  
48:            // CREATE_NEW_CONSOLE 대신 0을 전달해 확인할 수 있음  
49:            NULL, NULL, &si, &pi  
50:            );  
51:    
52:       if(state!=0)  
53:            _fputts(_T("Creation OK! \n"), stdout);  
54:       else  
55:            _fputts(_T("Creation ERROR! \n"), stdout);  
56:    
57:       return 0;  
58:  }  


< 응용 >

Calculator.cpp

1:  #include <stdio.h>  
2:  #include <tchar.h>  
3:  #include <Windows.h>  
4:    
5:  enum{DIV=1, MUL, ADD, MIN, ELSE, EXIT};  
6:    
7:  DWORD ShowMenu();  
8:  void Divide(double, double);  
9:  void Multiple(double, double);  
10:  void Add(double, double);  
11:  void Min(double, double);  
12:    
13:  int _tmain(int argc, TCHAR* argv[]) {  
14:       STARTUPINFO si={0, };  
15:       PROCESS_INFORMATION pi;  
16:       si.cb=sizeof(si);  
17:    
18:       TCHAR command[]=_T("calc.exe");  
19:       SetCurrentDirectory(_T("C:\\WINDOWS\\system32"));  
20:    
21:       DWORD sel;  
22:       double num1, num2;  
23:       while(true) {  
24:            sel=ShowMenu();  
25:            if(sel==EXIT)  
26:                 return 0;  
27:    
28:            if(sel != ELSE) {  
29:                 _fputts(_T("Input Num1 Num2 : "), stdout);  
30:                 _tscanf(_T("%lf %lf"), &num1, &num2);  
31:            }  
32:    
33:            switch(sel) {  
34:            case DIV:  
35:                 Divide(num1, num2);  
36:                 break;  
37:            case MUL:  
38:                 Multiple(num1, num2);  
39:                 break;  
40:            case ADD:  
41:                 Add(num1, num2);  
42:                 break;  
43:            case MIN:  
44:                 Min(num1, num2);  
45:                 break;  
46:            case ELSE:  
47:                 ZeroMemory(&pi, sizeof(pi));  
48:                 CreateProcess(  
49:                      NULL, command, NULL, NULL,  
50:                      TRUE, 0, NULL, NULL, &si, &pi);  
51:                 break;  
52:            }  
53:       }  
54:         
55:       return 0;  
56:  }  
57:    
58:  DWORD ShowMenu() {  
59:       DWORD sel;  
60:    
61:       _fputts(_T("------Menu------\n"), stdout);  
62:       _fputts(_T("num1: Divide\n"), stdout);  
63:       _fputts(_T("num2: Multiple\n"), stdout);  
64:       _fputts(_T("num3: Add\n"), stdout);  
65:       _fputts(_T("num4: Minus\n"), stdout);  
66:       _fputts(_T("num5: Any other operations\n"), stdout);  
67:       _fputts(_T("num6: EXIT"), stdout);  
68:       _fputts(_T("SELECION >> "), stdout);  
69:       _tscanf(_T("%d"), &sel);  
70:    
71:       return sel;  
72:  }  
73:    
74:  void Divide(double a, double b) {  
75:       _tprintf(_T("%f/%f=%f \n\n"), a, b, a/b);  
76:  }  
77:    
78:  void Multiple(double a, double b) {  
79:       _tprintf(_T("%f*%f=%f \n\n"), a, b, a*b);  
80:  }  
81:    
82:  void Add(double a, double b) {  
83:       _tprintf(_T("%f+%f=%f \n\n"), a, b, a+b);  
84:  }  
85:    
86:  void Min(double a, double b) {  
87:       _tprintf(_T("%f-%f=%f \n\n"), a, b, a-b);  
88:  }  




참고 : 뇌를 자극하는 윈도우즈 시스템 프로그래밍. 윤성우 저



댓글 없음:

댓글 쓰기