提交 bbebcb12 编写于 作者: M Marc G. Fournier

Fixes:

Async notifies received while a backend is in the middle of a begin/end
transaction block are lost by libpq when the final end command is issued.

The bug is in the routine PQexec of libpq. The routine throws away any
message from the backend when a message of type 'C' is received. This
type of message is sent when the result of a portal query command with
no tuples is returned. Unfortunately this is the case of the end command.
As all async notification are sent only when the transaction is finished,
if they are received in the middle of a transaction they are lost in the
libpq library. I added some tracing code to PQexec and this is the output:

Submitted by: Massimo Dal Zotto <dz@cs.unitn.it>
上级 e3b41d40
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/interfaces/libpq/fe-exec.c,v 1.17 1996/08/14 16:44:51 scrappy Exp $ * $Header: /cvsroot/pgsql/src/interfaces/libpq/fe-exec.c,v 1.18 1996/09/16 05:50:46 scrappy Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -370,6 +370,10 @@ PQexec(PGconn* conn, const char* query) ...@@ -370,6 +370,10 @@ PQexec(PGconn* conn, const char* query)
PGnotify *newNotify; PGnotify *newNotify;
FILE *pfin, *pfout, *pfdebug; FILE *pfin, *pfout, *pfdebug;
#ifdef PQ_NOTIFY_PATCH
int isCommand = 0; /* DZ - 31-8-1996 */
#endif
pname[0]='\0'; pname[0]='\0';
if (!conn) return NULL; if (!conn) return NULL;
...@@ -457,6 +461,13 @@ PQexec(PGconn* conn, const char* query) ...@@ -457,6 +461,13 @@ PQexec(PGconn* conn, const char* query)
clear = 0; clear = 0;
pqPuts("Q ",pfout,pfdebug); /* send an empty query */ pqPuts("Q ",pfout,pfdebug); /* send an empty query */
#ifdef PQ_NOTIFY_PATCH
/*
* Set a flag and process messages in the usual way because
* there may be async notifications pending. DZ - 31-8-1996
*/
isCommand = 1;
#else
while (!clear) while (!clear)
{ {
if (pqGets(buffer,ERROR_MSG_LENGTH,pfin,pfdebug) == 1) if (pqGets(buffer,ERROR_MSG_LENGTH,pfin,pfdebug) == 1)
...@@ -466,6 +477,7 @@ PQexec(PGconn* conn, const char* query) ...@@ -466,6 +477,7 @@ PQexec(PGconn* conn, const char* query)
result = makeEmptyPGresult(conn,PGRES_COMMAND_OK); result = makeEmptyPGresult(conn,PGRES_COMMAND_OK);
strncpy(result->cmdStatus,cmdStatus, CMDSTATUS_LEN-1); strncpy(result->cmdStatus,cmdStatus, CMDSTATUS_LEN-1);
return result; return result;
#endif
} }
break; break;
case 'E': /* error return */ case 'E': /* error return */
...@@ -482,6 +494,17 @@ PQexec(PGconn* conn, const char* query) ...@@ -482,6 +494,17 @@ PQexec(PGconn* conn, const char* query)
if ((c = pqGetc(pfin,pfdebug)) != '\0') { if ((c = pqGetc(pfin,pfdebug)) != '\0') {
fprintf(stderr,"error!, unexpected character %c following 'I'\n", c); fprintf(stderr,"error!, unexpected character %c following 'I'\n", c);
} }
#ifdef PQ_NOTIFY_PATCH
if (isCommand) {
/*
* If this is the result of a portal query command set the
* command status and message accordingly. DZ - 31-8-1996
*/
result = makeEmptyPGresult(conn,PGRES_COMMAND_OK);
strncpy(result->cmdStatus,cmdStatus, CMDSTATUS_LEN-1);
return result;
}
#endif
result = makeEmptyPGresult(conn, PGRES_EMPTY_QUERY); result = makeEmptyPGresult(conn, PGRES_EMPTY_QUERY);
return result; return result;
} }
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册