summaryrefslogtreecommitdiff
path: root/src/bin/psql/psql.c
diff options
context:
space:
mode:
authorMarc G. Fournier <scrappy@hub.org>1998-07-09 03:29:11 +0000
committerMarc G. Fournier <scrappy@hub.org>1998-07-09 03:29:11 +0000
commita0659e3e2c79be49feb4aa527d823c71d7bcaf07 (patch)
tree7dc58e872cdfce999dd0848000fcd3f2e4edbafa /src/bin/psql/psql.c
parent8bf61820f033d7df0e89433a0272d7b2567378b8 (diff)
From: Tom Lane <tgl@sss.pgh.pa.us>
Making PQrequestCancel safe to call in a signal handler turned out to be much easier than I feared. So here are the diffs. Some notes: * I modified the postmaster's packet "iodone" callback interface to allow the callback routine to return a continue-or-drop-connection return code; this was necessary to allow the connection to be closed after receiving a Cancel, rather than proceeding to launch a new backend... Being a neatnik, I also made the iodone proc have a typechecked parameter list. * I deleted all code I could find that had to do with OOB. * I made some edits to ensure that all signals mentioned in the code are referred to symbolically not by numbers ("SIGUSR2" not "2"). I think Bruce may have already done at least some of the same edits; I hope that merging these patches is not too painful.
Diffstat (limited to 'src/bin/psql/psql.c')
-rw-r--r--src/bin/psql/psql.c32
1 files changed, 23 insertions, 9 deletions
diff --git a/src/bin/psql/psql.c b/src/bin/psql/psql.c
index 1ed9e4561fd..65692bd9a11 100644
--- a/src/bin/psql/psql.c
+++ b/src/bin/psql/psql.c
@@ -7,7 +7,7 @@
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/bin/psql/Attic/psql.c,v 1.146 1998/06/16 07:29:38 momjian Exp $
+ * $Header: /cvsroot/pgsql/src/bin/psql/Attic/psql.c,v 1.147 1998/07/09 03:28:53 scrappy Exp $
*
*-------------------------------------------------------------------------
*/
@@ -291,27 +291,41 @@ PSQLexec(PsqlSettings *pset, char *query)
* If interactive, we enable a SIGINT signal catcher that sends
* a cancel request to the backend.
* Note that sending the cancel directly from the signal handler
- * is safe only because the cancel is sent as an OOB message.
- * If it were inline data, then we'd risk inserting it into the
- * middle of a normal data message by doing this.
- * (It's probably not too cool to write on stderr, for that matter...
- * but for debugging purposes we'll risk that.)
+ * is safe only because PQrequestCancel is carefully written to
+ * make it so. We have to be very careful what else we do in the
+ * signal handler.
+ * Writing on stderr is potentially dangerous, if the signal interrupted
+ * some stdio operation on stderr. On Unix we can avoid trouble by using
+ * write() instead; on Windows that's probably not workable, but we can
+ * at least avoid trusting printf by using the more primitive fputs.
*/
static PGconn * cancelConn = NULL; /* connection to try cancel on */
static void
+safe_write_stderr (const char * s)
+{
+#ifdef WIN32
+ fputs(s, stderr);
+#else
+ write(fileno(stderr), s, strlen(s));
+#endif
+}
+
+static void
handle_sigint (SIGNAL_ARGS)
{
if (cancelConn == NULL)
exit(1); /* accept signal if no connection */
/* Try to send cancel request */
if (PQrequestCancel(cancelConn))
- fprintf(stderr, "\nCANCEL request sent\n");
+ {
+ safe_write_stderr("\nCANCEL request sent\n");
+ }
else
{
- fprintf(stderr, "\nCannot send cancel request:\n%s\n",
- PQerrorMessage(cancelConn));
+ safe_write_stderr("\nCannot send cancel request:\n");
+ safe_write_stderr(PQerrorMessage(cancelConn));
}
}