2 * psql - the PostgreSQL interactive terminal
4 * Copyright (c) 2000-2010, PostgreSQL Global Development Group
6 * $PostgreSQL: pgsql/src/bin/psql/common.c,v 1.147 2010/07/28 04:39:14 petere Exp $
8 #include "postgres_fe.h"
14 #include <unistd.h> /* for write() */
16 #include <io.h> /* for _write() */
20 #include "portability/instr_time.h"
31 static bool ExecQueryUsingCursor(const char *query, double *elapsed_msec);
32 static bool command_no_begin(const char *query);
33 static bool is_select_command(const char *query);
36 * "Safe" wrapper around strdup()
39 pg_strdup(const char *string)
45 fprintf(stderr, _("%s: pg_strdup: cannot duplicate null pointer (internal error)\n"),
52 psql_error("out of memory\n");
59 pg_malloc(size_t size)
66 psql_error("out of memory\n");
73 pg_malloc_zero(size_t size)
77 tmp = pg_malloc(size);
83 pg_calloc(size_t nmemb, size_t size)
87 tmp = calloc(nmemb, size);
90 psql_error("out of memory");
98 * -- handler for -o command line option and \o command
100 * Tries to open file fname (or pipe if fname starts with '|')
101 * and stores the file handle in pset)
102 * Upon failure, sets stdout and returns false.
105 setQFout(const char *fname)
109 /* Close old file/pipe */
110 if (pset.queryFout && pset.queryFout != stdout && pset.queryFout != stderr)
112 if (pset.queryFoutPipe)
113 pclose(pset.queryFout);
115 fclose(pset.queryFout);
118 /* If no filename, set stdout */
119 if (!fname || fname[0] == '\0')
121 pset.queryFout = stdout;
122 pset.queryFoutPipe = false;
124 else if (*fname == '|')
126 pset.queryFout = popen(fname + 1, "w");
127 pset.queryFoutPipe = true;
131 pset.queryFout = fopen(fname, "w");
132 pset.queryFoutPipe = false;
135 if (!(pset.queryFout))
137 psql_error("%s: %s\n", fname, strerror(errno));
138 pset.queryFout = stdout;
139 pset.queryFoutPipe = false;
145 pqsignal(SIGPIPE, pset.queryFoutPipe ? SIG_IGN : SIG_DFL);
154 * Error reporting for scripts. Errors should look like
155 * psql:filename:lineno: message
159 psql_error(const char *fmt,...)
164 if (pset.queryFout != stdout)
165 fflush(pset.queryFout);
168 fprintf(stderr, "%s:%s:" UINT64_FORMAT ": ", pset.progname, pset.inputfile, pset.lineno);
170 vfprintf(stderr, _(fmt), ap);
177 * for backend Notice messages (INFO, WARNING, etc)
180 NoticeProcessor(void *arg, const char *message)
182 (void) arg; /* not used */
183 psql_error("%s", message);
189 * Code to support query cancellation
191 * Before we start a query, we enable the SIGINT signal catcher to send a
192 * cancel request to the backend. Note that sending the cancel directly from
193 * the signal handler is safe because PQcancel() is written to make it
194 * so. We use write() to report to stderr because it's better to use simple
195 * facilities in a signal handler.
197 * On win32, the signal cancelling happens on a separate thread, because
198 * that's how SetConsoleCtrlHandler works. The PQcancel function is safe
199 * for this (unlike PQrequestCancel). However, a CRITICAL_SECTION is required
200 * to protect the PGcancel structure against being changed while the signal
201 * thread is using it.
203 * SIGINT is supposed to abort all long-running psql operations, not only
204 * database queries. In most places, this is accomplished by checking
205 * cancel_pressed during long-running loops. However, that won't work when
206 * blocked on user input (in readline() or fgets()). In those places, we
207 * set sigint_interrupt_enabled TRUE while blocked, instructing the signal
208 * catcher to longjmp through sigint_interrupt_jmp. We assume readline and
209 * fgets are coded to handle possible interruption. (XXX currently this does
210 * not work on win32, so control-C is less useful there)
212 volatile bool sigint_interrupt_enabled = false;
214 sigjmp_buf sigint_interrupt_jmp;
216 static PGcancel *volatile cancelConn = NULL;
219 static CRITICAL_SECTION cancelConnLock;
222 #define write_stderr(str) write(fileno(stderr), str, strlen(str))
228 handle_sigint(SIGNAL_ARGS)
230 int save_errno = errno;
233 /* if we are waiting for input, longjmp out of it */
234 if (sigint_interrupt_enabled)
236 sigint_interrupt_enabled = false;
237 siglongjmp(sigint_interrupt_jmp, 1);
240 /* else, set cancel flag to stop any long-running loops */
241 cancel_pressed = true;
243 /* and send QueryCancel if we are processing a database query */
244 if (cancelConn != NULL)
246 if (PQcancel(cancelConn, errbuf, sizeof(errbuf)))
247 write_stderr("Cancel request sent\n");
250 write_stderr("Could not send cancel request: ");
251 write_stderr(errbuf);
255 errno = save_errno; /* just in case the write changed it */
259 setup_cancel_handler(void)
261 pqsignal(SIGINT, handle_sigint);
266 consoleHandler(DWORD dwCtrlType)
270 if (dwCtrlType == CTRL_C_EVENT ||
271 dwCtrlType == CTRL_BREAK_EVENT)
274 * Can't longjmp here, because we are in wrong thread :-(
277 /* set cancel flag to stop any long-running loops */
278 cancel_pressed = true;
280 /* and send QueryCancel if we are processing a database query */
281 EnterCriticalSection(&cancelConnLock);
282 if (cancelConn != NULL)
284 if (PQcancel(cancelConn, errbuf, sizeof(errbuf)))
285 write_stderr("Cancel request sent\n");
288 write_stderr("Could not send cancel request: ");
289 write_stderr(errbuf);
292 LeaveCriticalSection(&cancelConnLock);
297 /* Return FALSE for any signals not being handled */
302 setup_cancel_handler(void)
304 InitializeCriticalSection(&cancelConnLock);
306 SetConsoleCtrlHandler(consoleHandler, TRUE);
313 * Returns whether our backend connection is still there.
318 return PQstatus(pset.db) != CONNECTION_BAD;
325 * Verify that we still have a good connection to the backend, and if not,
326 * see if it can be restored.
328 * Returns true if either the connection was still there, or it could be
329 * restored successfully; false otherwise. If, however, there was no
330 * connection and the session is non-interactive, this will exit the program
331 * with a code of EXIT_BADCONN.
334 CheckConnection(void)
341 if (!pset.cur_cmd_interactive)
343 psql_error("connection to server was lost\n");
347 fputs(_("The connection to the server was lost. Attempting reset: "), stderr);
352 fputs(_("Failed.\n"), stderr);
359 fputs(_("Succeeded.\n"), stderr);
370 * Set cancelConn to point to the current database connection.
375 PGcancel *oldCancelConn;
378 EnterCriticalSection(&cancelConnLock);
381 /* Free the old one if we have one */
382 oldCancelConn = cancelConn;
383 /* be sure handle_sigint doesn't use pointer while freeing */
386 if (oldCancelConn != NULL)
387 PQfreeCancel(oldCancelConn);
389 cancelConn = PQgetCancel(pset.db);
392 LeaveCriticalSection(&cancelConnLock);
400 * Free the current cancel connection, if any, and set to NULL.
403 ResetCancelConn(void)
405 PGcancel *oldCancelConn;
408 EnterCriticalSection(&cancelConnLock);
411 oldCancelConn = cancelConn;
412 /* be sure handle_sigint doesn't use pointer while freeing */
415 if (oldCancelConn != NULL)
416 PQfreeCancel(oldCancelConn);
419 LeaveCriticalSection(&cancelConnLock);
427 * Checks whether a result is valid, giving an error message if necessary;
428 * and ensures that the connection to the backend is still up.
430 * Returns true for valid result, false for error state.
433 AcceptResult(const PGresult *result)
440 switch (PQresultStatus(result))
442 case PGRES_COMMAND_OK:
443 case PGRES_TUPLES_OK:
444 case PGRES_EMPTY_QUERY:
447 /* Fine, do nothing */
457 const char *error = PQerrorMessage(pset.db);
460 psql_error("%s", error);
473 * This is the way to send "backdoor" queries (those not directly entered
474 * by the user). It is subject to -E but not -e.
476 * In autocommit-off mode, a new transaction block is started if start_xact
477 * is true; nothing special is done when start_xact is false. Typically,
478 * start_xact = false is used for SELECTs and explicit BEGIN/COMMIT commands.
480 * Caller is responsible for handling the ensuing processing if a COPY
483 * Note: we don't bother to check PQclientEncoding; it is assumed that no
484 * caller uses this path to issue "SET CLIENT_ENCODING".
487 PSQLexec(const char *query, bool start_xact)
493 psql_error("You are currently not connected to a database.\n");
497 if (pset.echo_hidden != PSQL_ECHO_HIDDEN_OFF)
499 printf(_("********* QUERY **********\n"
501 "**************************\n\n"), query);
505 fprintf(pset.logfile,
506 _("********* QUERY **********\n"
508 "**************************\n\n"), query);
509 fflush(pset.logfile);
512 if (pset.echo_hidden == PSQL_ECHO_HIDDEN_NOEXEC)
520 PQtransactionStatus(pset.db) == PQTRANS_IDLE)
522 res = PQexec(pset.db, "BEGIN");
523 if (PQresultStatus(res) != PGRES_COMMAND_OK)
525 psql_error("%s", PQerrorMessage(pset.db));
533 res = PQexec(pset.db, query);
537 if (!AcceptResult(res))
549 * PrintNotifications: check for asynchronous notifications, and print them out
552 PrintNotifications(void)
556 while ((notify = PQnotifies(pset.db)))
558 /* for backward compatibility, only show payload if nonempty */
559 if (notify->extra[0])
560 fprintf(pset.queryFout, _("Asynchronous notification \"%s\" with payload \"%s\" received from server process with PID %d.\n"),
561 notify->relname, notify->extra, notify->be_pid);
563 fprintf(pset.queryFout, _("Asynchronous notification \"%s\" received from server process with PID %d.\n"),
564 notify->relname, notify->be_pid);
565 fflush(pset.queryFout);
572 * PrintQueryTuples: assuming query result is OK, print its tuples
574 * Returns true if successful, false otherwise.
577 PrintQueryTuples(const PGresult *results)
579 printQueryOpt my_popt = pset.popt;
581 /* write output to \g argument, if any */
584 /* keep this code in sync with ExecQueryUsingCursor */
585 FILE *queryFout_copy = pset.queryFout;
586 bool queryFoutPipe_copy = pset.queryFoutPipe;
588 pset.queryFout = stdout; /* so it doesn't get closed */
591 if (!setQFout(pset.gfname))
593 pset.queryFout = queryFout_copy;
594 pset.queryFoutPipe = queryFoutPipe_copy;
598 printQuery(results, &my_popt, pset.queryFout, pset.logfile);
600 /* close file/pipe, restore old setting */
603 pset.queryFout = queryFout_copy;
604 pset.queryFoutPipe = queryFoutPipe_copy;
610 printQuery(results, &my_popt, pset.queryFout, pset.logfile);
617 * ProcessCopyResult: if command was a COPY FROM STDIN/TO STDOUT, handle it
619 * Note: Utility function for use by SendQuery() only.
621 * Returns true if the query executed successfully, false otherwise.
624 ProcessCopyResult(PGresult *results)
626 bool success = false;
631 switch (PQresultStatus(results))
633 case PGRES_TUPLES_OK:
634 case PGRES_COMMAND_OK:
635 case PGRES_EMPTY_QUERY:
636 /* nothing to do here */
642 success = handleCopyOut(pset.db, pset.queryFout);
648 success = handleCopyIn(pset.db, pset.cur_cmd_source,
649 PQbinaryTuples(results));
657 /* may need this to recover from conn loss during COPY */
658 if (!CheckConnection())
666 * PrintQueryStatus: report command status as required
668 * Note: Utility function for use by PrintQueryResults() only.
671 PrintQueryStatus(PGresult *results)
677 if (pset.popt.topt.format == PRINT_HTML)
679 fputs("<p>", pset.queryFout);
680 html_escaped_print(PQcmdStatus(results), pset.queryFout);
681 fputs("</p>\n", pset.queryFout);
684 fprintf(pset.queryFout, "%s\n", PQcmdStatus(results));
688 fprintf(pset.logfile, "%s\n", PQcmdStatus(results));
690 snprintf(buf, sizeof(buf), "%u", (unsigned int) PQoidValue(results));
691 SetVariable(pset.vars, "LASTOID", buf);
696 * PrintQueryResults: print out query results as required
698 * Note: Utility function for use by SendQuery() only.
700 * Returns true if the query executed successfully, false otherwise.
703 PrintQueryResults(PGresult *results)
705 bool success = false;
706 const char *cmdstatus;
711 switch (PQresultStatus(results))
713 case PGRES_TUPLES_OK:
714 /* print the data ... */
715 success = PrintQueryTuples(results);
716 /* if it's INSERT/UPDATE/DELETE RETURNING, also print status */
717 cmdstatus = PQcmdStatus(results);
718 if (strncmp(cmdstatus, "INSERT", 6) == 0 ||
719 strncmp(cmdstatus, "UPDATE", 6) == 0 ||
720 strncmp(cmdstatus, "DELETE", 6) == 0)
721 PrintQueryStatus(results);
724 case PGRES_COMMAND_OK:
725 PrintQueryStatus(results);
729 case PGRES_EMPTY_QUERY:
735 /* nothing to do here */
743 fflush(pset.queryFout);
750 * SendQuery: send the query string to the backend
751 * (and print out results)
753 * Note: This is the "front door" way to send a query. That is, use it to
754 * send queries actually entered by the user. These queries will be subject to
756 * To send "back door" queries (generated by slash commands, etc.) in a
757 * controlled way, use PSQLexec().
759 * Returns true if the query executed successfully, false otherwise.
762 SendQuery(const char *query)
765 PGTransactionStatusType transaction_status;
766 double elapsed_msec = 0;
768 on_error_rollback_savepoint = false;
769 static bool on_error_rollback_warning = false;
773 psql_error("You are currently not connected to a database.\n");
781 printf(_("***(Single step mode: verify command)*******************************************\n"
783 "***(press return to proceed or enter x and return to cancel)********************\n"),
786 if (fgets(buf, sizeof(buf), stdin) != NULL)
790 else if (pset.echo == PSQL_ECHO_QUERIES)
798 fprintf(pset.logfile,
799 _("********* QUERY **********\n"
801 "**************************\n\n"), query);
802 fflush(pset.logfile);
807 transaction_status = PQtransactionStatus(pset.db);
809 if (transaction_status == PQTRANS_IDLE &&
811 !command_no_begin(query))
813 results = PQexec(pset.db, "BEGIN");
814 if (PQresultStatus(results) != PGRES_COMMAND_OK)
816 psql_error("%s", PQerrorMessage(pset.db));
822 transaction_status = PQtransactionStatus(pset.db);
825 if (transaction_status == PQTRANS_INTRANS &&
826 pset.on_error_rollback != PSQL_ERROR_ROLLBACK_OFF &&
827 (pset.cur_cmd_interactive ||
828 pset.on_error_rollback == PSQL_ERROR_ROLLBACK_ON))
830 if (on_error_rollback_warning == false && pset.sversion < 80000)
832 fprintf(stderr, _("The server (version %d.%d) does not support savepoints for ON_ERROR_ROLLBACK.\n"),
833 pset.sversion / 10000, (pset.sversion / 100) % 100);
834 on_error_rollback_warning = true;
838 results = PQexec(pset.db, "SAVEPOINT pg_psql_temporary_savepoint");
839 if (PQresultStatus(results) != PGRES_COMMAND_OK)
841 psql_error("%s", PQerrorMessage(pset.db));
847 on_error_rollback_savepoint = true;
851 if (pset.fetch_count <= 0 || !is_select_command(query))
853 /* Default fetch-it-all-and-print mode */
858 INSTR_TIME_SET_CURRENT(before);
860 results = PQexec(pset.db, query);
862 /* these operations are included in the timing result: */
864 OK = (AcceptResult(results) && ProcessCopyResult(results));
868 INSTR_TIME_SET_CURRENT(after);
869 INSTR_TIME_SUBTRACT(after, before);
870 elapsed_msec = INSTR_TIME_GET_MILLISEC(after);
873 /* but printing results isn't: */
875 OK = PrintQueryResults(results);
879 /* Fetch-in-segments mode */
880 OK = ExecQueryUsingCursor(query, &elapsed_msec);
882 results = NULL; /* PQclear(NULL) does nothing */
885 /* If we made a temporary savepoint, possibly release/rollback */
886 if (on_error_rollback_savepoint)
890 transaction_status = PQtransactionStatus(pset.db);
892 if (transaction_status == PQTRANS_INERROR)
894 /* We always rollback on an error */
895 svptcmd = "ROLLBACK TO pg_psql_temporary_savepoint";
897 else if (transaction_status != PQTRANS_INTRANS)
899 /* If they are no longer in a transaction, then do nothing */
905 * Do nothing if they are messing with savepoints themselves: If
906 * the user did RELEASE or ROLLBACK, our savepoint is gone. If
907 * they issued a SAVEPOINT, releasing ours would remove theirs.
910 (strcmp(PQcmdStatus(results), "SAVEPOINT") == 0 ||
911 strcmp(PQcmdStatus(results), "RELEASE") == 0 ||
912 strcmp(PQcmdStatus(results), "ROLLBACK") == 0))
915 svptcmd = "RELEASE pg_psql_temporary_savepoint";
922 svptres = PQexec(pset.db, svptcmd);
923 if (PQresultStatus(svptres) != PGRES_COMMAND_OK)
925 psql_error("%s", PQerrorMessage(pset.db));
938 /* Possible microtiming output */
939 if (OK && pset.timing)
940 printf(_("Time: %.3f ms\n"), elapsed_msec);
942 /* check for events that may occur during query execution */
944 if (pset.encoding != PQclientEncoding(pset.db) &&
945 PQclientEncoding(pset.db) >= 0)
947 /* track effects of SET CLIENT_ENCODING */
948 pset.encoding = PQclientEncoding(pset.db);
949 pset.popt.topt.encoding = pset.encoding;
950 SetVariable(pset.vars, "ENCODING",
951 pg_encoding_to_char(pset.encoding));
954 PrintNotifications();
961 * ExecQueryUsingCursor: run a SELECT-like query using a cursor
963 * This feature allows result sets larger than RAM to be dealt with.
965 * Returns true if the query executed successfully, false otherwise.
967 * If pset.timing is on, total query time (exclusive of result-printing) is
968 * stored into *elapsed_msec.
971 ExecQueryUsingCursor(const char *query, double *elapsed_msec)
976 printQueryOpt my_popt = pset.popt;
977 FILE *queryFout_copy = pset.queryFout;
978 bool queryFoutPipe_copy = pset.queryFoutPipe;
979 bool started_txn = false;
980 bool did_pager = false;
989 /* initialize print options for partial table output */
990 my_popt.topt.start_table = true;
991 my_popt.topt.stop_table = false;
992 my_popt.topt.prior_records = 0;
995 INSTR_TIME_SET_CURRENT(before);
997 /* if we're not in a transaction, start one */
998 if (PQtransactionStatus(pset.db) == PQTRANS_IDLE)
1000 results = PQexec(pset.db, "BEGIN");
1001 OK = AcceptResult(results) &&
1002 (PQresultStatus(results) == PGRES_COMMAND_OK);
1009 /* Send DECLARE CURSOR */
1010 initPQExpBuffer(&buf);
1011 appendPQExpBuffer(&buf, "DECLARE _psql_cursor NO SCROLL CURSOR FOR\n%s",
1014 results = PQexec(pset.db, buf.data);
1015 OK = AcceptResult(results) &&
1016 (PQresultStatus(results) == PGRES_COMMAND_OK);
1018 termPQExpBuffer(&buf);
1024 INSTR_TIME_SET_CURRENT(after);
1025 INSTR_TIME_SUBTRACT(after, before);
1026 *elapsed_msec += INSTR_TIME_GET_MILLISEC(after);
1029 snprintf(fetch_cmd, sizeof(fetch_cmd),
1030 "FETCH FORWARD %d FROM _psql_cursor",
1033 /* prepare to write output to \g argument, if any */
1036 /* keep this code in sync with PrintQueryTuples */
1037 pset.queryFout = stdout; /* so it doesn't get closed */
1039 /* open file/pipe */
1040 if (!setQFout(pset.gfname))
1042 pset.queryFout = queryFout_copy;
1043 pset.queryFoutPipe = queryFoutPipe_copy;
1049 /* clear any pre-existing error indication on the output stream */
1050 clearerr(pset.queryFout);
1055 INSTR_TIME_SET_CURRENT(before);
1057 /* get FETCH_COUNT tuples at a time */
1058 results = PQexec(pset.db, fetch_cmd);
1062 INSTR_TIME_SET_CURRENT(after);
1063 INSTR_TIME_SUBTRACT(after, before);
1064 *elapsed_msec += INSTR_TIME_GET_MILLISEC(after);
1067 if (PQresultStatus(results) != PGRES_TUPLES_OK)
1069 /* shut down pager before printing error message */
1072 ClosePager(pset.queryFout);
1073 pset.queryFout = queryFout_copy;
1074 pset.queryFoutPipe = queryFoutPipe_copy;
1078 OK = AcceptResult(results);
1084 ntuples = PQntuples(results);
1086 if (ntuples < pset.fetch_count)
1088 /* this is the last result set, so allow footer decoration */
1089 my_popt.topt.stop_table = true;
1091 else if (pset.queryFout == stdout && !did_pager)
1094 * If query requires multiple result sets, hack to ensure that
1095 * only one pager instance is used for the whole mess
1097 pset.queryFout = PageOutput(100000, my_popt.topt.pager);
1101 printQuery(results, &my_popt, pset.queryFout, pset.logfile);
1105 /* after the first result set, disallow header decoration */
1106 my_popt.topt.start_table = false;
1107 my_popt.topt.prior_records += ntuples;
1110 * Make sure to flush the output stream, so intermediate results are
1111 * visible to the client immediately. We check the results because if
1112 * the pager dies/exits/etc, there's no sense throwing more data at
1115 flush_error = fflush(pset.queryFout);
1118 * Check if we are at the end, if a cancel was pressed, or if there
1119 * were any errors either trying to flush out the results, or more
1120 * generally on the output stream at all. If we hit any errors
1121 * writing things to the stream, we presume $PAGER has disappeared and
1122 * stop bothering to pull down more data.
1124 if (ntuples < pset.fetch_count || cancel_pressed || flush_error ||
1125 ferror(pset.queryFout))
1129 /* close \g argument file/pipe, restore old setting */
1132 /* keep this code in sync with PrintQueryTuples */
1135 pset.queryFout = queryFout_copy;
1136 pset.queryFoutPipe = queryFoutPipe_copy;
1143 ClosePager(pset.queryFout);
1144 pset.queryFout = queryFout_copy;
1145 pset.queryFoutPipe = queryFoutPipe_copy;
1150 INSTR_TIME_SET_CURRENT(before);
1153 * We try to close the cursor on either success or failure, but on failure
1154 * ignore the result (it's probably just a bleat about being in an aborted
1157 results = PQexec(pset.db, "CLOSE _psql_cursor");
1160 OK = AcceptResult(results) &&
1161 (PQresultStatus(results) == PGRES_COMMAND_OK);
1167 results = PQexec(pset.db, OK ? "COMMIT" : "ROLLBACK");
1168 OK &= AcceptResult(results) &&
1169 (PQresultStatus(results) == PGRES_COMMAND_OK);
1175 INSTR_TIME_SET_CURRENT(after);
1176 INSTR_TIME_SUBTRACT(after, before);
1177 *elapsed_msec += INSTR_TIME_GET_MILLISEC(after);
1185 * Advance the given char pointer over white space and SQL comments.
1188 skip_white_space(const char *query)
1190 int cnestlevel = 0; /* slash-star comment nest level */
1194 int mblen = PQmblen(query, pset.encoding);
1197 * Note: we assume the encoding is a superset of ASCII, so that for
1198 * example "query[0] == '/'" is meaningful. However, we do NOT assume
1199 * that the second and subsequent bytes of a multibyte character
1200 * couldn't look like ASCII characters; so it is critical to advance
1201 * by mblen, not 1, whenever we haven't exactly identified the
1202 * character we are skipping over.
1204 if (isspace((unsigned char) *query))
1206 else if (query[0] == '/' && query[1] == '*')
1211 else if (cnestlevel > 0 && query[0] == '*' && query[1] == '/')
1216 else if (cnestlevel == 0 && query[0] == '-' && query[1] == '-')
1221 * We have to skip to end of line since any slash-star inside the
1222 * -- comment does NOT start a slash-star comment.
1231 query += PQmblen(query, pset.encoding);
1234 else if (cnestlevel > 0)
1237 break; /* found first token */
1245 * Check whether a command is one of those for which we should NOT start
1246 * a new transaction block (ie, send a preceding BEGIN).
1248 * These include the transaction control statements themselves, plus
1249 * certain statements that the backend disallows inside transaction blocks.
1252 command_no_begin(const char *query)
1257 * First we must advance over any whitespace and comments.
1259 query = skip_white_space(query);
1262 * Check word length (since "beginx" is not "begin").
1265 while (isalpha((unsigned char) query[wordlen]))
1266 wordlen += PQmblen(&query[wordlen], pset.encoding);
1269 * Transaction control commands. These should include every keyword that
1270 * gives rise to a TransactionStmt in the backend grammar, except for the
1271 * savepoint-related commands.
1273 * (We assume that START must be START TRANSACTION, since there is
1274 * presently no other "START foo" command.)
1276 if (wordlen == 5 && pg_strncasecmp(query, "abort", 5) == 0)
1278 if (wordlen == 5 && pg_strncasecmp(query, "begin", 5) == 0)
1280 if (wordlen == 5 && pg_strncasecmp(query, "start", 5) == 0)
1282 if (wordlen == 6 && pg_strncasecmp(query, "commit", 6) == 0)
1284 if (wordlen == 3 && pg_strncasecmp(query, "end", 3) == 0)
1286 if (wordlen == 8 && pg_strncasecmp(query, "rollback", 8) == 0)
1288 if (wordlen == 7 && pg_strncasecmp(query, "prepare", 7) == 0)
1290 /* PREPARE TRANSACTION is a TC command, PREPARE foo is not */
1293 query = skip_white_space(query);
1296 while (isalpha((unsigned char) query[wordlen]))
1297 wordlen += PQmblen(&query[wordlen], pset.encoding);
1299 if (wordlen == 11 && pg_strncasecmp(query, "transaction", 11) == 0)
1305 * Commands not allowed within transactions. The statements checked for
1306 * here should be exactly those that call PreventTransactionChain() in the
1309 if (wordlen == 6 && pg_strncasecmp(query, "vacuum", 6) == 0)
1311 if (wordlen == 7 && pg_strncasecmp(query, "cluster", 7) == 0)
1313 /* CLUSTER with any arguments is allowed in transactions */
1316 query = skip_white_space(query);
1318 if (isalpha((unsigned char) query[0]))
1319 return false; /* has additional words */
1320 return true; /* it's CLUSTER without arguments */
1323 if (wordlen == 6 && pg_strncasecmp(query, "create", 6) == 0)
1327 query = skip_white_space(query);
1330 while (isalpha((unsigned char) query[wordlen]))
1331 wordlen += PQmblen(&query[wordlen], pset.encoding);
1333 if (wordlen == 8 && pg_strncasecmp(query, "database", 8) == 0)
1335 if (wordlen == 10 && pg_strncasecmp(query, "tablespace", 10) == 0)
1338 /* CREATE [UNIQUE] INDEX CONCURRENTLY isn't allowed in xacts */
1339 if (wordlen == 6 && pg_strncasecmp(query, "unique", 6) == 0)
1343 query = skip_white_space(query);
1346 while (isalpha((unsigned char) query[wordlen]))
1347 wordlen += PQmblen(&query[wordlen], pset.encoding);
1350 if (wordlen == 5 && pg_strncasecmp(query, "index", 5) == 0)
1354 query = skip_white_space(query);
1357 while (isalpha((unsigned char) query[wordlen]))
1358 wordlen += PQmblen(&query[wordlen], pset.encoding);
1360 if (wordlen == 12 && pg_strncasecmp(query, "concurrently", 12) == 0)
1368 * Note: these tests will match DROP SYSTEM and REINDEX TABLESPACE, which
1369 * aren't really valid commands so we don't care much. The other four
1370 * possible matches are correct.
1372 if ((wordlen == 4 && pg_strncasecmp(query, "drop", 4) == 0) ||
1373 (wordlen == 7 && pg_strncasecmp(query, "reindex", 7) == 0))
1377 query = skip_white_space(query);
1380 while (isalpha((unsigned char) query[wordlen]))
1381 wordlen += PQmblen(&query[wordlen], pset.encoding);
1383 if (wordlen == 8 && pg_strncasecmp(query, "database", 8) == 0)
1385 if (wordlen == 6 && pg_strncasecmp(query, "system", 6) == 0)
1387 if (wordlen == 10 && pg_strncasecmp(query, "tablespace", 10) == 0)
1396 * Check whether the specified command is a SELECT (or VALUES).
1399 is_select_command(const char *query)
1404 * First advance over any whitespace, comments and left parentheses.
1408 query = skip_white_space(query);
1409 if (query[0] == '(')
1416 * Check word length (since "selectx" is not "select").
1419 while (isalpha((unsigned char) query[wordlen]))
1420 wordlen += PQmblen(&query[wordlen], pset.encoding);
1422 if (wordlen == 6 && pg_strncasecmp(query, "select", 6) == 0)
1425 if (wordlen == 6 && pg_strncasecmp(query, "values", 6) == 0)
1433 * Test if the current user is a database superuser.
1435 * Note: this will correctly detect superuserness only with a protocol-3.0
1436 * or newer backend; otherwise it will always say "false".
1446 val = PQparameterStatus(pset.db, "is_superuser");
1448 if (val && strcmp(val, "on") == 0)
1456 * Test if the current session uses standard string literals.
1458 * Note: With a pre-protocol-3.0 connection this will always say "false",
1459 * which should be the right answer.
1462 standard_strings(void)
1469 val = PQparameterStatus(pset.db, "standard_conforming_strings");
1471 if (val && strcmp(val, "on") == 0)
1479 * Return the session user of the current connection.
1481 * Note: this will correctly detect the session user only with a
1482 * protocol-3.0 or newer backend; otherwise it will return the
1486 session_username(void)
1493 val = PQparameterStatus(pset.db, "session_authorization");
1497 return PQuser(pset.db);
1503 * substitute '~' with HOME or '~username' with username's home dir
1507 expand_tilde(char **filename)
1509 if (!filename || !(*filename))
1513 * WIN32 doesn't use tilde expansion for file names. Also, it uses tilde
1514 * for short versions of long file names, though the tilde is usually
1515 * toward the end, not at the beginning.
1519 /* try tilde expansion */
1520 if (**filename == '~')
1526 char home[MAXPGPATH];
1532 while (*p != '/' && *p != '\0')
1538 if (*(fn + 1) == '\0')
1539 get_home_path(home); /* ~ or ~/ only */
1540 else if ((pw = getpwnam(fn + 1)) != NULL)
1541 strlcpy(home, pw->pw_dir, sizeof(home)); /* ~user */
1544 if (strlen(home) != 0)
1548 newfn = pg_malloc(strlen(home) + strlen(p) + 1);
1549 strcpy(newfn, home);