pthread관련 질문입니다. 도와주세요..ㅠㅠ

nchris의 이미지

pthread를 소스 코딩하는건대요

리눅스 환경을 다루는건 하나도 할줄 모른다고 봐도 될정도이고 약간의 c 소스만 짤줄 아는 중생입니다.

#include
#include
#include

void* runner(void *data)
{
int i;
int me = *((int *)data);

printf("Thread id == %d\n", me);
execl("/bin/date","date",NULL);

}

void* runner1(void *data)
{
int i;
int me = *((int *)data);

printf("Thread id == %d\n", me);
execl("/bin/pwd","pwd",NULL);

}

void* runner2(void *data)
{
int i;
int me = *((int *)data);

printf("Thread id == %d\n", me);
execl("/bin/ls","ls",NULL);

}

int main()
{
pthread_t p_thread[3];
int a=1,b=2,c=3;

pthread_create(&p_thread[0], NULL, runner, (void *)&a);
pthread_create(&p_thread[1], NULL, runner1, (void *)&b);
pthread_create(&p_thread[2], NULL, runner2, (void *)&c);
pthread_join(p_thread[0],NULL);
pthread_join(p_thread[1],NULL);
pthread_join(p_thread[2],NULL);

return 0;
}
이런 소스가 있다면 스레드가 하나만 실행되고 ls가 실행되고 끝나버리는대 unix명령을 끝내고 계속해서 thread id라는게 출력될려면 도대체 어떻게 해야 하나요? ...12시간동안 찾아보고 뒤져보고 해도 도저히 답이 않나오내요

fork함수를 배워서 execlp가 샐행문이라는건 아는대 posix에서는 저 실행문을 쓰면 프로세스가 대치가 되고 바로 프로그램이 종료되버리는대 유닉스 명령문을 더 추가시키기 위한 방법을 도대체 어떻게 해야하는건지 궁금합니다...제발 도와주세요...

새벽 5시인대도 이 작업으로 골머리를 썪고 있습니다. 스레드가 3개는 생성되는대 프로그램은 왜 따라서 실행이 안되는지를 모르겠습니다. 스스로 해결해볼려고 했지만 도저히 안되서 답답한 마음에 질문을 올리게 되었내요...답변 부탁드리겠습니다.ㅠㅠ

아무리 봐도 저 execlp라는 실행문에 문제가 있어보입니다만...그걸 대치하는 다른 방법은 전혀 모르겠내요...

혹 설마 인자를 넣어야 한다면 인자는 어떻게 넣어야 하는건지.......

FIFO의 이미지

그냥 fork를 쓰시면 이렇게 해결할 수 있는 것 같네요.
http://kin.naver.com/detail/detail.php?d1id=1&dir_id=10104&eid=/S/0RQRjdeslO6OExHHO0Qgk+Igs8SBB

그런데 fork()가 thread-safe한지 모르겠네요.
아마도 아닐 것 같은데... 이건 execlp()도 마찬가지일듯
그러면 호출을 동기화해줘야 한다는 건데 개발환경이 아니라서 잘 모르겠네요

winner의 이미지

이런 code 보면 보고 싶지 않다능...

dorado2의 이미지

execl 함수를 수행하게 되면 현재 프로세스 이미지를 새로운 프로세스 이미지로 대체하게 됩니다.
그러므로 기존 프로세스에서 생성한 thread들이 다 동작하지 않고 새 프로세스 수행후 프로그램이 종료되는 것으로 보이네요.

fork() 후에 execl 수행을 하도록 변경해보세요.

mach의 이미지

유닉스에서 프로세스를 P라고하고, 그 프로세스 P에서 생성한 쓰레드를 t0, t1,t2,t3라고 하면, 좀 어색하지만 다음과 같은 형식으로 표현해 볼 수 있습니다.

P = {t0, t1,t2,t3}

t0: 메인쓰레드, 즉, 명시적으로(pthread_create함수를 호출해서) 생성한 적은 없지만, 존재하는 것, 위 프로그램에서는 pthread_join()을 대기하고 있는 쓰레드가 되겠군요. 3번 호출하니까, 3개의 쓰레드가 종료대기를 기다리겠군요. 참고로, 이러한 메인 쓰레드는 다른 쓰레드 보다 먼저, 종료되어서는 아니됩니다. 메인쓰레드가 종료되면, 프로세스의 종료로 이어지고, 나머지 쓰레드는 전부 죽게되지요. 위에서 처럼 기다리던가(pthread_join()), 또는 무한루프 스타일로 가게끔 만들게 되지요.
t1: runner() - date를 출력하고 종료(아시겠지만, 기본적으로 쓰레드의 주 함수의 끝이 쓰레드의 종료지요)
t2: runner1() - pwd를 출력하고 종료
t3: runner2() - ls를 출력하고 종료

이렇게 의도한 것인데,
즉, date, pwd, ls를 각각 1번씩 실행후 종료하는 프로그램(?)을 의도한 코드로 보입니다.

그런데, 위 프로그램은 3개의 쓰레드중 1개만 실행될 수 밖에 없습니다.

그 이유는 exec*()에 있습니다.
exec로 시작되는 시스템호출들은, 이를 호출한 프로세스를 변신시킵니다. 예를 들어, 어떤 프로세스가 쓰레드를 100개 가지고 있건, 메모리를 1기가 사용중이건, 데이터베이스에 연결하고 있었건, 파일을 열었거나, 말았거나, 네트워크 연결을 하고 있었건 아니건간에,...등등에 전혀!! 관계없이 새로운 프로그램으로 변신해 버립니다.

4개의 쓰레드 t0,t1,t2,t3로 구성되었던 위 프로세스는, t1,t2,t3중에서 exec*()를 먼저 호출한 1개의 프로세스로 변하면서, 기존에 존재했던, t0,t1,t2,t3는 없애버리고, (완전하게 클리어시키고), 하나의 프로세스로 변신하게 됩니다.
이를테면 ls라는 프로세스로 완벽하게 변하게 됩니다.(질문자의 사례) 이때, 나머지 쓰레드는 조용히~ 사라지겠지요.
이제 더이상 쓰레드는 없고, ls이므로, 이를 수행하고 종료합니다.

부가적으로, 질문자의 경우, t3가 운이 좋게도, 운영체제에 의해, 먼저, 스케쥴되어 ls가 나왔을 뿐, t1,t2,t3중 어느것이 먼저 실행될지는 며느리도 모른답니다. t1,t2,t3중 어느 것이 먼저 실행된다는 것은 예측할 수 없다는 얘기입니다.
----------
위 프로그램이 date, pwd, ls를 각각 전부 실행하고 종료하고자 한다면, exec*()전에 fork()한 후, fork()에 의해 생성된 프로세스, 즉, 자식 프로세스로 하여금 exec()를 실행하도록 바꾸면 되겠습니다.

많은 경우에, fork와 exec는 같이(pair로) 동작하게 되며, 심지어 fork_and_exec라는 검색어가 등장할 수 있을 정도인 것입니다.

------------------ P.S. --------------
지식은 오픈해서 검증받아야 산지식이된다고 동네 아저씨가 그러더라.

------------------ P.S. --------------
지식은 오픈해서 검증받아야 산지식이된다고 동네 아저씨가 그러더라.

댓글 달기

Filtered HTML

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

BBCode

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param>
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

Textile

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • You can use Textile markup to format text.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Markdown

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • Quick Tips:
    • Two or more spaces at a line's end = Line break
    • Double returns = Paragraph
    • *Single asterisks* or _single underscores_ = Emphasis
    • **Double** or __double__ = Strong
    • This is [a link](http://the.link.example.com "The optional title text")
    For complete details on the Markdown syntax, see the Markdown documentation and Markdown Extra documentation for tables, footnotes, and more.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Plain text

  • HTML 태그를 사용할 수 없습니다.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 줄과 단락은 자동으로 분리됩니다.
댓글 첨부 파일
이 댓글에 이미지나 파일을 업로드 합니다.
파일 크기는 8 MB보다 작아야 합니다.
허용할 파일 형식: txt pdf doc xls gif jpg jpeg mp3 png rar zip.
CAPTCHA
이것은 자동으로 스팸을 올리는 것을 막기 위해서 제공됩니다.