이 게시물에서 는 모듈이 부족하거나 적어도 TCP 소켓을 만드는 데 사용할 수 있는 stcp 장치 클론수를 심각하게 고갈시킬 수 있는 일반적인 코딩 오류에 대해 논의하고자 합니다.
소켓 함수에 대한 모든 호출로 인해 STCP는 stcp 장치의 새 복제본을 생성합니다. 생성할 수 있는 최대 클론 수는 device.tin 항목의 clone_limit 필드에 의해 제어됩니다.
/ =이름 stcp.m17
=module_name m17
=device_type 스트림
=access_list_name stcp_access
=streams_driver stcp
=clone_limit 5120
=주석은 TCP API를 제공합니다.
|
analyze_system 장치 구조를 덤프하고 clone_count 값을 보고 현재 사용 중인 클론 수를 확인할 수 있습니다. clone_count clone_limit 같으면 소켓 함수로 호출하면 "장치의 복제 한도를 초과했습니다"라는 오류가 e$clone_limit_exceeded 반환됩니다.
as: 일치 복제본; dump_dvt -name stcp.m17
clone_limit: 5120
clone_count: 42
cloned_from: -27271
remote_clone_limit: 0
|
일반적으로 클론 장치를 만드는 소켓 호출 다음에 연결 호출 또는 바인딩 및 수신 대기 호출이 뒤따릅니다. 이 시점에서 "netstat 명령"을 실행할 때 해당 항목을 볼 수 있습니다.
넷스타트-숫자 -all_sockets 활성 연결(서버 포함) 프로토 Recv-Q Send-Q 현지 주소 외국 주소(주) tcp 0 172.16.124.217:23 192.168.109.22:50038 설립 tcp 0 172.16.124.217:22 172.16.124.24:54987 설립 tcp 0 10.20.1.1:37 10.20.1.26:1528 TIME_WAIT tcp 0 10.20.1.1:37 10.20.1.27:1579 TIME_WAIT tcp 0 172.16.124.217:61780 192.168.109.22:23 설립 tcp 0 172.16.124.217:22 172.16.124.50:17421 설립 tcp 0 172.16.124.217:22 172.16.124.50:17658 설립 tcp 0 *:23 *:* 듣기 tcp 0 *:6666 *:* 듣기 tcp 0 *:21 *:* 듣기 tcp 0 *:3000 *:* 듣기 tcp 0 *:7 *:* 듣기 tcp 0 *:9 *:* 듣기 tcp 0 *:13 *:* 듣기 tcp 0 *:19 *:* 듣기 tcp 0 *:37 *:* 듣기 tcp 0 *:901 *:* 듣기 tcp 0 *:1414 *:* 듣기 tcp 0 *:81 *:* 듣기 tcp 0 10.20.1.1:37 10.20.1.9:3633 TIME_WAIT tcp 0 50 10.10.10.1.1:52653 10.10.1.200:3001 설립 tcp 0 10.10.10.1.1:52624 10.10.1.200:3001 FIN_WAIT_1 tcp 0 10.20.1.1:61704 10.20.1.3:48879 설립 tcp 0 *:3001 *:* 듣기 tcp 0 *:3002 *:* 듣기 tcp 0 *:3003 *:* 듣기 tcp 0 *:4000 *:* 듣기 tcp 0 172.16.124.217:4000 172.16.124.78:1024 설립 tcp 0 172.16.124.217:4000 172.16.124.227:1025 설립 tcp 0 *:4001 *:* 듣기 tcp 0 *:4002 *:* 듣기 tcp 0 *:4003 *:* 듣기 tcp 0 *:4004 *:* 듣기 tcp 0 *:22 *:* 듣기 tcp 0 *:4005 *:* 듣기 tcp 0 *:4006 *:* 듣기 tcp 0 172.16.124.217:4006 172.16.124.203:49231 설립 tcp 0 *:4007 *:* 듣기 tcp 0 *:4008 *:* 듣기 tcp 0 *:4009 *:* 듣기 tcp 0 172.16.124.217:4008 172.16.124.203:49262 설립 tcp 0 *:4010 *:* 듣기 tcp 0 *:4011 *:* 듣기 tcp 0 *:4012 *:* 듣기 tcp 0 *:4013 *:* 듣기 tcp 0 *:4014 *:* 듣기 tcp 0 *:4015 *:* 듣기 tcp 0 *:80 *:* 듣기 tcp 0 *:9182 *:* 듣기 tcp 0 *:445 *:* 듣기 tcp 0 *:139 *:* 듣기 tcp 0 10.20.1.1:53495 10.20.1.9:48879 설립 tcp 0 10.20.1.1:61703 10.20.1.3:48879 설립 tcp 0 10.20.1.1:61707 10.20.1.3:48879 설립 tcp 0 10.20.1.1:61705 10.20.1.9:48879 설립 tcp 0 10.20.1.1:61709 10.20.1.9:48879 설립 tcp 0 10.20.1.1:61710 10.20.1.9:48879 설립 tcp 0 172.16.124.217:61789 172.16.124.203:4000 설립 tcp 0 400 172.16.124.217:22 172.16.124.50:17674 설립 |
42개 이상의 줄수를 계산하는 경우 netstat에서 표시된 모든 항목이 stcp 장치 복제본을 사용하는 것은 아니기 때문입니다. 예를 들어 OSL 연결 및 NIO와 함께 사용되는 X25_cpc 연결입니다. 자세한 내용은 socket_count.cm를 살펴보십시오.
연결이나 바인딩 없이 소켓 호출이 이루어지거나 바인딩이 실패하면 반대 문제를 만들 수 있으며 clone_count 값은 netstat에서 표시된 항목 수보다 큽습니다.
as: 일치 복제본; dump_dvt -name stcp.m17
clone_limit: 5120
clone_count: 4131
cloned_from: -23179
remote_clone_limit: 0
로:
|
넷스타트 출력을 다시 포함하지는 않지만 이전 예제에서 변경되지 않은 것을 믿습니다.
이 상황, 추가 (4131 – 42) 그리고 분명히 회계되지 않은 STCP 장치 클론은 다음 코드 조각에 의해 만들어졌습니다. 코드는 소켓 함수를 호출한 다음 바인드 함수를 호출합니다. 바인딩이 실패하면 루프가 반복됩니다. 많은 응용 프로그램은 타이머를 추가하여 1, 60 초 또는 300 초를 기다려야하고 오류를 일으키는 조건이 사라지지 않는다는 가정하에 피할 수없는 지연을 다시 시도합니다.
tryAgain = 1; while (tryAgain) { if ((socks0 = socket (AF_INET, SOCK_STREAM, 0)) < 0) { if (debugFlag) perror ("badService: can't create listening socket"); } else { /* build a sockaddr structure holding the address we will bind to. The IP address is INADDR_ANY meaning we will listen on all active IP addresses */ bzero ( (char *) &serv_addr, sizeof (serv_addr)); serv_addr.sin_family = AF_INET; serv_addr.sin_addr.s_addr = htonl (INADDR_ANY); serv_addr.sin_port = htons (portNumber); /* now bind to the address and port */ if (bind (socks0, (struct sockaddr *) &serv_addr, sizeof (serv_addr)) < 0) { if (debugFlag) perror ("badService: can't bind address, trying again"); } else tryAgain = 0; } } |
가장 일반적인 오류는 다른 프로세스가 이미 요청된 포트에 바인딩되어 있다는 것입니다. 오류 의 이유에 관계없이 솔루션은 바인드 오류를 보고한 후 소켓을 닫는 것입니다.
tryAgain = 1;
while (tryAgain)
{
if ((socks0 = socket (AF_INET, SOCK_STREAM, 0)) < 0)
{
if (debugFlag)
perror ("goodService: can't create listening socket");
}
else {
/* build a sockaddr structure holding the address we will bind to.
The IP address is INADDR_ANY meaning we will listen on all active
IP addresses */
bzero ( (char *) &serv_addr, sizeof (serv_addr));
serv_addr.sin_family = AF_INET;
serv_addr.sin_addr.s_addr = htonl (INADDR_ANY);
serv_addr.sin_port = htons (portNumber);
/* now bind to the address and port */
if (bind (socks0, (struct sockaddr *) &serv_addr,
sizeof (serv_addr)) < 0)
{
if (debugFlag)
perror ("goodService: can't bind address, trying again");
if (close (socks0) < 0)
if (debugFlag)
perror ("goodService: can't close old socket");
}
else
tryAgain = 0;
}
}
|
이 게시물은 코딩 오류로 인해 clone_limit 도달하는 것에 관한 것이지만 오류가 없는 경우 응용 프로그램 환경이 실제로 모든 복제 장치를 사용하는 경우 어떻게해야 합니까? 그럼, 당신이 16,000의 시스템 한계에 도달하지 않은 가정당신은 한계를 올릴 수 있습니다. device.tin 파일에서 stcp 장치의 clone_limit 필드를 업데이트하고 device.table을 다시 만들어야 합니다. 17.1 또는 이후 릴리스에 있는 경우 update_device_info 명령을 사용하여 현재 부팅에 대한 제한을 높이고 업데이트된 device.table에 의존하여 다음 부팅을 처리합니다. 17.1 전에 릴리스에서 유일한 진짜 옵션은 재부팅하는 것입니다. 현재 요구 사항에 해당하는 값과 예상 된 성장에 대한 제한을 설정해야합니다. 한도를 16,000으로 인상해서는 안 됩니다. 복제 장치를 소비하는 응용 프로그램 버그가 없더라도 나중에 는 필요하지 않습니다. 사용 가능한 모든 클론 장치를 소비하는 응용 프로그램은 많은 스트림 메모리를 소비하고 스트림 메모리가 소진되면 기존 TCP 연결에 부정적인 영향을 미칩니다.