Business
Jobs
  • About Us
  • Solutions
    • Job Postings
      Post your job and receive qualified candidates in 48h.
    • Candidate Assessments
      500+ technical and psychological tests, plus anti-fraud.
    • Headhunting
      Tailor-made executive search from start to finish.
    • Payroll + EOR
      Payroll dispersal and EOR across 15+ LATAM countries.
  • Pricing
  • Jobs

0

271
Views
PostgreSQL se conecta de forma asíncrona con epoll_wait

Quiero trabajar con PostgreSQL (9.1) de forma asíncrona en mi proyecto de Linux. Para esto tengo que usar epoll_wait (debido a otras partes de la aplicación). El objetivo será finalmente usar epoll en modo activado por borde. Pero no puedo hacer que el proceso de conexión funcione, incluso en el modo sin activación por borde. Y no sé por qué. Sin embargo, cuando el nombre de usuario y la contraseña son correctos, funciona. Pero también tiene que funcionar cuando la contraseña es incorrecta. En ese caso, me sale un error que no entiendo. :-/ Aquí está el código que uso (la conexión ya está inicializada con un PQconnectStart() y una lista de parámetros que funciona bien con PQconnectdb()):

 void ConnectDB(PGconn * connection) { int pq_fd = PQsocket(connection); int epoll_fd = epoll_create1(0); struct epoll_event event; struct epoll_event *eventList = (epoll_event *)calloc(64, sizeof(epoll_event)); event.data.fd = pq_fd; event.events = EPOLLOUT | EPOLLERR; epoll_ctl(epoll_fd, EPOLL_CTL_ADD, pq_fd, &event); while (true) { PostgresPollingStatusType pt = PQconnectPoll(connection); switch (pt) { case PGRES_POLLING_OK: printf("*** connection established!\n"); return; case PGRES_POLLING_FAILED: printf("*** connection failed: %s\n", PQerrorMessage(connection)); return; case PGRES_POLLING_ACTIVE: printf(" --- poll result: PGRES_POLLING_ACTIVE\n"); break; case PGRES_POLLING_READING: printf(" --- poll result: PGRES_POLLING_READING - Modifiing epoll to EPOLLIN\n"); event.events = EPOLLIN | EPOLLERR; if (epoll_ctl(epoll_fd, EPOLL_CTL_MOD, PQsocket(connection), &event) == -1) { printf("epoll_ctl() error: %u: %s\n", errno, strerror(errno)); exit(1); } break; case PGRES_POLLING_WRITING: printf(" --- poll result: PGRES_POLLING_WRITING - Modifiing epoll to EPOLLOUT\n"); event.events = EPOLLOUT | EPOLLERR; if (epoll_ctl(epoll_fd, EPOLL_CTL_MOD, PQsocket(connection), &event) == -1) { printf("epoll_ctl() error: %u: %s\n", errno, strerror(errno)); exit(1); } break; } int n = epoll_wait(epoll_fd, eventList, 64, -1); if (n == -1) { printf("epoll_wait() error: %u: %s\n", errno, strerror(errno)); exit(1); } } }

Y aquí está la salida que obtengo:

 --- poll result: PGRES_POLLING_WRITING - Modifiing epoll to EPOLLOUT --- poll result: PGRES_POLLING_READING - Modifiing epoll to EPOLLIN --- poll result: PGRES_POLLING_READING - Modifiing epoll to EPOLLIN --- poll result: PGRES_POLLING_READING - Modifiing epoll to EPOLLIN --- poll result: PGRES_POLLING_WRITING - Modifiing epoll to EPOLLOUT --- poll result: PGRES_POLLING_READING - Modifiing epoll to EPOLLIN --- poll result: PGRES_POLLING_READING - Modifiing epoll to EPOLLIN --- poll result: PGRES_POLLING_WRITING - Modifiing epoll to EPOLLOUT epoll_ctl() error: 2: No such file or directory

¿Alguien tiene una idea?

over 4 years ago · Santiago Trujillo
1 answers
Answer question

0

La biblioteca cliente de postgresql primero intenta una conexión SSL y, si falla, vuelve a intentarlo sin SSL. Esto se hace independientemente de la razón por la que falló la conexión y lo hace sin notificar a la persona que llama en absoluto. Entonces, incluso si el error es una contraseña incorrecta , la biblioteca del cliente cerrará el descriptor de archivo y volverá a abrir la conexión del socket para el texto sin formato.

Si se cierra un descriptor de archivo, se elimina automáticamente del conjunto de encuestas electrónicas (lo que da como resultado el mensaje de error "No existe tal archivo o directorio"). Entonces tendrías que volver a agregarlo manualmente:

 if (epoll_ctl(epoll_fd, EPOLL_CTL_MOD, PQsocket(connection), &event) == -1) { if (errno == ENOENT) { epoll_ctl(epoll_fd, EPOLL_CTL_ADD, PQsocket(connection), &event); } else { printf("epoll_ctl() error: %u: %s\n", errno, strerror(errno)); exit(1); } }

Otra opción sería habilitar o deshabilitar ssl permanentemente, agregar sslmode=require o sslmode=disable a su cadena de conexión para esto. Pero si planea usar PGreset() (o encuentra cualquier otra situación en la que el socket se cierre y se vuelva a abrir de forma transparente para la persona que llama), entonces tendrá el mismo problema.

Es cierto que este comportamiento de postgresql-client-library no es muy amigable con epoll() . En los viejos tiempos, cuando se usaba select() o poll() , esto no era un problema, porque no había un estado en el núcleo como con epoll() ahora.

over 4 years ago · Santiago Trujillo Report
Answer question
Find remote jobs

Discover the new way to find a job!

Top jobs
Top job categories
Business
Post vacancy Pricing Sales
Legal
Terms and conditions Privacy policy
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Show me some job opportunities
There's an error!