소켓이 안끊깁니다.
글쓴이: 하하 / 작성시간: 화, 2005/05/31 - 9:47오전
소켓이 안끊깁니다.
서버이구요.
accept 로 반환된 즉 클라이언트와 통신 소켓을
바로 close(sockfd) 하면 바로 끊겨서 클라이언트가 감지를 합니다
헌데 한 5초정도 지난후에 close(sockfd)를 하면 close return
값은 바로 끊을때와 같이 0 (정상) 으로 끊기지만
클라이언트는 전혀 감지를 못합니다.
정말 이상합니다.... ㅜㅡ
tcpdump , netstat 하면 FIN을 보내지 않아 아직도 establish
상태입니다. 왜.. close 정상 인데 실제 소켓이 끊기지 않죠?
당연히 fin을 안보내기 때문에 클라이언트는 자기가 끊겼는지 절대
알지를 못합니다...
Forums:
정말 왜.. 서버가 소켓을 닫았는데클라이언트는 모를까요??
정말 왜.. 서버가 소켓을 닫았는데
클라이언트는 모를까요??
특이한건 thread로 분기된 넘이 main thread에서 accept
특이한건 thread로 분기된 넘이 main thread에서 accept한
소켓을 닫는거 정도입니다.
당연 accept된 소켓은 전역 변수에 들어가 있어 thread간 공유가
가능하구요...
또...
accept 하자 마자 끊으면.. 클라이언트가 압니다. read = 0 이라고
이젠 끊으라고..
근데 분기된 thread에서 close하면 클라이언트가 알수가 없습니다.
데이터가 전혀 안들어옵니다. ㅡㅜ
클라이언트가 무슨 데이터를 썼을때.. 서버는 이미 끊은 소켓이니깐..
그때야.. FIN 이던 RESET이던 보내 클라이언트가 비로소 자기가 끊겼
다는걸 압니다.
이게 정상일까요??
쩝.. 그럼 서버에서 처음에 소켓을 끊으면 클라이언트에 접속 종료 이
쩝.. 그럼 서버에서 처음에 소켓을 끊으면 클라이언트에 접속 종료
이벤트를 받은 후에 클라이언트에서 같이 끊어주나요?
그냥 이벤트만 받고 안끊어주는건 아닌가요?
[quote]... 클라이언트에 접속 종료 이벤트를 받은 후에 ...
아뇨 서버가 active close를 하면 클라이언트는 아무것도 못받습니다.
그래서 자기가 끊겼다는것도 모릅니다.
서버가 close할때 tcpdump를 떠봤더니 fin 도 안나가더군요..
클라이언트는.. select를 또는 poll 을 통해 이벤트를 기다리지만 정말로
아무것도 못봤씁니다.
일예로..
telnet xx.xx.xx.xx port (서버데몬) 에 연결하면.. 마찬가지고 서버가
소켓을 끊어도 끊는걸 감지못하는것같더군요.
사용하시는 플랫폼이?그리고 혹시 fork 한 후 close 하시는
사용하시는 플랫폼이?
그리고 혹시 fork 한 후 close 하시는건 아닌가요?
shutdown 함수로 한번 닫아 보세요.
[quote="ssehoony"]사용하시는 플랫폼이?그리고 혹시
저도 요 녀석이 의심이 되었는데, 스레드를 쓴다니 fork를 안 쓰실 수도 있다는 생각과,
클라이언트에서 해당 소켓에 write를 하면 그때가서 끊긴 것을 안다는 것이 무언가 좀 안 맞는다는 생각이 들고,
소켓 디스크립터를 전역으로 두어서 각 스레드들이 공유한다는 것이 좀 찜찜하다는 생각이 드는데요..
이 정도면, shutdown으로 닫아보시고 그래도 안되면 코드로 얘기하는 것이 빠를 듯 합니다.
일단 fork는 전혀 사용을 안하구요.typedef struct
일단 fork는 전혀 사용을 안하구요.
typedef struct
{
int sock;
} t_user[100];
t_user User;
--------- 여기 까지가 전역 변수 이구요 ------------
main()
{
transaction_thread();
poll()
User[i].sock = accept();
}
transaction_thread()
{
pthread_create(Process(본쓰레드함수));
}
void * Process(void * arg)
{
send(User[i].sock, buf, bufsize);
close(User[i].sock);
}
대강 이런 구조입니다. 참고로 서버입니다.
이렇게 close를 하면.. 클라이언트가 이벤트를 전혀 받지를 못합니다.
도움되는 답글도 안 올리면서 이런 말씀드리기 상당히 죄송하지만,올리신
도움되는 답글도 안 올리면서 이런 말씀드리기 상당히 죄송하지만,
올리신 코드만으론 어떤 얘기를 하기가 힘들 듯 싶습니다.
전역변수 변경이나 소켓관련 호출의 리턴값에 주의하시면서,
디버거, 디버깅 메시지, 시스템 트레이스나 라이브러리 트레이스 툴, lsof, 스니퍼 등으로
다시 한번 꼼꼼히 확인해 보시라는 일반적인 말씀밖에 못 드릴 듯 합니다.
:(
똑같은 서버 소스를 solaris에서 돌려봤더니 서버가 소켓을 끊
똑같은 서버 소스를 solaris에서 돌려봤더니
서버가 소켓을 끊을때 바로 클라이언트가 감지합니다.. ㅡㅡ
리눅스에선 안되던것이.. 으..
댓글 달기