PostgreSQL Source Code  git master
common.c
Go to the documentation of this file.
1 /*
2  * psql - the PostgreSQL interactive terminal
3  *
4  * Copyright (c) 2000-2021, PostgreSQL Global Development Group
5  *
6  * src/bin/psql/common.c
7  */
8 #include "postgres_fe.h"
9 
10 #include <ctype.h>
11 #include <limits.h>
12 #include <math.h>
13 #include <signal.h>
14 #ifndef WIN32
15 #include <unistd.h> /* for write() */
16 #else
17 #include <io.h> /* for _write() */
18 #include <win32.h>
19 #endif
20 
21 #include "command.h"
22 #include "common.h"
23 #include "common/logging.h"
24 #include "copy.h"
25 #include "crosstabview.h"
26 #include "fe_utils/cancel.h"
27 #include "fe_utils/mbprint.h"
28 #include "fe_utils/string_utils.h"
29 #include "portability/instr_time.h"
30 #include "settings.h"
31 
32 static bool DescribeQuery(const char *query, double *elapsed_msec);
33 static bool ExecQueryUsingCursor(const char *query, double *elapsed_msec);
34 static bool command_no_begin(const char *query);
35 static bool is_select_command(const char *query);
36 
37 
38 /*
39  * openQueryOutputFile --- attempt to open a query output file
40  *
41  * fname == NULL selects stdout, else an initial '|' selects a pipe,
42  * else plain file.
43  *
44  * Returns output file pointer into *fout, and is-a-pipe flag into *is_pipe.
45  * Caller is responsible for adjusting SIGPIPE state if it's a pipe.
46  *
47  * On error, reports suitable error message and returns false.
48  */
49 bool
50 openQueryOutputFile(const char *fname, FILE **fout, bool *is_pipe)
51 {
52  if (!fname || fname[0] == '\0')
53  {
54  *fout = stdout;
55  *is_pipe = false;
56  }
57  else if (*fname == '|')
58  {
59  *fout = popen(fname + 1, "w");
60  *is_pipe = true;
61  }
62  else
63  {
64  *fout = fopen(fname, "w");
65  *is_pipe = false;
66  }
67 
68  if (*fout == NULL)
69  {
70  pg_log_error("%s: %m", fname);
71  return false;
72  }
73 
74  return true;
75 }
76 
77 /*
78  * setQFout
79  * -- handler for -o command line option and \o command
80  *
81  * On success, updates pset with the new output file and returns true.
82  * On failure, returns false without changing pset state.
83  */
84 bool
85 setQFout(const char *fname)
86 {
87  FILE *fout;
88  bool is_pipe;
89 
90  /* First make sure we can open the new output file/pipe */
91  if (!openQueryOutputFile(fname, &fout, &is_pipe))
92  return false;
93 
94  /* Close old file/pipe */
95  if (pset.queryFout && pset.queryFout != stdout && pset.queryFout != stderr)
96  {
97  if (pset.queryFoutPipe)
98  pclose(pset.queryFout);
99  else
100  fclose(pset.queryFout);
101  }
102 
103  pset.queryFout = fout;
104  pset.queryFoutPipe = is_pipe;
105 
106  /* Adjust SIGPIPE handling appropriately: ignore signal if is_pipe */
107  set_sigpipe_trap_state(is_pipe);
109 
110  return true;
111 }
112 
113 
114 /*
115  * Variable-fetching callback for flex lexer
116  *
117  * If the specified variable exists, return its value as a string (malloc'd
118  * and expected to be freed by the caller); else return NULL.
119  *
120  * If "quote" isn't PQUOTE_PLAIN, then return the value suitably quoted and
121  * escaped for the specified quoting requirement. (Failure in escaping
122  * should lead to printing an error and returning NULL.)
123  *
124  * "passthrough" is the pointer previously given to psql_scan_set_passthrough.
125  * In psql, passthrough points to a ConditionalStack, which we check to
126  * determine whether variable expansion is allowed.
127  */
128 char *
129 psql_get_variable(const char *varname, PsqlScanQuoteType quote,
130  void *passthrough)
131 {
132  char *result = NULL;
133  const char *value;
134 
135  /* In an inactive \if branch, suppress all variable substitutions */
136  if (passthrough && !conditional_active((ConditionalStack) passthrough))
137  return NULL;
138 
139  value = GetVariable(pset.vars, varname);
140  if (!value)
141  return NULL;
142 
143  switch (quote)
144  {
145  case PQUOTE_PLAIN:
146  result = pg_strdup(value);
147  break;
148  case PQUOTE_SQL_LITERAL:
149  case PQUOTE_SQL_IDENT:
150  {
151  /*
152  * For these cases, we use libpq's quoting functions, which
153  * assume the string is in the connection's client encoding.
154  */
155  char *escaped_value;
156 
157  if (!pset.db)
158  {
159  pg_log_error("cannot escape without active connection");
160  return NULL;
161  }
162 
163  if (quote == PQUOTE_SQL_LITERAL)
164  escaped_value =
165  PQescapeLiteral(pset.db, value, strlen(value));
166  else
167  escaped_value =
168  PQescapeIdentifier(pset.db, value, strlen(value));
169 
170  if (escaped_value == NULL)
171  {
172  const char *error = PQerrorMessage(pset.db);
173 
174  pg_log_info("%s", error);
175  return NULL;
176  }
177 
178  /*
179  * Rather than complicate the lexer's API with a notion of
180  * which free() routine to use, just pay the price of an extra
181  * strdup().
182  */
183  result = pg_strdup(escaped_value);
184  PQfreemem(escaped_value);
185  break;
186  }
187  case PQUOTE_SHELL_ARG:
188  {
189  /*
190  * For this we use appendShellStringNoError, which is
191  * encoding-agnostic, which is fine since the shell probably
192  * is too. In any case, the only special character is "'",
193  * which is not known to appear in valid multibyte characters.
194  */
196 
197  initPQExpBuffer(&buf);
198  if (!appendShellStringNoError(&buf, value))
199  {
200  pg_log_error("shell command argument contains a newline or carriage return: \"%s\"",
201  value);
202  free(buf.data);
203  return NULL;
204  }
205  result = buf.data;
206  break;
207  }
208 
209  /* No default: we want a compiler warning for missing cases */
210  }
211 
212  return result;
213 }
214 
215 
216 /*
217  * for backend Notice messages (INFO, WARNING, etc)
218  */
219 void
220 NoticeProcessor(void *arg, const char *message)
221 {
222  (void) arg; /* not used */
223  pg_log_info("%s", message);
224 }
225 
226 
227 
228 /*
229  * Code to support query cancellation
230  *
231  * Before we start a query, we enable the SIGINT signal catcher to send a
232  * cancel request to the backend.
233  *
234  * SIGINT is supposed to abort all long-running psql operations, not only
235  * database queries. In most places, this is accomplished by checking
236  * cancel_pressed during long-running loops. However, that won't work when
237  * blocked on user input (in readline() or fgets()). In those places, we
238  * set sigint_interrupt_enabled true while blocked, instructing the signal
239  * catcher to longjmp through sigint_interrupt_jmp. We assume readline and
240  * fgets are coded to handle possible interruption.
241  *
242  * On Windows, currently this does not work, so control-C is less useful
243  * there.
244  */
245 volatile bool sigint_interrupt_enabled = false;
246 
248 
249 static void
251 {
252 #ifndef WIN32
253  /* if we are waiting for input, longjmp out of it */
255  {
256  sigint_interrupt_enabled = false;
257  siglongjmp(sigint_interrupt_jmp, 1);
258  }
259 #endif
260 
261  /* else, set cancel flag to stop any long-running loops */
262  cancel_pressed = true;
263 }
264 
265 void
267 {
269 }
270 
271 
272 /* ConnectionUp
273  *
274  * Returns whether our backend connection is still there.
275  */
276 static bool
278 {
279  return PQstatus(pset.db) != CONNECTION_BAD;
280 }
281 
282 
283 
284 /* CheckConnection
285  *
286  * Verify that we still have a good connection to the backend, and if not,
287  * see if it can be restored.
288  *
289  * Returns true if either the connection was still there, or it could be
290  * restored successfully; false otherwise. If, however, there was no
291  * connection and the session is non-interactive, this will exit the program
292  * with a code of EXIT_BADCONN.
293  */
294 static bool
296 {
297  bool OK;
298 
299  OK = ConnectionUp();
300  if (!OK)
301  {
303  {
304  pg_log_fatal("connection to server was lost");
305  exit(EXIT_BADCONN);
306  }
307 
308  fprintf(stderr, _("The connection to the server was lost. Attempting reset: "));
309  PQreset(pset.db);
310  OK = ConnectionUp();
311  if (!OK)
312  {
313  fprintf(stderr, _("Failed.\n"));
314 
315  /*
316  * Transition to having no connection; but stash away the failed
317  * connection so that we can still refer to its parameters in a
318  * later \connect attempt. Keep the state cleanup here in sync
319  * with do_connect().
320  */
321  if (pset.dead_conn)
323  pset.dead_conn = pset.db;
324  pset.db = NULL;
325  ResetCancelConn();
326  UnsyncVariables();
327  }
328  else
329  {
330  fprintf(stderr, _("Succeeded.\n"));
331 
332  /*
333  * Re-sync, just in case anything changed. Keep this in sync with
334  * do_connect().
335  */
336  SyncVariables();
337  connection_warnings(false); /* Must be after SyncVariables */
338  }
339  }
340 
341  return OK;
342 }
343 
344 
345 
346 
347 /*
348  * AcceptResult
349  *
350  * Checks whether a result is valid, giving an error message if necessary;
351  * and ensures that the connection to the backend is still up.
352  *
353  * Returns true for valid result, false for error state.
354  */
355 static bool
356 AcceptResult(const PGresult *result)
357 {
358  bool OK;
359 
360  if (!result)
361  OK = false;
362  else
363  switch (PQresultStatus(result))
364  {
365  case PGRES_COMMAND_OK:
366  case PGRES_TUPLES_OK:
367  case PGRES_EMPTY_QUERY:
368  case PGRES_COPY_IN:
369  case PGRES_COPY_OUT:
370  /* Fine, do nothing */
371  OK = true;
372  break;
373 
374  case PGRES_BAD_RESPONSE:
376  case PGRES_FATAL_ERROR:
377  OK = false;
378  break;
379 
380  default:
381  OK = false;
382  pg_log_error("unexpected PQresultStatus: %d",
383  PQresultStatus(result));
384  break;
385  }
386 
387  if (!OK)
388  {
389  const char *error = PQerrorMessage(pset.db);
390 
391  if (strlen(error))
392  pg_log_info("%s", error);
393 
394  CheckConnection();
395  }
396 
397  return OK;
398 }
399 
400 
401 /*
402  * Set special variables from a query result
403  * - ERROR: true/false, whether an error occurred on this query
404  * - SQLSTATE: code of error, or "00000" if no error, or "" if unknown
405  * - ROW_COUNT: how many rows were returned or affected, or "0"
406  * - LAST_ERROR_SQLSTATE: same for last error
407  * - LAST_ERROR_MESSAGE: message of last error
408  *
409  * Note: current policy is to apply this only to the results of queries
410  * entered by the user, not queries generated by slash commands.
411  */
412 static void
414 {
415  if (success)
416  {
417  const char *ntuples = PQcmdTuples(results);
418 
419  SetVariable(pset.vars, "ERROR", "false");
420  SetVariable(pset.vars, "SQLSTATE", "00000");
421  SetVariable(pset.vars, "ROW_COUNT", *ntuples ? ntuples : "0");
422  }
423  else
424  {
425  const char *code = PQresultErrorField(results, PG_DIAG_SQLSTATE);
426  const char *mesg = PQresultErrorField(results, PG_DIAG_MESSAGE_PRIMARY);
427 
428  SetVariable(pset.vars, "ERROR", "true");
429 
430  /*
431  * If there is no SQLSTATE code, use an empty string. This can happen
432  * for libpq-detected errors (e.g., lost connection, ENOMEM).
433  */
434  if (code == NULL)
435  code = "";
436  SetVariable(pset.vars, "SQLSTATE", code);
437  SetVariable(pset.vars, "ROW_COUNT", "0");
438  SetVariable(pset.vars, "LAST_ERROR_SQLSTATE", code);
439  SetVariable(pset.vars, "LAST_ERROR_MESSAGE", mesg ? mesg : "");
440  }
441 }
442 
443 
444 /*
445  * ClearOrSaveResult
446  *
447  * If the result represents an error, remember it for possible display by
448  * \errverbose. Otherwise, just PQclear() it.
449  *
450  * Note: current policy is to apply this to the results of all queries,
451  * including "back door" queries, for debugging's sake. It's OK to use
452  * PQclear() directly on results known to not be error results, however.
453  */
454 static void
456 {
457  if (result)
458  {
459  switch (PQresultStatus(result))
460  {
462  case PGRES_FATAL_ERROR:
465  pset.last_error_result = result;
466  break;
467 
468  default:
469  PQclear(result);
470  break;
471  }
472  }
473 }
474 
475 
476 /*
477  * Print microtiming output. Always print raw milliseconds; if the interval
478  * is >= 1 second, also break it down into days/hours/minutes/seconds.
479  */
480 static void
481 PrintTiming(double elapsed_msec)
482 {
483  double seconds;
484  double minutes;
485  double hours;
486  double days;
487 
488  if (elapsed_msec < 1000.0)
489  {
490  /* This is the traditional (pre-v10) output format */
491  printf(_("Time: %.3f ms\n"), elapsed_msec);
492  return;
493  }
494 
495  /*
496  * Note: we could print just seconds, in a format like %06.3f, when the
497  * total is less than 1min. But that's hard to interpret unless we tack
498  * on "s" or otherwise annotate it. Forcing the display to include
499  * minutes seems like a better solution.
500  */
501  seconds = elapsed_msec / 1000.0;
502  minutes = floor(seconds / 60.0);
503  seconds -= 60.0 * minutes;
504  if (minutes < 60.0)
505  {
506  printf(_("Time: %.3f ms (%02d:%06.3f)\n"),
507  elapsed_msec, (int) minutes, seconds);
508  return;
509  }
510 
511  hours = floor(minutes / 60.0);
512  minutes -= 60.0 * hours;
513  if (hours < 24.0)
514  {
515  printf(_("Time: %.3f ms (%02d:%02d:%06.3f)\n"),
516  elapsed_msec, (int) hours, (int) minutes, seconds);
517  return;
518  }
519 
520  days = floor(hours / 24.0);
521  hours -= 24.0 * days;
522  printf(_("Time: %.3f ms (%.0f d %02d:%02d:%06.3f)\n"),
523  elapsed_msec, days, (int) hours, (int) minutes, seconds);
524 }
525 
526 
527 /*
528  * PSQLexec
529  *
530  * This is the way to send "backdoor" queries (those not directly entered
531  * by the user). It is subject to -E but not -e.
532  *
533  * Caller is responsible for handling the ensuing processing if a COPY
534  * command is sent.
535  *
536  * Note: we don't bother to check PQclientEncoding; it is assumed that no
537  * caller uses this path to issue "SET CLIENT_ENCODING".
538  */
539 PGresult *
540 PSQLexec(const char *query)
541 {
542  PGresult *res;
543 
544  if (!pset.db)
545  {
546  pg_log_error("You are currently not connected to a database.");
547  return NULL;
548  }
549 
551  {
552  printf(_("********* QUERY **********\n"
553  "%s\n"
554  "**************************\n\n"), query);
555  fflush(stdout);
556  if (pset.logfile)
557  {
559  _("********* QUERY **********\n"
560  "%s\n"
561  "**************************\n\n"), query);
562  fflush(pset.logfile);
563  }
564 
566  return NULL;
567  }
568 
570 
571  res = PQexec(pset.db, query);
572 
573  ResetCancelConn();
574 
575  if (!AcceptResult(res))
576  {
577  ClearOrSaveResult(res);
578  res = NULL;
579  }
580 
581  return res;
582 }
583 
584 
585 /*
586  * PSQLexecWatch
587  *
588  * This function is used for \watch command to send the query to
589  * the server and print out the results.
590  *
591  * Returns 1 if the query executed successfully, 0 if it cannot be repeated,
592  * e.g., because of the interrupt, -1 on error.
593  */
594 int
595 PSQLexecWatch(const char *query, const printQueryOpt *opt, FILE *printQueryFout)
596 {
597  PGresult *res;
598  double elapsed_msec = 0;
600  instr_time after;
601  FILE *fout;
602 
603  if (!pset.db)
604  {
605  pg_log_error("You are currently not connected to a database.");
606  return 0;
607  }
608 
610 
611  if (pset.timing)
612  INSTR_TIME_SET_CURRENT(before);
613 
614  res = PQexec(pset.db, query);
615 
616  ResetCancelConn();
617 
618  if (!AcceptResult(res))
619  {
620  ClearOrSaveResult(res);
621  return 0;
622  }
623 
624  if (pset.timing)
625  {
626  INSTR_TIME_SET_CURRENT(after);
627  INSTR_TIME_SUBTRACT(after, before);
628  elapsed_msec = INSTR_TIME_GET_MILLISEC(after);
629  }
630 
631  /*
632  * If SIGINT is sent while the query is processing, the interrupt will be
633  * consumed. The user's intention, though, is to cancel the entire watch
634  * process, so detect a sent cancellation request and exit in this case.
635  */
636  if (cancel_pressed)
637  {
638  PQclear(res);
639  return 0;
640  }
641 
642  fout = printQueryFout ? printQueryFout : pset.queryFout;
643 
644  switch (PQresultStatus(res))
645  {
646  case PGRES_TUPLES_OK:
647  printQuery(res, opt, fout, false, pset.logfile);
648  break;
649 
650  case PGRES_COMMAND_OK:
651  fprintf(fout, "%s\n%s\n\n", opt->title, PQcmdStatus(res));
652  break;
653 
654  case PGRES_EMPTY_QUERY:
655  pg_log_error("\\watch cannot be used with an empty query");
656  PQclear(res);
657  return -1;
658 
659  case PGRES_COPY_OUT:
660  case PGRES_COPY_IN:
661  case PGRES_COPY_BOTH:
662  pg_log_error("\\watch cannot be used with COPY");
663  PQclear(res);
664  return -1;
665 
666  default:
667  pg_log_error("unexpected result status for \\watch");
668  PQclear(res);
669  return -1;
670  }
671 
672  PQclear(res);
673 
674  fflush(fout);
675 
676  /* Possible microtiming output */
677  if (pset.timing)
678  PrintTiming(elapsed_msec);
679 
680  return 1;
681 }
682 
683 
684 /*
685  * PrintNotifications: check for asynchronous notifications, and print them out
686  */
687 static void
689 {
690  PGnotify *notify;
691 
693  while ((notify = PQnotifies(pset.db)) != NULL)
694  {
695  /* for backward compatibility, only show payload if nonempty */
696  if (notify->extra[0])
697  fprintf(pset.queryFout, _("Asynchronous notification \"%s\" with payload \"%s\" received from server process with PID %d.\n"),
698  notify->relname, notify->extra, notify->be_pid);
699  else
700  fprintf(pset.queryFout, _("Asynchronous notification \"%s\" received from server process with PID %d.\n"),
701  notify->relname, notify->be_pid);
702  fflush(pset.queryFout);
703  PQfreemem(notify);
705  }
706 }
707 
708 
709 /*
710  * PrintQueryTuples: assuming query result is OK, print its tuples
711  *
712  * Returns true if successful, false otherwise.
713  */
714 static bool
715 PrintQueryTuples(const PGresult *results)
716 {
717  bool result = true;
718 
719  /* write output to \g argument, if any */
720  if (pset.gfname)
721  {
722  FILE *fout;
723  bool is_pipe;
724 
725  if (!openQueryOutputFile(pset.gfname, &fout, &is_pipe))
726  return false;
727  if (is_pipe)
729 
730  printQuery(results, &pset.popt, fout, false, pset.logfile);
731  if (ferror(fout))
732  {
733  pg_log_error("could not print result table: %m");
734  result = false;
735  }
736 
737  if (is_pipe)
738  {
739  pclose(fout);
741  }
742  else
743  fclose(fout);
744  }
745  else
746  {
747  printQuery(results, &pset.popt, pset.queryFout, false, pset.logfile);
748  if (ferror(pset.queryFout))
749  {
750  pg_log_error("could not print result table: %m");
751  result = false;
752  }
753  }
754 
755  return result;
756 }
757 
758 
759 /*
760  * StoreQueryTuple: assuming query result is OK, save data into variables
761  *
762  * Returns true if successful, false otherwise.
763  */
764 static bool
765 StoreQueryTuple(const PGresult *result)
766 {
767  bool success = true;
768 
769  if (PQntuples(result) < 1)
770  {
771  pg_log_error("no rows returned for \\gset");
772  success = false;
773  }
774  else if (PQntuples(result) > 1)
775  {
776  pg_log_error("more than one row returned for \\gset");
777  success = false;
778  }
779  else
780  {
781  int i;
782 
783  for (i = 0; i < PQnfields(result); i++)
784  {
785  char *colname = PQfname(result, i);
786  char *varname;
787  char *value;
788 
789  /* concatenate prefix and column name */
790  varname = psprintf("%s%s", pset.gset_prefix, colname);
791 
792  if (VariableHasHook(pset.vars, varname))
793  {
794  pg_log_warning("attempt to \\gset into specially treated variable \"%s\" ignored",
795  varname);
796  continue;
797  }
798 
799  if (!PQgetisnull(result, 0, i))
800  value = PQgetvalue(result, 0, i);
801  else
802  {
803  /* for NULL value, unset rather than set the variable */
804  value = NULL;
805  }
806 
807  if (!SetVariable(pset.vars, varname, value))
808  {
809  free(varname);
810  success = false;
811  break;
812  }
813 
814  free(varname);
815  }
816  }
817 
818  return success;
819 }
820 
821 
822 /*
823  * ExecQueryTuples: assuming query result is OK, execute each query
824  * result field as a SQL statement
825  *
826  * Returns true if successful, false otherwise.
827  */
828 static bool
829 ExecQueryTuples(const PGresult *result)
830 {
831  bool success = true;
832  int nrows = PQntuples(result);
833  int ncolumns = PQnfields(result);
834  int r,
835  c;
836 
837  /*
838  * We must turn off gexec_flag to avoid infinite recursion. Note that
839  * this allows ExecQueryUsingCursor to be applied to the individual query
840  * results. SendQuery prevents it from being applied when fetching the
841  * queries-to-execute, because it can't handle recursion either.
842  */
843  pset.gexec_flag = false;
844 
845  for (r = 0; r < nrows; r++)
846  {
847  for (c = 0; c < ncolumns; c++)
848  {
849  if (!PQgetisnull(result, r, c))
850  {
851  const char *query = PQgetvalue(result, r, c);
852 
853  /* Abandon execution if cancel_pressed */
854  if (cancel_pressed)
855  goto loop_exit;
856 
857  /*
858  * ECHO_ALL mode should echo these queries, but SendQuery
859  * assumes that MainLoop did that, so we have to do it here.
860  */
862  {
863  puts(query);
864  fflush(stdout);
865  }
866 
867  if (!SendQuery(query))
868  {
869  /* Error - abandon execution if ON_ERROR_STOP */
870  success = false;
871  if (pset.on_error_stop)
872  goto loop_exit;
873  }
874  }
875  }
876  }
877 
878 loop_exit:
879 
880  /*
881  * Restore state. We know gexec_flag was on, else we'd not be here. (We
882  * also know it'll get turned off at end of command, but that's not ours
883  * to do here.)
884  */
885  pset.gexec_flag = true;
886 
887  /* Return true if all queries were successful */
888  return success;
889 }
890 
891 
892 /*
893  * ProcessResult: utility function for use by SendQuery() only
894  *
895  * When our command string contained a COPY FROM STDIN or COPY TO STDOUT,
896  * PQexec() has stopped at the PGresult associated with the first such
897  * command. In that event, we'll marshal data for the COPY and then cycle
898  * through any subsequent PGresult objects.
899  *
900  * When the command string contained no such COPY command, this function
901  * degenerates to an AcceptResult() call.
902  *
903  * Changes its argument to point to the last PGresult of the command string,
904  * or NULL if that result was for a COPY TO STDOUT. (Returning NULL prevents
905  * the command status from being printed, which we want in that case so that
906  * the status line doesn't get taken as part of the COPY data.)
907  *
908  * Returns true on complete success, false otherwise. Possible failure modes
909  * include purely client-side problems; check the transaction status for the
910  * server-side opinion.
911  */
912 static bool
914 {
915  bool success = true;
916  bool first_cycle = true;
917 
918  for (;;)
919  {
920  ExecStatusType result_status;
921  bool is_copy;
922  PGresult *next_result;
923 
924  if (!AcceptResult(*results))
925  {
926  /*
927  * Failure at this point is always a server-side failure or a
928  * failure to submit the command string. Either way, we're
929  * finished with this command string.
930  */
931  success = false;
932  break;
933  }
934 
935  result_status = PQresultStatus(*results);
936  switch (result_status)
937  {
938  case PGRES_EMPTY_QUERY:
939  case PGRES_COMMAND_OK:
940  case PGRES_TUPLES_OK:
941  is_copy = false;
942  break;
943 
944  case PGRES_COPY_OUT:
945  case PGRES_COPY_IN:
946  is_copy = true;
947  break;
948 
949  default:
950  /* AcceptResult() should have caught anything else. */
951  is_copy = false;
952  pg_log_error("unexpected PQresultStatus: %d", result_status);
953  break;
954  }
955 
956  if (is_copy)
957  {
958  /*
959  * Marshal the COPY data. Either subroutine will get the
960  * connection out of its COPY state, then call PQresultStatus()
961  * once and report any error.
962  *
963  * For COPY OUT, direct the output to pset.copyStream if it's set,
964  * otherwise to pset.gfname if it's set, otherwise to queryFout.
965  * For COPY IN, use pset.copyStream as data source if it's set,
966  * otherwise cur_cmd_source.
967  */
968  FILE *copystream;
969  PGresult *copy_result;
970 
972  if (result_status == PGRES_COPY_OUT)
973  {
974  bool need_close = false;
975  bool is_pipe = false;
976 
977  if (pset.copyStream)
978  {
979  /* invoked by \copy */
980  copystream = pset.copyStream;
981  }
982  else if (pset.gfname)
983  {
984  /* invoked by \g */
986  &copystream, &is_pipe))
987  {
988  need_close = true;
989  if (is_pipe)
991  }
992  else
993  copystream = NULL; /* discard COPY data entirely */
994  }
995  else
996  {
997  /* fall back to the generic query output stream */
998  copystream = pset.queryFout;
999  }
1000 
1001  success = handleCopyOut(pset.db,
1002  copystream,
1003  &copy_result)
1004  && success
1005  && (copystream != NULL);
1006 
1007  /*
1008  * Suppress status printing if the report would go to the same
1009  * place as the COPY data just went. Note this doesn't
1010  * prevent error reporting, since handleCopyOut did that.
1011  */
1012  if (copystream == pset.queryFout)
1013  {
1014  PQclear(copy_result);
1015  copy_result = NULL;
1016  }
1017 
1018  if (need_close)
1019  {
1020  /* close \g argument file/pipe */
1021  if (is_pipe)
1022  {
1023  pclose(copystream);
1025  }
1026  else
1027  {
1028  fclose(copystream);
1029  }
1030  }
1031  }
1032  else
1033  {
1034  /* COPY IN */
1035  copystream = pset.copyStream ? pset.copyStream : pset.cur_cmd_source;
1036  success = handleCopyIn(pset.db,
1037  copystream,
1038  PQbinaryTuples(*results),
1039  &copy_result) && success;
1040  }
1041  ResetCancelConn();
1042 
1043  /*
1044  * Replace the PGRES_COPY_OUT/IN result with COPY command's exit
1045  * status, or with NULL if we want to suppress printing anything.
1046  */
1047  PQclear(*results);
1048  *results = copy_result;
1049  }
1050  else if (first_cycle)
1051  {
1052  /* fast path: no COPY commands; PQexec visited all results */
1053  break;
1054  }
1055 
1056  /*
1057  * Check PQgetResult() again. In the typical case of a single-command
1058  * string, it will return NULL. Otherwise, we'll have other results
1059  * to process that may include other COPYs. We keep the last result.
1060  */
1061  next_result = PQgetResult(pset.db);
1062  if (!next_result)
1063  break;
1064 
1065  PQclear(*results);
1066  *results = next_result;
1067  first_cycle = false;
1068  }
1069 
1070  SetResultVariables(*results, success);
1071 
1072  /* may need this to recover from conn loss during COPY */
1073  if (!first_cycle && !CheckConnection())
1074  return false;
1075 
1076  return success;
1077 }
1078 
1079 
1080 /*
1081  * PrintQueryStatus: report command status as required
1082  *
1083  * Note: Utility function for use by PrintQueryResults() only.
1084  */
1085 static void
1087 {
1088  char buf[16];
1089 
1090  if (!pset.quiet)
1091  {
1092  if (pset.popt.topt.format == PRINT_HTML)
1093  {
1094  fputs("<p>", pset.queryFout);
1096  fputs("</p>\n", pset.queryFout);
1097  }
1098  else
1099  fprintf(pset.queryFout, "%s\n", PQcmdStatus(results));
1100  }
1101 
1102  if (pset.logfile)
1103  fprintf(pset.logfile, "%s\n", PQcmdStatus(results));
1104 
1105  snprintf(buf, sizeof(buf), "%u", (unsigned int) PQoidValue(results));
1106  SetVariable(pset.vars, "LASTOID", buf);
1107 }
1108 
1109 
1110 /*
1111  * PrintQueryResults: print out (or store or execute) query results as required
1112  *
1113  * Note: Utility function for use by SendQuery() only.
1114  *
1115  * Returns true if the query executed successfully, false otherwise.
1116  */
1117 static bool
1119 {
1120  bool success;
1121  const char *cmdstatus;
1122 
1123  if (!results)
1124  return false;
1125 
1126  switch (PQresultStatus(results))
1127  {
1128  case PGRES_TUPLES_OK:
1129  /* store or execute or print the data ... */
1130  if (pset.gset_prefix)
1131  success = StoreQueryTuple(results);
1132  else if (pset.gexec_flag)
1133  success = ExecQueryTuples(results);
1134  else if (pset.crosstab_flag)
1135  success = PrintResultsInCrosstab(results);
1136  else
1137  success = PrintQueryTuples(results);
1138  /* if it's INSERT/UPDATE/DELETE RETURNING, also print status */
1139  cmdstatus = PQcmdStatus(results);
1140  if (strncmp(cmdstatus, "INSERT", 6) == 0 ||
1141  strncmp(cmdstatus, "UPDATE", 6) == 0 ||
1142  strncmp(cmdstatus, "DELETE", 6) == 0)
1143  PrintQueryStatus(results);
1144  break;
1145 
1146  case PGRES_COMMAND_OK:
1147  PrintQueryStatus(results);
1148  success = true;
1149  break;
1150 
1151  case PGRES_EMPTY_QUERY:
1152  success = true;
1153  break;
1154 
1155  case PGRES_COPY_OUT:
1156  case PGRES_COPY_IN:
1157  /* nothing to do here */
1158  success = true;
1159  break;
1160 
1161  case PGRES_BAD_RESPONSE:
1162  case PGRES_NONFATAL_ERROR:
1163  case PGRES_FATAL_ERROR:
1164  success = false;
1165  break;
1166 
1167  default:
1168  success = false;
1169  pg_log_error("unexpected PQresultStatus: %d",
1170  PQresultStatus(results));
1171  break;
1172  }
1173 
1174  fflush(pset.queryFout);
1175 
1176  return success;
1177 }
1178 
1179 
1180 /*
1181  * SendQuery: send the query string to the backend
1182  * (and print out results)
1183  *
1184  * Note: This is the "front door" way to send a query. That is, use it to
1185  * send queries actually entered by the user. These queries will be subject to
1186  * single step mode.
1187  * To send "back door" queries (generated by slash commands, etc.) in a
1188  * controlled way, use PSQLexec().
1189  *
1190  * Returns true if the query executed successfully, false otherwise.
1191  */
1192 bool
1193 SendQuery(const char *query)
1194 {
1195  PGresult *results;
1196  PGTransactionStatusType transaction_status;
1197  double elapsed_msec = 0;
1198  bool OK = false;
1199  int i;
1200  bool on_error_rollback_savepoint = false;
1201  static bool on_error_rollback_warning = false;
1202 
1203  if (!pset.db)
1204  {
1205  pg_log_error("You are currently not connected to a database.");
1206  goto sendquery_cleanup;
1207  }
1208 
1209  if (pset.singlestep)
1210  {
1211  char buf[3];
1212 
1213  fflush(stderr);
1214  printf(_("***(Single step mode: verify command)*******************************************\n"
1215  "%s\n"
1216  "***(press return to proceed or enter x and return to cancel)********************\n"),
1217  query);
1218  fflush(stdout);
1219  if (fgets(buf, sizeof(buf), stdin) != NULL)
1220  if (buf[0] == 'x')
1221  goto sendquery_cleanup;
1222  if (cancel_pressed)
1223  goto sendquery_cleanup;
1224  }
1225  else if (pset.echo == PSQL_ECHO_QUERIES)
1226  {
1227  puts(query);
1228  fflush(stdout);
1229  }
1230 
1231  if (pset.logfile)
1232  {
1234  _("********* QUERY **********\n"
1235  "%s\n"
1236  "**************************\n\n"), query);
1237  fflush(pset.logfile);
1238  }
1239 
1241 
1242  transaction_status = PQtransactionStatus(pset.db);
1243 
1244  if (transaction_status == PQTRANS_IDLE &&
1245  !pset.autocommit &&
1246  !command_no_begin(query))
1247  {
1248  results = PQexec(pset.db, "BEGIN");
1249  if (PQresultStatus(results) != PGRES_COMMAND_OK)
1250  {
1252  ClearOrSaveResult(results);
1253  ResetCancelConn();
1254  goto sendquery_cleanup;
1255  }
1256  ClearOrSaveResult(results);
1257  transaction_status = PQtransactionStatus(pset.db);
1258  }
1259 
1260  if (transaction_status == PQTRANS_INTRANS &&
1264  {
1265  if (on_error_rollback_warning == false && pset.sversion < 80000)
1266  {
1267  char sverbuf[32];
1268 
1269  pg_log_warning("The server (version %s) does not support savepoints for ON_ERROR_ROLLBACK.",
1271  sverbuf, sizeof(sverbuf)));
1272  on_error_rollback_warning = true;
1273  }
1274  else
1275  {
1276  results = PQexec(pset.db, "SAVEPOINT pg_psql_temporary_savepoint");
1277  if (PQresultStatus(results) != PGRES_COMMAND_OK)
1278  {
1280  ClearOrSaveResult(results);
1281  ResetCancelConn();
1282  goto sendquery_cleanup;
1283  }
1284  ClearOrSaveResult(results);
1285  on_error_rollback_savepoint = true;
1286  }
1287  }
1288 
1289  if (pset.gdesc_flag)
1290  {
1291  /* Describe query's result columns, without executing it */
1292  OK = DescribeQuery(query, &elapsed_msec);
1293  ResetCancelConn();
1294  results = NULL; /* PQclear(NULL) does nothing */
1295  }
1296  else if (pset.fetch_count <= 0 || pset.gexec_flag ||
1298  {
1299  /* Default fetch-it-all-and-print mode */
1301  after;
1302 
1303  if (pset.timing)
1304  INSTR_TIME_SET_CURRENT(before);
1305 
1306  results = PQexec(pset.db, query);
1307 
1308  /* these operations are included in the timing result: */
1309  ResetCancelConn();
1310  OK = ProcessResult(&results);
1311 
1312  if (pset.timing)
1313  {
1314  INSTR_TIME_SET_CURRENT(after);
1315  INSTR_TIME_SUBTRACT(after, before);
1316  elapsed_msec = INSTR_TIME_GET_MILLISEC(after);
1317  }
1318 
1319  /* but printing results isn't: */
1320  if (OK && results)
1321  OK = PrintQueryResults(results);
1322  }
1323  else
1324  {
1325  /* Fetch-in-segments mode */
1326  OK = ExecQueryUsingCursor(query, &elapsed_msec);
1327  ResetCancelConn();
1328  results = NULL; /* PQclear(NULL) does nothing */
1329  }
1330 
1331  if (!OK && pset.echo == PSQL_ECHO_ERRORS)
1332  pg_log_info("STATEMENT: %s", query);
1333 
1334  /* If we made a temporary savepoint, possibly release/rollback */
1335  if (on_error_rollback_savepoint)
1336  {
1337  const char *svptcmd = NULL;
1338 
1339  transaction_status = PQtransactionStatus(pset.db);
1340 
1341  switch (transaction_status)
1342  {
1343  case PQTRANS_INERROR:
1344  /* We always rollback on an error */
1345  svptcmd = "ROLLBACK TO pg_psql_temporary_savepoint";
1346  break;
1347 
1348  case PQTRANS_IDLE:
1349  /* If they are no longer in a transaction, then do nothing */
1350  break;
1351 
1352  case PQTRANS_INTRANS:
1353 
1354  /*
1355  * Do nothing if they are messing with savepoints themselves:
1356  * If the user did COMMIT AND CHAIN, RELEASE or ROLLBACK, our
1357  * savepoint is gone. If they issued a SAVEPOINT, releasing
1358  * ours would remove theirs.
1359  */
1360  if (results &&
1361  (strcmp(PQcmdStatus(results), "COMMIT") == 0 ||
1362  strcmp(PQcmdStatus(results), "SAVEPOINT") == 0 ||
1363  strcmp(PQcmdStatus(results), "RELEASE") == 0 ||
1364  strcmp(PQcmdStatus(results), "ROLLBACK") == 0))
1365  svptcmd = NULL;
1366  else
1367  svptcmd = "RELEASE pg_psql_temporary_savepoint";
1368  break;
1369 
1370  case PQTRANS_ACTIVE:
1371  case PQTRANS_UNKNOWN:
1372  default:
1373  OK = false;
1374  /* PQTRANS_UNKNOWN is expected given a broken connection. */
1375  if (transaction_status != PQTRANS_UNKNOWN || ConnectionUp())
1376  pg_log_error("unexpected transaction status (%d)",
1377  transaction_status);
1378  break;
1379  }
1380 
1381  if (svptcmd)
1382  {
1383  PGresult *svptres;
1384 
1385  svptres = PQexec(pset.db, svptcmd);
1386  if (PQresultStatus(svptres) != PGRES_COMMAND_OK)
1387  {
1389  ClearOrSaveResult(svptres);
1390  OK = false;
1391 
1392  PQclear(results);
1393  ResetCancelConn();
1394  goto sendquery_cleanup;
1395  }
1396  PQclear(svptres);
1397  }
1398  }
1399 
1400  ClearOrSaveResult(results);
1401 
1402  /* Possible microtiming output */
1403  if (pset.timing)
1404  PrintTiming(elapsed_msec);
1405 
1406  /* check for events that may occur during query execution */
1407 
1408  if (pset.encoding != PQclientEncoding(pset.db) &&
1409  PQclientEncoding(pset.db) >= 0)
1410  {
1411  /* track effects of SET CLIENT_ENCODING */
1414  SetVariable(pset.vars, "ENCODING",
1416  }
1417 
1419 
1420  /* perform cleanup that should occur after any attempted query */
1421 
1422 sendquery_cleanup:
1423 
1424  /* reset \g's output-to-filename trigger */
1425  if (pset.gfname)
1426  {
1427  free(pset.gfname);
1428  pset.gfname = NULL;
1429  }
1430 
1431  /* restore print settings if \g changed them */
1432  if (pset.gsavepopt)
1433  {
1435  pset.gsavepopt = NULL;
1436  }
1437 
1438  /* reset \gset trigger */
1439  if (pset.gset_prefix)
1440  {
1442  pset.gset_prefix = NULL;
1443  }
1444 
1445  /* reset \gdesc trigger */
1446  pset.gdesc_flag = false;
1447 
1448  /* reset \gexec trigger */
1449  pset.gexec_flag = false;
1450 
1451  /* reset \crosstabview trigger */
1452  pset.crosstab_flag = false;
1453  for (i = 0; i < lengthof(pset.ctv_args); i++)
1454  {
1455  pg_free(pset.ctv_args[i]);
1456  pset.ctv_args[i] = NULL;
1457  }
1458 
1459  return OK;
1460 }
1461 
1462 
1463 /*
1464  * DescribeQuery: describe the result columns of a query, without executing it
1465  *
1466  * Returns true if the operation executed successfully, false otherwise.
1467  *
1468  * If pset.timing is on, total query time (exclusive of result-printing) is
1469  * stored into *elapsed_msec.
1470  */
1471 static bool
1472 DescribeQuery(const char *query, double *elapsed_msec)
1473 {
1474  PGresult *results;
1475  bool OK;
1477  after;
1478 
1479  *elapsed_msec = 0;
1480 
1481  if (pset.timing)
1482  INSTR_TIME_SET_CURRENT(before);
1483 
1484  /*
1485  * To parse the query but not execute it, we prepare it, using the unnamed
1486  * prepared statement. This is invisible to psql users, since there's no
1487  * way to access the unnamed prepared statement from psql user space. The
1488  * next Parse or Query protocol message would overwrite the statement
1489  * anyway. (So there's no great need to clear it when done, which is a
1490  * good thing because libpq provides no easy way to do that.)
1491  */
1492  results = PQprepare(pset.db, "", query, 0, NULL);
1493  if (PQresultStatus(results) != PGRES_COMMAND_OK)
1494  {
1496  SetResultVariables(results, false);
1497  ClearOrSaveResult(results);
1498  return false;
1499  }
1500  PQclear(results);
1501 
1502  results = PQdescribePrepared(pset.db, "");
1503  OK = AcceptResult(results) &&
1504  (PQresultStatus(results) == PGRES_COMMAND_OK);
1505  if (OK && results)
1506  {
1507  if (PQnfields(results) > 0)
1508  {
1510  int i;
1511 
1512  initPQExpBuffer(&buf);
1513 
1514  printfPQExpBuffer(&buf,
1515  "SELECT name AS \"%s\", pg_catalog.format_type(tp, tpm) AS \"%s\"\n"
1516  "FROM (VALUES ",
1517  gettext_noop("Column"),
1518  gettext_noop("Type"));
1519 
1520  for (i = 0; i < PQnfields(results); i++)
1521  {
1522  const char *name;
1523  char *escname;
1524 
1525  if (i > 0)
1526  appendPQExpBufferStr(&buf, ",");
1527 
1528  name = PQfname(results, i);
1529  escname = PQescapeLiteral(pset.db, name, strlen(name));
1530 
1531  if (escname == NULL)
1532  {
1534  PQclear(results);
1535  termPQExpBuffer(&buf);
1536  return false;
1537  }
1538 
1539  appendPQExpBuffer(&buf, "(%s, '%u'::pg_catalog.oid, %d)",
1540  escname,
1541  PQftype(results, i),
1542  PQfmod(results, i));
1543 
1544  PQfreemem(escname);
1545  }
1546 
1547  appendPQExpBufferStr(&buf, ") s(name, tp, tpm)");
1548  PQclear(results);
1549 
1550  results = PQexec(pset.db, buf.data);
1551  OK = AcceptResult(results);
1552 
1553  if (pset.timing)
1554  {
1555  INSTR_TIME_SET_CURRENT(after);
1556  INSTR_TIME_SUBTRACT(after, before);
1557  *elapsed_msec += INSTR_TIME_GET_MILLISEC(after);
1558  }
1559 
1560  if (OK && results)
1561  OK = PrintQueryResults(results);
1562 
1563  termPQExpBuffer(&buf);
1564  }
1565  else
1567  _("The command has no result, or the result has no columns.\n"));
1568  }
1569 
1570  SetResultVariables(results, OK);
1571  ClearOrSaveResult(results);
1572 
1573  return OK;
1574 }
1575 
1576 
1577 /*
1578  * ExecQueryUsingCursor: run a SELECT-like query using a cursor
1579  *
1580  * This feature allows result sets larger than RAM to be dealt with.
1581  *
1582  * Returns true if the query executed successfully, false otherwise.
1583  *
1584  * If pset.timing is on, total query time (exclusive of result-printing) is
1585  * stored into *elapsed_msec.
1586  */
1587 static bool
1588 ExecQueryUsingCursor(const char *query, double *elapsed_msec)
1589 {
1590  bool OK = true;
1591  PGresult *results;
1593  printQueryOpt my_popt = pset.popt;
1594  FILE *fout;
1595  bool is_pipe;
1596  bool is_pager = false;
1597  bool started_txn = false;
1598  int64 total_tuples = 0;
1599  int ntuples;
1600  int fetch_count;
1601  char fetch_cmd[64];
1603  after;
1604  int flush_error;
1605 
1606  *elapsed_msec = 0;
1607 
1608  /* initialize print options for partial table output */
1609  my_popt.topt.start_table = true;
1610  my_popt.topt.stop_table = false;
1611  my_popt.topt.prior_records = 0;
1612 
1613  if (pset.timing)
1614  INSTR_TIME_SET_CURRENT(before);
1615 
1616  /* if we're not in a transaction, start one */
1618  {
1619  results = PQexec(pset.db, "BEGIN");
1620  OK = AcceptResult(results) &&
1621  (PQresultStatus(results) == PGRES_COMMAND_OK);
1622  ClearOrSaveResult(results);
1623  if (!OK)
1624  return false;
1625  started_txn = true;
1626  }
1627 
1628  /* Send DECLARE CURSOR */
1629  initPQExpBuffer(&buf);
1630  appendPQExpBuffer(&buf, "DECLARE _psql_cursor NO SCROLL CURSOR FOR\n%s",
1631  query);
1632 
1633  results = PQexec(pset.db, buf.data);
1634  OK = AcceptResult(results) &&
1635  (PQresultStatus(results) == PGRES_COMMAND_OK);
1636  if (!OK)
1637  SetResultVariables(results, OK);
1638  ClearOrSaveResult(results);
1639  termPQExpBuffer(&buf);
1640  if (!OK)
1641  goto cleanup;
1642 
1643  if (pset.timing)
1644  {
1645  INSTR_TIME_SET_CURRENT(after);
1646  INSTR_TIME_SUBTRACT(after, before);
1647  *elapsed_msec += INSTR_TIME_GET_MILLISEC(after);
1648  }
1649 
1650  /*
1651  * In \gset mode, we force the fetch count to be 2, so that we will throw
1652  * the appropriate error if the query returns more than one row.
1653  */
1654  if (pset.gset_prefix)
1655  fetch_count = 2;
1656  else
1657  fetch_count = pset.fetch_count;
1658 
1659  snprintf(fetch_cmd, sizeof(fetch_cmd),
1660  "FETCH FORWARD %d FROM _psql_cursor",
1661  fetch_count);
1662 
1663  /* prepare to write output to \g argument, if any */
1664  if (pset.gfname)
1665  {
1666  if (!openQueryOutputFile(pset.gfname, &fout, &is_pipe))
1667  {
1668  OK = false;
1669  goto cleanup;
1670  }
1671  if (is_pipe)
1673  }
1674  else
1675  {
1676  fout = pset.queryFout;
1677  is_pipe = false; /* doesn't matter */
1678  }
1679 
1680  /* clear any pre-existing error indication on the output stream */
1681  clearerr(fout);
1682 
1683  for (;;)
1684  {
1685  if (pset.timing)
1686  INSTR_TIME_SET_CURRENT(before);
1687 
1688  /* get fetch_count tuples at a time */
1689  results = PQexec(pset.db, fetch_cmd);
1690 
1691  if (pset.timing)
1692  {
1693  INSTR_TIME_SET_CURRENT(after);
1694  INSTR_TIME_SUBTRACT(after, before);
1695  *elapsed_msec += INSTR_TIME_GET_MILLISEC(after);
1696  }
1697 
1698  if (PQresultStatus(results) != PGRES_TUPLES_OK)
1699  {
1700  /* shut down pager before printing error message */
1701  if (is_pager)
1702  {
1703  ClosePager(fout);
1704  is_pager = false;
1705  }
1706 
1707  OK = AcceptResult(results);
1708  Assert(!OK);
1709  SetResultVariables(results, OK);
1710  ClearOrSaveResult(results);
1711  break;
1712  }
1713 
1714  if (pset.gset_prefix)
1715  {
1716  /* StoreQueryTuple will complain if not exactly one row */
1717  OK = StoreQueryTuple(results);
1718  ClearOrSaveResult(results);
1719  break;
1720  }
1721 
1722  /*
1723  * Note we do not deal with \gdesc, \gexec or \crosstabview modes here
1724  */
1725 
1726  ntuples = PQntuples(results);
1727  total_tuples += ntuples;
1728 
1729  if (ntuples < fetch_count)
1730  {
1731  /* this is the last result set, so allow footer decoration */
1732  my_popt.topt.stop_table = true;
1733  }
1734  else if (fout == stdout && !is_pager)
1735  {
1736  /*
1737  * If query requires multiple result sets, hack to ensure that
1738  * only one pager instance is used for the whole mess
1739  */
1740  fout = PageOutput(INT_MAX, &(my_popt.topt));
1741  is_pager = true;
1742  }
1743 
1744  printQuery(results, &my_popt, fout, is_pager, pset.logfile);
1745 
1746  ClearOrSaveResult(results);
1747 
1748  /* after the first result set, disallow header decoration */
1749  my_popt.topt.start_table = false;
1750  my_popt.topt.prior_records += ntuples;
1751 
1752  /*
1753  * Make sure to flush the output stream, so intermediate results are
1754  * visible to the client immediately. We check the results because if
1755  * the pager dies/exits/etc, there's no sense throwing more data at
1756  * it.
1757  */
1758  flush_error = fflush(fout);
1759 
1760  /*
1761  * Check if we are at the end, if a cancel was pressed, or if there
1762  * were any errors either trying to flush out the results, or more
1763  * generally on the output stream at all. If we hit any errors
1764  * writing things to the stream, we presume $PAGER has disappeared and
1765  * stop bothering to pull down more data.
1766  */
1767  if (ntuples < fetch_count || cancel_pressed || flush_error ||
1768  ferror(fout))
1769  break;
1770  }
1771 
1772  if (pset.gfname)
1773  {
1774  /* close \g argument file/pipe */
1775  if (is_pipe)
1776  {
1777  pclose(fout);
1779  }
1780  else
1781  fclose(fout);
1782  }
1783  else if (is_pager)
1784  {
1785  /* close transient pager */
1786  ClosePager(fout);
1787  }
1788 
1789  if (OK)
1790  {
1791  /*
1792  * We don't have a PGresult here, and even if we did it wouldn't have
1793  * the right row count, so fake SetResultVariables(). In error cases,
1794  * we already set the result variables above.
1795  */
1796  char buf[32];
1797 
1798  SetVariable(pset.vars, "ERROR", "false");
1799  SetVariable(pset.vars, "SQLSTATE", "00000");
1800  snprintf(buf, sizeof(buf), INT64_FORMAT, total_tuples);
1801  SetVariable(pset.vars, "ROW_COUNT", buf);
1802  }
1803 
1804 cleanup:
1805  if (pset.timing)
1806  INSTR_TIME_SET_CURRENT(before);
1807 
1808  /*
1809  * We try to close the cursor on either success or failure, but on failure
1810  * ignore the result (it's probably just a bleat about being in an aborted
1811  * transaction)
1812  */
1813  results = PQexec(pset.db, "CLOSE _psql_cursor");
1814  if (OK)
1815  {
1816  OK = AcceptResult(results) &&
1817  (PQresultStatus(results) == PGRES_COMMAND_OK);
1818  ClearOrSaveResult(results);
1819  }
1820  else
1821  PQclear(results);
1822 
1823  if (started_txn)
1824  {
1825  results = PQexec(pset.db, OK ? "COMMIT" : "ROLLBACK");
1826  OK &= AcceptResult(results) &&
1827  (PQresultStatus(results) == PGRES_COMMAND_OK);
1828  ClearOrSaveResult(results);
1829  }
1830 
1831  if (pset.timing)
1832  {
1833  INSTR_TIME_SET_CURRENT(after);
1834  INSTR_TIME_SUBTRACT(after, before);
1835  *elapsed_msec += INSTR_TIME_GET_MILLISEC(after);
1836  }
1837 
1838  return OK;
1839 }
1840 
1841 
1842 /*
1843  * Advance the given char pointer over white space and SQL comments.
1844  */
1845 static const char *
1846 skip_white_space(const char *query)
1847 {
1848  int cnestlevel = 0; /* slash-star comment nest level */
1849 
1850  while (*query)
1851  {
1852  int mblen = PQmblenBounded(query, pset.encoding);
1853 
1854  /*
1855  * Note: we assume the encoding is a superset of ASCII, so that for
1856  * example "query[0] == '/'" is meaningful. However, we do NOT assume
1857  * that the second and subsequent bytes of a multibyte character
1858  * couldn't look like ASCII characters; so it is critical to advance
1859  * by mblen, not 1, whenever we haven't exactly identified the
1860  * character we are skipping over.
1861  */
1862  if (isspace((unsigned char) *query))
1863  query += mblen;
1864  else if (query[0] == '/' && query[1] == '*')
1865  {
1866  cnestlevel++;
1867  query += 2;
1868  }
1869  else if (cnestlevel > 0 && query[0] == '*' && query[1] == '/')
1870  {
1871  cnestlevel--;
1872  query += 2;
1873  }
1874  else if (cnestlevel == 0 && query[0] == '-' && query[1] == '-')
1875  {
1876  query += 2;
1877 
1878  /*
1879  * We have to skip to end of line since any slash-star inside the
1880  * -- comment does NOT start a slash-star comment.
1881  */
1882  while (*query)
1883  {
1884  if (*query == '\n')
1885  {
1886  query++;
1887  break;
1888  }
1889  query += PQmblenBounded(query, pset.encoding);
1890  }
1891  }
1892  else if (cnestlevel > 0)
1893  query += mblen;
1894  else
1895  break; /* found first token */
1896  }
1897 
1898  return query;
1899 }
1900 
1901 
1902 /*
1903  * Check whether a command is one of those for which we should NOT start
1904  * a new transaction block (ie, send a preceding BEGIN).
1905  *
1906  * These include the transaction control statements themselves, plus
1907  * certain statements that the backend disallows inside transaction blocks.
1908  */
1909 static bool
1910 command_no_begin(const char *query)
1911 {
1912  int wordlen;
1913 
1914  /*
1915  * First we must advance over any whitespace and comments.
1916  */
1917  query = skip_white_space(query);
1918 
1919  /*
1920  * Check word length (since "beginx" is not "begin").
1921  */
1922  wordlen = 0;
1923  while (isalpha((unsigned char) query[wordlen]))
1924  wordlen += PQmblenBounded(&query[wordlen], pset.encoding);
1925 
1926  /*
1927  * Transaction control commands. These should include every keyword that
1928  * gives rise to a TransactionStmt in the backend grammar, except for the
1929  * savepoint-related commands.
1930  *
1931  * (We assume that START must be START TRANSACTION, since there is
1932  * presently no other "START foo" command.)
1933  */
1934  if (wordlen == 5 && pg_strncasecmp(query, "abort", 5) == 0)
1935  return true;
1936  if (wordlen == 5 && pg_strncasecmp(query, "begin", 5) == 0)
1937  return true;
1938  if (wordlen == 5 && pg_strncasecmp(query, "start", 5) == 0)
1939  return true;
1940  if (wordlen == 6 && pg_strncasecmp(query, "commit", 6) == 0)
1941  return true;
1942  if (wordlen == 3 && pg_strncasecmp(query, "end", 3) == 0)
1943  return true;
1944  if (wordlen == 8 && pg_strncasecmp(query, "rollback", 8) == 0)
1945  return true;
1946  if (wordlen == 7 && pg_strncasecmp(query, "prepare", 7) == 0)
1947  {
1948  /* PREPARE TRANSACTION is a TC command, PREPARE foo is not */
1949  query += wordlen;
1950 
1951  query = skip_white_space(query);
1952 
1953  wordlen = 0;
1954  while (isalpha((unsigned char) query[wordlen]))
1955  wordlen += PQmblenBounded(&query[wordlen], pset.encoding);
1956 
1957  if (wordlen == 11 && pg_strncasecmp(query, "transaction", 11) == 0)
1958  return true;
1959  return false;
1960  }
1961 
1962  /*
1963  * Commands not allowed within transactions. The statements checked for
1964  * here should be exactly those that call PreventInTransactionBlock() in
1965  * the backend.
1966  */
1967  if (wordlen == 6 && pg_strncasecmp(query, "vacuum", 6) == 0)
1968  return true;
1969  if (wordlen == 7 && pg_strncasecmp(query, "cluster", 7) == 0)
1970  {
1971  /* CLUSTER with any arguments is allowed in transactions */
1972  query += wordlen;
1973 
1974  query = skip_white_space(query);
1975 
1976  if (isalpha((unsigned char) query[0]))
1977  return false; /* has additional words */
1978  return true; /* it's CLUSTER without arguments */
1979  }
1980 
1981  if (wordlen == 6 && pg_strncasecmp(query, "create", 6) == 0)
1982  {
1983  query += wordlen;
1984 
1985  query = skip_white_space(query);
1986 
1987  wordlen = 0;
1988  while (isalpha((unsigned char) query[wordlen]))
1989  wordlen += PQmblenBounded(&query[wordlen], pset.encoding);
1990 
1991  if (wordlen == 8 && pg_strncasecmp(query, "database", 8) == 0)
1992  return true;
1993  if (wordlen == 10 && pg_strncasecmp(query, "tablespace", 10) == 0)
1994  return true;
1995 
1996  /* CREATE [UNIQUE] INDEX CONCURRENTLY isn't allowed in xacts */
1997  if (wordlen == 6 && pg_strncasecmp(query, "unique", 6) == 0)
1998  {
1999  query += wordlen;
2000 
2001  query = skip_white_space(query);
2002 
2003  wordlen = 0;
2004  while (isalpha((unsigned char) query[wordlen]))
2005  wordlen += PQmblenBounded(&query[wordlen], pset.encoding);
2006  }
2007 
2008  if (wordlen == 5 && pg_strncasecmp(query, "index", 5) == 0)
2009  {
2010  query += wordlen;
2011 
2012  query = skip_white_space(query);
2013 
2014  wordlen = 0;
2015  while (isalpha((unsigned char) query[wordlen]))
2016  wordlen += PQmblenBounded(&query[wordlen], pset.encoding);
2017 
2018  if (wordlen == 12 && pg_strncasecmp(query, "concurrently", 12) == 0)
2019  return true;
2020  }
2021 
2022  return false;
2023  }
2024 
2025  if (wordlen == 5 && pg_strncasecmp(query, "alter", 5) == 0)
2026  {
2027  query += wordlen;
2028 
2029  query = skip_white_space(query);
2030 
2031  wordlen = 0;
2032  while (isalpha((unsigned char) query[wordlen]))
2033  wordlen += PQmblenBounded(&query[wordlen], pset.encoding);
2034 
2035  /* ALTER SYSTEM isn't allowed in xacts */
2036  if (wordlen == 6 && pg_strncasecmp(query, "system", 6) == 0)
2037  return true;
2038 
2039  return false;
2040  }
2041 
2042  /*
2043  * Note: these tests will match DROP SYSTEM and REINDEX TABLESPACE, which
2044  * aren't really valid commands so we don't care much. The other four
2045  * possible matches are correct.
2046  */
2047  if ((wordlen == 4 && pg_strncasecmp(query, "drop", 4) == 0) ||
2048  (wordlen == 7 && pg_strncasecmp(query, "reindex", 7) == 0))
2049  {
2050  query += wordlen;
2051 
2052  query = skip_white_space(query);
2053 
2054  wordlen = 0;
2055  while (isalpha((unsigned char) query[wordlen]))
2056  wordlen += PQmblenBounded(&query[wordlen], pset.encoding);
2057 
2058  if (wordlen == 8 && pg_strncasecmp(query, "database", 8) == 0)
2059  return true;
2060  if (wordlen == 6 && pg_strncasecmp(query, "system", 6) == 0)
2061  return true;
2062  if (wordlen == 10 && pg_strncasecmp(query, "tablespace", 10) == 0)
2063  return true;
2064  if (wordlen == 5 && (pg_strncasecmp(query, "index", 5) == 0 ||
2065  pg_strncasecmp(query, "table", 5) == 0))
2066  {
2067  query += wordlen;
2068  query = skip_white_space(query);
2069  wordlen = 0;
2070  while (isalpha((unsigned char) query[wordlen]))
2071  wordlen += PQmblenBounded(&query[wordlen], pset.encoding);
2072 
2073  /*
2074  * REINDEX [ TABLE | INDEX ] CONCURRENTLY are not allowed in
2075  * xacts.
2076  */
2077  if (wordlen == 12 && pg_strncasecmp(query, "concurrently", 12) == 0)
2078  return true;
2079  }
2080 
2081  /* DROP INDEX CONCURRENTLY isn't allowed in xacts */
2082  if (wordlen == 5 && pg_strncasecmp(query, "index", 5) == 0)
2083  {
2084  query += wordlen;
2085 
2086  query = skip_white_space(query);
2087 
2088  wordlen = 0;
2089  while (isalpha((unsigned char) query[wordlen]))
2090  wordlen += PQmblenBounded(&query[wordlen], pset.encoding);
2091 
2092  if (wordlen == 12 && pg_strncasecmp(query, "concurrently", 12) == 0)
2093  return true;
2094 
2095  return false;
2096  }
2097 
2098  return false;
2099  }
2100 
2101  /* DISCARD ALL isn't allowed in xacts, but other variants are allowed. */
2102  if (wordlen == 7 && pg_strncasecmp(query, "discard", 7) == 0)
2103  {
2104  query += wordlen;
2105 
2106  query = skip_white_space(query);
2107 
2108  wordlen = 0;
2109  while (isalpha((unsigned char) query[wordlen]))
2110  wordlen += PQmblenBounded(&query[wordlen], pset.encoding);
2111 
2112  if (wordlen == 3 && pg_strncasecmp(query, "all", 3) == 0)
2113  return true;
2114  return false;
2115  }
2116 
2117  return false;
2118 }
2119 
2120 
2121 /*
2122  * Check whether the specified command is a SELECT (or VALUES).
2123  */
2124 static bool
2125 is_select_command(const char *query)
2126 {
2127  int wordlen;
2128 
2129  /*
2130  * First advance over any whitespace, comments and left parentheses.
2131  */
2132  for (;;)
2133  {
2134  query = skip_white_space(query);
2135  if (query[0] == '(')
2136  query++;
2137  else
2138  break;
2139  }
2140 
2141  /*
2142  * Check word length (since "selectx" is not "select").
2143  */
2144  wordlen = 0;
2145  while (isalpha((unsigned char) query[wordlen]))
2146  wordlen += PQmblenBounded(&query[wordlen], pset.encoding);
2147 
2148  if (wordlen == 6 && pg_strncasecmp(query, "select", 6) == 0)
2149  return true;
2150 
2151  if (wordlen == 6 && pg_strncasecmp(query, "values", 6) == 0)
2152  return true;
2153 
2154  return false;
2155 }
2156 
2157 
2158 /*
2159  * Test if the current user is a database superuser.
2160  */
2161 bool
2163 {
2164  const char *val;
2165 
2166  if (!pset.db)
2167  return false;
2168 
2169  val = PQparameterStatus(pset.db, "is_superuser");
2170 
2171  if (val && strcmp(val, "on") == 0)
2172  return true;
2173 
2174  return false;
2175 }
2176 
2177 
2178 /*
2179  * Test if the current session uses standard string literals.
2180  */
2181 bool
2183 {
2184  const char *val;
2185 
2186  if (!pset.db)
2187  return false;
2188 
2189  val = PQparameterStatus(pset.db, "standard_conforming_strings");
2190 
2191  if (val && strcmp(val, "on") == 0)
2192  return true;
2193 
2194  return false;
2195 }
2196 
2197 
2198 /*
2199  * Return the session user of the current connection.
2200  */
2201 const char *
2203 {
2204  const char *val;
2205 
2206  if (!pset.db)
2207  return NULL;
2208 
2209  val = PQparameterStatus(pset.db, "session_authorization");
2210  if (val)
2211  return val;
2212  else
2213  return PQuser(pset.db);
2214 }
2215 
2216 
2217 /* expand_tilde
2218  *
2219  * substitute '~' with HOME or '~username' with username's home dir
2220  *
2221  */
2222 void
2224 {
2225  if (!filename || !(*filename))
2226  return;
2227 
2228  /*
2229  * WIN32 doesn't use tilde expansion for file names. Also, it uses tilde
2230  * for short versions of long file names, though the tilde is usually
2231  * toward the end, not at the beginning.
2232  */
2233 #ifndef WIN32
2234 
2235  /* try tilde expansion */
2236  if (**filename == '~')
2237  {
2238  char *fn;
2239  char oldp,
2240  *p;
2241  struct passwd *pw;
2242  char home[MAXPGPATH];
2243 
2244  fn = *filename;
2245  *home = '\0';
2246 
2247  p = fn + 1;
2248  while (*p != '/' && *p != '\0')
2249  p++;
2250 
2251  oldp = *p;
2252  *p = '\0';
2253 
2254  if (*(fn + 1) == '\0')
2255  get_home_path(home); /* ~ or ~/ only */
2256  else if ((pw = getpwnam(fn + 1)) != NULL)
2257  strlcpy(home, pw->pw_dir, sizeof(home)); /* ~user */
2258 
2259  *p = oldp;
2260  if (strlen(home) != 0)
2261  {
2262  char *newfn;
2263 
2264  newfn = psprintf("%s%s", home, p);
2265  free(fn);
2266  *filename = newfn;
2267  }
2268  }
2269 #endif
2270 }
2271 
2272 /*
2273  * Checks if connection string starts with either of the valid URI prefix
2274  * designators.
2275  *
2276  * Returns the URI prefix length, 0 if the string doesn't contain a URI prefix.
2277  *
2278  * XXX This is a duplicate of the eponymous libpq function.
2279  */
2280 static int
2282 {
2283  /* The connection URI must start with either of the following designators: */
2284  static const char uri_designator[] = "postgresql://";
2285  static const char short_uri_designator[] = "postgres://";
2286 
2287  if (strncmp(connstr, uri_designator,
2288  sizeof(uri_designator) - 1) == 0)
2289  return sizeof(uri_designator) - 1;
2290 
2291  if (strncmp(connstr, short_uri_designator,
2292  sizeof(short_uri_designator) - 1) == 0)
2293  return sizeof(short_uri_designator) - 1;
2294 
2295  return 0;
2296 }
2297 
2298 /*
2299  * Recognized connection string either starts with a valid URI prefix or
2300  * contains a "=" in it.
2301  *
2302  * Must be consistent with parse_connection_string: anything for which this
2303  * returns true should at least look like it's parseable by that routine.
2304  *
2305  * XXX This is a duplicate of the eponymous libpq function.
2306  */
2307 bool
2309 {
2310  return uri_prefix_length(connstr) != 0 || strchr(connstr, '=') != NULL;
2311 }
static void PrintQueryStatus(PGresult *results)
Definition: common.c:1086
PSQL_ECHO echo
Definition: settings.h:142
bool singlestep
Definition: settings.h:136
char * gset_prefix
Definition: settings.h:96
char * extra
Definition: libpq-fe.h:189
static bool PrintQueryResults(PGresult *results)
Definition: common.c:1118
int PQnfields(const PGresult *res)
Definition: fe-exec.c:3256
PGresult * PQprepare(PGconn *conn, const char *stmtName, const char *query, int nParams, const Oid *paramTypes)
Definition: fe-exec.c:2237
PGconn * db
Definition: settings.h:82
char * PQerrorMessage(const PGconn *conn)
Definition: fe-connect.c:6744
PGresult * PQdescribePrepared(PGconn *conn, const char *stmt)
Definition: fe-exec.c:2386
void printfPQExpBuffer(PQExpBuffer str, const char *fmt,...)
Definition: pqexpbuffer.c:237
bool conditional_active(ConditionalStack cstack)
Definition: conditional.c:128
volatile bool sigint_interrupt_enabled
Definition: common.c:245
#define PG_DIAG_MESSAGE_PRIMARY
Definition: postgres_ext.h:58
int encoding
Definition: print.h:122
PsqlSettings pset
Definition: startup.c:32
static void ClearOrSaveResult(PGresult *result)
Definition: common.c:455
void SyncVariables(void)
Definition: command.c:3661
char * PQgetvalue(const PGresult *res, int tup_num, int field_num)
Definition: fe-exec.c:3642
static void error(void)
Definition: sql-dyntest.c:147
const char * PQparameterStatus(const PGconn *conn, const char *paramName)
Definition: fe-connect.c:6709
PGnotify * PQnotifies(PGconn *conn)
Definition: fe-exec.c:2516
char * PQfname(const PGresult *res, int field_num)
Definition: fe-exec.c:3334
void disable_sigpipe_trap(void)
Definition: print.c:2925
void termPQExpBuffer(PQExpBuffer str)
Definition: pqexpbuffer.c:131
#define pg_log_error(...)
Definition: logging.h:80
void ResetCancelConn(void)
Definition: cancel.c:100
char * PQcmdTuples(PGresult *res)
Definition: fe-exec.c:3589
bool appendShellStringNoError(PQExpBuffer buf, const char *str)
Definition: string_utils.c:441
static bool ExecQueryTuples(const PGresult *result)
Definition: common.c:829
void appendPQExpBufferStr(PQExpBuffer str, const char *data)
Definition: pqexpbuffer.c:369
void ClosePager(FILE *pagerpipe)
Definition: print.c:3026
static bool PrintQueryTuples(const PGresult *results)
Definition: common.c:715
static void SetResultVariables(PGresult *results, bool success)
Definition: common.c:413
char * psprintf(const char *fmt,...)
Definition: psprintf.c:46
bool recognized_connection_string(const char *connstr)
Definition: common.c:2308
#define INSTR_TIME_GET_MILLISEC(t)
Definition: instr_time.h:202
Oid PQoidValue(const PGresult *res)
Definition: fe-exec.c:3560
struct timeval instr_time
Definition: instr_time.h:150
bool gexec_flag
Definition: settings.h:98
bool start_table
Definition: print.h:111
enum printFormat format
Definition: print.h:101
printTableOpt topt
Definition: print.h:169
static void PrintTiming(double elapsed_msec)
Definition: common.c:481
printQueryOpt * gsavepopt
Definition: settings.h:94
bool queryFoutPipe
Definition: settings.h:85
#define gettext_noop(x)
Definition: c.h:1197
FILE * queryFout
Definition: settings.h:84
void set_sigpipe_trap_state(bool ignore)
Definition: print.c:2961
void PQfinish(PGconn *conn)
Definition: fe-connect.c:4231
static bool CheckConnection(void)
Definition: common.c:295
#define printf(...)
Definition: port.h:222
static bool ConnectionUp(void)
Definition: common.c:277
ExecStatusType
Definition: libpq-fe.h:92
static void setup_cancel_handler(void)
Definition: parallel.c:613
bool on_error_stop
Definition: settings.h:133
bool autocommit
Definition: settings.h:132
#define lengthof(array)
Definition: c.h:734
int PQbinaryTuples(const PGresult *res)
Definition: fe-exec.c:3264
int PQntuples(const PGresult *res)
Definition: fe-exec.c:3248
#define PG_DIAG_SQLSTATE
Definition: postgres_ext.h:57
#define fprintf
Definition: port.h:220
unsigned long prior_records
Definition: print.h:114
FILE * copyStream
Definition: settings.h:87
PSQL_ERROR_ROLLBACK on_error_rollback
Definition: settings.h:144
int PQclientEncoding(const PGconn *conn)
Definition: fe-connect.c:6821
ExecStatusType PQresultStatus(const PGresult *res)
Definition: fe-exec.c:3178
FILE * cur_cmd_source
Definition: settings.h:105
void UnsyncVariables(void)
Definition: command.c:3702
static bool AcceptResult(const PGresult *result)
Definition: common.c:356
char * PQuser(const PGconn *conn)
Definition: fe-connect.c:6598
sigjmp_buf sigint_interrupt_jmp
Definition: common.c:247
#define EXIT_BADCONN
Definition: settings.h:165
static void PrintNotifications(void)
Definition: common.c:688
static int uri_prefix_length(const char *connstr)
Definition: common.c:2281
int pg_strncasecmp(const char *s1, const char *s2, size_t n)
Definition: pgstrcasecmp.c:69
char * ctv_args[4]
Definition: settings.h:100
char * PQescapeIdentifier(PGconn *conn, const char *str, size_t len)
Definition: fe-exec.c:4075
static int before(chr x, chr y)
Definition: regc_locale.c:492
bool cur_cmd_interactive
Definition: settings.h:107
PSQL_ECHO_HIDDEN echo_hidden
Definition: settings.h:143
FILE * PageOutput(int lines, const printTableOpt *topt)
Definition: print.c:2975
static bool is_select_command(const char *query)
Definition: common.c:2125
#define INSTR_TIME_SUBTRACT(x, y)
Definition: instr_time.h:170
int be_pid
Definition: libpq-fe.h:188
void expand_tilde(char **filename)
Definition: common.c:2223
#define MAXPGPATH
void appendPQExpBuffer(PQExpBuffer str, const char *fmt,...)
Definition: pqexpbuffer.c:267
void restorePsetInfo(printQueryOpt *popt, printQueryOpt *save)
Definition: command.c:4700
Oid PQftype(const PGresult *res, int field_num)
Definition: fe-exec.c:3486
bool gdesc_flag
Definition: settings.h:97
char * c
static char * buf
Definition: pg_test_fsync.c:68
const char * session_username(void)
Definition: common.c:2202
int fetch_count
Definition: settings.h:139
static bool ProcessResult(PGresult **results)
Definition: common.c:913
char * pg_strdup(const char *in)
Definition: fe_memutils.c:85
bool handleCopyOut(PGconn *conn, FILE *copystream, PGresult **res)
Definition: copy.c:436
void SetCancelConn(PGconn *conn)
Definition: cancel.c:70
bool PrintResultsInCrosstab(const PGresult *res)
Definition: crosstabview.c:103
const char *const days[]
Definition: datetime.c:68
char * relname
Definition: libpq-fe.h:187
void restore_sigpipe_trap(void)
Definition: print.c:2948
static bool ExecQueryUsingCursor(const char *query, double *elapsed_msec)
Definition: common.c:1588
PsqlScanQuoteType
Definition: psqlscan.h:52
PGTransactionStatusType PQtransactionStatus(const PGconn *conn)
Definition: fe-connect.c:6699
const char * GetVariable(VariableSpace space, const char *name)
Definition: variables.c:71
static bool DescribeQuery(const char *query, double *elapsed_msec)
Definition: common.c:1472
char * PQcmdStatus(PGresult *res)
Definition: fe-exec.c:3519
bool openQueryOutputFile(const char *fname, FILE **fout, bool *is_pipe)
Definition: common.c:50
char * gfname
Definition: settings.h:93
bool setQFout(const char *fname)
Definition: common.c:85
bool VariableHasHook(VariableSpace space, const char *name)
Definition: variables.c:368
static void cleanup(void)
Definition: bootstrap.c:697
int PQconsumeInput(PGconn *conn)
Definition: fe-exec.c:1904
PGresult * last_error_result
Definition: settings.h:89
FILE * logfile
Definition: settings.h:116
char * PQescapeLiteral(PGconn *conn, const char *str, size_t len)
Definition: fe-exec.c:4069
volatile sig_atomic_t cancel_pressed
Definition: print.c:43
static struct @143 value
bool stop_table
Definition: print.h:112
void PQclear(PGresult *res)
Definition: fe-exec.c:694
static void * fn(void *arg)
bool is_superuser(void)
Definition: common.c:2162
bool standard_strings(void)
Definition: common.c:2182
#define free(a)
Definition: header.h:65
static void psql_cancel_callback(void)
Definition: common.c:250
void NoticeProcessor(void *arg, const char *message)
Definition: common.c:220
size_t strlcpy(char *dst, const char *src, size_t siz)
Definition: strlcpy.c:45
const char * pg_encoding_to_char(int encoding)
Definition: encnames.c:588
bool handleCopyIn(PGconn *conn, FILE *copystream, bool isbinary, PGresult **res)
Definition: copy.c:513
PGTransactionStatusType
Definition: libpq-fe.h:114
char * title
Definition: print.h:171
char * PQresultErrorField(const PGresult *res, int fieldcode)
Definition: fe-exec.c:3233
#define Assert(condition)
Definition: c.h:804
bool SetVariable(VariableSpace space, const char *name, const char *value)
Definition: variables.c:211
printQueryOpt popt
Definition: settings.h:91
int PQfmod(const PGresult *res, int field_num)
Definition: fe-exec.c:3508
PGconn * dead_conn
Definition: settings.h:125
void printQuery(const PGresult *result, const printQueryOpt *opt, FILE *fout, bool is_pager, FILE *flog)
Definition: print.c:3420
void pg_free(void *ptr)
Definition: fe_memutils.c:105
#define INSTR_TIME_SET_CURRENT(t)
Definition: instr_time.h:156
#define INT64_FORMAT
Definition: c.h:483
const char * name
Definition: encode.c:561
static const char short_uri_designator[]
Definition: fe-connect.c:372
char * psql_get_variable(const char *varname, PsqlScanQuoteType quote, void *passthrough)
Definition: common.c:129
int PQmblenBounded(const char *s, int encoding)
Definition: fe-misc.c:1202
static char * filename
Definition: pg_dumpall.c:92
void psql_setup_cancel_handler(void)
Definition: common.c:266
static const char uri_designator[]
Definition: fe-connect.c:371
int i
static bool StoreQueryTuple(const PGresult *result)
Definition: common.c:765
int PSQLexecWatch(const char *query, const printQueryOpt *opt, FILE *printQueryFout)
Definition: common.c:595
void html_escaped_print(const char *in, FILE *fout)
Definition: print.c:1838
bool crosstab_flag
Definition: settings.h:99
PGresult * PQexec(PGconn *conn, const char *query)
Definition: fe-exec.c:2193
void * arg
bool SendQuery(const char *query)
Definition: common.c:1193
void connection_warnings(bool in_startup)
Definition: command.c:3538
#define pg_log_warning(...)
Definition: pgfnames.c:24
int encoding
Definition: settings.h:83
int PQgetisnull(const PGresult *res, int tup_num, int field_num)
Definition: fe-exec.c:3667
ConnStatusType PQstatus(const PGconn *conn)
Definition: fe-connect.c:6691
static bool command_no_begin(const char *query)
Definition: common.c:1910
static bool success
Definition: initdb.c:165
#define snprintf
Definition: port.h:216
#define _(x)
Definition: elog.c:89
void PQfreemem(void *ptr)
Definition: fe-exec.c:3796
long val
Definition: informix.c:664
PGresult * PQgetResult(PGconn *conn)
Definition: fe-exec.c:1978
static const char * skip_white_space(const char *query)
Definition: common.c:1846
void initPQExpBuffer(PQExpBuffer str)
Definition: pqexpbuffer.c:92
#define pg_log_info(...)
Definition: logging.h:88
void PQreset(PGconn *conn)
Definition: fe-connect.c:4245
bool get_home_path(char *ret_path)
Definition: path.c:807
char * formatPGVersionNumber(int version_number, bool include_minor, char *buf, size_t buflen)
Definition: string_utils.c:177
PGresult * PSQLexec(const char *query)
Definition: common.c:540
VariableSpace vars
Definition: settings.h:118
static char * connstr
Definition: pg_dumpall.c:62
#define pg_log_fatal(...)
Definition: logging.h:76