【发布时间】:2019-07-31 03:31:26
【问题描述】:
我正在运行 epoll 来处理网络连接。我认为一切都运行良好。
现在我正在尝试从子进程连接到 Postgresql 数据库。我有 4 个子进程。
有时当我尝试连接到服务器时。它挂起。
有时我会收到此错误 fserver: tpp.c:84: __pthread_tpp_change_priority: 断言`new_prio
如果有人能够对我的代码提出建议,我们将不胜感激。谢谢
如果我删除 Postgresql 连接代码,问题就会消失。
/******CHILD PROCESS **************/
void childProcess()
{
const char conninfo[] = "postgresql://postgres@localhost?port=5432&dbname=ram&password=xxx";
PGconn *conn = PQconnectdb(conninfo);
const ConnStatusType connStatusType = PQstatus(conn);
if (connStatusType == CONNECTION_BAD) {
printf("pg connection not OK");
if (conn) {
PQfinish(conn);
}
exit(1);
} else {
printf("pg connection OK");
}
int efd = epoll_create1(0);
if(efd == -1)
{
perror("Epoll Creation Failed\n");
}
nonblocksocket(&p2c_var);
struct epoll_event event0;
event0.data.fd = p2c_var;
event0.events = EPOLLIN | EPOLLET;
if(epoll_ctl(efd,EPOLL_CTL_ADD,p2c_var,&event0) == -1)
{
perror("First Failed to add file descriptor to epoll watch list\n");
}
nonblocksocket(&c2p_var);
struct epoll_event event1;
event1.data.fd = c2p_var;
event1.events = EPOLLOUT | EPOLLET;
if(epoll_ctl(efd,EPOLL_CTL_ADD,c2p_var,&event1) == -1)
{
perror("Second Failed to add file descriptor to epoll watch list\n");
}
struct epoll_event *ttlevents;
ttlevents = calloc(MAXEVENTS, sizeof(event0));
int head = 0,tail = 0;
pthread_mutex_t buflock;
pthread_mutex_t fdlock;
int bufhead=0,buftail=0;
struct fifoarr *fifoptr = (struct fifoarr *) calloc(QSIZE,sizeof(struct fifoarr));
int co = 0;
char st[1050];
memset(st,0,sizeof(st));
st[0] = 1;
while(1)
{
int eventcount = epoll_wait(efd,ttlevents,MAXEVENTS,-1);
for(int i =0;i<eventcount;i++)
{
if ((ttlevents[i].events & EPOLLERR) || (ttlevents[i].events & EPOLLHUP))
{
/* An error has occured on this fd, or the socket is not ready for reading (why were we notified then?) */
fprintf (stderr, "epoll error\n");
close (ttlevents[i].data.fd);
continue;
}
if(ttlevents[i].events & EPOLLOUT)
{
if(ttlevents[i].data.fd == c2p_var)
{
pthread_mutex_lock(&buflock);
int bufval = popfd(&bufhead,&buftail);
if(bufval != -1)
{
write(c2p_var,fifoptr[bufval].buffer,sizeof(fifoptr[bufval].buffer));
}
pthread_mutex_unlock(&buflock);
}
}
if(ttlevents[i].events & EPOLLIN)
{
if(ttlevents[i].data.fd == p2c_var)
{
char buffer[1050];
while(1)
{
memset(buffer,0,sizeof(buffer));
int c = read(ttlevents[i].data.fd,buffer,sizeof(buffer));
if(c == -1)
{
if(errno == EAGAIN)
{
printf("Completed Reading From Parent Process\n");
break;
}
}
if(c == 0)
{
printf("Parent terminated Connection.\n");
break;
}
if(buffer[0] != 1)
{
pthread_mutex_lock(&buflock);
int bufval = pushfd(&bufhead);
if(bufval != -1)
{ memset(fifoptr[bufval].buffer,0,sizeof(fifoptr[bufval].buffer)); memcpy(fifoptr[bufval].buffer,buffer,sizeof(buffer));
// processRequest(fifoptr[bufval].buffer,conn);
write(c2p_var,&st,sizeof(st));
}
pthread_mutex_unlock(&buflock);
}//buffer[0]
}//While
}
}//if epollin
} //for
}//while(1)
PQfinish(conn);
}
程序往往会挂起。
【问题讨论】:
-
你检查过你没有用尽 PostgreSQL 上的
max_connections吗? -
我认为我还没有耗尽 max_connection,因为当我尝试 telnet 到服务器时也会出现问题。它有时也会发生在一个连接上。当我尝试 strace 时,我看到子进程正在等待 futex -> futex(0x7ffc0db430b0, FUTEX_WAIT, 2, NULL
-
这对我来说看起来太低级了。
标签: linux postgresql epoll