socket() 함수가 일정 시간이 지나면 fd를 못 가져 옵니다 ;

fenign의 이미지

SUN 운영체제 & 유닉스 환경에서 C로 프로그래밍을 하고 있습니다.

소스는 다음과 같습니다.

void*   createThread ()
{
        struct  timeval                 timeval;
        struct  sockaddr_in             serveraddr;
        char                            czFuncName[256] = "createThread";
        char                            czTmpBuf[256];
 
        memset(&serveraddr, 0, sizeof(serveraddr));
 
        serveraddr.sin_family                           = AF_INET;
        serveraddr.sin_addr.s_addr                      = inet_addr(IP);
        serveraddr.sin_port                             = htons(Port);
        while(1)
        {
                if(Connect == DISCONNECT )
                {
                     if( (fd= socket(AF_INET, SOCK_STREAM, 0)) < 0 )
                     {
                             Log("socket() Error FD : %d, Errno : %d", fd, errno);
                             sleep(1);
                             continue;
                     }
                     if( connect(listenfd1,(struct sockaddr *)&serveraddr, sizeof(serveraddr)) == -1 )
                     {
                            sleep(5);
                            close(fd);
                            continue;
                     }
                        else
                        {
                                     ....
                                     연결 후 처리..
                        }

===================================================================
위 소스는 상위 Thread가 위의 쓰레드를 실행시키고
생성된 위의 Thread는 while(1)을 돌면서 서버와 연결되어 있지 않는 상태면
socket() 로 fd를 가져오고 이를 바탕으로 접속을 시도 하는 소스입니다.
연결 되지 않은 경우에는 5초 간격으로 계속 반복 하는 것이구요...

정상적인 연결은 문제가 되지 않습니다.
즉, 서버가 정상적으로 listen하고 있고 위의 Client가 접속하면 문제없이 해결되는데
테스트를 해볼 요량으로 서버의 Process를 죽이고 Client, 즉 위의 Thread를 실행시켜 보았습니다.

그런데.... 처음에는 5초 간격으로 계속 Try를 하는데...
어느정도 시간이 지나면
socket() Error FD : -1, Errno : 35
와 같은 에러가 뜹니다.
위에서 socket() 함수에서 fd를 못 가져올 때 발생하는 Log 이구요..
fd가 없으니까 connect를 실행하지 못 하고 ... 계속 fd를 못 가져온다는 Log만 남기네요..

Errno 35는 ENOMSG 인데....
이건 메시지의 내용이 없거나 할 때 발생하는것 아닌가요?
위와 같은 상황에 위와 같은 Error가 발생한다면
어떤 문제일까요?

------ 수정 이후 ---------
답변 감사드립니다 ^^
말씀 해주신대로 erron.h 헤더 파일은 포함되어 있구요...
그에 따른 errno 가 35번으로 찍힙니다...

그리고 connect가 정상적으로 이루어지지 않을경우 해당 fd를 close()하구요...
저도 일정 시간 지난후에 fd를 못 가져오는 것으로 봐서
할당 수치가 넘어간것 같은데...

close()를 해 주어도 위와 같은 상황이 발생하니 난감할 따름입니다...ㅠ.ㅠ

fenign의 이미지

아래 부분이 왜 안 보이죠? ;;

IsExist의 이미지

code 태그로 싸주세요.
---------
간디가 말한 우리를 파괴시키는 7가지 요소

첫째, 노동 없는 부(富)/둘째, 양심 없는 쾌락
셋째, 인격 없는 지! 식/넷째, 윤리 없는 비지니스

이익추구를 위해서라면..

다섯째, 인성(人性)없는 과학
여섯째, 희생 없는 종교/일곱째, 신념 없는 정치

---------
간디가 말한 우리를 파괴시키는 7가지 요소

첫째, 노동 없는 부(富)/둘째, 양심 없는 쾌락
셋째, 인격 없는 지! 식/넷째, 윤리 없는 비지니스

이익추구를 위해서라면..

다섯째, 인성(人性)없는 과학
여섯째, 희생 없는 종교/일곱째, 신념 없는 정치

IsExist의 이미지

정확한것은 errno.h 헤더를 포함시키고 errno 값을 확인해 보시기 바랍니다.
.
.
.

#include <errno.h> /* errno */
#include <string.h> /* strerror() */
...
if (-1 == (fd = socket( ... ))) 
{
    printf ("socket error!.(errno=%d,%s)\n", errno, strerrror(errno));
    ...
}

---------
간디가 말한 우리를 파괴시키는 7가지 요소

첫째, 노동 없는 부(富)/둘째, 양심 없는 쾌락
셋째, 인격 없는 지! 식/넷째, 윤리 없는 비지니스

이익추구를 위해서라면..

다섯째, 인성(人性)없는 과학
여섯째, 희생 없는 종교/일곱째, 신념 없는 정치

---------
간디가 말한 우리를 파괴시키는 7가지 요소

첫째, 노동 없는 부(富)/둘째, 양심 없는 쾌락
셋째, 인격 없는 지! 식/넷째, 윤리 없는 비지니스

이익추구를 위해서라면..

다섯째, 인성(人性)없는 과학
여섯째, 희생 없는 종교/일곱째, 신념 없는 정치

park7275의 이미지

while 과 open(socket)

왠지 fd를 다 쓴듯하네요..

ulimit -a로 확인해보세요..

[KILL] 죽을각오로.........

[KILL] 죽을각오로.........

ljs0766의 이미지

제가 봤을땐 할당 가능한 fd를 모두 할당한듯 한데요?

일정 시간이 지난후 fd를 받아오지 못한다면요.

우선 errno.h를 include하고 errno를 얻어서 어떤 오류인지 파악을 해보시고요

perror()함수를 이용하셔서 파악하셔도 되고요.

아마 제 생각엔 할당 가능한 모든 file descriptor를 할당한 상태로 해제는 안하고

다시 할당 받으려고 해서 문제가 생기는 듯 한데요..

그리고 무한루프내에 socket을 생성하는 부분이 보이는데 저렇게 한 이유가 따로 있나요?

fenign의 이미지

서버와 연결이 끊어지거나, 서버의 프로세스가 재구동 된다면
클라이언트에서 무한으로 접속을 시도하려고 while 내에 socket 함수를 넣었답니다.^^;

ljs0766의 이미지

좀 무겁게 동작할듯 한데..

코딩 안한지 오래되서 기억이 가물가물하긴 한데

socket();
 
while(1) {
   if( Connect == DISCONNECT ) {
      connect();
   }
}

위 코드처럼 해줘도 되지 않나요?

IsExist의 이미지

socket으로 생성한 fd를 왜 connect 에서 사용하지 않는거죠? connect 함수에서 사용한 listenfd1 은 어디서 나온건가요?
---------
간디가 말한 우리를 파괴시키는 7가지 요소

첫째, 노동 없는 부(富)/둘째, 양심 없는 쾌락
셋째, 인격 없는 지! 식/넷째, 윤리 없는 비지니스

이익추구를 위해서라면..

다섯째, 인성(人性)없는 과학
여섯째, 희생 없는 종교/일곱째, 신념 없는 정치

---------
간디가 말한 우리를 파괴시키는 7가지 요소

첫째, 노동 없는 부(富)/둘째, 양심 없는 쾌락
셋째, 인격 없는 지! 식/넷째, 윤리 없는 비지니스

이익추구를 위해서라면..

다섯째, 인성(人性)없는 과학
여섯째, 희생 없는 종교/일곱째, 신념 없는 정치

fenign의 이미지

괜히 변수 이름이나 쓸데없는 로그가 길면 보기 귀찮으실까바
임의로 바꾸다가 미처 거기까지 바꾸진 못했네요....;;
죄송합니다..
socket()에서 할당받은 fd와 connect()에서 사용하는 fd가 같습니다.
제가 listenfd를 fd로 보기 쉽게 바꾸다가... 실수로 못 바꿨습니다...
오해를 불러일으켜 죄송합니다 ㅠㅠ.

coremaker의 이미지

Connect 변수의 초기화 값과 Setting 이 되는 경우를 알아야할 것 같고..
Socket FD의 close가 언제 일어나는지도 알아야할 것같습니다..

'IsExit' 님이 말씀하신 것처럼..
listenfd1은 어디서 나타난 녀석인지도 밝혀야할 것 같고..

Socket이 실제 몇 개나 열렸는지도.. 확인해 보세요..
Process당 Open 할 수 있는 File 갯수는 한계가 있습니다.. (수정이 가능하긴 합니다만..)

Socket의 사용 갯수와 (다른 파일을 열지 않았다는 전제에서..)
ulimit 을 통해 open파일 제한 갯수를 대조해 보세요..
저 코드 자체에서 뭔가 분석하기엔 제가 내공이 매우 달리네요..

fenign의 이미지

감사합니다~!!!

여러님들의 충고에 따라 이러케도 해보고 저러케도 해보다가..
혹시 이 문제일까 해서 했던 것이 맞아 떨어지네요..

원인인 즉슨...
socket()에서 실패할 경우 fd를 close()해주지 않아서 문제가 발생한 것 같습니다.

제 딴에는 socket()에서 fd를 얻어온 후 connect()할 때 실패하면
이를 close()해주는것만으로 되리라 생각했는데...
socket()에서 실패한 경우 close()를 해주지 않아 문제가 발생한 것 같습니다.
자세한 내부적인 상황은 모르겠지만...
문제없이 돌아간다는데 안심을 하고 있습니다 ^^;

조언 감사드립니다!!!!

IsExist의 이미지

socket()에서 실패할 경우 -1을 리턴 할테고 그걸 close(-1) 하는건 의미가 없어요.
---------
간디가 말한 우리를 파괴시키는 7가지 요소

첫째, 노동 없는 부(富)/둘째, 양심 없는 쾌락
셋째, 인격 없는 지! 식/넷째, 윤리 없는 비지니스

이익추구를 위해서라면..

다섯째, 인성(人性)없는 과학
여섯째, 희생 없는 종교/일곱째, 신념 없는 정치

---------
간디가 말한 우리를 파괴시키는 7가지 요소

첫째, 노동 없는 부(富)/둘째, 양심 없는 쾌락
셋째, 인격 없는 지! 식/넷째, 윤리 없는 비지니스

이익추구를 위해서라면..

다섯째, 인성(人性)없는 과학
여섯째, 희생 없는 종교/일곱째, 신념 없는 정치

fenign의 이미지

제가 위에 잘못 쓴건지....제대로 쓴건지 모르겠습니다만...

socket()에서 실패할 경우가 잘 없고
connecte()에서 실패하여 close()를 해주고 다시 while문을 도는데 (서버를 죽여놓으니 당연한 문제....)
이상하게 일정 시간이 지나면 socket()에서 -1을 리턴하는 경우가 발생하더라구요...
그래서 혹시나 해서 socket()에서도 close를 해 줬더니
위의 문제가 발생하지 않더라구요...

저도 이유를 모르겠어요..ㅠ.ㅠ

익명사용자의 이미지

disconnect 될 당시에 close 해주셨나요?

그리고 close 반환값도 체크해두세요, close 도

항상 성공하는게 아니라서...

사랑천사의 이미지

정상적인 경우에 close가 되어 주기 때문에 문제가 없는게 아닐까 싶습니다. socket에서 -1을 리턴 하는 경우는 close가 동작을 안 하겠죠.. 대신 socket에서 정상적인 FD 번호를 돌려 주고 connect에서 오류가 발생 하는 경우가 연속 발생 하는 거라면 socket해 준 다음에 close가 수행 되는 것도 의미가 있겠죠... 근대 socket한 다음에 바로 close가 되면 당연히 소켓이 죽어 버릴 태니 뭐 이런건 알아서 적당히 넣으셨겠죠...
----
Lee Yeosong(이여송 사도요한)
E-Mail: yeosong@gmail.com
MSN: ysnglee2000@hotmail.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
이것은 자동으로 스팸을 올리는 것을 막기 위해서 제공됩니다.