서브프로세스 제어

서브프로세스 제어 (Controlling Subprocesses)

Octave 안에서 다른 프로그램을 실행하고 싶을 때가 있어요. system이나 popen 같은 고수준 명령이 있고, 더 낮은 수준의 Unix 계열 함수들도 준비돼 있어요. 어떤 상황에 어떤 함수를 쓰면 좋은지 Octave 매뉴얼 36.5절을 정리해 볼게요.

출처: Controlling Subprocesses

본문

Octave는 서브프로세스를 시작하기 위한 systempopen 같은 고수준 명령을 포함하고 있어요. 어떤 작업을 수행하기 위해 다른 프로그램을 실행하고 그 출력을 살펴보고 싶다면, 아마 이 함수들을 쓰게 될 거예요.

Octave는 또한 서브프로세스를 시작하는 데 쓸 수 있는 매우 낮은 수준의 Unix 계열 함수를 여럿 제공하지만, 고수준 함수로 필요한 것을 처리할 방법을 찾지 못할 때만 쓰는 게 좋아요.

system, unix, dos

system ("string"), system ("string", return_output), system ("string", return_output, type), [status, output] = system (…)string으로 지정된 셸 명령을 실행해요. 하나 이상의 출력 인자를 가지고 호출하거나, 선택 인자 return_output이 true이고 서브프로세스가 동기적으로 시작되면, 명령의 출력이 변수로 반환됩니다. 그 외에 서브프로세스가 동기적으로 실행되면 그 출력은 표준 출력으로 보내져요.

system으로 실행한 명령의 출력을 페이저(pager)로 보내려면 다음과 같은 명령을 쓰면 돼요.

[~, text] = system ("cmd");
more on;
disp (text);

또는

more on;
printf ("%s\n", nthargout (2, "system", "cmd"));

선택 인자 type"async"면 프로세스가 백그라운드로 시작되고 자식 프로세스의 프로세스 ID가 즉시 반환됩니다. 그 외에는 자식 프로세스가 시작되고 Octave는 그것이 종료될 때까지 기다려요. type 인자가 생략되면 기본값은 "sync"입니다.

system 함수는 두 값을 반환할 수 있어요. 첫 번째는 명령의 종료 상태, 두 번째는 표준 출력 스트림에 쓰인 명령의 출력입니다. 예를 들어,

[status, output] = system ("echo foo & exit 2");

은 변수 output을 문자열 'foo'로, 변수 status를 정수 2로 설정해요. 비동기적으로 실행된 명령에 대해 status는 그 명령을 실행하기 위해 시작된 명령 셸의 프로세스 ID입니다.

명령을 실행하는 데 쓰는 셸은 운영 체제에 따라 달라요. UNIX 시스템에서는 보통 /bin/sh, Windows 시스템에서는 cmd.exe입니다. See also: unix, dos.

unix ("command"), status = unix ("command"), [status, text] = unix ("command"), […] = unix ("command", "-echo") — Unix 계열 운영 체제에서 실행 중이면 시스템 명령을 실행하고, 그렇지 않으면 아무것도 하지 않아요. Octave는 외부 명령이 끝날 때까지 기다린 뒤 프로그램의 종료 상태를 status로, 출력을 text로 반환해요. 출력 인자 없이 호출하거나 "-echo" 인자를 주면 text도 표준 출력으로 보내집니다. See also: dos, system, isunix, ismac, ispc.

dos ("command"), status = dos ("command"), [status, text] = dos ("command"), […] = dos ("command", "-echo") — Windows 계열 운영 체제에서 실행 중이면 시스템 명령을 실행하고, 그렇지 않으면 아무것도 하지 않아요. Octave는 외부 명령이 끝날 때까지 기다린 뒤 프로그램의 종료 상태를 status로, 출력을 text로 반환해요. 출력 인자 없이 호출하거나 "-echo" 인자를 주면 text도 표준 출력으로 보내집니다. See also: unix, system, isunix, ismac, ispc.

open

open file, output = open (file) — 파일 이름 확장자로 결정된 파일 유형에 따라, file을 Octave 안이나 외부 응용 프로그램에서 열어요. 기본적으로 인식되는 파일 유형은 다음과 같습니다.

  • .m — 파일을 편집기에서 열어요. 반환 출력은 없습니다.
  • .mat, octave-workspaceload로 데이터 파일을 열어요. 반환 출력 output을 요청하지 않으면 변수가 기본 워크스페이스에 로드되고, 그렇지 않으면 output은 로드된 데이터를 담은 구조체가 됩니다. load 함수 참고.
  • .ofighgload로 figure를 열어요. hgload 함수 참고.
  • .fig, .ofig — figure를 로드해요.
  • .exe — 프로그램을 실행해요 (Windows 시스템에서만). 반환 출력은 없습니다.

로드 경로에 openxxx(여기서 xxx는 확장자)라는 함수가 있으면 사용자 정의 파일 확장자도 처리할 수 있어요. 그 함수는 파일 이름을 입력으로 받아야 합니다. 예를 들어 .dat 데이터 파일을 .mat 파일이 기본으로 하는 것처럼 기본 워크스페이스에 로드하려면, 다음과 같은 내용의 opendat.m을 정의할 수 있어요.

function retval = opendat (fname)
  evalin ("base", sprintf ("load ('%s');", fname));
endfunction

다른 파일 유형은 적절한 외부 응용 프로그램에서 열립니다.

perl, python

output = perl (scriptfile), output = perl (scriptfile, argument1, argument2, …), [output, status] = perl (…) — Perl 스크립트 scriptfile을, 선택적으로 명령줄 인자 목록과 함께 호출해요. 출력은 output으로, 선택 상태는 status로 반환합니다. scriptfile이 절대 파일 이름이 아니면 현재 디렉토리와 Octave 로드 경로에서 찾아요. See also: system, python.

output = python (scriptfile), output = python (scriptfile, argument1, argument2, …), [output, status] = python (…) — Python 스크립트 scriptfile을, 선택적으로 명령줄 인자 목록과 함께 호출해요. 출력은 output으로, 선택 상태는 status로 반환합니다. scriptfile이 절대 파일 이름이 아니면 현재 디렉토리와 Octave 로드 경로에서 찾아요.

Programming Note: UNIX 시스템에서는 스크립트가 python3으로, Windows에서는 python으로 실행됩니다. PYTHON 환경 변수를 설정해 이 기본값을 바꿀 수 있어요. 예를 들어 Octave 안에서 setenv PYTHON /usr/local/bin/python3처럼요. See also: system, perl.

popen, pclose

fid = popen (command, mode) — 프로세스를 시작하고 파이프를 만들어요. 실행할 명령 이름은 command로 주어지고, mode 인자는 다음과 같아요.

  • "r" — 파이프가 프로세스의 표준 출력에 연결되고 읽기용으로 열립니다.
  • "w" — 파이프가 프로세스의 표준 입력에 연결되고 쓰기용으로 열립니다.

프로세스의 입력 또는 출력 스트림에 해당하는 파일 식별자가 fid로 반환됩니다. 예를 들어,

fid = popen ("ls -ltr / | tail -3", "r");
while (ischar (s = fgets (fid)))
  fputs (stdout, s);
endwhile

   -| drwxr-xr-x  33 root  root  3072 Feb 15 13:28 etc
   -| drwxr-xr-x   3 root  root  1024 Feb 15 13:28 lib
   -| drwxrwxrwt  15 root  root  2048 Feb 17 14:53 tmp

See also: popen2.

status = pclose (fid)popen으로 열었던 파일 식별자 fid를 닫아요. 성공하면 fclose는 0을, 그렇지 않으면 -1을 반환합니다. Programming Note: fclose 함수도 같은 용도로 쓸 수 있어요. See also: fclose, popen.

[in, out, pid] = popen2 (command, args) — 양방향 통신이 가능한 서브프로세스를 시작해요. 프로세스 이름은 command로, args는 명령 옵션을 담은 문자열의 배열 또는 셀 배열이에요. 서브프로세스의 입력·출력 스트림의 파일 식별자가 각각 inout으로 반환됩니다. 명령 실행이 성공하면 pid가 서브프로세스의 프로세스 ID를 포함하고, 그렇지 않으면 pid는 −1이에요. 예를 들어,

[in, out, pid] = popen2 ("sort", "-r");
fputs (in, "these\nare\nsome\nstrings\n");
fclose (in);
EAGAIN = errno ("EAGAIN");
done = false;
do
  s = fgets (out);
  if (ischar (s))
    fputs (stdout, s);
  elseif (errno () == EAGAIN)
    pause (0.1);
    fclear (out);
  else
    done = true;
  endif
until (done)
fclose (out);
waitpid (pid);

   -| these
   -| strings
   -| some
   -| are

popen2popen과 달리 자식 프로세스를 "reap"하지 않는다는 점을 유의하세요. waitpid로 자식의 종료 상태를 확인하지 않으면, 그것은 Octave가 종료될 때까지 남아 있게 됩니다. See also: popen, waitpid.

EXEC_PATH

val = EXEC_PATH (), old_val = EXEC_PATH (new_val), old_val = EXEC_PATH (new_val, "local") — 외부 프로그램을 실행할 때 셸 PATH에 추가할 콜론으로 구분된 디렉토리 목록을 지정하는 내부 변수를 조회하거나 설정해요. 초기값은 환경 변수 OCTAVE_EXEC_PATH에서 가져오지만, 그 값은 명령줄 인자 --exec-path PATH로 재정의될 수 있습니다. 함수 안에서 "local" 옵션과 함께 호출하면 그 변수가 그 함수와 그것이 호출하는 서브루틴 안에서만 지역적으로 바뀌고, 함수를 빠져나오면 원래 변수 값이 복원됩니다. See also: IMAGE_PATH, OCTAVE_HOME, OCTAVE_EXEC_HOME.

낮은 수준의 Unix 계열 함수

대부분의 경우 아래 함수들은 인자를 해석해 대응하는 Unix 시스템 호출을 만드는 역할만 해요. 완전한 사용 예시는 popen2 함수의 정의를 보면 됩니다.

[pid, msg] = fork () — 현재 프로세스의 복사본을 만들어요. fork는 다음 값 중 하나를 반환할 수 있어요.

  • > 0 — 부모 프로세스에 있어요. fork가 반환한 값은 자식 프로세스의 프로세스 ID입니다. waitpid로 자식 프로세스들이 종료되기를 기다리도록 정리하는 게 좋아요.
  • 0 — 자식 프로세스에 있어요. 다른 프로세스를 시작하려면 exec를 호출할 수 있어요. 그것이 실패하면 자식을 종료하기 위해 _Exit를 호출하는 게 좋습니다.
  • < 0 — 어떤 이유로 fork 호출이 실패했어요. 대처가 필요합니다. 시스템 의존적 오류 메시지가 msg에 담겨 있어요.

See also: exec, _Exit.

_Exit (), _Exit (status) — 종료 코드 status로 현재 실행 중인 프로세스를 종료해요. 인자 없이 호출하면 성공을 나타내는 상태 0으로 종료합니다. 선택 정수 인자 status는 종료 코드를 지정해요. Programming Note: 이 함수는 C++ 함수 quick_exit에 대응합니다. 호출 프로세스가 중지되고 열린 파일 디스크립터는 닫힙니다. Octave에서 시작한 자식 프로세스를 끝내려면 정확히 이 함수를 호출해야 해요. 일반적인 C 라이브러리 함수 exit는 동작하지 않습니다. See also: fork.

[err, msg] = exec (file, args) — 현재 프로세스를 새 프로세스로 교체해요. 먼저 fork 없이 exec를 호출하면 현재 Octave 프로세스가 종료되고 file이라는 이름의 프로그램으로 교체됩니다. 예를 들어,

exec ("ls", "-l")

ls를 실행하고 셸 프롬프트로 돌아오게 해요. 성공하면 exec는 반환하지 않습니다. exec가 반환하면 err는 0이 아니고, msg에는 시스템 의존적 오류 메시지가 담겨 있어요.

[read_fd, write_fd, err, msg] = pipe () — 파이프를 만들고 파이프의 읽기·쓰기 끝을 각각 read_fdwrite_fd로 반환해요. 성공하면 err는 0이고 msg는 빈 문자열입니다. 그렇지 않으면 err는 0이 아니고 msg에는 시스템 의존적 오류 메시지가 담겨요. See also: mkfifo.

[fid, msg] = dup2 (old, new) — 파일 디스크립터를 복제해요. 성공하면 fid는 0보다 크고 새 파일 ID를 포함하며, 그렇지 않으면 fid는 음수이고 msg에는 시스템 의존적 오류 메시지가 담겨요. See also: fopen, fclose, fcntl.

[pid, status, msg] = waitpid (pid, options) — 프로세스 pid가 종료되기를 기다려요. pid 인자는 다음과 같아요.

  • −1 — 아무 자식 프로세스나 기다립니다.
  • 0 — Octave 인터프리터 프로세스의 프로세스 그룹 ID와 같은 프로세스 그룹의 어떤 자식 프로세스든 기다립니다.
  • > 0 — ID가 pid인 자식 프로세스가 종료되기를 기다립니다.

options 인자는 다음 상수 중 0개 이상의 비트 OR일 수 있어요.

  • 0 — 신호를 받거나 자식 프로세스가 종료될 때까지 기다립니다 (options 인자가 없을 때의 기본값).
  • WNOHANG — 상태가 즉시 이용 가능하지 않으면 대기하지 않아요.
  • WUNTRACED — 중지된 자식 프로세스와, 중지된 이후 아직 보고되지 않은 상태를 보고해요.
  • WCONTINUE — 중지된 자식이 SIGCONT 전달로 재개되면 반환해요. 이 값은 모든 시스템에서 의미가 있지는 않을 수 있어요.

반환된 pid가 0보다 크면 그것은 종료한 자식 프로세스의 프로세스 ID입니다. 오류가 발생하면 pid는 0보다 작아지고 msg에는 시스템 의존적 오류 메시지가 담겨요. status 값에는 종료한 서브프로세스에 대한 추가적인 시스템 의존 정보가 포함됩니다. See also: WCONTINUE, WCOREDUMP, WEXITSTATUS, WIFCONTINUED, WIFSIGNALED, WIFSTOPPED, WNOHANG, WSTOPSIG, WTERMSIG, WUNTRACED.

v = WCONTINUE ()WCONTINUE 매크로의 숫자 값을 반환해요. WCONTINUE는 SIGCONT 신호 전달로 재개된 중지된 자식이 있으면 waitpid도 반환하도록 할 수 있는 옵션 인자입니다. See also: waitpid, WNOHANG, WUNTRACED.

tf = WCOREDUMP (status)waitpid 호출의 status가 주어지면, 자식이 코어 덤프를 만들었으면 true를 반환해요. 이 함수는 WIFSIGNALED가 true를 반환했을 때만 사용해야 합니다. 이 함수를 구현하는 데 쓰는 매크로는 POSIX.1-2001에 지정되어 있지 않고, 일부 Unix 구현(AIX, SunOS 등)에서는 이용할 수 없어요. See also: waitpid, WIFEXITED, WEXITSTATUS, WIFSIGNALED, WTERMSIG, WIFSTOPPED, WSTOPSIG, WIFCONTINUED.

tf = WEXITSTATUS (status)waitpid 호출의 status가 주어지면, 자식의 종료 상태를 반환해요. 이 함수는 WIFEXITED가 true를 반환했을 때만 사용해야 합니다. See also: waitpid, WIFEXITED, WIFSIGNALED, WTERMSIG, WCOREDUMP, WIFSTOPPED, WSTOPSIG, WIFCONTINUED.

tf = WIFCONTINUED (status)waitpid 호출의 status가 주어지면, 자식 프로세스가 SIGCONT 전달로 재개되었으면 true를 반환해요. See also: waitpid, WIFEXITED, WEXITSTATUS, WIFSIGNALED, WTERMSIG, WCOREDUMP, WIFSTOPPED, WSTOPSIG.

tf = WIFSIGNALED (status)waitpid 호출의 status가 주어지면, 자식 프로세스가 신호로 종료되었으면 true를 반환해요. See also: waitpid, WIFEXITED, WEXITSTATUS, WTERMSIG, WCOREDUMP, WIFSTOPPED, WSTOPSIG, WIFCONTINUED.

tf = WIFSTOPPED (status)waitpid 호출의 status가 주어지면, 자식 프로세스가 신호 전달로 중지되었으면 true를 반환해요. 이는 WUNTRACED로 호출하거나 자식이 추적되고 있을 때만 가능합니다 (ptrace(2) 참고). See also: waitpid, WIFEXITED, WEXITSTATUS, WIFSIGNALED, WTERMSIG, WCOREDUMP, WSTOPSIG, WIFCONTINUED.

tf = WIFEXITED (status)waitpid 호출의 status가 주어지면, 자식이 정상적으로 종료되었으면 true를 반환해요. See also: waitpid, WEXITSTATUS, WIFSIGNALED, WTERMSIG, WCOREDUMP, WIFSTOPPED, WSTOPSIG, WIFCONTINUED.

v = WNOHANG ()WNOHANG 매크로의 숫자 값을 반환해요. WNOHANG은 프로세스가 종료되기를 기다리지 않고 즉시 상태를 반환할지 나타내기 위해 waitpid에 전달할 수 있는 옵션 인자입니다. See also: waitpid, WUNTRACED, WCONTINUE.

tf = WSTOPSIG (status)waitpid 호출의 status가 주어지면, 자식을 중지시킨 신호의 번호를 반환해요. 이 함수는 WIFSTOPPED가 true를 반환했을 때만 사용해야 합니다. See also: waitpid, WIFEXITED, WEXITSTATUS, WIFSIGNALED, WTERMSIG, WCOREDUMP, WIFSTOPPED, WIFCONTINUED.

tf = WTERMSIG (status)waitpid 호출의 status가 주어지면, 자식 프로세스를 종료시킨 신호의 번호를 반환해요. 이 함수는 WIFSIGNALED가 true를 반환했을 때만 사용해야 합니다. See also: waitpid, WIFEXITED, WEXITSTATUS, WIFSIGNALED, WCOREDUMP, WIFSTOPPED, WSTOPSIG, WIFCONTINUED.

v = WUNTRACED ()WUNTRACED 매크로의 숫자 값을 반환해요. WUNTRACED는 자식이 ptrace 시스템 호출로 추적되지는 않았지만 중지되었을 때도 반환할 수 있도록 waitpid에 전달할 수 있는 옵션 인자입니다. See also: waitpid, WNOHANG, WCONTINUE.

fcntl (fid, request, arg), [status, msg] = fcntl (fid, request, arg) — 열린 파일 fid의 속성을 바꿔요. request로 다음 값을 전달할 수 있습니다.

  • F_DUPFD — 복제된 파일 디스크립터를 반환해요.
  • F_GETFDfid의 파일 디스크립터 플래그를 반환해요.
  • F_SETFDfid의 파일 디스크립터 플래그를 설정해요.
  • F_GETFLfid의 파일 상태 플래그를 반환해요. 다음 코드들이 반환될 수 있어요 (일부 플래그는 일부 시스템에서 정의되지 않을 수 있음).
  • O_RDONLY — 읽기 전용으로 열기.
  • O_WRONLY — 쓰기 전용으로 열기.
  • O_RDWR — 읽기와 쓰기로 열기.
  • O_APPEND — 매 쓰기마다 추가하기.
  • O_CREAT — 파일이 없으면 만들기.
  • O_NONBLOCK — 비차단 모드.
  • O_SYNC — 쓰기가 완료될 때까지 기다리기.
  • O_ASYNC — 비동기 I/O.
  • F_SETFLfid의 파일 상태 플래그를 arg로 지정한 값으로 설정해요. 바꿀 수 있는 플래그는 O_APPENDO_NONBLOCK뿐입니다.

성공하면 status는 0이고 msg는 빈 문자열이에요. 그렇지 않으면 status는 -1이고 msg에는 시스템 의존적 오류 메시지가 담겨요. See also: fopen, dup2.

kill (pid, sig), [status, msg] = kill (pid, sig) — 신호 sig를 프로세스 pid로 보내요. pid가 양수면 신호 sigpid로 보내집니다. pid가 0이면 신호가 현재 프로세스의 프로세스 그룹의 모든 프로세스로 보내져요. pid가 -1이면 프로세스 1을 제외한 모든 프로세스로 보내집니다. pid가 -1보다 작으면 신호가 프로세스 그룹 -pid의 모든 프로세스로 보내져요. sig가 0이면 신호는 보내지지 않지만 오류 검사는 여전히 수행됩니다. 성공하면 status는 0이고 msg는 빈 문자열이에요. 그렇지 않으면 status는 -1이고 msg에는 시스템 의존적 오류 메시지가 담겨요.

S = SIG () — Unix 신호 이름과 그것들의 정의된 값을 담은 구조체를 반환해요.

더 알아보기

  • octave-file-archiving-utilities — 파일 압축·해제 유틸리티
  • octave-opening-and-closing-files — 파일 열기와 닫기
  • octave-input-and-output — 입출력 전반