From: "Paul 'Shag' Walmsley" Date: Thu, 11 Jul 1996 02:07:54 -0500 (CDT) Subject: Re: [PG95]: Backend process has died unexpectedly... On Thu, 11 Jul 1996, Paul 'Shag' Walmsley wrote: > However, I am of the opinion that libpq should never dump core, so I've > hacked together a patch to prevent libpq from dereferencing the connection > and result pointers if they're null. This patch is included at the end of > this message. While this patch compiled cleanly with SGI's easygoing IRIX cc, Marc Fournier has advised me that gcc doesn't like some of the aspects of the patch - namely, gcc wants some casts and PQresultStatus() to return an ExecStatusType. The patch enclosed below replaces the one that I recently sent. If you've already installed the first one, do a "cp src/libpq/fe-exec.c.orig src/libpq/fe-exec.c" and then install the patch below. - - Paul "Shag" Walmsley "Knowing is not enough." -- Hal Hartley, "Surviving Desire" - -----------[ cut here ]------------------------------------------------- *** src/libpq/fe-exec.c Thu Jul 11 01:45:24 1996 - --- src/libpq/fe-exec.c.new Thu Jul 11 01:43:44 1996 *************** *** 358,369 **** char cmdStatus[MAX_MESSAGE_LEN]; char pname[MAX_MESSAGE_LEN]; /* portal name */ PGnotify *newNotify; ! FILE *Pfin = conn->Pfin; ! FILE *Pfout = conn->Pfout; ! FILE* Pfdebug = conn->Pfdebug; pname[0]='\0'; /*clear the error string */ conn->errorMessage[0] = '\0'; - --- 358,377 ---- char cmdStatus[MAX_MESSAGE_LEN]; char pname[MAX_MESSAGE_LEN]; /* portal name */ PGnotify *newNotify; ! FILE *Pfin, *Pfout, *Pfdebug; pname[0]='\0'; + if (!conn) return NULL; + if (!query) { + sprintf(conn->errorMessage, "PQexec() -- query pointer is null."); + return NULL; + } + + Pfin = conn->Pfin; + Pfout = conn->Pfout; + Pfdebug = conn->Pfdebug; + /*clear the error string */ conn->errorMessage[0] = '\0'; *************** *** 500,505 **** - --- 508,516 ---- PQnotifies(PGconn *conn) { Dlelem *e; + + if (!conn) return NULL; + if (conn->status != CONNECTION_OK) return NULL; /* RemHead returns NULL if list is empy */ *************** *** 531,536 **** - --- 542,549 ---- PQgetline(PGconn *conn, char *s, int maxlen) { int c = '\0'; + + if (!conn) return EOF; if (!conn->Pfin || !s || maxlen <= 1) return(EOF); *************** *** 561,567 **** void PQputline(PGconn *conn, char *s) { ! if (conn->Pfout) { (void) fputs(s, conn->Pfout); fflush(conn->Pfout); } - --- 574,580 ---- void PQputline(PGconn *conn, char *s) { ! if (conn && (conn->Pfout)) { (void) fputs(s, conn->Pfout); fflush(conn->Pfout); } *************** *** 580,588 **** PQendcopy(PGconn *conn) { char id; ! FILE *Pfin = conn->Pfin; ! FILE* Pfdebug = conn->Pfdebug; if ( (id = pqGetc(Pfin,Pfdebug)) > 0) return(0); switch (id) { - --- 593,605 ---- PQendcopy(PGconn *conn) { char id; ! FILE *Pfin, *Pfdebug; ! ! if (!conn) return (int)NULL; + Pfin = conn->Pfin; + Pfdebug = conn->Pfdebug; + if ( (id = pqGetc(Pfin,Pfdebug)) > 0) return(0); switch (id) { *************** *** 836,847 **** PQArgBlock *args, int nargs) { ! FILE *Pfin = conn->Pfin; ! FILE *Pfout = conn->Pfout; ! FILE* Pfdebug = conn->Pfdebug; int id; int i; /* clear the error string */ conn->errorMessage[0] = '\0'; - --- 853,868 ---- PQArgBlock *args, int nargs) { ! FILE *Pfin, *Pfout, *Pfdebug; int id; int i; + if (!conn) return NULL; + + Pfin = conn->Pfin; + Pfout = conn->Pfout; + Pfdebug = conn->Pfdebug; + /* clear the error string */ conn->errorMessage[0] = '\0'; *************** *** 916,921 **** - --- 937,947 ---- ExecStatusType PQresultStatus(PGresult* res) { + if (!res) { + fprintf(stderr, "PQresultStatus() -- pointer to PQresult is null"); + return PGRES_NONFATAL_ERROR; + } + return res->resultStatus; } *************** *** 922,927 **** - --- 948,958 ---- int PQntuples(PGresult *res) { + if (!res) { + fprintf(stderr, "PQntuples() -- pointer to PQresult is null"); + return (int)NULL; + } + return res->ntups; } *************** *** 928,933 **** - --- 959,969 ---- int PQnfields(PGresult *res) { + if (!res) { + fprintf(stderr, "PQnfields() -- pointer to PQresult is null"); + return (int)NULL; + } + return res->numAttributes; } *************** *** 937,942 **** - --- 973,984 ---- char* PQfname(PGresult *res, int field_num) { + + if (!res) { + fprintf(stderr, "PQfname() -- pointer to PQresult is null"); + return NULL; + } + if (field_num > (res->numAttributes - 1)) { fprintf(stderr, "PQfname: ERROR! name of field %d(of %d) is not available", *************** *** 957,962 **** - --- 999,1009 ---- { int i; + if (!res) { + fprintf(stderr, "PQfnumber() -- pointer to PQresult is null"); + return -1; + } + if (field_name == NULL || field_name[0] == '\0' || res->attDescs == NULL) *************** *** 973,978 **** - --- 1020,1030 ---- Oid PQftype(PGresult *res, int field_num) { + if (!res) { + fprintf(stderr, "PQftype() -- pointer to PQresult is null"); + return InvalidOid; + } + if (field_num > (res->numAttributes - 1)) { fprintf(stderr, "PQftype: ERROR! type of field %d(of %d) is not available", *************** *** 987,992 **** - --- 1039,1049 ---- int2 PQfsize(PGresult *res, int field_num) { + if (!res) { + fprintf(stderr, "PQfsize() -- pointer to PQresult is null"); + return (int2)NULL; + } + if (field_num > (res->numAttributes - 1)) { fprintf(stderr, "PQfsize: ERROR! size of field %d(of %d) is not available", *************** *** 999,1004 **** - --- 1056,1066 ---- } char* PQcmdStatus(PGresult *res) { + if (!res) { + fprintf(stderr, "PQcmdStatus() -- pointer to PQresult is null"); + return NULL; + } + return res->cmdStatus; } *************** *** 1008,1013 **** - --- 1070,1080 ---- if not, return "" */ char* PQoidStatus(PGresult *res) { + if (!res) { + fprintf(stderr, "PQoidStatus() -- pointer to PQresult is null"); + return NULL; + } + if (!res->cmdStatus) return ""; *************** *** 1031,1036 **** - --- 1098,1108 ---- char* PQgetvalue(PGresult *res, int tup_num, int field_num) { + if (!res) { + fprintf(stderr, "PQgetvalue() -- pointer to PQresult is null"); + return NULL; + } + if (tup_num > (res->ntups - 1) || field_num > (res->numAttributes - 1)) { fprintf(stderr, *************** *** 1050,1055 **** - --- 1122,1132 ---- int PQgetlength(PGresult *res, int tup_num, int field_num) { + if (!res) { + fprintf(stderr, "PQgetlength() -- pointer to PQresult is null"); + return (int)NULL; + } + if (tup_num > (res->ntups - 1 )|| field_num > (res->numAttributes - 1)) { fprintf(stderr, - ---------[ cut here ]----------------------------------------------------