리눅스에서 돌아가는 thread서버가 SunOS에서 안되네요

bluesound의 이미지

간단한 http 서버를 만들고 있습니다.
(사실 학교 프로젝트네요, fork()대신 thread사용하기)
음...전 리눅스에서 잘 바꿔서 만들었구 잘되거든요?
근데 학교 서버에선 안되는군요
리눅스는 레드햇9 이구 학교는 SunOS 5.7 입니다.

안되는 부분은 클라이언트 접속시에 pthread_create()가 -1을 반환하면서
에러가 납니다. ..리눅스에선 되서 안심하구 냈는데...
소스 코드 동봉할테니 도움 부탁드립니다.

에러는 다음과 같습니다.
Thread creation failed: Error 0
제가 pthread_create가 0이 아닌 값을 반환할때 출력하는 메시지 입니다.

#include<unistd.h>
#include<stdlib.h>
#include<stdio.h>
#include<string.h>
#include<sys/types.h>
#include<sys/socket.h>
#include<netinet/in.h>
#include<sys/stat.h>
#include<fcntl.h>

#include<pthread.h> //thread를 사용하기위해 헤더파일 포함

#define LEN (1024*1024)

//void http_msg(int);
void *http_msg(void *);  // http_msg를 phtread_create에 알맞게 조정

int main(int argc, char *argv[])
{
  struct sockaddr_in server_addr, client_addr;
  //int server_fd, client_fd;
  int server_fd, *iptr;   //client_fd 를 thread함수에 넘겨주기위해 포인터로 선언
  int sin_size;
  char *http_message;

  int res;
  pthread_t a_thread;
  void *thread_result;

  /* arguments check */
  /* 실행명령어 오류시 에러메시지 출력 */
  /* 출력예 usage : 실행파일 포트번호 */
  if(argc!=2){
    printf("usage : %s port\n", argv[0]);
    return 1;
  }

  /* 소켓 생성 및 오류시 처리 */
  if((server_fd=socket(AF_INET, SOCK_STREAM, 0))<0){
    perror("socket");
    return -1;
  }

  /* struct sockaddr_in 구조체의 멤버들에 값 할당 */
  bzero((char *)&server_addr, sizeof(server_addr));  /*Same size as struct sockaddr*/
  server_addr.sin_family=AF_INET;  /*Address family,  AF_xxx*/
  server_addr.sin_addr.s_addr=htonl(INADDR_ANY);  /*Internet address*/
  server_addr.sin_port=htons(atoi(argv[1]));  /*Port number*/

  /* 소켓을 현재 시스템의 포트에 연결 및 오류시 처리 */
  if(bind(server_fd, (struct sockaddr *)&server_addr, sizeof(server_addr))<0){
    perror("bind");
    return -1;
  }

  /* 외부로부터의 접속 대기 및 오류시 처리*/
  if(listen(server_fd, 5)<0){
    perror("listen");
    return -1;
  }
  
  while(1){
    /* 연결 수락 및 오류시 처리*/
    sin_size=sizeof(struct sockaddr_in);
    //if((client_fd=accept(server_fd, (struct sockaddr *)&client_addr, &sin_size))<0){
	iptr = malloc(sizeof(int));
	if((*iptr=accept(server_fd, (struct sockaddr *)&client_addr, &sin_size))<0){
      perror("accept");
      continue;
    }
    printf("Server : got connection from %s\n", inet_ntoa(client_addr.sin_addr));

    /* 자식 프로세스를 생성하여 request 처리 - http_msg() 함수 호출*/
    //if(!fork()){
    //  http_msg(client_fd);
    //  close(client_fd);
    //}
	
	// thread 만들기, 클라이언트의 request가 들어오면 쓰레드 만들어 http_msg함수 호출
	res = pthread_create(&a_thread, NULL, &http_msg, iptr);
	if (res!=0){
		perror("Thread creation failed");
		exit(EXIT_FAILURE);
	}
	
  }
  close(server_fd);
}

/* http protocol에 따라 request 처리해주는 루틴 */
//void http_msg(int client_fd)
void *http_msg(void *arg)
{
  FILE *fp;
  char method[10], url[10], version[10];
  char buffer[LEN], filename[30];
  char *http_header="HTTP/1.1 200 OK\r\nServer : Hanyang Univ. ECE Web Server\r\nContent-type : text/html\r\n\r\n";
  
  int client_fd;
  client_fd = *((int *) arg);
  free(arg);
  pthread_detach(pthread_self());
	
  bzero(buffer, sizeof(buffer));
  bzero(method, sizeof(method));
  bzero(url, sizeof(url));
  bzero(version, sizeof(version));

  if((fp=fdopen(client_fd, "r+"))==NULL){
    perror("fdopen");
    //exit(-1);
    pthread_exit("fdopen"); // error 시에 thread만 닫음
  }

  fgets(buffer, sizeof(buffer), fp);
  sscanf(buffer, "%s %s %s\n", &method, &url, &version);
  printf("file stream = %s\n", buffer);
  printf("method : %s, url : %s, version : %s\n", method, url, version);

  if(strcmp(method, "GET")==0){
    if(strcmp(url, "/")==0)
      strcpy(filename, "index.html");
    else{
      *filename='.';
      sprintf(filename+1, url);
    }
    printf("filename=%s\n", filename);

    bzero(buffer, sizeof(buffer));
    if((fp=fopen(filename, "r"))==NULL){
      perror("fopen");
      //exit(-1);
      pthread_exit("fopen");	// error 시에 thread만 닫음
    }
    if(fread(buffer, 1, sizeof(buffer), fp)==0){
      perror("fread");
      //exit(-1);
      pthread_exit("fread");	// error 시에 thread만 닫음
    }


    /* http 헤더와 http 메시지 전송 및 오류시 처리 */
    printf("header = \n%s\n", http_header);
    if(send(client_fd, http_header, sizeof(http_header), 0)<0){
      perror("send-header");
      //exit(-1);
      pthread_exit("send-header");	// error 시에 thread만 닫음
    }
    if(send(client_fd, buffer, sizeof(buffer), 0)<0){
      perror("send-body");
      //exit(-1);
      pthread_exit("send-body");	// error 시에 thread만 닫음
    }
  }
  fclose(fp);
  close(client_fd);	
  pthread_exit("thread has been closed correctly");
}
bluesound의 이미지

pthread_create()가 에러는 안나는군요
근데 제가 올린 소스에서
#define LEN (1024*1024) 부분때문에
Segmentation Fault (core dumped) 라면서 죽네요 (클라이언트 접속시)
100*1024 정도로 줄여주면 제대로 작동을 합니다.

왜 그런가요?

alsong의 이미지

아마도 디폴트 스택량이 부족해서 발생했을 가능성이 많습니다.
스레드의 스택사이즈를 조정해 보시기 바랍니다.

그나저나 백수 언제 탈출하냐... ㅡㅡ; 배고파라.

menupan의 이미지

확실하지는 않습니다만...
pthread_create 하고 나서 usleep(100)정도 줘 보십시오...
솔라리스에서는 쓰레드 생성후에 바로 실행되는게 아니라
호출한 메인 쓰레드가 종료후에 멀티쓰레드가 도는 걸로 알고 있어서
sleep으로 넘겨주지 않으면 바로 시작되지 않는 걸로 알고 있는데..
가물가물.. ^^;
수고하세요...

myroot의 이미지

menupan wrote:
확실하지는 않습니다만...
pthread_create 하고 나서 usleep(100)정도 줘 보십시오...
솔라리스에서는 쓰레드 생성후에 바로 실행되는게 아니라
호출한 메인 쓰레드가 종료후에 멀티쓰레드가 도는 걸로 알고 있어서
sleep으로 넘겨주지 않으면 바로 시작되지 않는 걸로 알고 있는데..
가물가물.. ^^;
수고하세요...

요즘 posix 쓰레드프로그래밍 책을 보고 있는데 거기에 나와있더군요...

솔라리스 2.5에서는 쓰레드가 시분할되지 않아서 두개 쓰래드를 병렬로 동작하도록 보장하려면 병행 레벨을 2로 높여줘야 한다고....

#ifdef sun
    thr_setconcurrency(2);
#endif
choissi의 이미지

쓰레드 스택이 오버 플로어 난거 같네요.

쓰레드내에.. 있는 buffer를 스택에 두지 말고
malloc으로 바꿔서 작업해보세요.

울랄라~ 호기심 천국~!!
http://www.ezdoum.com

댓글 달기

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
이것은 자동으로 스팸을 올리는 것을 막기 위해서 제공됩니다.