- 論壇徽章:
- 0
|
本帖最后由 weifeng270 于 2012-05-15 16:59 編輯
linux 多線程溢出問(wèn)題
附件是
valgrind --leak-check=full -v --show-reachable=yes --log-file=/opt/oracle/new/DeviceServer/log/DeviceRegistServer.log ./DeviceRegistServer
的日志
現(xiàn)象是隔一段時(shí)間。內(nèi)存就漲132K
int main(int argc, char* argv[])
{
if(argc < 3)
{
printf("Usage: DeviceRegistServer -p Port(Default port 40005)\n");
printf(" eg: DeviceRegistServer -p 30000\n");
}
int port = 50005; //服務(wù)器監(jiān)聽(tīng)端口號(hào)
int arginc = 1; //指針?biāo)饕?br />
if(argc >= 3)
{
if(argv[arginc][0]=='-' && (argv[arginc][1]=='p'))
{
++arginc;
port = atoi(argv[arginc++]);
}
}
// 創(chuàng)建一個(gè)Server socket
int sock = socket(AF_INET, SOCK_STREAM, 0);
if(sock == SOCKET_ERROR)
{
printf("create sock error.%s \n",strerror(errno));
return 1;
}
sockaddr_in my_addr;
my_addr.sin_family = AF_INET;
my_addr.sin_port = htons((u_short)port);
my_addr.sin_addr.s_addr = INADDR_ANY;
if (bind(sock, (struct sockaddr *)&my_addr, sizeof(struct sockaddr)) == SOCKET_ERROR)
{
printf("bind sock error\n");
return 1;
}
if (listen(sock, BACKLOG_SIZE) == SOCKET_ERROR)
{
printf("listen sock error\n");
return 1;
}
sockaddr_in their_addr;
int sin_size = 0;
sin_size = sizeof(struct sockaddr_in);
// 等待客戶端連接
int loopcount=1;
//while(loopcount<10000)
while(TRUE)
{
loopcount++;
printf("loopcount==%d\n",loopcount);
#if defined(WIN32)
int newsock = accept(sock, (struct sockaddr *)&their_addr,&sin_size);
HANDLE handle = CreateThread(NULL, 0, LPTHREAD_START_ROUTINE(AnswerClientThread), (LPVOID)newsock, 0, NULL);
CloseHandle(handle);
#elif defined(__linux__)
int newsock = accept(sock, (struct sockaddr *)&their_addr,(socklen_t*)&sin_size);
pthread_t ntid;
//void* ntidstatus;
int err;
if((err = pthread_create(&ntid, NULL, AnswerClientThread, (void*)newsock)) != 0)
{
printf("AnswerClientThread線程創(chuàng)建失敗!\n");
}
else
{
printf("AnswerClientThread線程被創(chuàng)建\n");
}
if(ntid !=0)
{
pthread_join(ntid,NULL);
printf("AnswerClientThread線程已經(jīng)結(jié)束\n");
}
else
{
printf("AnswerClientThread線程未結(jié)束\n");
}
pthread_detach(ntid);
#endif
}
OCI_Cleanup();
return 0;
}
調(diào)用的函數(shù)如下
void* AnswerClientThread(void* pParam)
{
int psock = *(int*)&pParam;
int nrecvlen = 0;
char* recvbuf = new char[6400];
char* recvbufpt = recvbuf;
//printf("****** sum= %d ,%d******* \n",dw_k_run,dw_x_run);
while(TRUE)
{
recvbuf = recvbufpt;
memset(recvbuf, 0, 6400);
nrecvlen = ::recv(psock, recvbuf, 6400, 0);
if(nrecvlen == SOCKET_ERROR || nrecvlen > 6400)
{
delete [] recvbuf;
ReleasePortInManage(psock);
close(psock);
return ((void*)1);
}
int ncmd = UNKNOWN_CMD;
bool bcmd = false;
int ndatalen = 0;
while(bcmd = get_cmd(recvbuf, nrecvlen, ncmd, ndatalen))
{
printf("ncmd==%d\n",ncmd);
switch(ncmd)
{
case REGIST_CMD: // 注冊(cè)命令
{
RegistDevInfo(recvbuf, nrecvlen, psock);
break;
}
case KEEPALIVE_CMD: // 心跳命令
{
KeepAlive(recvbuf, nrecvlen, psock);
break;
}
case XML_CMD: // xml
{
xml_deco(recvbuf, nrecvlen, psock);
break;
}
default: // 未知命令
{
break;
}
}
if(ncmd == REGIST_CMD || ncmd == KEEPALIVE_CMD || ncmd==XML_CMD) // 和設(shè)備的心跳維持短連接
goto end;
nrecvlen = nrecvlen-ndatalen+2;
recvbuf = recvbuf+ndatalen-2;
}
//usleep(10);
}
end:
{
// 除非客戶端告知要關(guān)閉鏈接,否則服務(wù)器是不會(huì)主動(dòng)關(guān)閉鏈接的
delete [] recvbufpt;
ReleasePortInManage(psock);
close(psock);
pthread_exit(NULL);
}
return ((void*)0); |
|