aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/interfaces/libpq/fe-protocol3.c19
1 files changed, 16 insertions, 3 deletions
diff --git a/src/interfaces/libpq/fe-protocol3.c b/src/interfaces/libpq/fe-protocol3.c
index 43898a45e37..3034773972a 100644
--- a/src/interfaces/libpq/fe-protocol3.c
+++ b/src/interfaces/libpq/fe-protocol3.c
@@ -467,7 +467,7 @@ handleSyncLoss(PGconn *conn, char id, int msgLength)
* command for a prepared statement) containing the attribute data.
* Returns: 0 if processed message successfully, EOF to suspend parsing
* (the latter case is not actually used currently).
- * In either case, conn->inStart has been advanced past the message.
+ * In the former case, conn->inStart has been advanced past the message.
*/
static int
getRowDescriptions(PGconn *conn, int msgLength)
@@ -641,6 +641,7 @@ advance_and_error:
* parseInput subroutine to read a 't' (ParameterDescription) message.
* We'll build a new PGresult structure containing the parameter data.
* Returns: 0 if completed message, EOF if not enough data yet.
+ * In the former case, conn->inStart has been advanced past the message.
*
* Note that if we run out of data, we have to release the partially
* constructed PGresult, and rebuild it again next time. Fortunately,
@@ -650,9 +651,9 @@ static int
getParamDescriptions(PGconn *conn, int msgLength)
{
PGresult *result;
+ const char *errmsg = NULL; /* means "out of memory", see below */
int nparams;
int i;
- const char *errmsg = NULL;
result = PQmakeEmptyPGresult(conn, PGRES_COMMAND_OK);
if (!result)
@@ -684,6 +685,13 @@ getParamDescriptions(PGconn *conn, int msgLength)
result->paramDescs[i].typid = typid;
}
+ /* Sanity check that we absorbed all the data */
+ if (conn->inCursor != conn->inStart + 5 + msgLength)
+ {
+ errmsg = libpq_gettext("extraneous data in \"t\" message");
+ goto advance_and_error;
+ }
+
/* Success! */
conn->result = result;
@@ -721,6 +729,11 @@ advance_and_error:
printfPQExpBuffer(&conn->errorMessage, "%s\n", errmsg);
pqSaveErrorResult(conn);
+ /*
+ * Return zero to allow input parsing to continue. Essentially, we've
+ * replaced the COMMAND_OK result with an error result, but since this
+ * doesn't affect the protocol state, it's fine.
+ */
return 0;
}
@@ -729,7 +742,7 @@ advance_and_error:
* We fill rowbuf with column pointers and then call the row processor.
* Returns: 0 if processed message successfully, EOF to suspend parsing
* (the latter case is not actually used currently).
- * In either case, conn->inStart has been advanced past the message.
+ * In the former case, conn->inStart has been advanced past the message.
*/
static int
getAnotherTuple(PGconn *conn, int msgLength)