kpdetach.c
最終更新:2009/12/16
001: /* kpdetach.c 002: * プロセス処理のサンプル 003: * ・外部プログラムのプロセスをデタッチ(detach)する。 004: * ・子プロセスには現在の環境変数が引き継がれる。 005: * ・子プロセスのプロセスIDを表示する。 006: * ・Unix ではデーモン化、Windows ではコンソールなしに起動する。 007: * ・デタッチした子プロセスの終了は、Windows ではタスクマネージャなどを使う。 008: */ 009: 010: #define USAGE "Usage: kpdetach <prog_name> <args>" 011: 012: #include "apr_general.h" 013: #include "apr_file_io.h" 014: #include "apr_errno.h" 015: #include "apr_env.h" 016: #include "apr_strings.h" 017: #include "apr_thread_proc.h" 018: 019: #include "mystab.h" 020: 021: int apr_my_main ( 022: int ac, char **av 023: , apr_file_t * astdin 024: , apr_file_t * astdout 025: , apr_file_t * astderr 026: , apr_pool_t * pool 027: ) { 028: 029: apr_status_t rv=APR_SUCCESS; 030: 031: char *prog_name = NULL; 032: char **args = NULL; 033: 034: apr_proc_t proc; 035: apr_pool_t *pool2 = NULL; 036: 037: apr_procattr_t *proc_attr = NULL; 038: 039: if (ac < 2) { 040: apr_file_printf(astderr, "%s\n", USAGE); 041: goto _FINALLY_; 042: } 043: 044: /* 子プロセスが実行するコマンド */ 045: 046: prog_name = av[1]; 047: 048: /* 子プロセスの実行するコマンドへの引数配列の準備 */ 049: 050: if (ac > 1) { 051: int i; 052: args = (char**)apr_palloc(pool, sizeof(char*)*(ac)); 053: for (i=0; i<ac-1; i++) { /* args[0] には av[1] が入る */ 054: args[i] = av[i+1]; 055: } 056: args[i]=NULL; /* 最後はヌル */ 057: 058: } 059: 060: /* 子プロセス用引数配列の確認 */ 061: 062: if (args) { 063: char **x=args; 064: printf("#prog_name=[%s]\n", prog_name); 065: for (; *x; x++) { 066: printf("#args[%d]=[%s]\n", x-args, *x); 067: } 068: } 069: 070: /* 子プロセス用メモリプール生成 */ 071: 072: rv=apr_pool_create(&pool2, NULL); 073: if (APR_SUCCESS != rv) { 074: goto _FINALLY_; 075: } 076: 077: /* 子プロセスの属性情報生成 */ 078: 079: rv=apr_procattr_create(&proc_attr, pool); 080: if (APR_SUCCESS != rv) { 081: goto _FINALLY_; 082: } 083: 084: /* 子プロセスのコマンドタイプ設定 */ 085: 086: rv=apr_procattr_cmdtype_set(proc_attr, APR_PROGRAM_ENV); 087: if (APR_SUCCESS != rv) { 088: goto _FINALLY_; 089: } 090: 091: /* 子プロセスのデタッチ属性をセット(デーモン化) */ 092: apr_procattr_detach_set(proc_attr, TRUE); 093: 094: /* 子プロセスのパイプ準備 */ 095: 096: rv=apr_procattr_io_set(proc_attr, APR_NO_PIPE, APR_NO_PIPE, APR_NO_PIPE); 097: if (APR_SUCCESS != rv) { 098: goto _FINALLY_; 099: } 100: 101: /* 子プロセスの生成 */ 102: 103: rv = apr_proc_create(&proc, prog_name, (const char*const*)args, NULL, proc_attr, pool2); 104: if (APR_SUCCESS!=rv) { 105: goto _FINALLY_; 106: } 107: 108: /* 子プロセスのPID */ 109: apr_file_printf(astdout, "PID=[%d]\n", proc.pid); 110: 111: _FINALLY_: 112: 113: /* 子プロセス用メモリプールの解放 */ 114: 115: if (pool2) { 116: apr_pool_destroy(pool2); 117: pool2 = NULL; 118: } 119: 120: if (APR_SUCCESS != rv) { 121: char error_buf[64]; 122: apr_file_printf(astderr, 123: "ERROR: %s\n", apr_strerror(rv, error_buf, sizeof(error_buf))); 124: 125: apr_file_printf(astderr, "failed!\n"); 126: return 1; /* 異常終了 */ 127: 128: } 129: 130: apr_file_printf(astdout, "\ndone.\n"); 131: 132: return 0; /* 正常終了 */ 133: 134: 135: } /* end of main */
KAKU PROJECT (2009) |