PostgreSQL Source Code  git master
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros
command.c
Go to the documentation of this file.
1 /*
2  * psql - the PostgreSQL interactive terminal
3  *
4  * Copyright (c) 2000-2017, PostgreSQL Global Development Group
5  *
6  * src/bin/psql/command.c
7  */
8 #include "postgres_fe.h"
9 #include "command.h"
10 
11 #include <ctype.h>
12 #include <time.h>
13 #include <pwd.h>
14 #ifndef WIN32
15 #include <sys/stat.h> /* for stat() */
16 #include <fcntl.h> /* open() flags */
17 #include <unistd.h> /* for geteuid(), getpid(), stat() */
18 #else
19 #include <win32.h>
20 #include <io.h>
21 #include <fcntl.h>
22 #include <direct.h>
23 #include <sys/stat.h> /* for stat() */
24 #endif
25 
26 #include "catalog/pg_class.h"
27 #include "portability/instr_time.h"
28 
29 #include "libpq-fe.h"
30 #include "pqexpbuffer.h"
31 #include "fe_utils/string_utils.h"
32 
33 #include "common.h"
34 #include "copy.h"
35 #include "crosstabview.h"
36 #include "describe.h"
37 #include "help.h"
38 #include "input.h"
39 #include "large_obj.h"
40 #include "mainloop.h"
41 #include "fe_utils/print.h"
42 #include "psqlscanslash.h"
43 #include "settings.h"
44 #include "variables.h"
45 
46 /*
47  * Editable database object types.
48  */
49 typedef enum EditableObjectType
50 {
54 
55 /* local function declarations */
56 static backslashResult exec_command(const char *cmd,
57  PsqlScanState scan_state,
58  ConditionalStack cstack,
59  PQExpBuffer query_buf,
60  PQExpBuffer previous_buf);
61 static backslashResult exec_command_a(PsqlScanState scan_state, bool active_branch);
62 static backslashResult exec_command_C(PsqlScanState scan_state, bool active_branch);
63 static backslashResult exec_command_connect(PsqlScanState scan_state, bool active_branch);
64 static backslashResult exec_command_cd(PsqlScanState scan_state, bool active_branch,
65  const char *cmd);
66 static backslashResult exec_command_conninfo(PsqlScanState scan_state, bool active_branch);
67 static backslashResult exec_command_copy(PsqlScanState scan_state, bool active_branch);
68 static backslashResult exec_command_copyright(PsqlScanState scan_state, bool active_branch);
69 static backslashResult exec_command_crosstabview(PsqlScanState scan_state, bool active_branch);
70 static backslashResult exec_command_d(PsqlScanState scan_state, bool active_branch,
71  const char *cmd);
72 static backslashResult exec_command_edit(PsqlScanState scan_state, bool active_branch,
73  PQExpBuffer query_buf, PQExpBuffer previous_buf);
74 static backslashResult exec_command_ef(PsqlScanState scan_state, bool active_branch,
75  PQExpBuffer query_buf);
76 static backslashResult exec_command_ev(PsqlScanState scan_state, bool active_branch,
77  PQExpBuffer query_buf);
78 static backslashResult exec_command_echo(PsqlScanState scan_state, bool active_branch,
79  const char *cmd);
81  PQExpBuffer query_buf);
83  PQExpBuffer query_buf);
85  PQExpBuffer query_buf);
86 static backslashResult exec_command_encoding(PsqlScanState scan_state, bool active_branch);
87 static backslashResult exec_command_errverbose(PsqlScanState scan_state, bool active_branch);
88 static backslashResult exec_command_f(PsqlScanState scan_state, bool active_branch);
89 static backslashResult exec_command_g(PsqlScanState scan_state, bool active_branch,
90  const char *cmd);
91 static backslashResult exec_command_gexec(PsqlScanState scan_state, bool active_branch);
92 static backslashResult exec_command_gset(PsqlScanState scan_state, bool active_branch);
93 static backslashResult exec_command_help(PsqlScanState scan_state, bool active_branch);
94 static backslashResult exec_command_html(PsqlScanState scan_state, bool active_branch);
95 static backslashResult exec_command_include(PsqlScanState scan_state, bool active_branch,
96  const char *cmd);
98  PQExpBuffer query_buf);
99 static backslashResult exec_command_list(PsqlScanState scan_state, bool active_branch,
100  const char *cmd);
101 static backslashResult exec_command_lo(PsqlScanState scan_state, bool active_branch,
102  const char *cmd);
103 static backslashResult exec_command_out(PsqlScanState scan_state, bool active_branch);
104 static backslashResult exec_command_print(PsqlScanState scan_state, bool active_branch,
105  PQExpBuffer query_buf, PQExpBuffer previous_buf);
106 static backslashResult exec_command_password(PsqlScanState scan_state, bool active_branch);
107 static backslashResult exec_command_prompt(PsqlScanState scan_state, bool active_branch,
108  const char *cmd);
109 static backslashResult exec_command_pset(PsqlScanState scan_state, bool active_branch);
110 static backslashResult exec_command_quit(PsqlScanState scan_state, bool active_branch);
111 static backslashResult exec_command_reset(PsqlScanState scan_state, bool active_branch,
112  PQExpBuffer query_buf);
113 static backslashResult exec_command_s(PsqlScanState scan_state, bool active_branch);
114 static backslashResult exec_command_set(PsqlScanState scan_state, bool active_branch);
115 static backslashResult exec_command_setenv(PsqlScanState scan_state, bool active_branch,
116  const char *cmd);
117 static backslashResult exec_command_sf(PsqlScanState scan_state, bool active_branch,
118  const char *cmd);
119 static backslashResult exec_command_sv(PsqlScanState scan_state, bool active_branch,
120  const char *cmd);
121 static backslashResult exec_command_t(PsqlScanState scan_state, bool active_branch);
122 static backslashResult exec_command_T(PsqlScanState scan_state, bool active_branch);
123 static backslashResult exec_command_timing(PsqlScanState scan_state, bool active_branch);
124 static backslashResult exec_command_unset(PsqlScanState scan_state, bool active_branch,
125  const char *cmd);
126 static backslashResult exec_command_write(PsqlScanState scan_state, bool active_branch,
127  const char *cmd,
128  PQExpBuffer query_buf, PQExpBuffer previous_buf);
129 static backslashResult exec_command_watch(PsqlScanState scan_state, bool active_branch,
130  PQExpBuffer query_buf, PQExpBuffer previous_buf);
131 static backslashResult exec_command_x(PsqlScanState scan_state, bool active_branch);
132 static backslashResult exec_command_z(PsqlScanState scan_state, bool active_branch);
133 static backslashResult exec_command_shell_escape(PsqlScanState scan_state, bool active_branch);
134 static backslashResult exec_command_slash_command_help(PsqlScanState scan_state, bool active_branch);
135 static char *read_connect_arg(PsqlScanState scan_state);
137 static bool is_true_boolean_expression(PsqlScanState scan_state, const char *name);
138 static void ignore_boolean_expression(PsqlScanState scan_state);
139 static void ignore_slash_options(PsqlScanState scan_state);
140 static void ignore_slash_filepipe(PsqlScanState scan_state);
141 static void ignore_slash_whole_line(PsqlScanState scan_state);
142 static bool is_branching_command(const char *cmd);
143 static void save_query_text_state(PsqlScanState scan_state, ConditionalStack cstack,
144  PQExpBuffer query_buf);
145 static void discard_query_text(PsqlScanState scan_state, ConditionalStack cstack,
146  PQExpBuffer query_buf);
147 static void copy_previous_query(PQExpBuffer query_buf, PQExpBuffer previous_buf);
148 static bool do_connect(enum trivalue reuse_previous_specification,
149  char *dbname, char *user, char *host, char *port);
150 static bool do_edit(const char *filename_arg, PQExpBuffer query_buf,
151  int lineno, bool *edited);
152 static bool do_shell(const char *command);
153 static bool do_watch(PQExpBuffer query_buf, double sleep);
154 static bool lookup_object_oid(EditableObjectType obj_type, const char *desc,
155  Oid *obj_oid);
156 static bool get_create_object_cmd(EditableObjectType obj_type, Oid oid,
157  PQExpBuffer buf);
158 static int strip_lineno_from_objdesc(char *obj);
160 static void print_with_linenumbers(FILE *output, char *lines,
161  const char *header_keyword);
162 static void minimal_error_message(PGresult *res);
163 
164 static void printSSLInfo(void);
165 static bool printPsetInfo(const char *param, struct printQueryOpt *popt);
166 static char *pset_value_string(const char *param, struct printQueryOpt *popt);
167 
168 #ifdef WIN32
169 static void checkWin32Codepage(void);
170 #endif
171 
172 
173 
174 /*----------
175  * HandleSlashCmds:
176  *
177  * Handles all the different commands that start with '\'.
178  * Ordinarily called by MainLoop().
179  *
180  * scan_state is a lexer working state that is set to continue scanning
181  * just after the '\'. The lexer is advanced past the command and all
182  * arguments on return.
183  *
184  * cstack is the current \if stack state. This will be examined, and
185  * possibly modified by conditional commands.
186  *
187  * query_buf contains the query-so-far, which may be modified by
188  * execution of the backslash command (for example, \r clears it).
189  *
190  * previous_buf contains the query most recently sent to the server
191  * (empty if none yet). This should not be modified here, but some
192  * commands copy its content into query_buf.
193  *
194  * query_buf and previous_buf will be NULL when executing a "-c"
195  * command-line option.
196  *
197  * Returns a status code indicating what action is desired, see command.h.
198  *----------
199  */
200 
203  ConditionalStack cstack,
204  PQExpBuffer query_buf,
205  PQExpBuffer previous_buf)
206 {
208  char *cmd;
209  char *arg;
210 
211  Assert(scan_state != NULL);
212  Assert(cstack != NULL);
213 
214  /* Parse off the command name */
215  cmd = psql_scan_slash_command(scan_state);
216 
217  /* And try to execute it */
218  status = exec_command(cmd, scan_state, cstack, query_buf, previous_buf);
219 
220  if (status == PSQL_CMD_UNKNOWN)
221  {
223  psql_error("Invalid command \\%s. Try \\? for help.\n", cmd);
224  else
225  psql_error("invalid command \\%s\n", cmd);
226  status = PSQL_CMD_ERROR;
227  }
228 
229  if (status != PSQL_CMD_ERROR)
230  {
231  /*
232  * Eat any remaining arguments after a valid command. We want to
233  * suppress evaluation of backticks in this situation, so transiently
234  * push an inactive conditional-stack entry.
235  */
236  bool active_branch = conditional_active(cstack);
237 
239  while ((arg = psql_scan_slash_option(scan_state,
240  OT_NORMAL, NULL, false)))
241  {
242  if (active_branch)
243  psql_error("\\%s: extra argument \"%s\" ignored\n", cmd, arg);
244  free(arg);
245  }
246  conditional_stack_pop(cstack);
247  }
248  else
249  {
250  /* silently throw away rest of line after an erroneous command */
251  while ((arg = psql_scan_slash_option(scan_state,
252  OT_WHOLE_LINE, NULL, false)))
253  free(arg);
254  }
255 
256  /* if there is a trailing \\, swallow it */
257  psql_scan_slash_command_end(scan_state);
258 
259  free(cmd);
260 
261  /* some commands write to queryFout, so make sure output is sent */
262  fflush(pset.queryFout);
263 
264  return status;
265 }
266 
267 
268 /*
269  * Subroutine to actually try to execute a backslash command.
270  *
271  * The typical "success" result code is PSQL_CMD_SKIP_LINE, although some
272  * commands return something else. Failure results are PSQL_CMD_ERROR,
273  * unless PSQL_CMD_UNKNOWN is more appropriate.
274  */
275 static backslashResult
276 exec_command(const char *cmd,
277  PsqlScanState scan_state,
278  ConditionalStack cstack,
279  PQExpBuffer query_buf,
280  PQExpBuffer previous_buf)
281 {
283  bool active_branch = conditional_active(cstack);
284 
285  /*
286  * In interactive mode, warn when we're ignoring a command within a false
287  * \if-branch. But we continue on, so as to parse and discard the right
288  * amount of parameter text. Each individual backslash command subroutine
289  * is responsible for doing nothing after discarding appropriate
290  * arguments, if !active_branch.
291  */
292  if (pset.cur_cmd_interactive && !active_branch &&
293  !is_branching_command(cmd))
294  {
295  psql_error("\\%s command ignored; use \\endif or Ctrl-C to exit current \\if block\n",
296  cmd);
297  }
298 
299  if (strcmp(cmd, "a") == 0)
300  status = exec_command_a(scan_state, active_branch);
301  else if (strcmp(cmd, "C") == 0)
302  status = exec_command_C(scan_state, active_branch);
303  else if (strcmp(cmd, "c") == 0 || strcmp(cmd, "connect") == 0)
304  status = exec_command_connect(scan_state, active_branch);
305  else if (strcmp(cmd, "cd") == 0)
306  status = exec_command_cd(scan_state, active_branch, cmd);
307  else if (strcmp(cmd, "conninfo") == 0)
308  status = exec_command_conninfo(scan_state, active_branch);
309  else if (pg_strcasecmp(cmd, "copy") == 0)
310  status = exec_command_copy(scan_state, active_branch);
311  else if (strcmp(cmd, "copyright") == 0)
312  status = exec_command_copyright(scan_state, active_branch);
313  else if (strcmp(cmd, "crosstabview") == 0)
314  status = exec_command_crosstabview(scan_state, active_branch);
315  else if (cmd[0] == 'd')
316  status = exec_command_d(scan_state, active_branch, cmd);
317  else if (strcmp(cmd, "e") == 0 || strcmp(cmd, "edit") == 0)
318  status = exec_command_edit(scan_state, active_branch,
319  query_buf, previous_buf);
320  else if (strcmp(cmd, "ef") == 0)
321  status = exec_command_ef(scan_state, active_branch, query_buf);
322  else if (strcmp(cmd, "ev") == 0)
323  status = exec_command_ev(scan_state, active_branch, query_buf);
324  else if (strcmp(cmd, "echo") == 0 || strcmp(cmd, "qecho") == 0)
325  status = exec_command_echo(scan_state, active_branch, cmd);
326  else if (strcmp(cmd, "elif") == 0)
327  status = exec_command_elif(scan_state, cstack, query_buf);
328  else if (strcmp(cmd, "else") == 0)
329  status = exec_command_else(scan_state, cstack, query_buf);
330  else if (strcmp(cmd, "endif") == 0)
331  status = exec_command_endif(scan_state, cstack, query_buf);
332  else if (strcmp(cmd, "encoding") == 0)
333  status = exec_command_encoding(scan_state, active_branch);
334  else if (strcmp(cmd, "errverbose") == 0)
335  status = exec_command_errverbose(scan_state, active_branch);
336  else if (strcmp(cmd, "f") == 0)
337  status = exec_command_f(scan_state, active_branch);
338  else if (strcmp(cmd, "g") == 0 || strcmp(cmd, "gx") == 0)
339  status = exec_command_g(scan_state, active_branch, cmd);
340  else if (strcmp(cmd, "gexec") == 0)
341  status = exec_command_gexec(scan_state, active_branch);
342  else if (strcmp(cmd, "gset") == 0)
343  status = exec_command_gset(scan_state, active_branch);
344  else if (strcmp(cmd, "h") == 0 || strcmp(cmd, "help") == 0)
345  status = exec_command_help(scan_state, active_branch);
346  else if (strcmp(cmd, "H") == 0 || strcmp(cmd, "html") == 0)
347  status = exec_command_html(scan_state, active_branch);
348  else if (strcmp(cmd, "i") == 0 || strcmp(cmd, "include") == 0 ||
349  strcmp(cmd, "ir") == 0 || strcmp(cmd, "include_relative") == 0)
350  status = exec_command_include(scan_state, active_branch, cmd);
351  else if (strcmp(cmd, "if") == 0)
352  status = exec_command_if(scan_state, cstack, query_buf);
353  else if (strcmp(cmd, "l") == 0 || strcmp(cmd, "list") == 0 ||
354  strcmp(cmd, "l+") == 0 || strcmp(cmd, "list+") == 0)
355  status = exec_command_list(scan_state, active_branch, cmd);
356  else if (strncmp(cmd, "lo_", 3) == 0)
357  status = exec_command_lo(scan_state, active_branch, cmd);
358  else if (strcmp(cmd, "o") == 0 || strcmp(cmd, "out") == 0)
359  status = exec_command_out(scan_state, active_branch);
360  else if (strcmp(cmd, "p") == 0 || strcmp(cmd, "print") == 0)
361  status = exec_command_print(scan_state, active_branch,
362  query_buf, previous_buf);
363  else if (strcmp(cmd, "password") == 0)
364  status = exec_command_password(scan_state, active_branch);
365  else if (strcmp(cmd, "prompt") == 0)
366  status = exec_command_prompt(scan_state, active_branch, cmd);
367  else if (strcmp(cmd, "pset") == 0)
368  status = exec_command_pset(scan_state, active_branch);
369  else if (strcmp(cmd, "q") == 0 || strcmp(cmd, "quit") == 0)
370  status = exec_command_quit(scan_state, active_branch);
371  else if (strcmp(cmd, "r") == 0 || strcmp(cmd, "reset") == 0)
372  status = exec_command_reset(scan_state, active_branch, query_buf);
373  else if (strcmp(cmd, "s") == 0)
374  status = exec_command_s(scan_state, active_branch);
375  else if (strcmp(cmd, "set") == 0)
376  status = exec_command_set(scan_state, active_branch);
377  else if (strcmp(cmd, "setenv") == 0)
378  status = exec_command_setenv(scan_state, active_branch, cmd);
379  else if (strcmp(cmd, "sf") == 0 || strcmp(cmd, "sf+") == 0)
380  status = exec_command_sf(scan_state, active_branch, cmd);
381  else if (strcmp(cmd, "sv") == 0 || strcmp(cmd, "sv+") == 0)
382  status = exec_command_sv(scan_state, active_branch, cmd);
383  else if (strcmp(cmd, "t") == 0)
384  status = exec_command_t(scan_state, active_branch);
385  else if (strcmp(cmd, "T") == 0)
386  status = exec_command_T(scan_state, active_branch);
387  else if (strcmp(cmd, "timing") == 0)
388  status = exec_command_timing(scan_state, active_branch);
389  else if (strcmp(cmd, "unset") == 0)
390  status = exec_command_unset(scan_state, active_branch, cmd);
391  else if (strcmp(cmd, "w") == 0 || strcmp(cmd, "write") == 0)
392  status = exec_command_write(scan_state, active_branch, cmd,
393  query_buf, previous_buf);
394  else if (strcmp(cmd, "watch") == 0)
395  status = exec_command_watch(scan_state, active_branch,
396  query_buf, previous_buf);
397  else if (strcmp(cmd, "x") == 0)
398  status = exec_command_x(scan_state, active_branch);
399  else if (strcmp(cmd, "z") == 0)
400  status = exec_command_z(scan_state, active_branch);
401  else if (strcmp(cmd, "!") == 0)
402  status = exec_command_shell_escape(scan_state, active_branch);
403  else if (strcmp(cmd, "?") == 0)
404  status = exec_command_slash_command_help(scan_state, active_branch);
405  else
406  status = PSQL_CMD_UNKNOWN;
407 
408  /*
409  * All the commands that return PSQL_CMD_SEND want to execute previous_buf
410  * if query_buf is empty. For convenience we implement that here, not in
411  * the individual command subroutines.
412  */
413  if (status == PSQL_CMD_SEND)
414  copy_previous_query(query_buf, previous_buf);
415 
416  return status;
417 }
418 
419 
420 /*
421  * \a -- toggle field alignment
422  *
423  * This makes little sense but we keep it around.
424  */
425 static backslashResult
426 exec_command_a(PsqlScanState scan_state, bool active_branch)
427 {
428  bool success = true;
429 
430  if (active_branch)
431  {
433  success = do_pset("format", "aligned", &pset.popt, pset.quiet);
434  else
435  success = do_pset("format", "unaligned", &pset.popt, pset.quiet);
436  }
437 
438  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
439 }
440 
441 /*
442  * \C -- override table title (formerly change HTML caption)
443  */
444 static backslashResult
445 exec_command_C(PsqlScanState scan_state, bool active_branch)
446 {
447  bool success = true;
448 
449  if (active_branch)
450  {
451  char *opt = psql_scan_slash_option(scan_state,
452  OT_NORMAL, NULL, true);
453 
454  success = do_pset("title", opt, &pset.popt, pset.quiet);
455  free(opt);
456  }
457  else
458  ignore_slash_options(scan_state);
459 
460  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
461 }
462 
463 /*
464  * \c or \connect -- connect to database using the specified parameters.
465  *
466  * \c [-reuse-previous=BOOL] dbname user host port
467  *
468  * Specifying a parameter as '-' is equivalent to omitting it. Examples:
469  *
470  * \c - - hst Connect to current database on current port of
471  * host "hst" as current user.
472  * \c - usr - prt Connect to current database on port "prt" of current host
473  * as user "usr".
474  * \c dbs Connect to database "dbs" on current port of current host
475  * as current user.
476  */
477 static backslashResult
478 exec_command_connect(PsqlScanState scan_state, bool active_branch)
479 {
480  bool success = true;
481 
482  if (active_branch)
483  {
484  static const char prefix[] = "-reuse-previous=";
485  char *opt1,
486  *opt2,
487  *opt3,
488  *opt4;
489  enum trivalue reuse_previous = TRI_DEFAULT;
490 
491  opt1 = read_connect_arg(scan_state);
492  if (opt1 != NULL && strncmp(opt1, prefix, sizeof(prefix) - 1) == 0)
493  {
494  bool on_off;
495 
496  success = ParseVariableBool(opt1 + sizeof(prefix) - 1,
497  "-reuse-previous",
498  &on_off);
499  if (success)
500  {
501  reuse_previous = on_off ? TRI_YES : TRI_NO;
502  free(opt1);
503  opt1 = read_connect_arg(scan_state);
504  }
505  }
506 
507  if (success) /* give up if reuse_previous was invalid */
508  {
509  opt2 = read_connect_arg(scan_state);
510  opt3 = read_connect_arg(scan_state);
511  opt4 = read_connect_arg(scan_state);
512 
513  success = do_connect(reuse_previous, opt1, opt2, opt3, opt4);
514 
515  free(opt2);
516  free(opt3);
517  free(opt4);
518  }
519  free(opt1);
520  }
521  else
522  ignore_slash_options(scan_state);
523 
524  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
525 }
526 
527 /*
528  * \cd -- change directory
529  */
530 static backslashResult
531 exec_command_cd(PsqlScanState scan_state, bool active_branch, const char *cmd)
532 {
533  bool success = true;
534 
535  if (active_branch)
536  {
537  char *opt = psql_scan_slash_option(scan_state,
538  OT_NORMAL, NULL, true);
539  char *dir;
540 
541  if (opt)
542  dir = opt;
543  else
544  {
545 #ifndef WIN32
546  struct passwd *pw;
547  uid_t user_id = geteuid();
548 
549  errno = 0; /* clear errno before call */
550  pw = getpwuid(user_id);
551  if (!pw)
552  {
553  psql_error("could not get home directory for user ID %ld: %s\n",
554  (long) user_id,
555  errno ? strerror(errno) : _("user does not exist"));
556  exit(EXIT_FAILURE);
557  }
558  dir = pw->pw_dir;
559 #else /* WIN32 */
560 
561  /*
562  * On Windows, 'cd' without arguments prints the current
563  * directory, so if someone wants to code this here instead...
564  */
565  dir = "/";
566 #endif /* WIN32 */
567  }
568 
569  if (chdir(dir) == -1)
570  {
571  psql_error("\\%s: could not change directory to \"%s\": %s\n",
572  cmd, dir, strerror(errno));
573  success = false;
574  }
575 
576  if (opt)
577  free(opt);
578  }
579  else
580  ignore_slash_options(scan_state);
581 
582  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
583 }
584 
585 /*
586  * \conninfo -- display information about the current connection
587  */
588 static backslashResult
589 exec_command_conninfo(PsqlScanState scan_state, bool active_branch)
590 {
591  if (active_branch)
592  {
593  char *db = PQdb(pset.db);
594 
595  if (db == NULL)
596  printf(_("You are currently not connected to a database.\n"));
597  else
598  {
599  char *host;
600  PQconninfoOption *connOptions;
602 
603  host = PQhost(pset.db);
604  /* A usable "hostaddr" overrides the basic sense of host. */
605  connOptions = PQconninfo(pset.db);
606  if (connOptions == NULL)
607  {
608  psql_error("out of memory\n");
609  exit(EXIT_FAILURE);
610  }
611  for (option = connOptions; option && option->keyword; option++)
612  if (strcmp(option->keyword, "hostaddr") == 0)
613  {
614  if (option->val != NULL && option->val[0] != '\0')
615  host = option->val;
616  break;
617  }
618 
619  /* If the host is an absolute path, the connection is via socket */
620  if (is_absolute_path(host))
621  printf(_("You are connected to database \"%s\" as user \"%s\" via socket in \"%s\" at port \"%s\".\n"),
622  db, PQuser(pset.db), host, PQport(pset.db));
623  else
624  printf(_("You are connected to database \"%s\" as user \"%s\" on host \"%s\" at port \"%s\".\n"),
625  db, PQuser(pset.db), host, PQport(pset.db));
626  printSSLInfo();
627 
628  PQconninfoFree(connOptions);
629  }
630  }
631 
632  return PSQL_CMD_SKIP_LINE;
633 }
634 
635 /*
636  * \copy -- run a COPY command
637  */
638 static backslashResult
639 exec_command_copy(PsqlScanState scan_state, bool active_branch)
640 {
641  bool success = true;
642 
643  if (active_branch)
644  {
645  char *opt = psql_scan_slash_option(scan_state,
646  OT_WHOLE_LINE, NULL, false);
647 
648  success = do_copy(opt);
649  free(opt);
650  }
651  else
652  ignore_slash_whole_line(scan_state);
653 
654  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
655 }
656 
657 /*
658  * \copyright -- print copyright notice
659  */
660 static backslashResult
661 exec_command_copyright(PsqlScanState scan_state, bool active_branch)
662 {
663  if (active_branch)
664  print_copyright();
665 
666  return PSQL_CMD_SKIP_LINE;
667 }
668 
669 /*
670  * \crosstabview -- execute a query and display results in crosstab
671  */
672 static backslashResult
673 exec_command_crosstabview(PsqlScanState scan_state, bool active_branch)
674 {
676 
677  if (active_branch)
678  {
679  int i;
680 
681  for (i = 0; i < lengthof(pset.ctv_args); i++)
682  pset.ctv_args[i] = psql_scan_slash_option(scan_state,
683  OT_NORMAL, NULL, true);
684  pset.crosstab_flag = true;
685  status = PSQL_CMD_SEND;
686  }
687  else
688  ignore_slash_options(scan_state);
689 
690  return status;
691 }
692 
693 /*
694  * \d* commands
695  */
696 static backslashResult
697 exec_command_d(PsqlScanState scan_state, bool active_branch, const char *cmd)
698 {
700  bool success = true;
701 
702  if (active_branch)
703  {
704  char *pattern;
705  bool show_verbose,
706  show_system;
707 
708  /* We don't do SQLID reduction on the pattern yet */
709  pattern = psql_scan_slash_option(scan_state,
710  OT_NORMAL, NULL, true);
711 
712  show_verbose = strchr(cmd, '+') ? true : false;
713  show_system = strchr(cmd, 'S') ? true : false;
714 
715  switch (cmd[1])
716  {
717  case '\0':
718  case '+':
719  case 'S':
720  if (pattern)
721  success = describeTableDetails(pattern, show_verbose, show_system);
722  else
723  /* standard listing of interesting things */
724  success = listTables("tvmsE", NULL, show_verbose, show_system);
725  break;
726  case 'A':
727  success = describeAccessMethods(pattern, show_verbose);
728  break;
729  case 'a':
730  success = describeAggregates(pattern, show_verbose, show_system);
731  break;
732  case 'b':
733  success = describeTablespaces(pattern, show_verbose);
734  break;
735  case 'c':
736  success = listConversions(pattern, show_verbose, show_system);
737  break;
738  case 'C':
739  success = listCasts(pattern, show_verbose);
740  break;
741  case 'd':
742  if (strncmp(cmd, "ddp", 3) == 0)
743  success = listDefaultACLs(pattern);
744  else
745  success = objectDescription(pattern, show_system);
746  break;
747  case 'D':
748  success = listDomains(pattern, show_verbose, show_system);
749  break;
750  case 'f': /* function subsystem */
751  switch (cmd[2])
752  {
753  case '\0':
754  case '+':
755  case 'S':
756  case 'a':
757  case 'n':
758  case 't':
759  case 'w':
760  success = describeFunctions(&cmd[2], pattern, show_verbose, show_system);
761  break;
762  default:
763  status = PSQL_CMD_UNKNOWN;
764  break;
765  }
766  break;
767  case 'g':
768  /* no longer distinct from \du */
769  success = describeRoles(pattern, show_verbose, show_system);
770  break;
771  case 'l':
772  success = do_lo_list();
773  break;
774  case 'L':
775  success = listLanguages(pattern, show_verbose, show_system);
776  break;
777  case 'n':
778  success = listSchemas(pattern, show_verbose, show_system);
779  break;
780  case 'o':
781  success = describeOperators(pattern, show_verbose, show_system);
782  break;
783  case 'O':
784  success = listCollations(pattern, show_verbose, show_system);
785  break;
786  case 'p':
787  success = permissionsList(pattern);
788  break;
789  case 'T':
790  success = describeTypes(pattern, show_verbose, show_system);
791  break;
792  case 't':
793  case 'v':
794  case 'm':
795  case 'i':
796  case 's':
797  case 'E':
798  success = listTables(&cmd[1], pattern, show_verbose, show_system);
799  break;
800  case 'r':
801  if (cmd[2] == 'd' && cmd[3] == 's')
802  {
803  char *pattern2 = NULL;
804 
805  if (pattern)
806  pattern2 = psql_scan_slash_option(scan_state,
807  OT_NORMAL, NULL, true);
808  success = listDbRoleSettings(pattern, pattern2);
809  }
810  else
811  status = PSQL_CMD_UNKNOWN;
812  break;
813  case 'R':
814  switch (cmd[2])
815  {
816  case 'p':
817  if (show_verbose)
818  success = describePublications(pattern);
819  else
820  success = listPublications(pattern);
821  break;
822  case 's':
823  success = describeSubscriptions(pattern, show_verbose);
824  break;
825  default:
826  status = PSQL_CMD_UNKNOWN;
827  }
828  break;
829  case 'u':
830  success = describeRoles(pattern, show_verbose, show_system);
831  break;
832  case 'F': /* text search subsystem */
833  switch (cmd[2])
834  {
835  case '\0':
836  case '+':
837  success = listTSConfigs(pattern, show_verbose);
838  break;
839  case 'p':
840  success = listTSParsers(pattern, show_verbose);
841  break;
842  case 'd':
843  success = listTSDictionaries(pattern, show_verbose);
844  break;
845  case 't':
846  success = listTSTemplates(pattern, show_verbose);
847  break;
848  default:
849  status = PSQL_CMD_UNKNOWN;
850  break;
851  }
852  break;
853  case 'e': /* SQL/MED subsystem */
854  switch (cmd[2])
855  {
856  case 's':
857  success = listForeignServers(pattern, show_verbose);
858  break;
859  case 'u':
860  success = listUserMappings(pattern, show_verbose);
861  break;
862  case 'w':
863  success = listForeignDataWrappers(pattern, show_verbose);
864  break;
865  case 't':
866  success = listForeignTables(pattern, show_verbose);
867  break;
868  default:
869  status = PSQL_CMD_UNKNOWN;
870  break;
871  }
872  break;
873  case 'x': /* Extensions */
874  if (show_verbose)
875  success = listExtensionContents(pattern);
876  else
877  success = listExtensions(pattern);
878  break;
879  case 'y': /* Event Triggers */
880  success = listEventTriggers(pattern, show_verbose);
881  break;
882  default:
883  status = PSQL_CMD_UNKNOWN;
884  }
885 
886  if (pattern)
887  free(pattern);
888  }
889  else
890  ignore_slash_options(scan_state);
891 
892  if (!success)
893  status = PSQL_CMD_ERROR;
894 
895  return status;
896 }
897 
898 /*
899  * \e or \edit -- edit the current query buffer, or edit a file and
900  * make it the query buffer
901  */
902 static backslashResult
903 exec_command_edit(PsqlScanState scan_state, bool active_branch,
904  PQExpBuffer query_buf, PQExpBuffer previous_buf)
905 {
907 
908  if (active_branch)
909  {
910  if (!query_buf)
911  {
912  psql_error("no query buffer\n");
913  status = PSQL_CMD_ERROR;
914  }
915  else
916  {
917  char *fname;
918  char *ln = NULL;
919  int lineno = -1;
920 
921  fname = psql_scan_slash_option(scan_state,
922  OT_NORMAL, NULL, true);
923  if (fname)
924  {
925  /* try to get separate lineno arg */
926  ln = psql_scan_slash_option(scan_state,
927  OT_NORMAL, NULL, true);
928  if (ln == NULL)
929  {
930  /* only one arg; maybe it is lineno not fname */
931  if (fname[0] &&
932  strspn(fname, "0123456789") == strlen(fname))
933  {
934  /* all digits, so assume it is lineno */
935  ln = fname;
936  fname = NULL;
937  }
938  }
939  }
940  if (ln)
941  {
942  lineno = atoi(ln);
943  if (lineno < 1)
944  {
945  psql_error("invalid line number: %s\n", ln);
946  status = PSQL_CMD_ERROR;
947  }
948  }
949  if (status != PSQL_CMD_ERROR)
950  {
951  expand_tilde(&fname);
952  if (fname)
953  canonicalize_path(fname);
954 
955  /* If query_buf is empty, recall previous query for editing */
956  copy_previous_query(query_buf, previous_buf);
957 
958  if (do_edit(fname, query_buf, lineno, NULL))
959  status = PSQL_CMD_NEWEDIT;
960  else
961  status = PSQL_CMD_ERROR;
962  }
963  if (fname)
964  free(fname);
965  if (ln)
966  free(ln);
967  }
968  }
969  else
970  ignore_slash_options(scan_state);
971 
972  return status;
973 }
974 
975 /*
976  * \ef -- edit the named function, or present a blank CREATE FUNCTION
977  * template if no argument is given
978  */
979 static backslashResult
980 exec_command_ef(PsqlScanState scan_state, bool active_branch,
981  PQExpBuffer query_buf)
982 {
984 
985  if (active_branch)
986  {
987  char *func = psql_scan_slash_option(scan_state,
988  OT_WHOLE_LINE, NULL, true);
989  int lineno = -1;
990 
991  if (pset.sversion < 80400)
992  {
993  char sverbuf[32];
994 
995  psql_error("The server (version %s) does not support editing function source.\n",
997  sverbuf, sizeof(sverbuf)));
998  status = PSQL_CMD_ERROR;
999  }
1000  else if (!query_buf)
1001  {
1002  psql_error("no query buffer\n");
1003  status = PSQL_CMD_ERROR;
1004  }
1005  else
1006  {
1007  Oid foid = InvalidOid;
1008 
1009  lineno = strip_lineno_from_objdesc(func);
1010  if (lineno == 0)
1011  {
1012  /* error already reported */
1013  status = PSQL_CMD_ERROR;
1014  }
1015  else if (!func)
1016  {
1017  /* set up an empty command to fill in */
1018  printfPQExpBuffer(query_buf,
1019  "CREATE FUNCTION ( )\n"
1020  " RETURNS \n"
1021  " LANGUAGE \n"
1022  " -- common options: IMMUTABLE STABLE STRICT SECURITY DEFINER\n"
1023  "AS $function$\n"
1024  "\n$function$\n");
1025  }
1026  else if (!lookup_object_oid(EditableFunction, func, &foid))
1027  {
1028  /* error already reported */
1029  status = PSQL_CMD_ERROR;
1030  }
1031  else if (!get_create_object_cmd(EditableFunction, foid, query_buf))
1032  {
1033  /* error already reported */
1034  status = PSQL_CMD_ERROR;
1035  }
1036  else if (lineno > 0)
1037  {
1038  /*
1039  * lineno "1" should correspond to the first line of the
1040  * function body. We expect that pg_get_functiondef() will
1041  * emit that on a line beginning with "AS ", and that there
1042  * can be no such line before the real start of the function
1043  * body. Increment lineno by the number of lines before that
1044  * line, so that it becomes relative to the first line of the
1045  * function definition.
1046  */
1047  const char *lines = query_buf->data;
1048 
1049  while (*lines != '\0')
1050  {
1051  if (strncmp(lines, "AS ", 3) == 0)
1052  break;
1053  lineno++;
1054  /* find start of next line */
1055  lines = strchr(lines, '\n');
1056  if (!lines)
1057  break;
1058  lines++;
1059  }
1060  }
1061  }
1062 
1063  if (status != PSQL_CMD_ERROR)
1064  {
1065  bool edited = false;
1066 
1067  if (!do_edit(NULL, query_buf, lineno, &edited))
1068  status = PSQL_CMD_ERROR;
1069  else if (!edited)
1070  puts(_("No changes"));
1071  else
1072  status = PSQL_CMD_NEWEDIT;
1073  }
1074 
1075  if (func)
1076  free(func);
1077  }
1078  else
1079  ignore_slash_whole_line(scan_state);
1080 
1081  return status;
1082 }
1083 
1084 /*
1085  * \ev -- edit the named view, or present a blank CREATE VIEW
1086  * template if no argument is given
1087  */
1088 static backslashResult
1089 exec_command_ev(PsqlScanState scan_state, bool active_branch,
1090  PQExpBuffer query_buf)
1091 {
1093 
1094  if (active_branch)
1095  {
1096  char *view = psql_scan_slash_option(scan_state,
1097  OT_WHOLE_LINE, NULL, true);
1098  int lineno = -1;
1099 
1100  if (pset.sversion < 70400)
1101  {
1102  char sverbuf[32];
1103 
1104  psql_error("The server (version %s) does not support editing view definitions.\n",
1106  sverbuf, sizeof(sverbuf)));
1107  status = PSQL_CMD_ERROR;
1108  }
1109  else if (!query_buf)
1110  {
1111  psql_error("no query buffer\n");
1112  status = PSQL_CMD_ERROR;
1113  }
1114  else
1115  {
1116  Oid view_oid = InvalidOid;
1117 
1118  lineno = strip_lineno_from_objdesc(view);
1119  if (lineno == 0)
1120  {
1121  /* error already reported */
1122  status = PSQL_CMD_ERROR;
1123  }
1124  else if (!view)
1125  {
1126  /* set up an empty command to fill in */
1127  printfPQExpBuffer(query_buf,
1128  "CREATE VIEW AS\n"
1129  " SELECT \n"
1130  " -- something...\n");
1131  }
1132  else if (!lookup_object_oid(EditableView, view, &view_oid))
1133  {
1134  /* error already reported */
1135  status = PSQL_CMD_ERROR;
1136  }
1137  else if (!get_create_object_cmd(EditableView, view_oid, query_buf))
1138  {
1139  /* error already reported */
1140  status = PSQL_CMD_ERROR;
1141  }
1142  }
1143 
1144  if (status != PSQL_CMD_ERROR)
1145  {
1146  bool edited = false;
1147 
1148  if (!do_edit(NULL, query_buf, lineno, &edited))
1149  status = PSQL_CMD_ERROR;
1150  else if (!edited)
1151  puts(_("No changes"));
1152  else
1153  status = PSQL_CMD_NEWEDIT;
1154  }
1155 
1156  if (view)
1157  free(view);
1158  }
1159  else
1160  ignore_slash_whole_line(scan_state);
1161 
1162  return status;
1163 }
1164 
1165 /*
1166  * \echo and \qecho -- echo arguments to stdout or query output
1167  */
1168 static backslashResult
1169 exec_command_echo(PsqlScanState scan_state, bool active_branch, const char *cmd)
1170 {
1171  if (active_branch)
1172  {
1173  char *value;
1174  char quoted;
1175  bool no_newline = false;
1176  bool first = true;
1177  FILE *fout;
1178 
1179  if (strcmp(cmd, "qecho") == 0)
1180  fout = pset.queryFout;
1181  else
1182  fout = stdout;
1183 
1184  while ((value = psql_scan_slash_option(scan_state,
1185  OT_NORMAL, &quoted, false)))
1186  {
1187  if (!quoted && strcmp(value, "-n") == 0)
1188  no_newline = true;
1189  else
1190  {
1191  if (first)
1192  first = false;
1193  else
1194  fputc(' ', fout);
1195  fputs(value, fout);
1196  }
1197  free(value);
1198  }
1199  if (!no_newline)
1200  fputs("\n", fout);
1201  }
1202  else
1203  ignore_slash_options(scan_state);
1204 
1205  return PSQL_CMD_SKIP_LINE;
1206 }
1207 
1208 /*
1209  * \encoding -- set/show client side encoding
1210  */
1211 static backslashResult
1212 exec_command_encoding(PsqlScanState scan_state, bool active_branch)
1213 {
1214  if (active_branch)
1215  {
1216  char *encoding = psql_scan_slash_option(scan_state,
1217  OT_NORMAL, NULL, false);
1218 
1219  if (!encoding)
1220  {
1221  /* show encoding */
1223  }
1224  else
1225  {
1226  /* set encoding */
1227  if (PQsetClientEncoding(pset.db, encoding) == -1)
1228  psql_error("%s: invalid encoding name or conversion procedure not found\n", encoding);
1229  else
1230  {
1231  /* save encoding info into psql internal data */
1234  SetVariable(pset.vars, "ENCODING",
1236  }
1237  free(encoding);
1238  }
1239  }
1240  else
1241  ignore_slash_options(scan_state);
1242 
1243  return PSQL_CMD_SKIP_LINE;
1244 }
1245 
1246 /*
1247  * \errverbose -- display verbose message from last failed query
1248  */
1249 static backslashResult
1250 exec_command_errverbose(PsqlScanState scan_state, bool active_branch)
1251 {
1252  if (active_branch)
1253  {
1254  if (pset.last_error_result)
1255  {
1256  char *msg;
1257 
1261  if (msg)
1262  {
1263  psql_error("%s", msg);
1264  PQfreemem(msg);
1265  }
1266  else
1267  puts(_("out of memory"));
1268  }
1269  else
1270  puts(_("There is no previous error."));
1271  }
1272 
1273  return PSQL_CMD_SKIP_LINE;
1274 }
1275 
1276 /*
1277  * \f -- change field separator
1278  */
1279 static backslashResult
1280 exec_command_f(PsqlScanState scan_state, bool active_branch)
1281 {
1282  bool success = true;
1283 
1284  if (active_branch)
1285  {
1286  char *fname = psql_scan_slash_option(scan_state,
1287  OT_NORMAL, NULL, false);
1288 
1289  success = do_pset("fieldsep", fname, &pset.popt, pset.quiet);
1290  free(fname);
1291  }
1292  else
1293  ignore_slash_options(scan_state);
1294 
1295  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
1296 }
1297 
1298 /*
1299  * \g [filename] -- send query, optionally with output to file/pipe
1300  * \gx [filename] -- same as \g, with expanded mode forced
1301  */
1302 static backslashResult
1303 exec_command_g(PsqlScanState scan_state, bool active_branch, const char *cmd)
1304 {
1306 
1307  if (active_branch)
1308  {
1309  char *fname = psql_scan_slash_option(scan_state,
1310  OT_FILEPIPE, NULL, false);
1311 
1312  if (!fname)
1313  pset.gfname = NULL;
1314  else
1315  {
1316  expand_tilde(&fname);
1317  pset.gfname = pg_strdup(fname);
1318  }
1319  free(fname);
1320  if (strcmp(cmd, "gx") == 0)
1321  pset.g_expanded = true;
1322  status = PSQL_CMD_SEND;
1323  }
1324  else
1325  ignore_slash_filepipe(scan_state);
1326 
1327  return status;
1328 }
1329 
1330 /*
1331  * \gexec -- send query and execute each field of result
1332  */
1333 static backslashResult
1334 exec_command_gexec(PsqlScanState scan_state, bool active_branch)
1335 {
1337 
1338  if (active_branch)
1339  {
1340  pset.gexec_flag = true;
1341  status = PSQL_CMD_SEND;
1342  }
1343 
1344  return status;
1345 }
1346 
1347 /*
1348  * \gset [prefix] -- send query and store result into variables
1349  */
1350 static backslashResult
1351 exec_command_gset(PsqlScanState scan_state, bool active_branch)
1352 {
1354 
1355  if (active_branch)
1356  {
1357  char *prefix = psql_scan_slash_option(scan_state,
1358  OT_NORMAL, NULL, false);
1359 
1360  if (prefix)
1361  pset.gset_prefix = prefix;
1362  else
1363  {
1364  /* we must set a non-NULL prefix to trigger storing */
1365  pset.gset_prefix = pg_strdup("");
1366  }
1367  /* gset_prefix is freed later */
1368  status = PSQL_CMD_SEND;
1369  }
1370  else
1371  ignore_slash_options(scan_state);
1372 
1373  return status;
1374 }
1375 
1376 /*
1377  * \help [topic] -- print help about SQL commands
1378  */
1379 static backslashResult
1380 exec_command_help(PsqlScanState scan_state, bool active_branch)
1381 {
1382  if (active_branch)
1383  {
1384  char *opt = psql_scan_slash_option(scan_state,
1385  OT_WHOLE_LINE, NULL, false);
1386  size_t len;
1387 
1388  /* strip any trailing spaces and semicolons */
1389  if (opt)
1390  {
1391  len = strlen(opt);
1392  while (len > 0 &&
1393  (isspace((unsigned char) opt[len - 1])
1394  || opt[len - 1] == ';'))
1395  opt[--len] = '\0';
1396  }
1397 
1398  helpSQL(opt, pset.popt.topt.pager);
1399  free(opt);
1400  }
1401  else
1402  ignore_slash_whole_line(scan_state);
1403 
1404  return PSQL_CMD_SKIP_LINE;
1405 }
1406 
1407 /*
1408  * \H and \html -- toggle HTML formatting
1409  */
1410 static backslashResult
1411 exec_command_html(PsqlScanState scan_state, bool active_branch)
1412 {
1413  bool success = true;
1414 
1415  if (active_branch)
1416  {
1417  if (pset.popt.topt.format != PRINT_HTML)
1418  success = do_pset("format", "html", &pset.popt, pset.quiet);
1419  else
1420  success = do_pset("format", "aligned", &pset.popt, pset.quiet);
1421  }
1422 
1423  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
1424 }
1425 
1426 /*
1427  * \i and \ir -- include a file
1428  */
1429 static backslashResult
1430 exec_command_include(PsqlScanState scan_state, bool active_branch, const char *cmd)
1431 {
1432  bool success = true;
1433 
1434  if (active_branch)
1435  {
1436  char *fname = psql_scan_slash_option(scan_state,
1437  OT_NORMAL, NULL, true);
1438 
1439  if (!fname)
1440  {
1441  psql_error("\\%s: missing required argument\n", cmd);
1442  success = false;
1443  }
1444  else
1445  {
1446  bool include_relative;
1447 
1448  include_relative = (strcmp(cmd, "ir") == 0
1449  || strcmp(cmd, "include_relative") == 0);
1450  expand_tilde(&fname);
1451  success = (process_file(fname, include_relative) == EXIT_SUCCESS);
1452  free(fname);
1453  }
1454  }
1455  else
1456  ignore_slash_options(scan_state);
1457 
1458  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
1459 }
1460 
1461 /*
1462  * \if <expr> -- beginning of an \if..\endif block
1463  *
1464  * <expr> is parsed as a boolean expression. Invalid expressions will emit a
1465  * warning and be treated as false. Statements that follow a false expression
1466  * will be parsed but ignored. Note that in the case where an \if statement
1467  * is itself within an inactive section of a block, then the entire inner
1468  * \if..\endif block will be parsed but ignored.
1469  */
1470 static backslashResult
1472  PQExpBuffer query_buf)
1473 {
1474  if (conditional_active(cstack))
1475  {
1476  /*
1477  * First, push a new active stack entry; this ensures that the lexer
1478  * will perform variable substitution and backtick evaluation while
1479  * scanning the expression. (That should happen anyway, since we know
1480  * we're in an active outer branch, but let's be sure.)
1481  */
1483 
1484  /* Remember current query state in case we need to restore later */
1485  save_query_text_state(scan_state, cstack, query_buf);
1486 
1487  /*
1488  * Evaluate the expression; if it's false, change to inactive state.
1489  */
1490  if (!is_true_boolean_expression(scan_state, "\\if expression"))
1492  }
1493  else
1494  {
1495  /*
1496  * We're within an inactive outer branch, so this entire \if block
1497  * will be ignored. We don't want to evaluate the expression, so push
1498  * the "ignored" stack state before scanning it.
1499  */
1501 
1502  /* Remember current query state in case we need to restore later */
1503  save_query_text_state(scan_state, cstack, query_buf);
1504 
1505  ignore_boolean_expression(scan_state);
1506  }
1507 
1508  return PSQL_CMD_SKIP_LINE;
1509 }
1510 
1511 /*
1512  * \elif <expr> -- alternative branch in an \if..\endif block
1513  *
1514  * <expr> is evaluated the same as in \if <expr>.
1515  */
1516 static backslashResult
1518  PQExpBuffer query_buf)
1519 {
1520  bool success = true;
1521 
1522  switch (conditional_stack_peek(cstack))
1523  {
1524  case IFSTATE_TRUE:
1525 
1526  /*
1527  * Just finished active branch of this \if block. Update saved
1528  * state so we will keep whatever data was put in query_buf by the
1529  * active branch.
1530  */
1531  save_query_text_state(scan_state, cstack, query_buf);
1532 
1533  /*
1534  * Discard \elif expression and ignore the rest until \endif.
1535  * Switch state before reading expression to ensure proper lexer
1536  * behavior.
1537  */
1539  ignore_boolean_expression(scan_state);
1540  break;
1541  case IFSTATE_FALSE:
1542 
1543  /*
1544  * Discard any query text added by the just-skipped branch.
1545  */
1546  discard_query_text(scan_state, cstack, query_buf);
1547 
1548  /*
1549  * Have not yet found a true expression in this \if block, so this
1550  * might be the first. We have to change state before examining
1551  * the expression, or the lexer won't do the right thing.
1552  */
1554  if (!is_true_boolean_expression(scan_state, "\\elif expression"))
1556  break;
1557  case IFSTATE_IGNORED:
1558 
1559  /*
1560  * Discard any query text added by the just-skipped branch.
1561  */
1562  discard_query_text(scan_state, cstack, query_buf);
1563 
1564  /*
1565  * Skip expression and move on. Either the \if block already had
1566  * an active section, or whole block is being skipped.
1567  */
1568  ignore_boolean_expression(scan_state);
1569  break;
1570  case IFSTATE_ELSE_TRUE:
1571  case IFSTATE_ELSE_FALSE:
1572  psql_error("\\elif: cannot occur after \\else\n");
1573  success = false;
1574  break;
1575  case IFSTATE_NONE:
1576  /* no \if to elif from */
1577  psql_error("\\elif: no matching \\if\n");
1578  success = false;
1579  break;
1580  }
1581 
1582  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
1583 }
1584 
1585 /*
1586  * \else -- final alternative in an \if..\endif block
1587  *
1588  * Statements within an \else branch will only be executed if
1589  * all previous \if and \elif expressions evaluated to false
1590  * and the block was not itself being ignored.
1591  */
1592 static backslashResult
1594  PQExpBuffer query_buf)
1595 {
1596  bool success = true;
1597 
1598  switch (conditional_stack_peek(cstack))
1599  {
1600  case IFSTATE_TRUE:
1601 
1602  /*
1603  * Just finished active branch of this \if block. Update saved
1604  * state so we will keep whatever data was put in query_buf by the
1605  * active branch.
1606  */
1607  save_query_text_state(scan_state, cstack, query_buf);
1608 
1609  /* Now skip the \else branch */
1611  break;
1612  case IFSTATE_FALSE:
1613 
1614  /*
1615  * Discard any query text added by the just-skipped branch.
1616  */
1617  discard_query_text(scan_state, cstack, query_buf);
1618 
1619  /*
1620  * We've not found any true \if or \elif expression, so execute
1621  * the \else branch.
1622  */
1624  break;
1625  case IFSTATE_IGNORED:
1626 
1627  /*
1628  * Discard any query text added by the just-skipped branch.
1629  */
1630  discard_query_text(scan_state, cstack, query_buf);
1631 
1632  /*
1633  * Either we previously processed the active branch of this \if,
1634  * or the whole \if block is being skipped. Either way, skip the
1635  * \else branch.
1636  */
1638  break;
1639  case IFSTATE_ELSE_TRUE:
1640  case IFSTATE_ELSE_FALSE:
1641  psql_error("\\else: cannot occur after \\else\n");
1642  success = false;
1643  break;
1644  case IFSTATE_NONE:
1645  /* no \if to else from */
1646  psql_error("\\else: no matching \\if\n");
1647  success = false;
1648  break;
1649  }
1650 
1651  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
1652 }
1653 
1654 /*
1655  * \endif -- ends an \if...\endif block
1656  */
1657 static backslashResult
1659  PQExpBuffer query_buf)
1660 {
1661  bool success = true;
1662 
1663  switch (conditional_stack_peek(cstack))
1664  {
1665  case IFSTATE_TRUE:
1666  case IFSTATE_ELSE_TRUE:
1667  /* Close the \if block, keeping the query text */
1668  success = conditional_stack_pop(cstack);
1669  Assert(success);
1670  break;
1671  case IFSTATE_FALSE:
1672  case IFSTATE_IGNORED:
1673  case IFSTATE_ELSE_FALSE:
1674 
1675  /*
1676  * Discard any query text added by the just-skipped branch.
1677  */
1678  discard_query_text(scan_state, cstack, query_buf);
1679 
1680  /* Close the \if block */
1681  success = conditional_stack_pop(cstack);
1682  Assert(success);
1683  break;
1684  case IFSTATE_NONE:
1685  /* no \if to end */
1686  psql_error("\\endif: no matching \\if\n");
1687  success = false;
1688  break;
1689  }
1690 
1691  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
1692 }
1693 
1694 /*
1695  * \l -- list databases
1696  */
1697 static backslashResult
1698 exec_command_list(PsqlScanState scan_state, bool active_branch, const char *cmd)
1699 {
1700  bool success = true;
1701 
1702  if (active_branch)
1703  {
1704  char *pattern;
1705  bool show_verbose;
1706 
1707  pattern = psql_scan_slash_option(scan_state,
1708  OT_NORMAL, NULL, true);
1709 
1710  show_verbose = strchr(cmd, '+') ? true : false;
1711 
1712  success = listAllDbs(pattern, show_verbose);
1713 
1714  if (pattern)
1715  free(pattern);
1716  }
1717  else
1718  ignore_slash_options(scan_state);
1719 
1720  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
1721 }
1722 
1723 /*
1724  * \lo_* -- large object operations
1725  */
1726 static backslashResult
1727 exec_command_lo(PsqlScanState scan_state, bool active_branch, const char *cmd)
1728 {
1730  bool success = true;
1731 
1732  if (active_branch)
1733  {
1734  char *opt1,
1735  *opt2;
1736 
1737  opt1 = psql_scan_slash_option(scan_state,
1738  OT_NORMAL, NULL, true);
1739  opt2 = psql_scan_slash_option(scan_state,
1740  OT_NORMAL, NULL, true);
1741 
1742  if (strcmp(cmd + 3, "export") == 0)
1743  {
1744  if (!opt2)
1745  {
1746  psql_error("\\%s: missing required argument\n", cmd);
1747  success = false;
1748  }
1749  else
1750  {
1751  expand_tilde(&opt2);
1752  success = do_lo_export(opt1, opt2);
1753  }
1754  }
1755 
1756  else if (strcmp(cmd + 3, "import") == 0)
1757  {
1758  if (!opt1)
1759  {
1760  psql_error("\\%s: missing required argument\n", cmd);
1761  success = false;
1762  }
1763  else
1764  {
1765  expand_tilde(&opt1);
1766  success = do_lo_import(opt1, opt2);
1767  }
1768  }
1769 
1770  else if (strcmp(cmd + 3, "list") == 0)
1771  success = do_lo_list();
1772 
1773  else if (strcmp(cmd + 3, "unlink") == 0)
1774  {
1775  if (!opt1)
1776  {
1777  psql_error("\\%s: missing required argument\n", cmd);
1778  success = false;
1779  }
1780  else
1781  success = do_lo_unlink(opt1);
1782  }
1783 
1784  else
1785  status = PSQL_CMD_UNKNOWN;
1786 
1787  free(opt1);
1788  free(opt2);
1789  }
1790  else
1791  ignore_slash_options(scan_state);
1792 
1793  if (!success)
1794  status = PSQL_CMD_ERROR;
1795 
1796  return status;
1797 }
1798 
1799 /*
1800  * \o -- set query output
1801  */
1802 static backslashResult
1803 exec_command_out(PsqlScanState scan_state, bool active_branch)
1804 {
1805  bool success = true;
1806 
1807  if (active_branch)
1808  {
1809  char *fname = psql_scan_slash_option(scan_state,
1810  OT_FILEPIPE, NULL, true);
1811 
1812  expand_tilde(&fname);
1813  success = setQFout(fname);
1814  free(fname);
1815  }
1816  else
1817  ignore_slash_filepipe(scan_state);
1818 
1819  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
1820 }
1821 
1822 /*
1823  * \p -- print the current query buffer
1824  */
1825 static backslashResult
1826 exec_command_print(PsqlScanState scan_state, bool active_branch,
1827  PQExpBuffer query_buf, PQExpBuffer previous_buf)
1828 {
1829  if (active_branch)
1830  {
1831  /*
1832  * We want to print the same thing \g would execute, but not to change
1833  * the query buffer state; so we can't use copy_previous_query().
1834  * Also, beware of possibility that buffer pointers are NULL.
1835  */
1836  if (query_buf && query_buf->len > 0)
1837  puts(query_buf->data);
1838  else if (previous_buf && previous_buf->len > 0)
1839  puts(previous_buf->data);
1840  else if (!pset.quiet)
1841  puts(_("Query buffer is empty."));
1842  fflush(stdout);
1843  }
1844 
1845  return PSQL_CMD_SKIP_LINE;
1846 }
1847 
1848 /*
1849  * \password -- set user password
1850  */
1851 static backslashResult
1852 exec_command_password(PsqlScanState scan_state, bool active_branch)
1853 {
1854  bool success = true;
1855 
1856  if (active_branch)
1857  {
1858  char *opt0 = psql_scan_slash_option(scan_state,
1859  OT_SQLID, NULL, true);
1860  char pw1[100];
1861  char pw2[100];
1862 
1863  simple_prompt("Enter new password: ", pw1, sizeof(pw1), false);
1864  simple_prompt("Enter it again: ", pw2, sizeof(pw2), false);
1865 
1866  if (strcmp(pw1, pw2) != 0)
1867  {
1868  psql_error("Passwords didn't match.\n");
1869  success = false;
1870  }
1871  else
1872  {
1873  char *user;
1874  char *encrypted_password;
1875 
1876  if (opt0)
1877  user = opt0;
1878  else
1879  user = PQuser(pset.db);
1880 
1881  encrypted_password = PQencryptPasswordConn(pset.db, pw1, user, NULL);
1882 
1883  if (!encrypted_password)
1884  {
1885  psql_error("%s", PQerrorMessage(pset.db));
1886  success = false;
1887  }
1888  else
1889  {
1891  PGresult *res;
1892 
1893  initPQExpBuffer(&buf);
1894  printfPQExpBuffer(&buf, "ALTER USER %s PASSWORD ",
1895  fmtId(user));
1896  appendStringLiteralConn(&buf, encrypted_password, pset.db);
1897  res = PSQLexec(buf.data);
1898  termPQExpBuffer(&buf);
1899  if (!res)
1900  success = false;
1901  else
1902  PQclear(res);
1903  PQfreemem(encrypted_password);
1904  }
1905  }
1906 
1907  if (opt0)
1908  free(opt0);
1909  }
1910  else
1911  ignore_slash_options(scan_state);
1912 
1913  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
1914 }
1915 
1916 /*
1917  * \prompt -- prompt and set variable
1918  */
1919 static backslashResult
1920 exec_command_prompt(PsqlScanState scan_state, bool active_branch,
1921  const char *cmd)
1922 {
1923  bool success = true;
1924 
1925  if (active_branch)
1926  {
1927  char *opt,
1928  *prompt_text = NULL;
1929  char *arg1,
1930  *arg2;
1931 
1932  arg1 = psql_scan_slash_option(scan_state, OT_NORMAL, NULL, false);
1933  arg2 = psql_scan_slash_option(scan_state, OT_NORMAL, NULL, false);
1934 
1935  if (!arg1)
1936  {
1937  psql_error("\\%s: missing required argument\n", cmd);
1938  success = false;
1939  }
1940  else
1941  {
1942  char *result;
1943 
1944  if (arg2)
1945  {
1946  prompt_text = arg1;
1947  opt = arg2;
1948  }
1949  else
1950  opt = arg1;
1951 
1952  if (!pset.inputfile)
1953  {
1954  result = (char *) pg_malloc(4096);
1955  simple_prompt(prompt_text, result, 4096, true);
1956  }
1957  else
1958  {
1959  if (prompt_text)
1960  {
1961  fputs(prompt_text, stdout);
1962  fflush(stdout);
1963  }
1964  result = gets_fromFile(stdin);
1965  if (!result)
1966  {
1967  psql_error("\\%s: could not read value for variable\n",
1968  cmd);
1969  success = false;
1970  }
1971  }
1972 
1973  if (result &&
1974  !SetVariable(pset.vars, opt, result))
1975  success = false;
1976 
1977  if (result)
1978  free(result);
1979  if (prompt_text)
1980  free(prompt_text);
1981  free(opt);
1982  }
1983  }
1984  else
1985  ignore_slash_options(scan_state);
1986 
1987  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
1988 }
1989 
1990 /*
1991  * \pset -- set printing parameters
1992  */
1993 static backslashResult
1994 exec_command_pset(PsqlScanState scan_state, bool active_branch)
1995 {
1996  bool success = true;
1997 
1998  if (active_branch)
1999  {
2000  char *opt0 = psql_scan_slash_option(scan_state,
2001  OT_NORMAL, NULL, false);
2002  char *opt1 = psql_scan_slash_option(scan_state,
2003  OT_NORMAL, NULL, false);
2004 
2005  if (!opt0)
2006  {
2007  /* list all variables */
2008 
2009  int i;
2010  static const char *const my_list[] = {
2011  "border", "columns", "expanded", "fieldsep", "fieldsep_zero",
2012  "footer", "format", "linestyle", "null",
2013  "numericlocale", "pager", "pager_min_lines",
2014  "recordsep", "recordsep_zero",
2015  "tableattr", "title", "tuples_only",
2016  "unicode_border_linestyle",
2017  "unicode_column_linestyle",
2018  "unicode_header_linestyle",
2019  NULL
2020  };
2021 
2022  for (i = 0; my_list[i] != NULL; i++)
2023  {
2024  char *val = pset_value_string(my_list[i], &pset.popt);
2025 
2026  printf("%-24s %s\n", my_list[i], val);
2027  free(val);
2028  }
2029 
2030  success = true;
2031  }
2032  else
2033  success = do_pset(opt0, opt1, &pset.popt, pset.quiet);
2034 
2035  free(opt0);
2036  free(opt1);
2037  }
2038  else
2039  ignore_slash_options(scan_state);
2040 
2041  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
2042 }
2043 
2044 /*
2045  * \q or \quit -- exit psql
2046  */
2047 static backslashResult
2048 exec_command_quit(PsqlScanState scan_state, bool active_branch)
2049 {
2051 
2052  if (active_branch)
2053  status = PSQL_CMD_TERMINATE;
2054 
2055  return status;
2056 }
2057 
2058 /*
2059  * \r -- reset (clear) the query buffer
2060  */
2061 static backslashResult
2062 exec_command_reset(PsqlScanState scan_state, bool active_branch,
2063  PQExpBuffer query_buf)
2064 {
2065  if (active_branch)
2066  {
2067  resetPQExpBuffer(query_buf);
2068  psql_scan_reset(scan_state);
2069  if (!pset.quiet)
2070  puts(_("Query buffer reset (cleared)."));
2071  }
2072 
2073  return PSQL_CMD_SKIP_LINE;
2074 }
2075 
2076 /*
2077  * \s -- save history in a file or show it on the screen
2078  */
2079 static backslashResult
2080 exec_command_s(PsqlScanState scan_state, bool active_branch)
2081 {
2082  bool success = true;
2083 
2084  if (active_branch)
2085  {
2086  char *fname = psql_scan_slash_option(scan_state,
2087  OT_NORMAL, NULL, true);
2088 
2089  expand_tilde(&fname);
2090  success = printHistory(fname, pset.popt.topt.pager);
2091  if (success && !pset.quiet && fname)
2092  printf(_("Wrote history to file \"%s\".\n"), fname);
2093  if (!fname)
2094  putchar('\n');
2095  free(fname);
2096  }
2097  else
2098  ignore_slash_options(scan_state);
2099 
2100  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
2101 }
2102 
2103 /*
2104  * \set -- set variable
2105  */
2106 static backslashResult
2107 exec_command_set(PsqlScanState scan_state, bool active_branch)
2108 {
2109  bool success = true;
2110 
2111  if (active_branch)
2112  {
2113  char *opt0 = psql_scan_slash_option(scan_state,
2114  OT_NORMAL, NULL, false);
2115 
2116  if (!opt0)
2117  {
2118  /* list all variables */
2120  success = true;
2121  }
2122  else
2123  {
2124  /*
2125  * Set variable to the concatenation of the arguments.
2126  */
2127  char *newval;
2128  char *opt;
2129 
2130  opt = psql_scan_slash_option(scan_state,
2131  OT_NORMAL, NULL, false);
2132  newval = pg_strdup(opt ? opt : "");
2133  free(opt);
2134 
2135  while ((opt = psql_scan_slash_option(scan_state,
2136  OT_NORMAL, NULL, false)))
2137  {
2138  newval = pg_realloc(newval, strlen(newval) + strlen(opt) + 1);
2139  strcat(newval, opt);
2140  free(opt);
2141  }
2142 
2143  if (!SetVariable(pset.vars, opt0, newval))
2144  success = false;
2145 
2146  free(newval);
2147  }
2148  free(opt0);
2149  }
2150  else
2151  ignore_slash_options(scan_state);
2152 
2153  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
2154 }
2155 
2156 /*
2157  * \setenv -- set environment variable
2158  */
2159 static backslashResult
2160 exec_command_setenv(PsqlScanState scan_state, bool active_branch,
2161  const char *cmd)
2162 {
2163  bool success = true;
2164 
2165  if (active_branch)
2166  {
2167  char *envvar = psql_scan_slash_option(scan_state,
2168  OT_NORMAL, NULL, false);
2169  char *envval = psql_scan_slash_option(scan_state,
2170  OT_NORMAL, NULL, false);
2171 
2172  if (!envvar)
2173  {
2174  psql_error("\\%s: missing required argument\n", cmd);
2175  success = false;
2176  }
2177  else if (strchr(envvar, '=') != NULL)
2178  {
2179  psql_error("\\%s: environment variable name must not contain \"=\"\n",
2180  cmd);
2181  success = false;
2182  }
2183  else if (!envval)
2184  {
2185  /* No argument - unset the environment variable */
2186  unsetenv(envvar);
2187  success = true;
2188  }
2189  else
2190  {
2191  /* Set variable to the value of the next argument */
2192  char *newval;
2193 
2194  newval = psprintf("%s=%s", envvar, envval);
2195  putenv(newval);
2196  success = true;
2197 
2198  /*
2199  * Do not free newval here, it will screw up the environment if
2200  * you do. See putenv man page for details. That means we leak a
2201  * bit of memory here, but not enough to worry about.
2202  */
2203  }
2204  free(envvar);
2205  free(envval);
2206  }
2207  else
2208  ignore_slash_options(scan_state);
2209 
2210  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
2211 }
2212 
2213 /*
2214  * \sf -- show a function's source code
2215  */
2216 static backslashResult
2217 exec_command_sf(PsqlScanState scan_state, bool active_branch, const char *cmd)
2218 {
2220 
2221  if (active_branch)
2222  {
2223  bool show_linenumbers = (strcmp(cmd, "sf+") == 0);
2224  PQExpBuffer func_buf;
2225  char *func;
2226  Oid foid = InvalidOid;
2227 
2228  func_buf = createPQExpBuffer();
2229  func = psql_scan_slash_option(scan_state,
2230  OT_WHOLE_LINE, NULL, true);
2231  if (pset.sversion < 80400)
2232  {
2233  char sverbuf[32];
2234 
2235  psql_error("The server (version %s) does not support showing function source.\n",
2237  sverbuf, sizeof(sverbuf)));
2238  status = PSQL_CMD_ERROR;
2239  }
2240  else if (!func)
2241  {
2242  psql_error("function name is required\n");
2243  status = PSQL_CMD_ERROR;
2244  }
2245  else if (!lookup_object_oid(EditableFunction, func, &foid))
2246  {
2247  /* error already reported */
2248  status = PSQL_CMD_ERROR;
2249  }
2250  else if (!get_create_object_cmd(EditableFunction, foid, func_buf))
2251  {
2252  /* error already reported */
2253  status = PSQL_CMD_ERROR;
2254  }
2255  else
2256  {
2257  FILE *output;
2258  bool is_pager;
2259 
2260  /* Select output stream: stdout, pager, or file */
2261  if (pset.queryFout == stdout)
2262  {
2263  /* count lines in function to see if pager is needed */
2264  int lineno = count_lines_in_buf(func_buf);
2265 
2266  output = PageOutput(lineno, &(pset.popt.topt));
2267  is_pager = true;
2268  }
2269  else
2270  {
2271  /* use previously set output file, without pager */
2272  output = pset.queryFout;
2273  is_pager = false;
2274  }
2275 
2276  if (show_linenumbers)
2277  {
2278  /*
2279  * lineno "1" should correspond to the first line of the
2280  * function body. We expect that pg_get_functiondef() will
2281  * emit that on a line beginning with "AS ", and that there
2282  * can be no such line before the real start of the function
2283  * body.
2284  */
2285  print_with_linenumbers(output, func_buf->data, "AS ");
2286  }
2287  else
2288  {
2289  /* just send the function definition to output */
2290  fputs(func_buf->data, output);
2291  }
2292 
2293  if (is_pager)
2294  ClosePager(output);
2295  }
2296 
2297  if (func)
2298  free(func);
2299  destroyPQExpBuffer(func_buf);
2300  }
2301  else
2302  ignore_slash_whole_line(scan_state);
2303 
2304  return status;
2305 }
2306 
2307 /*
2308  * \sv -- show a view's source code
2309  */
2310 static backslashResult
2311 exec_command_sv(PsqlScanState scan_state, bool active_branch, const char *cmd)
2312 {
2314 
2315  if (active_branch)
2316  {
2317  bool show_linenumbers = (strcmp(cmd, "sv+") == 0);
2318  PQExpBuffer view_buf;
2319  char *view;
2320  Oid view_oid = InvalidOid;
2321 
2322  view_buf = createPQExpBuffer();
2323  view = psql_scan_slash_option(scan_state,
2324  OT_WHOLE_LINE, NULL, true);
2325  if (pset.sversion < 70400)
2326  {
2327  char sverbuf[32];
2328 
2329  psql_error("The server (version %s) does not support showing view definitions.\n",
2331  sverbuf, sizeof(sverbuf)));
2332  status = PSQL_CMD_ERROR;
2333  }
2334  else if (!view)
2335  {
2336  psql_error("view name is required\n");
2337  status = PSQL_CMD_ERROR;
2338  }
2339  else if (!lookup_object_oid(EditableView, view, &view_oid))
2340  {
2341  /* error already reported */
2342  status = PSQL_CMD_ERROR;
2343  }
2344  else if (!get_create_object_cmd(EditableView, view_oid, view_buf))
2345  {
2346  /* error already reported */
2347  status = PSQL_CMD_ERROR;
2348  }
2349  else
2350  {
2351  FILE *output;
2352  bool is_pager;
2353 
2354  /* Select output stream: stdout, pager, or file */
2355  if (pset.queryFout == stdout)
2356  {
2357  /* count lines in view to see if pager is needed */
2358  int lineno = count_lines_in_buf(view_buf);
2359 
2360  output = PageOutput(lineno, &(pset.popt.topt));
2361  is_pager = true;
2362  }
2363  else
2364  {
2365  /* use previously set output file, without pager */
2366  output = pset.queryFout;
2367  is_pager = false;
2368  }
2369 
2370  if (show_linenumbers)
2371  {
2372  /* add line numbers, numbering all lines */
2373  print_with_linenumbers(output, view_buf->data, NULL);
2374  }
2375  else
2376  {
2377  /* just send the view definition to output */
2378  fputs(view_buf->data, output);
2379  }
2380 
2381  if (is_pager)
2382  ClosePager(output);
2383  }
2384 
2385  if (view)
2386  free(view);
2387  destroyPQExpBuffer(view_buf);
2388  }
2389  else
2390  ignore_slash_whole_line(scan_state);
2391 
2392  return status;
2393 }
2394 
2395 /*
2396  * \t -- turn off table headers and row count
2397  */
2398 static backslashResult
2399 exec_command_t(PsqlScanState scan_state, bool active_branch)
2400 {
2401  bool success = true;
2402 
2403  if (active_branch)
2404  {
2405  char *opt = psql_scan_slash_option(scan_state,
2406  OT_NORMAL, NULL, true);
2407 
2408  success = do_pset("tuples_only", opt, &pset.popt, pset.quiet);
2409  free(opt);
2410  }
2411  else
2412  ignore_slash_options(scan_state);
2413 
2414  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
2415 }
2416 
2417 /*
2418  * \T -- define html <table ...> attributes
2419  */
2420 static backslashResult
2421 exec_command_T(PsqlScanState scan_state, bool active_branch)
2422 {
2423  bool success = true;
2424 
2425  if (active_branch)
2426  {
2427  char *value = psql_scan_slash_option(scan_state,
2428  OT_NORMAL, NULL, false);
2429 
2430  success = do_pset("tableattr", value, &pset.popt, pset.quiet);
2431  free(value);
2432  }
2433  else
2434  ignore_slash_options(scan_state);
2435 
2436  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
2437 }
2438 
2439 /*
2440  * \timing -- enable/disable timing of queries
2441  */
2442 static backslashResult
2443 exec_command_timing(PsqlScanState scan_state, bool active_branch)
2444 {
2445  bool success = true;
2446 
2447  if (active_branch)
2448  {
2449  char *opt = psql_scan_slash_option(scan_state,
2450  OT_NORMAL, NULL, false);
2451 
2452  if (opt)
2453  success = ParseVariableBool(opt, "\\timing", &pset.timing);
2454  else
2455  pset.timing = !pset.timing;
2456  if (!pset.quiet)
2457  {
2458  if (pset.timing)
2459  puts(_("Timing is on."));
2460  else
2461  puts(_("Timing is off."));
2462  }
2463  free(opt);
2464  }
2465  else
2466  ignore_slash_options(scan_state);
2467 
2468  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
2469 }
2470 
2471 /*
2472  * \unset -- unset variable
2473  */
2474 static backslashResult
2475 exec_command_unset(PsqlScanState scan_state, bool active_branch,
2476  const char *cmd)
2477 {
2478  bool success = true;
2479 
2480  if (active_branch)
2481  {
2482  char *opt = psql_scan_slash_option(scan_state,
2483  OT_NORMAL, NULL, false);
2484 
2485  if (!opt)
2486  {
2487  psql_error("\\%s: missing required argument\n", cmd);
2488  success = false;
2489  }
2490  else if (!SetVariable(pset.vars, opt, NULL))
2491  success = false;
2492 
2493  free(opt);
2494  }
2495  else
2496  ignore_slash_options(scan_state);
2497 
2498  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
2499 }
2500 
2501 /*
2502  * \w -- write query buffer to file
2503  */
2504 static backslashResult
2505 exec_command_write(PsqlScanState scan_state, bool active_branch,
2506  const char *cmd,
2507  PQExpBuffer query_buf, PQExpBuffer previous_buf)
2508 {
2510 
2511  if (active_branch)
2512  {
2513  char *fname = psql_scan_slash_option(scan_state,
2514  OT_FILEPIPE, NULL, true);
2515  FILE *fd = NULL;
2516  bool is_pipe = false;
2517 
2518  if (!query_buf)
2519  {
2520  psql_error("no query buffer\n");
2521  status = PSQL_CMD_ERROR;
2522  }
2523  else
2524  {
2525  if (!fname)
2526  {
2527  psql_error("\\%s: missing required argument\n", cmd);
2528  status = PSQL_CMD_ERROR;
2529  }
2530  else
2531  {
2532  expand_tilde(&fname);
2533  if (fname[0] == '|')
2534  {
2535  is_pipe = true;
2537  fd = popen(&fname[1], "w");
2538  }
2539  else
2540  {
2541  canonicalize_path(fname);
2542  fd = fopen(fname, "w");
2543  }
2544  if (!fd)
2545  {
2546  psql_error("%s: %s\n", fname, strerror(errno));
2547  status = PSQL_CMD_ERROR;
2548  }
2549  }
2550  }
2551 
2552  if (fd)
2553  {
2554  int result;
2555 
2556  /*
2557  * We want to print the same thing \g would execute, but not to
2558  * change the query buffer state; so we can't use
2559  * copy_previous_query(). Also, beware of possibility that buffer
2560  * pointers are NULL.
2561  */
2562  if (query_buf && query_buf->len > 0)
2563  fprintf(fd, "%s\n", query_buf->data);
2564  else if (previous_buf && previous_buf->len > 0)
2565  fprintf(fd, "%s\n", previous_buf->data);
2566 
2567  if (is_pipe)
2568  result = pclose(fd);
2569  else
2570  result = fclose(fd);
2571 
2572  if (result == EOF)
2573  {
2574  psql_error("%s: %s\n", fname, strerror(errno));
2575  status = PSQL_CMD_ERROR;
2576  }
2577  }
2578 
2579  if (is_pipe)
2581 
2582  free(fname);
2583  }
2584  else
2585  ignore_slash_filepipe(scan_state);
2586 
2587  return status;
2588 }
2589 
2590 /*
2591  * \watch -- execute a query every N seconds
2592  */
2593 static backslashResult
2594 exec_command_watch(PsqlScanState scan_state, bool active_branch,
2595  PQExpBuffer query_buf, PQExpBuffer previous_buf)
2596 {
2597  bool success = true;
2598 
2599  if (active_branch)
2600  {
2601  char *opt = psql_scan_slash_option(scan_state,
2602  OT_NORMAL, NULL, true);
2603  double sleep = 2;
2604 
2605  /* Convert optional sleep-length argument */
2606  if (opt)
2607  {
2608  sleep = strtod(opt, NULL);
2609  if (sleep <= 0)
2610  sleep = 1;
2611  free(opt);
2612  }
2613 
2614  /* If query_buf is empty, recall and execute previous query */
2615  copy_previous_query(query_buf, previous_buf);
2616 
2617  success = do_watch(query_buf, sleep);
2618 
2619  /* Reset the query buffer as though for \r */
2620  resetPQExpBuffer(query_buf);
2621  psql_scan_reset(scan_state);
2622  }
2623  else
2624  ignore_slash_options(scan_state);
2625 
2626  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
2627 }
2628 
2629 /*
2630  * \x -- set or toggle expanded table representation
2631  */
2632 static backslashResult
2633 exec_command_x(PsqlScanState scan_state, bool active_branch)
2634 {
2635  bool success = true;
2636 
2637  if (active_branch)
2638  {
2639  char *opt = psql_scan_slash_option(scan_state,
2640  OT_NORMAL, NULL, true);
2641 
2642  success = do_pset("expanded", opt, &pset.popt, pset.quiet);
2643  free(opt);
2644  }
2645  else
2646  ignore_slash_options(scan_state);
2647 
2648  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
2649 }
2650 
2651 /*
2652  * \z -- list table privileges (equivalent to \dp)
2653  */
2654 static backslashResult
2655 exec_command_z(PsqlScanState scan_state, bool active_branch)
2656 {
2657  bool success = true;
2658 
2659  if (active_branch)
2660  {
2661  char *pattern = psql_scan_slash_option(scan_state,
2662  OT_NORMAL, NULL, true);
2663 
2664  success = permissionsList(pattern);
2665  if (pattern)
2666  free(pattern);
2667  }
2668  else
2669  ignore_slash_options(scan_state);
2670 
2671  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
2672 }
2673 
2674 /*
2675  * \! -- execute shell command
2676  */
2677 static backslashResult
2678 exec_command_shell_escape(PsqlScanState scan_state, bool active_branch)
2679 {
2680  bool success = true;
2681 
2682  if (active_branch)
2683  {
2684  char *opt = psql_scan_slash_option(scan_state,
2685  OT_WHOLE_LINE, NULL, false);
2686 
2687  success = do_shell(opt);
2688  free(opt);
2689  }
2690  else
2691  ignore_slash_whole_line(scan_state);
2692 
2693  return success ? PSQL_CMD_SKIP_LINE : PSQL_CMD_ERROR;
2694 }
2695 
2696 /*
2697  * \? -- print help about backslash commands
2698  */
2699 static backslashResult
2700 exec_command_slash_command_help(PsqlScanState scan_state, bool active_branch)
2701 {
2702  if (active_branch)
2703  {
2704  char *opt0 = psql_scan_slash_option(scan_state,
2705  OT_NORMAL, NULL, false);
2706 
2707  if (!opt0 || strcmp(opt0, "commands") == 0)
2709  else if (strcmp(opt0, "options") == 0)
2711  else if (strcmp(opt0, "variables") == 0)
2713  else
2715 
2716  if (opt0)
2717  free(opt0);
2718  }
2719  else
2720  ignore_slash_options(scan_state);
2721 
2722  return PSQL_CMD_SKIP_LINE;
2723 }
2724 
2725 
2726 /*
2727  * Read and interpret an argument to the \connect slash command.
2728  */
2729 static char *
2731 {
2732  char *result;
2733  char quote;
2734 
2735  /*
2736  * Ideally we should treat the arguments as SQL identifiers. But for
2737  * backwards compatibility with 7.2 and older pg_dump files, we have to
2738  * take unquoted arguments verbatim (don't downcase them). For now,
2739  * double-quoted arguments may be stripped of double quotes (as if SQL
2740  * identifiers). By 7.4 or so, pg_dump files can be expected to
2741  * double-quote all mixed-case \connect arguments, and then we can get rid
2742  * of OT_SQLIDHACK.
2743  */
2744  result = psql_scan_slash_option(scan_state, OT_SQLIDHACK, &quote, true);
2745 
2746  if (!result)
2747  return NULL;
2748 
2749  if (quote)
2750  return result;
2751 
2752  if (*result == '\0' || strcmp(result, "-") == 0)
2753  return NULL;
2754 
2755  return result;
2756 }
2757 
2758 /*
2759  * Read a boolean expression, return it as a PQExpBuffer string.
2760  *
2761  * Note: anything more or less than one token will certainly fail to be
2762  * parsed by ParseVariableBool, so we don't worry about complaining here.
2763  * This routine's return data structure will need to be rethought anyway
2764  * to support likely future extensions such as "\if defined VARNAME".
2765  */
2766 static PQExpBuffer
2768 {
2769  PQExpBuffer exp_buf = createPQExpBuffer();
2770  int num_options = 0;
2771  char *value;
2772 
2773  /* collect all arguments for the conditional command into exp_buf */
2774  while ((value = psql_scan_slash_option(scan_state,
2775  OT_NORMAL, NULL, false)) != NULL)
2776  {
2777  /* add spaces between tokens */
2778  if (num_options > 0)
2779  appendPQExpBufferChar(exp_buf, ' ');
2780  appendPQExpBufferStr(exp_buf, value);
2781  num_options++;
2782  free(value);
2783  }
2784 
2785  return exp_buf;
2786 }
2787 
2788 /*
2789  * Read a boolean expression, return true if the expression
2790  * was a valid boolean expression that evaluated to true.
2791  * Otherwise return false.
2792  *
2793  * Note: conditional stack's top state must be active, else lexer will
2794  * fail to expand variables and backticks.
2795  */
2796 static bool
2798 {
2800  bool value = false;
2801  bool success = ParseVariableBool(buf->data, name, &value);
2802 
2803  destroyPQExpBuffer(buf);
2804  return success && value;
2805 }
2806 
2807 /*
2808  * Read a boolean expression, but do nothing with it.
2809  *
2810  * Note: conditional stack's top state must be INACTIVE, else lexer will
2811  * expand variables and backticks, which we do not want here.
2812  */
2813 static void
2815 {
2817 
2818  destroyPQExpBuffer(buf);
2819 }
2820 
2821 /*
2822  * Read and discard "normal" slash command options.
2823  *
2824  * This should be used for inactive-branch processing of any slash command
2825  * that eats one or more OT_NORMAL, OT_SQLID, or OT_SQLIDHACK parameters.
2826  * We don't need to worry about exactly how many it would eat, since the
2827  * cleanup logic in HandleSlashCmds would silently discard any extras anyway.
2828  */
2829 static void
2831 {
2832  char *arg;
2833 
2834  while ((arg = psql_scan_slash_option(scan_state,
2835  OT_NORMAL, NULL, false)) != NULL)
2836  free(arg);
2837 }
2838 
2839 /*
2840  * Read and discard FILEPIPE slash command argument.
2841  *
2842  * This *MUST* be used for inactive-branch processing of any slash command
2843  * that takes an OT_FILEPIPE option. Otherwise we might consume a different
2844  * amount of option text in active and inactive cases.
2845  */
2846 static void
2848 {
2849  char *arg = psql_scan_slash_option(scan_state,
2850  OT_FILEPIPE, NULL, false);
2851 
2852  if (arg)
2853  free(arg);
2854 }
2855 
2856 /*
2857  * Read and discard whole-line slash command argument.
2858  *
2859  * This *MUST* be used for inactive-branch processing of any slash command
2860  * that takes an OT_WHOLE_LINE option. Otherwise we might consume a different
2861  * amount of option text in active and inactive cases.
2862  */
2863 static void
2865 {
2866  char *arg = psql_scan_slash_option(scan_state,
2867  OT_WHOLE_LINE, NULL, false);
2868 
2869  if (arg)
2870  free(arg);
2871 }
2872 
2873 /*
2874  * Return true if the command given is a branching command.
2875  */
2876 static bool
2877 is_branching_command(const char *cmd)
2878 {
2879  return (strcmp(cmd, "if") == 0 ||
2880  strcmp(cmd, "elif") == 0 ||
2881  strcmp(cmd, "else") == 0 ||
2882  strcmp(cmd, "endif") == 0);
2883 }
2884 
2885 /*
2886  * Prepare to possibly restore query buffer to its current state
2887  * (cf. discard_query_text).
2888  *
2889  * We need to remember the length of the query buffer, and the lexer's
2890  * notion of the parenthesis nesting depth.
2891  */
2892 static void
2894  PQExpBuffer query_buf)
2895 {
2896  if (query_buf)
2897  conditional_stack_set_query_len(cstack, query_buf->len);
2899  psql_scan_get_paren_depth(scan_state));
2900 }
2901 
2902 /*
2903  * Discard any query text absorbed during an inactive conditional branch.
2904  *
2905  * We must discard data that was appended to query_buf during an inactive
2906  * \if branch. We don't have to do anything there if there's no query_buf.
2907  *
2908  * Also, reset the lexer state to the same paren depth there was before.
2909  * (The rest of its state doesn't need attention, since we could not be
2910  * inside a comment or literal or partial token.)
2911  */
2912 static void
2914  PQExpBuffer query_buf)
2915 {
2916  if (query_buf)
2917  {
2918  int new_len = conditional_stack_get_query_len(cstack);
2919 
2920  Assert(new_len >= 0 && new_len <= query_buf->len);
2921  query_buf->len = new_len;
2922  query_buf->data[new_len] = '\0';
2923  }
2924  psql_scan_set_paren_depth(scan_state,
2926 }
2927 
2928 /*
2929  * If query_buf is empty, copy previous_buf into it.
2930  *
2931  * This is used by various slash commands for which re-execution of a
2932  * previous query is a common usage. For convenience, we allow the
2933  * case of query_buf == NULL (and do nothing).
2934  */
2935 static void
2937 {
2938  if (query_buf && query_buf->len == 0)
2939  appendPQExpBufferStr(query_buf, previous_buf->data);
2940 }
2941 
2942 /*
2943  * Ask the user for a password; 'username' is the username the
2944  * password is for, if one has been explicitly specified. Returns a
2945  * malloc'd string.
2946  */
2947 static char *
2949 {
2950  char buf[100];
2951 
2952  if (username == NULL)
2953  simple_prompt("Password: ", buf, sizeof(buf), false);
2954  else
2955  {
2956  char *prompt_text;
2957 
2958  prompt_text = psprintf(_("Password for user %s: "), username);
2959  simple_prompt(prompt_text, buf, sizeof(buf), false);
2960  free(prompt_text);
2961  }
2962  return pg_strdup(buf);
2963 }
2964 
2965 static bool
2966 param_is_newly_set(const char *old_val, const char *new_val)
2967 {
2968  if (new_val == NULL)
2969  return false;
2970 
2971  if (old_val == NULL || strcmp(old_val, new_val) != 0)
2972  return true;
2973 
2974  return false;
2975 }
2976 
2977 /*
2978  * do_connect -- handler for \connect
2979  *
2980  * Connects to a database with given parameters. Absent an established
2981  * connection, all parameters are required. Given -reuse-previous=off or a
2982  * connection string without -reuse-previous=on, NULL values will pass through
2983  * to PQconnectdbParams(), so the libpq defaults will be used. Otherwise, NULL
2984  * values will be replaced with the ones in the current connection.
2985  *
2986  * In interactive mode, if connection fails with the given parameters,
2987  * the old connection will be kept.
2988  */
2989 static bool
2990 do_connect(enum trivalue reuse_previous_specification,
2991  char *dbname, char *user, char *host, char *port)
2992 {
2993  PGconn *o_conn = pset.db,
2994  *n_conn;
2995  char *password = NULL;
2996  bool keep_password;
2997  bool has_connection_string;
2998  bool reuse_previous;
3000 
3001  if (!o_conn && (!dbname || !user || !host || !port))
3002  {
3003  /*
3004  * We don't know the supplied connection parameters and don't want to
3005  * connect to the wrong database by using defaults, so require all
3006  * parameters to be specified.
3007  */
3008  psql_error("All connection parameters must be supplied because no "
3009  "database connection exists\n");
3010  return false;
3011  }
3012 
3013  has_connection_string = dbname ?
3014  recognized_connection_string(dbname) : false;
3015  switch (reuse_previous_specification)
3016  {
3017  case TRI_YES:
3018  reuse_previous = true;
3019  break;
3020  case TRI_NO:
3021  reuse_previous = false;
3022  break;
3023  default:
3024  reuse_previous = !has_connection_string;
3025  break;
3026  }
3027  /* Silently ignore arguments subsequent to a connection string. */
3028  if (has_connection_string)
3029  {
3030  user = NULL;
3031  host = NULL;
3032  port = NULL;
3033  }
3034 
3035  /* grab missing values from the old connection */
3036  if (!user && reuse_previous)
3037  user = PQuser(o_conn);
3038  if (!host && reuse_previous)
3039  host = PQhost(o_conn);
3040  if (!port && reuse_previous)
3041  port = PQport(o_conn);
3042 
3043  /*
3044  * Any change in the parameters read above makes us discard the password.
3045  * We also discard it if we're to use a conninfo rather than the
3046  * positional syntax.
3047  */
3048  if (has_connection_string)
3049  keep_password = false;
3050  else
3051  keep_password =
3052  (user && PQuser(o_conn) && strcmp(user, PQuser(o_conn)) == 0) &&
3053  (host && PQhost(o_conn) && strcmp(host, PQhost(o_conn)) == 0) &&
3054  (port && PQport(o_conn) && strcmp(port, PQport(o_conn)) == 0);
3055 
3056  /*
3057  * Grab missing dbname from old connection. No password discard if this
3058  * changes: passwords aren't (usually) database-specific.
3059  */
3060  if (!dbname && reuse_previous)
3061  {
3062  initPQExpBuffer(&connstr);
3063  appendPQExpBuffer(&connstr, "dbname=");
3064  appendConnStrVal(&connstr, PQdb(o_conn));
3065  dbname = connstr.data;
3066  /* has_connection_string=true would be a dead store */
3067  }
3068  else
3069  connstr.data = NULL;
3070 
3071  /*
3072  * If the user asked to be prompted for a password, ask for one now. If
3073  * not, use the password from the old connection, provided the username
3074  * etc have not changed. Otherwise, try to connect without a password
3075  * first, and then ask for a password if needed.
3076  *
3077  * XXX: this behavior leads to spurious connection attempts recorded in
3078  * the postmaster's log. But libpq offers no API that would let us obtain
3079  * a password and then continue with the first connection attempt.
3080  */
3081  if (pset.getPassword == TRI_YES)
3082  {
3083  password = prompt_for_password(user);
3084  }
3085  else if (o_conn && keep_password)
3086  {
3087  password = PQpass(o_conn);
3088  if (password && *password)
3089  password = pg_strdup(password);
3090  else
3091  password = NULL;
3092  }
3093 
3094  while (true)
3095  {
3096 #define PARAMS_ARRAY_SIZE 8
3097  const char **keywords = pg_malloc(PARAMS_ARRAY_SIZE * sizeof(*keywords));
3098  const char **values = pg_malloc(PARAMS_ARRAY_SIZE * sizeof(*values));
3099  int paramnum = -1;
3100 
3101  keywords[++paramnum] = "host";
3102  values[paramnum] = host;
3103  keywords[++paramnum] = "port";
3104  values[paramnum] = port;
3105  keywords[++paramnum] = "user";
3106  values[paramnum] = user;
3107 
3108  /*
3109  * Position in the array matters when the dbname is a connection
3110  * string, because settings in a connection string override earlier
3111  * array entries only. Thus, user= in the connection string always
3112  * takes effect, but client_encoding= often will not.
3113  *
3114  * If you change this code, also change the initial-connection code in
3115  * main(). For no good reason, a connection string password= takes
3116  * precedence in main() but not here.
3117  */
3118  keywords[++paramnum] = "dbname";
3119  values[paramnum] = dbname;
3120  keywords[++paramnum] = "password";
3121  values[paramnum] = password;
3122  keywords[++paramnum] = "fallback_application_name";
3123  values[paramnum] = pset.progname;
3124  keywords[++paramnum] = "client_encoding";
3125  values[paramnum] = (pset.notty || getenv("PGCLIENTENCODING")) ? NULL : "auto";
3126 
3127  /* add array terminator */
3128  keywords[++paramnum] = NULL;
3129  values[paramnum] = NULL;
3130 
3131  n_conn = PQconnectdbParams(keywords, values, true);
3132 
3133  pg_free(keywords);
3134  pg_free(values);
3135 
3136  /* We can immediately discard the password -- no longer needed */
3137  if (password)
3138  pg_free(password);
3139 
3140  if (PQstatus(n_conn) == CONNECTION_OK)
3141  break;
3142 
3143  /*
3144  * Connection attempt failed; either retry the connection attempt with
3145  * a new password, or give up.
3146  */
3147  if (!password && PQconnectionNeedsPassword(n_conn) && pset.getPassword != TRI_NO)
3148  {
3149  PQfinish(n_conn);
3150  password = prompt_for_password(user);
3151  continue;
3152  }
3153 
3154  /*
3155  * Failed to connect to the database. In interactive mode, keep the
3156  * previous connection to the DB; in scripting mode, close our
3157  * previous connection as well.
3158  */
3160  {
3161  psql_error("%s", PQerrorMessage(n_conn));
3162 
3163  /* pset.db is left unmodified */
3164  if (o_conn)
3165  psql_error("Previous connection kept\n");
3166  }
3167  else
3168  {
3169  psql_error("\\connect: %s", PQerrorMessage(n_conn));
3170  if (o_conn)
3171  {
3172  PQfinish(o_conn);
3173  pset.db = NULL;
3174  }
3175  }
3176 
3177  PQfinish(n_conn);
3178  if (connstr.data)
3179  termPQExpBuffer(&connstr);
3180  return false;
3181  }
3182  if (connstr.data)
3183  termPQExpBuffer(&connstr);
3184 
3185  /*
3186  * Replace the old connection with the new one, and update
3187  * connection-dependent variables.
3188  */
3190  pset.db = n_conn;
3191  SyncVariables();
3192  connection_warnings(false); /* Must be after SyncVariables */
3193 
3194  /* Tell the user about the new connection */
3195  if (!pset.quiet)
3196  {
3197  if (!o_conn ||
3198  param_is_newly_set(PQhost(o_conn), PQhost(pset.db)) ||
3199  param_is_newly_set(PQport(o_conn), PQport(pset.db)))
3200  {
3201  char *host = PQhost(pset.db);
3202 
3203  /* If the host is an absolute path, the connection is via socket */
3204  if (is_absolute_path(host))
3205  printf(_("You are now connected to database \"%s\" as user \"%s\" via socket in \"%s\" at port \"%s\".\n"),
3206  PQdb(pset.db), PQuser(pset.db), host, PQport(pset.db));
3207  else
3208  printf(_("You are now connected to database \"%s\" as user \"%s\" on host \"%s\" at port \"%s\".\n"),
3209  PQdb(pset.db), PQuser(pset.db), host, PQport(pset.db));
3210  }
3211  else
3212  printf(_("You are now connected to database \"%s\" as user \"%s\".\n"),
3213  PQdb(pset.db), PQuser(pset.db));
3214  }
3215 
3216  if (o_conn)
3217  PQfinish(o_conn);
3218  return true;
3219 }
3220 
3221 
3222 void
3223 connection_warnings(bool in_startup)
3224 {
3225  if (!pset.quiet && !pset.notty)
3226  {
3227  int client_ver = PG_VERSION_NUM;
3228  char cverbuf[32];
3229  char sverbuf[32];
3230 
3231  if (pset.sversion != client_ver)
3232  {
3233  const char *server_version;
3234 
3235  /* Try to get full text form, might include "devel" etc */
3236  server_version = PQparameterStatus(pset.db, "server_version");
3237  /* Otherwise fall back on pset.sversion */
3238  if (!server_version)
3239  {
3241  sverbuf, sizeof(sverbuf));
3242  server_version = sverbuf;
3243  }
3244 
3245  printf(_("%s (%s, server %s)\n"),
3246  pset.progname, PG_VERSION, server_version);
3247  }
3248  /* For version match, only print psql banner on startup. */
3249  else if (in_startup)
3250  printf("%s (%s)\n", pset.progname, PG_VERSION);
3251 
3252  if (pset.sversion / 100 > client_ver / 100)
3253  printf(_("WARNING: %s major version %s, server major version %s.\n"
3254  " Some psql features might not work.\n"),
3255  pset.progname,
3256  formatPGVersionNumber(client_ver, false,
3257  cverbuf, sizeof(cverbuf)),
3259  sverbuf, sizeof(sverbuf)));
3260 
3261 #ifdef WIN32
3262  checkWin32Codepage();
3263 #endif
3264  printSSLInfo();
3265  }
3266 }
3267 
3268 
3269 /*
3270  * printSSLInfo
3271  *
3272  * Prints information about the current SSL connection, if SSL is in use
3273  */
3274 static void
3276 {
3277  const char *protocol;
3278  const char *cipher;
3279  const char *bits;
3280  const char *compression;
3281 
3282  if (!PQsslInUse(pset.db))
3283  return; /* no SSL */
3284 
3285  protocol = PQsslAttribute(pset.db, "protocol");
3286  cipher = PQsslAttribute(pset.db, "cipher");
3287  bits = PQsslAttribute(pset.db, "key_bits");
3288  compression = PQsslAttribute(pset.db, "compression");
3289 
3290  printf(_("SSL connection (protocol: %s, cipher: %s, bits: %s, compression: %s)\n"),
3291  protocol ? protocol : _("unknown"),
3292  cipher ? cipher : _("unknown"),
3293  bits ? bits : _("unknown"),
3294  (compression && strcmp(compression, "off") != 0) ? _("on") : _("off"));
3295 }
3296 
3297 
3298 /*
3299  * checkWin32Codepage
3300  *
3301  * Prints a warning when win32 console codepage differs from Windows codepage
3302  */
3303 #ifdef WIN32
3304 static void
3305 checkWin32Codepage(void)
3306 {
3307  unsigned int wincp,
3308  concp;
3309 
3310  wincp = GetACP();
3311  concp = GetConsoleCP();
3312  if (wincp != concp)
3313  {
3314  printf(_("WARNING: Console code page (%u) differs from Windows code page (%u)\n"
3315  " 8-bit characters might not work correctly. See psql reference\n"
3316  " page \"Notes for Windows users\" for details.\n"),
3317  concp, wincp);
3318  }
3319 }
3320 #endif
3321 
3322 
3323 /*
3324  * SyncVariables
3325  *
3326  * Make psql's internal variables agree with connection state upon
3327  * establishing a new connection.
3328  */
3329 void
3331 {
3332  /* get stuff from connection */
3336 
3337  SetVariable(pset.vars, "DBNAME", PQdb(pset.db));
3338  SetVariable(pset.vars, "USER", PQuser(pset.db));
3339  SetVariable(pset.vars, "HOST", PQhost(pset.db));
3340  SetVariable(pset.vars, "PORT", PQport(pset.db));
3342 
3343  /* send stuff to it, too */
3346 }
3347 
3348 /*
3349  * UnsyncVariables
3350  *
3351  * Clear variables that should be not be set when there is no connection.
3352  */
3353 void
3355 {
3356  SetVariable(pset.vars, "DBNAME", NULL);
3357  SetVariable(pset.vars, "USER", NULL);
3358  SetVariable(pset.vars, "HOST", NULL);
3359  SetVariable(pset.vars, "PORT", NULL);
3360  SetVariable(pset.vars, "ENCODING", NULL);
3361 }
3362 
3363 
3364 /*
3365  * do_edit -- handler for \e
3366  *
3367  * If you do not specify a filename, the current query buffer will be copied
3368  * into a temporary one.
3369  */
3370 static bool
3371 editFile(const char *fname, int lineno)
3372 {
3373  const char *editorName;
3374  const char *editor_lineno_arg = NULL;
3375  char *sys;
3376  int result;
3377 
3378  Assert(fname != NULL);
3379 
3380  /* Find an editor to use */
3381  editorName = getenv("PSQL_EDITOR");
3382  if (!editorName)
3383  editorName = getenv("EDITOR");
3384  if (!editorName)
3385  editorName = getenv("VISUAL");
3386  if (!editorName)
3387  editorName = DEFAULT_EDITOR;
3388 
3389  /* Get line number argument, if we need it. */
3390  if (lineno > 0)
3391  {
3392  editor_lineno_arg = getenv("PSQL_EDITOR_LINENUMBER_ARG");
3393 #ifdef DEFAULT_EDITOR_LINENUMBER_ARG
3394  if (!editor_lineno_arg)
3395  editor_lineno_arg = DEFAULT_EDITOR_LINENUMBER_ARG;
3396 #endif
3397  if (!editor_lineno_arg)
3398  {
3399  psql_error("environment variable PSQL_EDITOR_LINENUMBER_ARG must be set to specify a line number\n");
3400  return false;
3401  }
3402  }
3403 
3404  /*
3405  * On Unix the EDITOR value should *not* be quoted, since it might include
3406  * switches, eg, EDITOR="pico -t"; it's up to the user to put quotes in it
3407  * if necessary. But this policy is not very workable on Windows, due to
3408  * severe brain damage in their command shell plus the fact that standard
3409  * program paths include spaces.
3410  */
3411 #ifndef WIN32
3412  if (lineno > 0)
3413  sys = psprintf("exec %s %s%d '%s'",
3414  editorName, editor_lineno_arg, lineno, fname);
3415  else
3416  sys = psprintf("exec %s '%s'",
3417  editorName, fname);
3418 #else
3419  if (lineno > 0)
3420  sys = psprintf("\"%s\" %s%d \"%s\"",
3421  editorName, editor_lineno_arg, lineno, fname);
3422  else
3423  sys = psprintf("\"%s\" \"%s\"",
3424  editorName, fname);
3425 #endif
3426  result = system(sys);
3427  if (result == -1)
3428  psql_error("could not start editor \"%s\"\n", editorName);
3429  else if (result == 127)
3430  psql_error("could not start /bin/sh\n");
3431  free(sys);
3432 
3433  return result == 0;
3434 }
3435 
3436 
3437 /* call this one */
3438 static bool
3439 do_edit(const char *filename_arg, PQExpBuffer query_buf,
3440  int lineno, bool *edited)
3441 {
3442  char fnametmp[MAXPGPATH];
3443  FILE *stream = NULL;
3444  const char *fname;
3445  bool error = false;
3446  int fd;
3447 
3448  struct stat before,
3449  after;
3450 
3451  if (filename_arg)
3452  fname = filename_arg;
3453  else
3454  {
3455  /* make a temp file to edit */
3456 #ifndef WIN32
3457  const char *tmpdir = getenv("TMPDIR");
3458 
3459  if (!tmpdir)
3460  tmpdir = "/tmp";
3461 #else
3462  char tmpdir[MAXPGPATH];
3463  int ret;
3464 
3465  ret = GetTempPath(MAXPGPATH, tmpdir);
3466  if (ret == 0 || ret > MAXPGPATH)
3467  {
3468  psql_error("could not locate temporary directory: %s\n",
3469  !ret ? strerror(errno) : "");
3470  return false;
3471  }
3472 
3473  /*
3474  * No canonicalize_path() here. EDIT.EXE run from CMD.EXE prepends the
3475  * current directory to the supplied path unless we use only
3476  * backslashes, so we do that.
3477  */
3478 #endif
3479 #ifndef WIN32
3480  snprintf(fnametmp, sizeof(fnametmp), "%s%spsql.edit.%d.sql", tmpdir,
3481  "/", (int) getpid());
3482 #else
3483  snprintf(fnametmp, sizeof(fnametmp), "%s%spsql.edit.%d.sql", tmpdir,
3484  "" /* trailing separator already present */ , (int) getpid());
3485 #endif
3486 
3487  fname = (const char *) fnametmp;
3488 
3489  fd = open(fname, O_WRONLY | O_CREAT | O_EXCL, 0600);
3490  if (fd != -1)
3491  stream = fdopen(fd, "w");
3492 
3493  if (fd == -1 || !stream)
3494  {
3495  psql_error("could not open temporary file \"%s\": %s\n", fname, strerror(errno));
3496  error = true;
3497  }
3498  else
3499  {
3500  unsigned int ql = query_buf->len;
3501 
3502  if (ql == 0 || query_buf->data[ql - 1] != '\n')
3503  {
3504  appendPQExpBufferChar(query_buf, '\n');
3505  ql++;
3506  }
3507 
3508  if (fwrite(query_buf->data, 1, ql, stream) != ql)
3509  {
3510  psql_error("%s: %s\n", fname, strerror(errno));
3511 
3512  if (fclose(stream) != 0)
3513  psql_error("%s: %s\n", fname, strerror(errno));
3514 
3515  if (remove(fname) != 0)
3516  psql_error("%s: %s\n", fname, strerror(errno));
3517 
3518  error = true;
3519  }
3520  else if (fclose(stream) != 0)
3521  {
3522  psql_error("%s: %s\n", fname, strerror(errno));
3523  if (remove(fname) != 0)
3524  psql_error("%s: %s\n", fname, strerror(errno));
3525  error = true;
3526  }
3527  }
3528  }
3529 
3530  if (!error && stat(fname, &before) != 0)
3531  {
3532  psql_error("%s: %s\n", fname, strerror(errno));
3533  error = true;
3534  }
3535 
3536  /* call editor */
3537  if (!error)
3538  error = !editFile(fname, lineno);
3539 
3540  if (!error && stat(fname, &after) != 0)
3541  {
3542  psql_error("%s: %s\n", fname, strerror(errno));
3543  error = true;
3544  }
3545 
3546  if (!error && before.st_mtime != after.st_mtime)
3547  {
3548  stream = fopen(fname, PG_BINARY_R);
3549  if (!stream)
3550  {
3551  psql_error("%s: %s\n", fname, strerror(errno));
3552  error = true;
3553  }
3554  else
3555  {
3556  /* read file back into query_buf */
3557  char line[1024];
3558 
3559  resetPQExpBuffer(query_buf);
3560  while (fgets(line, sizeof(line), stream) != NULL)
3561  appendPQExpBufferStr(query_buf, line);
3562 
3563  if (ferror(stream))
3564  {
3565  psql_error("%s: %s\n", fname, strerror(errno));
3566  error = true;
3567  }
3568  else if (edited)
3569  {
3570  *edited = true;
3571  }
3572 
3573  fclose(stream);
3574  }
3575  }
3576 
3577  /* remove temp file */
3578  if (!filename_arg)
3579  {
3580  if (remove(fname) == -1)
3581  {
3582  psql_error("%s: %s\n", fname, strerror(errno));
3583  error = true;
3584  }
3585  }
3586 
3587  return !error;
3588 }
3589 
3590 
3591 
3592 /*
3593  * process_file
3594  *
3595  * Reads commands from filename and passes them to the main processing loop.
3596  * Handler for \i and \ir, but can be used for other things as well. Returns
3597  * MainLoop() error code.
3598  *
3599  * If use_relative_path is true and filename is not an absolute path, then open
3600  * the file from where the currently processed file (if any) is located.
3601  */
3602 int
3603 process_file(char *filename, bool use_relative_path)
3604 {
3605  FILE *fd;
3606  int result;
3607  char *oldfilename;
3608  char relpath[MAXPGPATH];
3609 
3610  if (!filename)
3611  {
3612  fd = stdin;
3613  filename = NULL;
3614  }
3615  else if (strcmp(filename, "-") != 0)
3616  {
3617  canonicalize_path(filename);
3618 
3619  /*
3620  * If we were asked to resolve the pathname relative to the location
3621  * of the currently executing script, and there is one, and this is a
3622  * relative pathname, then prepend all but the last pathname component
3623  * of the current script to this pathname.
3624  */
3625  if (use_relative_path && pset.inputfile &&
3626  !is_absolute_path(filename) && !has_drive_prefix(filename))
3627  {
3628  strlcpy(relpath, pset.inputfile, sizeof(relpath));
3629  get_parent_directory(relpath);
3630  join_path_components(relpath, relpath, filename);
3631  canonicalize_path(relpath);
3632 
3633  filename = relpath;
3634  }
3635 
3636  fd = fopen(filename, PG_BINARY_R);
3637 
3638  if (!fd)
3639  {
3640  psql_error("%s: %s\n", filename, strerror(errno));
3641  return EXIT_FAILURE;
3642  }
3643  }
3644  else
3645  {
3646  fd = stdin;
3647  filename = "<stdin>"; /* for future error messages */
3648  }
3649 
3650  oldfilename = pset.inputfile;
3652 
3653  result = MainLoop(fd);
3654 
3655  if (fd != stdin)
3656  fclose(fd);
3657 
3658  pset.inputfile = oldfilename;
3659  return result;
3660 }
3661 
3662 
3663 
3664 static const char *
3666 {
3667  switch (in)
3668  {
3669  case PRINT_NOTHING:
3670  return "nothing";
3671  break;
3672  case PRINT_UNALIGNED:
3673  return "unaligned";
3674  break;
3675  case PRINT_ALIGNED:
3676  return "aligned";
3677  break;
3678  case PRINT_WRAPPED:
3679  return "wrapped";
3680  break;
3681  case PRINT_HTML:
3682  return "html";
3683  break;
3684  case PRINT_ASCIIDOC:
3685  return "asciidoc";
3686  break;
3687  case PRINT_LATEX:
3688  return "latex";
3689  break;
3690  case PRINT_LATEX_LONGTABLE:
3691  return "latex-longtable";
3692  break;
3693  case PRINT_TROFF_MS:
3694  return "troff-ms";
3695  break;
3696  }
3697  return "unknown";
3698 }
3699 
3700 /*
3701  * Parse entered Unicode linestyle. If ok, update *linestyle and return
3702  * true, else return false.
3703  */
3704 static bool
3705 set_unicode_line_style(const char *value, size_t vallen,
3706  unicode_linestyle *linestyle)
3707 {
3708  if (pg_strncasecmp("single", value, vallen) == 0)
3709  *linestyle = UNICODE_LINESTYLE_SINGLE;
3710  else if (pg_strncasecmp("double", value, vallen) == 0)
3711  *linestyle = UNICODE_LINESTYLE_DOUBLE;
3712  else
3713  return false;
3714  return true;
3715 }
3716 
3717 static const char *
3719 {
3720  switch (linestyle)
3721  {
3723  return "single";
3724  break;
3726  return "double";
3727  break;
3728  }
3729  return "unknown";
3730 }
3731 
3732 /*
3733  * do_pset
3734  *
3735  */
3736 bool
3737 do_pset(const char *param, const char *value, printQueryOpt *popt, bool quiet)
3738 {
3739  size_t vallen = 0;
3740 
3741  Assert(param != NULL);
3742 
3743  if (value)
3744  vallen = strlen(value);
3745 
3746  /* set format */
3747  if (strcmp(param, "format") == 0)
3748  {
3749  if (!value)
3750  ;
3751  else if (pg_strncasecmp("unaligned", value, vallen) == 0)
3752  popt->topt.format = PRINT_UNALIGNED;
3753  else if (pg_strncasecmp("aligned", value, vallen) == 0)
3754  popt->topt.format = PRINT_ALIGNED;
3755  else if (pg_strncasecmp("wrapped", value, vallen) == 0)
3756  popt->topt.format = PRINT_WRAPPED;
3757  else if (pg_strncasecmp("html", value, vallen) == 0)
3758  popt->topt.format = PRINT_HTML;
3759  else if (pg_strncasecmp("asciidoc", value, vallen) == 0)
3760  popt->topt.format = PRINT_ASCIIDOC;
3761  else if (pg_strncasecmp("latex", value, vallen) == 0)
3762  popt->topt.format = PRINT_LATEX;
3763  else if (pg_strncasecmp("latex-longtable", value, vallen) == 0)
3765  else if (pg_strncasecmp("troff-ms", value, vallen) == 0)
3766  popt->topt.format = PRINT_TROFF_MS;
3767  else
3768  {
3769  psql_error("\\pset: allowed formats are unaligned, aligned, wrapped, html, asciidoc, latex, latex-longtable, troff-ms\n");
3770  return false;
3771  }
3772  }
3773 
3774  /* set table line style */
3775  else if (strcmp(param, "linestyle") == 0)
3776  {
3777  if (!value)
3778  ;
3779  else if (pg_strncasecmp("ascii", value, vallen) == 0)
3780  popt->topt.line_style = &pg_asciiformat;
3781  else if (pg_strncasecmp("old-ascii", value, vallen) == 0)
3783  else if (pg_strncasecmp("unicode", value, vallen) == 0)
3784  popt->topt.line_style = &pg_utf8format;
3785  else
3786  {
3787  psql_error("\\pset: allowed line styles are ascii, old-ascii, unicode\n");
3788  return false;
3789  }
3790  }
3791 
3792  /* set unicode border line style */
3793  else if (strcmp(param, "unicode_border_linestyle") == 0)
3794  {
3795  if (!value)
3796  ;
3797  else if (set_unicode_line_style(value, vallen,
3799  refresh_utf8format(&(popt->topt));
3800  else
3801  {
3802  psql_error("\\pset: allowed Unicode border line styles are single, double\n");
3803  return false;
3804  }
3805  }
3806 
3807  /* set unicode column line style */
3808  else if (strcmp(param, "unicode_column_linestyle") == 0)
3809  {
3810  if (!value)
3811  ;
3812  else if (set_unicode_line_style(value, vallen,
3814  refresh_utf8format(&(popt->topt));
3815  else
3816  {
3817  psql_error("\\pset: allowed Unicode column line styles are single, double\n");
3818  return false;
3819  }
3820  }
3821 
3822  /* set unicode header line style */
3823  else if (strcmp(param, "unicode_header_linestyle") == 0)
3824  {
3825  if (!value)
3826  ;
3827  else if (set_unicode_line_style(value, vallen,
3829  refresh_utf8format(&(popt->topt));
3830  else
3831  {
3832  psql_error("\\pset: allowed Unicode header line styles are single, double\n");
3833  return false;
3834  }
3835  }
3836 
3837  /* set border style/width */
3838  else if (strcmp(param, "border") == 0)
3839  {
3840  if (value)
3841  popt->topt.border = atoi(value);
3842  }
3843 
3844  /* set expanded/vertical mode */
3845  else if (strcmp(param, "x") == 0 ||
3846  strcmp(param, "expanded") == 0 ||
3847  strcmp(param, "vertical") == 0)
3848  {
3849  if (value && pg_strcasecmp(value, "auto") == 0)
3850  popt->topt.expanded = 2;
3851  else if (value)
3852  {
3853  bool on_off;
3854 
3855  if (ParseVariableBool(value, NULL, &on_off))
3856  popt->topt.expanded = on_off ? 1 : 0;
3857  else
3858  {
3859  PsqlVarEnumError(param, value, "on, off, auto");
3860  return false;
3861  }
3862  }
3863  else
3864  popt->topt.expanded = !popt->topt.expanded;
3865  }
3866 
3867  /* locale-aware numeric output */
3868  else if (strcmp(param, "numericlocale") == 0)
3869  {
3870  if (value)
3871  return ParseVariableBool(value, param, &popt->topt.numericLocale);
3872  else
3873  popt->topt.numericLocale = !popt->topt.numericLocale;
3874  }
3875 
3876  /* null display */
3877  else if (strcmp(param, "null") == 0)
3878  {
3879  if (value)
3880  {
3881  free(popt->nullPrint);
3882  popt->nullPrint = pg_strdup(value);
3883  }
3884  }
3885 
3886  /* field separator for unaligned text */
3887  else if (strcmp(param, "fieldsep") == 0)
3888  {
3889  if (value)
3890  {
3891  free(popt->topt.fieldSep.separator);
3892  popt->topt.fieldSep.separator = pg_strdup(value);
3893  popt->topt.fieldSep.separator_zero = false;
3894  }
3895  }
3896 
3897  else if (strcmp(param, "fieldsep_zero") == 0)
3898  {
3899  free(popt->topt.fieldSep.separator);
3900  popt->topt.fieldSep.separator = NULL;
3901  popt->topt.fieldSep.separator_zero = true;
3902  }
3903 
3904  /* record separator for unaligned text */
3905  else if (strcmp(param, "recordsep") == 0)
3906  {
3907  if (value)
3908  {
3909  free(popt->topt.recordSep.separator);
3910  popt->topt.recordSep.separator = pg_strdup(value);
3911  popt->topt.recordSep.separator_zero = false;
3912  }
3913  }
3914 
3915  else if (strcmp(param, "recordsep_zero") == 0)
3916  {
3917  free(popt->topt.recordSep.separator);
3918  popt->topt.recordSep.separator = NULL;
3919  popt->topt.recordSep.separator_zero = true;
3920  }
3921 
3922  /* toggle between full and tuples-only format */
3923  else if (strcmp(param, "t") == 0 || strcmp(param, "tuples_only") == 0)
3924  {
3925  if (value)
3926  return ParseVariableBool(value, param, &popt->topt.tuples_only);
3927  else
3928  popt->topt.tuples_only = !popt->topt.tuples_only;
3929  }
3930 
3931  /* set title override */
3932  else if (strcmp(param, "C") == 0 || strcmp(param, "title") == 0)
3933  {
3934  free(popt->title);
3935  if (!value)
3936  popt->title = NULL;
3937  else
3938  popt->title = pg_strdup(value);
3939  }
3940 
3941  /* set HTML table tag options */
3942  else if (strcmp(param, "T") == 0 || strcmp(param, "tableattr") == 0)
3943  {
3944  free(popt->topt.tableAttr);
3945  if (!value)
3946  popt->topt.tableAttr = NULL;
3947  else
3948  popt->topt.tableAttr = pg_strdup(value);
3949  }
3950 
3951  /* toggle use of pager */
3952  else if (strcmp(param, "pager") == 0)
3953  {
3954  if (value && pg_strcasecmp(value, "always") == 0)
3955  popt->topt.pager = 2;
3956  else if (value)
3957  {
3958  bool on_off;
3959 
3960  if (!ParseVariableBool(value, NULL, &on_off))
3961  {
3962  PsqlVarEnumError(param, value, "on, off, always");
3963  return false;
3964  }
3965  popt->topt.pager = on_off ? 1 : 0;
3966  }
3967  else if (popt->topt.pager == 1)
3968  popt->topt.pager = 0;
3969  else
3970  popt->topt.pager = 1;
3971  }
3972 
3973  /* set minimum lines for pager use */
3974  else if (strcmp(param, "pager_min_lines") == 0)
3975  {
3976  if (value)
3977  popt->topt.pager_min_lines = atoi(value);
3978  }
3979 
3980  /* disable "(x rows)" footer */
3981  else if (strcmp(param, "footer") == 0)
3982  {
3983  if (value)
3984  return ParseVariableBool(value, param, &popt->topt.default_footer);
3985  else
3986  popt->topt.default_footer = !popt->topt.default_footer;
3987  }
3988 
3989  /* set border style/width */
3990  else if (strcmp(param, "columns") == 0)
3991  {
3992  if (value)
3993  popt->topt.columns = atoi(value);
3994  }
3995  else
3996  {
3997  psql_error("\\pset: unknown option: %s\n", param);
3998  return false;
3999  }
4000 
4001  if (!quiet)
4002  printPsetInfo(param, &pset.popt);
4003 
4004  return true;
4005 }
4006 
4007 
4008 static bool
4009 printPsetInfo(const char *param, struct printQueryOpt *popt)
4010 {
4011  Assert(param != NULL);
4012 
4013  /* show border style/width */
4014  if (strcmp(param, "border") == 0)
4015  printf(_("Border style is %d.\n"), popt->topt.border);
4016 
4017  /* show the target width for the wrapped format */
4018  else if (strcmp(param, "columns") == 0)
4019  {
4020  if (!popt->topt.columns)
4021  printf(_("Target width is unset.\n"));
4022  else
4023  printf(_("Target width is %d.\n"), popt->topt.columns);
4024  }
4025 
4026  /* show expanded/vertical mode */
4027  else if (strcmp(param, "x") == 0 || strcmp(param, "expanded") == 0 || strcmp(param, "vertical") == 0)
4028  {
4029  if (popt->topt.expanded == 1)
4030  printf(_("Expanded display is on.\n"));
4031  else if (popt->topt.expanded == 2)
4032  printf(_("Expanded display is used automatically.\n"));
4033  else
4034  printf(_("Expanded display is off.\n"));
4035  }
4036 
4037  /* show field separator for unaligned text */
4038  else if (strcmp(param, "fieldsep") == 0)
4039  {
4040  if (popt->topt.fieldSep.separator_zero)
4041  printf(_("Field separator is zero byte.\n"));
4042  else
4043  printf(_("Field separator is \"%s\".\n"),
4044  popt->topt.fieldSep.separator);
4045  }
4046 
4047  else if (strcmp(param, "fieldsep_zero") == 0)
4048  {
4049  printf(_("Field separator is zero byte.\n"));
4050  }
4051 
4052  /* show disable "(x rows)" footer */
4053  else if (strcmp(param, "footer") == 0)
4054  {
4055  if (popt->topt.default_footer)
4056  printf(_("Default footer is on.\n"));
4057  else
4058  printf(_("Default footer is off.\n"));
4059  }
4060 
4061  /* show format */
4062  else if (strcmp(param, "format") == 0)
4063  {
4064  printf(_("Output format is %s.\n"), _align2string(popt->topt.format));
4065  }
4066 
4067  /* show table line style */
4068  else if (strcmp(param, "linestyle") == 0)
4069  {
4070  printf(_("Line style is %s.\n"),
4071  get_line_style(&popt->topt)->name);
4072  }
4073 
4074  /* show null display */
4075  else if (strcmp(param, "null") == 0)
4076  {
4077  printf(_("Null display is \"%s\".\n"),
4078  popt->nullPrint ? popt->nullPrint : "");
4079  }
4080 
4081  /* show locale-aware numeric output */
4082  else if (strcmp(param, "numericlocale") == 0)
4083  {
4084  if (popt->topt.numericLocale)
4085  printf(_("Locale-adjusted numeric output is on.\n"));
4086  else
4087  printf(_("Locale-adjusted numeric output is off.\n"));
4088  }
4089 
4090  /* show toggle use of pager */
4091  else if (strcmp(param, "pager") == 0)
4092  {
4093  if (popt->topt.pager == 1)
4094  printf(_("Pager is used for long output.\n"));
4095  else if (popt->topt.pager == 2)
4096  printf(_("Pager is always used.\n"));
4097  else
4098  printf(_("Pager usage is off.\n"));
4099  }
4100 
4101  /* show minimum lines for pager use */
4102  else if (strcmp(param, "pager_min_lines") == 0)
4103  {
4104  printf(ngettext("Pager won't be used for less than %d line.\n",
4105  "Pager won't be used for less than %d lines.\n",
4106  popt->topt.pager_min_lines),
4107  popt->topt.pager_min_lines);
4108  }
4109 
4110  /* show record separator for unaligned text */
4111  else if (strcmp(param, "recordsep") == 0)
4112  {
4113  if (popt->topt.recordSep.separator_zero)
4114  printf(_("Record separator is zero byte.\n"));
4115  else if (strcmp(popt->topt.recordSep.separator, "\n") == 0)
4116  printf(_("Record separator is <newline>.\n"));
4117  else
4118  printf(_("Record separator is \"%s\".\n"),
4119  popt->topt.recordSep.separator);
4120  }
4121 
4122  else if (strcmp(param, "recordsep_zero") == 0)
4123  {
4124  printf(_("Record separator is zero byte.\n"));
4125  }
4126 
4127  /* show HTML table tag options */
4128  else if (strcmp(param, "T") == 0 || strcmp(param, "tableattr") == 0)
4129  {
4130  if (popt->topt.tableAttr)
4131  printf(_("Table attributes are \"%s\".\n"),
4132  popt->topt.tableAttr);
4133  else
4134  printf(_("Table attributes unset.\n"));
4135  }
4136 
4137  /* show title override */
4138  else if (strcmp(param, "C") == 0 || strcmp(param, "title") == 0)
4139  {
4140  if (popt->title)
4141  printf(_("Title is \"%s\".\n"), popt->title);
4142  else
4143  printf(_("Title is unset.\n"));
4144  }
4145 
4146  /* show toggle between full and tuples-only format */
4147  else if (strcmp(param, "t") == 0 || strcmp(param, "tuples_only") == 0)
4148  {
4149  if (popt->topt.tuples_only)
4150  printf(_("Tuples only is on.\n"));
4151  else
4152  printf(_("Tuples only is off.\n"));
4153  }
4154 
4155  /* Unicode style formatting */
4156  else if (strcmp(param, "unicode_border_linestyle") == 0)
4157  {
4158  printf(_("Unicode border line style is \"%s\".\n"),
4160  }
4161 
4162  else if (strcmp(param, "unicode_column_linestyle") == 0)
4163  {
4164  printf(_("Unicode column line style is \"%s\".\n"),
4166  }
4167 
4168  else if (strcmp(param, "unicode_header_linestyle") == 0)
4169  {
4170  printf(_("Unicode header line style is \"%s\".\n"),
4172  }
4173 
4174  else
4175  {
4176  psql_error("\\pset: unknown option: %s\n", param);
4177  return false;
4178  }
4179 
4180  return true;
4181 }
4182 
4183 
4184 static const char *
4186 {
4187  return val ? "on" : "off";
4188 }
4189 
4190 
4191 static char *
4192 pset_quoted_string(const char *str)
4193 {
4194  char *ret = pg_malloc(strlen(str) * 2 + 3);
4195  char *r = ret;
4196 
4197  *r++ = '\'';
4198 
4199  for (; *str; str++)
4200  {
4201  if (*str == '\n')
4202  {
4203  *r++ = '\\';
4204  *r++ = 'n';
4205  }
4206  else if (*str == '\'')
4207  {
4208  *r++ = '\\';
4209  *r++ = '\'';
4210  }
4211  else
4212  *r++ = *str;
4213  }
4214 
4215  *r++ = '\'';
4216  *r = '\0';
4217 
4218  return ret;
4219 }
4220 
4221 
4222 /*
4223  * Return a malloc'ed string for the \pset value.
4224  *
4225  * Note that for some string parameters, print.c distinguishes between unset
4226  * and empty string, but for others it doesn't. This function should produce
4227  * output that produces the correct setting when fed back into \pset.
4228  */
4229 static char *
4230 pset_value_string(const char *param, struct printQueryOpt *popt)
4231 {
4232  Assert(param != NULL);
4233 
4234  if (strcmp(param, "border") == 0)
4235  return psprintf("%d", popt->topt.border);
4236  else if (strcmp(param, "columns") == 0)
4237  return psprintf("%d", popt->topt.columns);
4238  else if (strcmp(param, "expanded") == 0)
4239  return pstrdup(popt->topt.expanded == 2
4240  ? "auto"
4241  : pset_bool_string(popt->topt.expanded));
4242  else if (strcmp(param, "fieldsep") == 0)
4244  ? popt->topt.fieldSep.separator
4245  : "");
4246  else if (strcmp(param, "fieldsep_zero") == 0)
4248  else if (strcmp(param, "footer") == 0)
4250  else if (strcmp(param, "format") == 0)
4251  return psprintf("%s", _align2string(popt->topt.format));
4252  else if (strcmp(param, "linestyle") == 0)
4253  return psprintf("%s", get_line_style(&popt->topt)->name);
4254  else if (strcmp(param, "null") == 0)
4255  return pset_quoted_string(popt->nullPrint
4256  ? popt->nullPrint
4257  : "");
4258  else if (strcmp(param, "numericlocale") == 0)
4259  return pstrdup(pset_bool_string(popt->topt.numericLocale));
4260  else if (strcmp(param, "pager") == 0)
4261  return psprintf("%d", popt->topt.pager);
4262  else if (strcmp(param, "pager_min_lines") == 0)
4263  return psprintf("%d", popt->topt.pager_min_lines);
4264  else if (strcmp(param, "recordsep") == 0)
4266  ? popt->topt.recordSep.separator
4267  : "");
4268  else if (strcmp(param, "recordsep_zero") == 0)
4270  else if (strcmp(param, "tableattr") == 0)
4271  return popt->topt.tableAttr ? pset_quoted_string(popt->topt.tableAttr) : pstrdup("");
4272  else if (strcmp(param, "title") == 0)
4273  return popt->title ? pset_quoted_string(popt->title) : pstrdup("");
4274  else if (strcmp(param, "tuples_only") == 0)
4275  return pstrdup(pset_bool_string(popt->topt.tuples_only));
4276  else if (strcmp(param, "unicode_border_linestyle") == 0)
4278  else if (strcmp(param, "unicode_column_linestyle") == 0)
4280  else if (strcmp(param, "unicode_header_linestyle") == 0)
4282  else
4283  return pstrdup("ERROR");
4284 }
4285 
4286 
4287 
4288 #ifndef WIN32
4289 #define DEFAULT_SHELL "/bin/sh"
4290 #else
4291 /*
4292  * CMD.EXE is in different places in different Win32 releases so we
4293  * have to rely on the path to find it.
4294  */
4295 #define DEFAULT_SHELL "cmd.exe"
4296 #endif
4297 
4298 static bool
4299 do_shell(const char *command)
4300 {
4301  int result;
4302 
4303  if (!command)
4304  {
4305  char *sys;
4306  const char *shellName;
4307 
4308  shellName = getenv("SHELL");
4309 #ifdef WIN32
4310  if (shellName == NULL)
4311  shellName = getenv("COMSPEC");
4312 #endif
4313  if (shellName == NULL)
4314  shellName = DEFAULT_SHELL;
4315 
4316  /* See EDITOR handling comment for an explanation */
4317 #ifndef WIN32
4318  sys = psprintf("exec %s", shellName);
4319 #else
4320  sys = psprintf("\"%s\"", shellName);
4321 #endif
4322  result = system(sys);
4323  free(sys);
4324  }
4325  else
4326  result = system(command);
4327 
4328  if (result == 127 || result == -1)
4329  {
4330  psql_error("\\!: failed\n");
4331  return false;
4332  }
4333  return true;
4334 }
4335 
4336 /*
4337  * do_watch -- handler for \watch
4338  *
4339  * We break this out of exec_command to avoid having to plaster "volatile"
4340  * onto a bunch of exec_command's variables to silence stupider compilers.
4341  */
4342 static bool
4343 do_watch(PQExpBuffer query_buf, double sleep)
4344 {
4345  long sleep_ms = (long) (sleep * 1000);
4346  printQueryOpt myopt = pset.popt;
4347  const char *strftime_fmt;
4348  const char *user_title;
4349  char *title;
4350  int title_len;
4351  int res = 0;
4352 
4353  if (!query_buf || query_buf->len <= 0)
4354  {
4355  psql_error(_("\\watch cannot be used with an empty query\n"));
4356  return false;
4357  }
4358 
4359  /*
4360  * Choose format for timestamps. We might eventually make this a \pset
4361  * option. In the meantime, using a variable for the format suppresses
4362  * overly-anal-retentive gcc warnings about %c being Y2K sensitive.
4363  */
4364  strftime_fmt = "%c";
4365 
4366  /*
4367  * Set up rendering options, in particular, disable the pager, because
4368  * nobody wants to be prompted while watching the output of 'watch'.
4369  */
4370  myopt.topt.pager = 0;
4371 
4372  /*
4373  * If there's a title in the user configuration, make sure we have room
4374  * for it in the title buffer. Allow 128 bytes for the timestamp plus 128
4375  * bytes for the rest.
4376  */
4377  user_title = myopt.title;
4378  title_len = (user_title ? strlen(user_title) : 0) + 256;
4379  title = pg_malloc(title_len);
4380 
4381  for (;;)
4382  {
4383  time_t timer;
4384  char timebuf[128];
4385  long i;
4386 
4387  /*
4388  * Prepare title for output. Note that we intentionally include a
4389  * newline at the end of the title; this is somewhat historical but it
4390  * makes for reasonably nicely formatted output in simple cases.
4391  */
4392  timer = time(NULL);
4393  strftime(timebuf, sizeof(timebuf), strftime_fmt, localtime(&timer));
4394 
4395  if (user_title)
4396  snprintf(title, title_len, _("%s\t%s (every %gs)\n"),
4397  user_title, timebuf, sleep);
4398  else
4399  snprintf(title, title_len, _("%s (every %gs)\n"),
4400  timebuf, sleep);
4401  myopt.title = title;
4402 
4403  /* Run the query and print out the results */
4404  res = PSQLexecWatch(query_buf->data, &myopt);
4405 
4406  /*
4407  * PSQLexecWatch handles the case where we can no longer repeat the
4408  * query, and returns 0 or -1.
4409  */
4410  if (res <= 0)
4411  break;
4412 
4413  /*
4414  * Set up cancellation of 'watch' via SIGINT. We redo this each time
4415  * through the loop since it's conceivable something inside
4416  * PSQLexecWatch could change sigint_interrupt_jmp.
4417  */
4418  if (sigsetjmp(sigint_interrupt_jmp, 1) != 0)
4419  break;
4420 
4421  /*
4422  * Enable 'watch' cancellations and wait a while before running the
4423  * query again. Break the sleep into short intervals (at most 1s)
4424  * since pg_usleep isn't interruptible on some platforms.
4425  */
4426  sigint_interrupt_enabled = true;
4427  i = sleep_ms;
4428  while (i > 0)
4429  {
4430  long s = Min(i, 1000L);
4431 
4432  pg_usleep(s * 1000L);
4433  if (cancel_pressed)
4434  break;
4435  i -= s;
4436  }
4437  sigint_interrupt_enabled = false;
4438  }
4439 
4440  pg_free(title);
4441  return (res >= 0);
4442 }
4443 
4444 /*
4445  * a little code borrowed from PSQLexec() to manage ECHO_HIDDEN output.
4446  * returns true unless we have ECHO_HIDDEN_NOEXEC.
4447  */
4448 static bool
4449 echo_hidden_command(const char *query)
4450 {
4452  {
4453  printf(_("********* QUERY **********\n"
4454  "%s\n"
4455  "**************************\n\n"), query);
4456  fflush(stdout);
4457  if (pset.logfile)
4458  {
4459  fprintf(pset.logfile,
4460  _("********* QUERY **********\n"
4461  "%s\n"
4462  "**************************\n\n"), query);
4463  fflush(pset.logfile);
4464  }
4465 
4467  return false;
4468  }
4469  return true;
4470 }
4471 
4472 /*
4473  * Look up the object identified by obj_type and desc. If successful,
4474  * store its OID in *obj_oid and return TRUE, else return FALSE.
4475  *
4476  * Note that we'll fail if the object doesn't exist OR if there are multiple
4477  * matching candidates OR if there's something syntactically wrong with the
4478  * object description; unfortunately it can be hard to tell the difference.
4479  */
4480 static bool
4481 lookup_object_oid(EditableObjectType obj_type, const char *desc,
4482  Oid *obj_oid)
4483 {
4484  bool result = true;
4485  PQExpBuffer query = createPQExpBuffer();
4486  PGresult *res;
4487 
4488  switch (obj_type)
4489  {
4490  case EditableFunction:
4491 
4492  /*
4493  * We have a function description, e.g. "x" or "x(int)". Issue a
4494  * query to retrieve the function's OID using a cast to regproc or
4495  * regprocedure (as appropriate).
4496  */
4497  appendPQExpBufferStr(query, "SELECT ");
4498  appendStringLiteralConn(query, desc, pset.db);
4499  appendPQExpBuffer(query, "::pg_catalog.%s::pg_catalog.oid",
4500  strchr(desc, '(') ? "regprocedure" : "regproc");
4501  break;
4502 
4503  case EditableView:
4504 
4505  /*
4506  * Convert view name (possibly schema-qualified) to OID. Note:
4507  * this code doesn't check if the relation is actually a view.
4508  * We'll detect that in get_create_object_cmd().
4509  */
4510  appendPQExpBufferStr(query, "SELECT ");
4511  appendStringLiteralConn(query, desc, pset.db);
4512  appendPQExpBuffer(query, "::pg_catalog.regclass::pg_catalog.oid");
4513  break;
4514  }
4515 
4516  if (!echo_hidden_command(query->data))
4517  {
4518  destroyPQExpBuffer(query);
4519  return false;
4520  }
4521  res = PQexec(pset.db, query->data);
4522  if (PQresultStatus(res) == PGRES_TUPLES_OK && PQntuples(res) == 1)
4523  *obj_oid = atooid(PQgetvalue(res, 0, 0));
4524  else
4525  {
4526  minimal_error_message(res);
4527  result = false;
4528  }
4529 
4530  PQclear(res);
4531  destroyPQExpBuffer(query);
4532 
4533  return result;
4534 }
4535 
4536 /*
4537  * Construct a "CREATE OR REPLACE ..." command that describes the specified
4538  * database object. If successful, the result is stored in buf.
4539  */
4540 static bool
4542  PQExpBuffer buf)
4543 {
4544  bool result = true;
4545  PQExpBuffer query = createPQExpBuffer();
4546  PGresult *res;
4547 
4548  switch (obj_type)
4549  {
4550  case EditableFunction:
4551  printfPQExpBuffer(query,
4552  "SELECT pg_catalog.pg_get_functiondef(%u)",
4553  oid);
4554  break;
4555 
4556  case EditableView:
4557 
4558  /*
4559  * pg_get_viewdef() just prints the query, so we must prepend
4560  * CREATE for ourselves. We must fully qualify the view name to
4561  * ensure the right view gets replaced. Also, check relation kind
4562  * to be sure it's a view.
4563  *
4564  * Starting with 9.2, views may have reloptions (security_barrier)
4565  * and from 9.4 onwards they may also have WITH [LOCAL|CASCADED]
4566  * CHECK OPTION. These are not part of the view definition
4567  * returned by pg_get_viewdef() and so need to be retrieved
4568  * separately. Materialized views (introduced in 9.3) may have
4569  * arbitrary storage parameter reloptions.
4570  */
4571  if (pset.sversion >= 90400)
4572  {
4573  printfPQExpBuffer(query,
4574  "SELECT nspname, relname, relkind, "
4575  "pg_catalog.pg_get_viewdef(c.oid, true), "
4576  "array_remove(array_remove(c.reloptions,'check_option=local'),'check_option=cascaded') AS reloptions, "
4577  "CASE WHEN 'check_option=local' = ANY (c.reloptions) THEN 'LOCAL'::text "
4578  "WHEN 'check_option=cascaded' = ANY (c.reloptions) THEN 'CASCADED'::text ELSE NULL END AS checkoption "
4579  "FROM pg_catalog.pg_class c "
4580  "LEFT JOIN pg_catalog.pg_namespace n "
4581  "ON c.relnamespace = n.oid WHERE c.oid = %u",
4582  oid);
4583  }
4584  else if (pset.sversion >= 90200)
4585  {
4586  printfPQExpBuffer(query,
4587  "SELECT nspname, relname, relkind, "
4588  "pg_catalog.pg_get_viewdef(c.oid, true), "
4589  "c.reloptions AS reloptions, "
4590  "NULL AS checkoption "
4591  "FROM pg_catalog.pg_class c "
4592  "LEFT JOIN pg_catalog.pg_namespace n "
4593  "ON c.relnamespace = n.oid WHERE c.oid = %u",
4594  oid);
4595  }
4596  else
4597  {
4598  printfPQExpBuffer(query,
4599  "SELECT nspname, relname, relkind, "
4600  "pg_catalog.pg_get_viewdef(c.oid, true), "
4601  "NULL AS reloptions, "
4602  "NULL AS checkoption "
4603  "FROM pg_catalog.pg_class c "
4604  "LEFT JOIN pg_catalog.pg_namespace n "
4605  "ON c.relnamespace = n.oid WHERE c.oid = %u",
4606  oid);
4607  }
4608  break;
4609  }
4610 
4611  if (!echo_hidden_command(query->data))
4612  {
4613  destroyPQExpBuffer(query);
4614  return false;
4615  }
4616  res = PQexec(pset.db, query->data);
4617  if (PQresultStatus(res) == PGRES_TUPLES_OK && PQntuples(res) == 1)
4618  {
4619  resetPQExpBuffer(buf);
4620  switch (obj_type)
4621  {
4622  case EditableFunction:
4623  appendPQExpBufferStr(buf, PQgetvalue(res, 0, 0));
4624  break;
4625 
4626  case EditableView:
4627  {
4628  char *nspname = PQgetvalue(res, 0, 0);
4629  char *relname = PQgetvalue(res, 0, 1);
4630  char *relkind = PQgetvalue(res, 0, 2);
4631  char *viewdef = PQgetvalue(res, 0, 3);
4632  char *reloptions = PQgetvalue(res, 0, 4);
4633  char *checkoption = PQgetvalue(res, 0, 5);
4634 
4635  /*
4636  * If the backend ever supports CREATE OR REPLACE
4637  * MATERIALIZED VIEW, allow that here; but as of today it
4638  * does not, so editing a matview definition in this way
4639  * is impossible.
4640  */
4641  switch (relkind[0])
4642  {
4643 #ifdef NOT_USED
4644  case RELKIND_MATVIEW:
4645  appendPQExpBufferStr(buf, "CREATE OR REPLACE MATERIALIZED VIEW ");
4646  break;
4647 #endif
4648  case RELKIND_VIEW:
4649  appendPQExpBufferStr(buf, "CREATE OR REPLACE VIEW ");
4650  break;
4651  default:
4652  psql_error("\"%s.%s\" is not a view\n",
4653  nspname, relname);
4654  result = false;
4655  break;
4656  }
4657  appendPQExpBuffer(buf, "%s.", fmtId(nspname));
4658  appendPQExpBufferStr(buf, fmtId(relname));
4659 
4660  /* reloptions, if not an empty array "{}" */
4661  if (reloptions != NULL && strlen(reloptions) > 2)
4662  {
4663  appendPQExpBufferStr(buf, "\n WITH (");
4664  if (!appendReloptionsArray(buf, reloptions, "",
4665  pset.encoding,
4666  standard_strings()))
4667  {
4668  psql_error("could not parse reloptions array\n");
4669  result = false;
4670  }
4671  appendPQExpBufferStr(buf, ")");
4672  }
4673 
4674  /* View definition from pg_get_viewdef (a SELECT query) */
4675  appendPQExpBuffer(buf, " AS\n%s", viewdef);
4676 
4677  /* Get rid of the semicolon that pg_get_viewdef appends */
4678  if (buf->len > 0 && buf->data[buf->len - 1] == ';')
4679  buf->data[--(buf->len)] = '\0';
4680 
4681  /* WITH [LOCAL|CASCADED] CHECK OPTION */
4682  if (checkoption && checkoption[0] != '\0')
4683  appendPQExpBuffer(buf, "\n WITH %s CHECK OPTION",
4684  checkoption);
4685  }
4686  break;
4687  }
4688  /* Make sure result ends with a newline */
4689  if (buf->len > 0 && buf->data[buf->len - 1] != '\n')
4690  appendPQExpBufferChar(buf, '\n');
4691  }
4692  else
4693  {
4694  minimal_error_message(res);
4695  result = false;
4696  }
4697 
4698  PQclear(res);
4699  destroyPQExpBuffer(query);
4700 
4701  return result;
4702 }
4703 
4704 /*
4705  * If the given argument of \ef or \ev ends with a line number, delete the line
4706  * number from the argument string and return it as an integer. (We need
4707  * this kluge because we're too lazy to parse \ef's function or \ev's view
4708  * argument carefully --- we just slop it up in OT_WHOLE_LINE mode.)
4709  *
4710  * Returns -1 if no line number is present, 0 on error, or a positive value
4711  * on success.
4712  */
4713 static int
4715 {
4716  char *c;
4717  int lineno;
4718 
4719  if (!obj || obj[0] == '\0')
4720  return -1;
4721 
4722  c = obj + strlen(obj) - 1;
4723 
4724  /*
4725  * This business of parsing backwards is dangerous as can be in a
4726  * multibyte environment: there is no reason to believe that we are
4727  * looking at the first byte of a character, nor are we necessarily
4728  * working in a "safe" encoding. Fortunately the bitpatterns we are
4729  * looking for are unlikely to occur as non-first bytes, but beware of
4730  * trying to expand the set of cases that can be recognized. We must
4731  * guard the <ctype.h> macros by using isascii() first, too.
4732  */
4733 
4734  /* skip trailing whitespace */
4735  while (c > obj && isascii((unsigned char) *c) && isspace((unsigned char) *c))
4736  c--;
4737 
4738  /* must have a digit as last non-space char */
4739  if (c == obj || !isascii((unsigned char) *c) || !isdigit((unsigned char) *c))
4740  return -1;
4741 
4742  /* find start of digit string */
4743  while (c > obj && isascii((unsigned char) *c) && isdigit((unsigned char) *c))
4744  c--;
4745 
4746  /* digits must be separated from object name by space or closing paren */
4747  /* notice also that we are not allowing an empty object name ... */
4748  if (c == obj || !isascii((unsigned char) *c) ||
4749  !(isspace((unsigned char) *c) || *c == ')'))
4750  return -1;
4751 
4752  /* parse digit string */
4753  c++;
4754  lineno = atoi(c);
4755  if (lineno < 1)
4756  {
4757  psql_error("invalid line number: %s\n", c);
4758  return 0;
4759  }
4760 
4761  /* strip digit string from object name */
4762  *c = '\0';
4763 
4764  return lineno;
4765 }
4766 
4767 /*
4768  * Count number of lines in the buffer.
4769  * This is used to test if pager is needed or not.
4770  */
4771 static int
4773 {
4774  int lineno = 0;
4775  const char *lines = buf->data;
4776 
4777  while (*lines != '\0')
4778  {
4779  lineno++;
4780  /* find start of next line */
4781  lines = strchr(lines, '\n');
4782  if (!lines)
4783  break;
4784  lines++;
4785  }
4786 
4787  return lineno;
4788 }
4789 
4790 /*
4791  * Write text at *lines to output with line numbers.
4792  *
4793  * If header_keyword isn't NULL, then line 1 should be the first line beginning
4794  * with header_keyword; lines before that are unnumbered.
4795  *
4796  * Caution: this scribbles on *lines.
4797  */
4798 static void
4799 print_with_linenumbers(FILE *output, char *lines,
4800  const char *header_keyword)
4801 {
4802  bool in_header = (header_keyword != NULL);
4803  size_t header_sz = in_header ? strlen(header_keyword) : 0;
4804  int lineno = 0;
4805 
4806  while (*lines != '\0')
4807  {
4808  char *eol;
4809 
4810  if (in_header && strncmp(lines, header_keyword, header_sz) == 0)
4811  in_header = false;
4812 
4813  /* increment lineno only for body's lines */
4814  if (!in_header)
4815  lineno++;
4816 
4817  /* find and mark end of current line */
4818  eol = strchr(lines, '\n');
4819  if (eol != NULL)
4820  *eol = '\0';
4821 
4822  /* show current line as appropriate */
4823  if (in_header)
4824  fprintf(output, " %s\n", lines);
4825  else
4826  fprintf(output, "%-7d %s\n", lineno, lines);
4827 
4828  /* advance to next line, if any */
4829  if (eol == NULL)
4830  break;
4831  lines = ++eol;
4832  }
4833 }
4834 
4835 /*
4836  * Report just the primary error; this is to avoid cluttering the output
4837  * with, for instance, a redisplay of the internally generated query
4838  */
4839 static void
4841 {
4842  PQExpBuffer msg;
4843  const char *fld;
4844 
4845  msg = createPQExpBuffer();
4846 
4848  if (fld)
4849  printfPQExpBuffer(msg, "%s: ", fld);
4850  else
4851  printfPQExpBuffer(msg, "ERROR: ");
4853  if (fld)
4854  appendPQExpBufferStr(msg, fld);
4855  else
4856  appendPQExpBufferStr(msg, "(not available)");
4857  appendPQExpBufferStr(msg, "\n");
4858 
4859  psql_error("%s", msg->data);
4860 
4861  destroyPQExpBuffer(msg);
4862 }
static backslashResult exec_command_list(PsqlScanState scan_state, bool active_branch, const char *cmd)
Definition: command.c:1698
static backslashResult exec_command_echo(PsqlScanState scan_state, bool active_branch, const char *cmd)
Definition: command.c:1169
char * gset_prefix
Definition: settings.h:95
static void usage(void)
Definition: pg_standby.c:503
static char password[100]
Definition: streamutil.c:41
static backslashResult exec_command_include(PsqlScanState scan_state, bool active_branch, const char *cmd)
Definition: command.c:1430
static backslashResult exec_command_unset(PsqlScanState scan_state, bool active_branch, const char *cmd)
Definition: command.c:2475
static void ignore_boolean_expression(PsqlScanState scan_state)
Definition: command.c:2814
bool do_lo_export(const char *loid_arg, const char *filename_arg)
Definition: large_obj.c:141
static bool param_is_newly_set(const char *old_val, const char *new_val)
Definition: command.c:2966
PGconn * db
Definition: settings.h:82
char * PQerrorMessage(const PGconn *conn)
Definition: fe-connect.c:6014
void psql_scan_slash_command_end(PsqlScanState state)
EditableObjectType
Definition: command.c:49
void printfPQExpBuffer(PQExpBuffer str, const char *fmt,...)
Definition: pqexpbuffer.c:234
const char * PQsslAttribute(PGconn *conn, const char *attribute_name)
static backslashResult exec_command_else(PsqlScanState scan_state, ConditionalStack cstack, PQExpBuffer query_buf)
Definition: command.c:1593
bool conditional_active(ConditionalStack cstack)
Definition: conditional.c:104
volatile bool sigint_interrupt_enabled
Definition: common.c:273
char * nullPrint
Definition: print.h:166
static backslashResult exec_command_prompt(PsqlScanState scan_state, bool active_branch, const char *cmd)
Definition: command.c:1920
static backslashResult exec_command_a(PsqlScanState scan_state, bool active_branch)
Definition: command.c:426
void print_copyright(void)
Definition: help.c:579
#define PG_DIAG_MESSAGE_PRIMARY
Definition: postgres_ext.h:58
int encoding
Definition: print.h:118
#define EXIT_SUCCESS
Definition: settings.h:147
PsqlSettings pset
Definition: startup.c:33
PQnoticeProcessor PQsetNoticeProcessor(PGconn *conn, PQnoticeProcessor proc, void *arg)
Definition: fe-connect.c:6190
void conditional_stack_set_query_len(ConditionalStack cstack, int len)
Definition: conditional.c:115
const printTextFormat * line_style
Definition: print.h:112
void SyncVariables(void)
Definition: command.c:3330
char * PQgetvalue(const PGresult *res, int tup_num, int field_num)
Definition: fe-exec.c:3067
bool listTSConfigs(const char *pattern, bool verbose)
Definition: describe.c:4377
static void error(void)
Definition: sql-dyntest.c:147
const char * PQparameterStatus(const PGconn *conn, const char *paramName)
Definition: fe-connect.c:5979
bool objectDescription(const char *pattern, bool showSystem)
Definition: describe.c:1095
void * pg_malloc(size_t size)
Definition: fe_memutils.c:47
bool conditional_stack_pop(ConditionalStack cstack)
Definition: conditional.c:55
int PSQLexecWatch(const char *query, const printQueryOpt *opt)
Definition: common.c:697
static backslashResult exec_command_help(PsqlScanState scan_state, bool active_branch)
Definition: command.c:1380
static void save_query_text_state(PsqlScanState scan_state, ConditionalStack cstack, PQExpBuffer query_buf)
Definition: command.c:2893
bool listExtensionContents(const char *pattern)
Definition: describe.c:4939
const char * fmtId(const char *rawid)
Definition: string_utils.c:66
int uid_t
Definition: win32.h:250
void disable_sigpipe_trap(void)
Definition: print.c:2801
static void output(uint64 loop_count)
void termPQExpBuffer(PQExpBuffer str)
Definition: pqexpbuffer.c:128
static bool is_branching_command(const char *cmd)
Definition: command.c:2877
static bool is_true_boolean_expression(PsqlScanState scan_state, const char *name)
Definition: command.c:2797
printTextFormat pg_utf8format
Definition: print.c:102
static backslashResult exec_command_edit(PsqlScanState scan_state, bool active_branch, PQExpBuffer query_buf, PQExpBuffer previous_buf)
Definition: command.c:903
void appendPQExpBufferStr(PQExpBuffer str, const char *data)
Definition: pqexpbuffer.c:385
char * psql_scan_slash_command(PsqlScanState state)
void ClosePager(FILE *pagerpipe)
Definition: print.c:2900
static backslashResult exec_command_ev(PsqlScanState scan_state, bool active_branch, PQExpBuffer query_buf)
Definition: command.c:1089
static backslashResult exec_command_f(PsqlScanState scan_state, bool active_branch)
Definition: command.c:1280
const printTextFormat pg_asciiformat_old
Definition: print.c:80
bool do_lo_unlink(const char *loid_arg)
Definition: large_obj.c:238
char * pstrdup(const char *in)
Definition: mcxt.c:1077
char * psprintf(const char *fmt,...)
Definition: psprintf.c:46
bool recognized_connection_string(const char *connstr)
Definition: common.c:2190
void conditional_stack_push(ConditionalStack cstack, ifState new_state)
Definition: conditional.c:39
static void minimal_error_message(PGresult *res)
Definition: command.c:4840
bool gexec_flag
Definition: settings.h:96
void psql_scan_set_paren_depth(PsqlScanState state, int depth)
enum printFormat format
Definition: print.h:98
void PsqlVarEnumError(const char *name, const char *value, const char *suggestions)
Definition: variables.c:391
int conditional_stack_get_query_len(ConditionalStack cstack)
Definition: conditional.c:126
#define Min(x, y)
Definition: c.h:806
printTableOpt topt
Definition: print.h:165
unicode_linestyle
Definition: print.h:84
bool listEventTriggers(const char *pattern, bool verbose)
Definition: describe.c:3691
static backslashResult exec_command_sv(PsqlScanState scan_state, bool active_branch, const char *cmd)
Definition: command.c:2311
bool listCollations(const char *pattern, bool verbose, bool showSystem)
Definition: describe.c:3856
bool listLanguages(const char *pattern, bool verbose, bool showSystem)
Definition: describe.c:3454
#define RELKIND_MATVIEW
Definition: pg_class.h:165
static bool lookup_object_oid(EditableObjectType obj_type, const char *desc, Oid *obj_oid)
Definition: command.c:4481
static void print_with_linenumbers(FILE *output, char *lines, const char *header_keyword)
Definition: command.c:4799
static backslashResult exec_command_slash_command_help(PsqlScanState scan_state, bool active_branch)
Definition: command.c:2700
static backslashResult exec_command_print(PsqlScanState scan_state, bool active_branch, PQExpBuffer query_buf, PQExpBuffer previous_buf)
Definition: command.c:1826
static backslashResult exec_command_t(PsqlScanState scan_state, bool active_branch)
Definition: command.c:2399
void appendConnStrVal(PQExpBuffer buf, const char *str)
Definition: string_utils.c:551
FILE * queryFout
Definition: settings.h:84
void canonicalize_path(char *path)
Definition: path.c:254
static backslashResult exec_command_pset(PsqlScanState scan_state, bool active_branch)
Definition: command.c:1994
unicode_linestyle unicode_header_linestyle
Definition: print.h:123
void PQfinish(PGconn *conn)
Definition: fe-connect.c:3547
char * PQport(const PGconn *conn)
Definition: fe-connect.c:5935
static const char * _unicode_linestyle2string(int linestyle)
Definition: command.c:3718
return result
Definition: formatting.c:1633
int snprintf(char *str, size_t count, const char *fmt,...) pg_attribute_printf(3
static backslashResult exec_command_errverbose(PsqlScanState scan_state, bool active_branch)
Definition: command.c:1250
char * inputfile
Definition: settings.h:108
bool do_copy(const char *args)
Definition: copy.c:269
int pg_strcasecmp(const char *s1, const char *s2)
Definition: pgstrcasecmp.c:36
#define lengthof(array)
Definition: c.h:562
static backslashResult exec_command_password(PsqlScanState scan_state, bool active_branch)
Definition: command.c:1852
unsigned int Oid
Definition: postgres_ext.h:31
int PQserverVersion(const PGconn *conn)
Definition: fe-connect.c:6004
bool listDomains(const char *pattern, bool verbose, bool showSystem)
Definition: describe.c:3529
const char * name
Definition: print.h:69
void PrintVariables(VariableSpace space)
Definition: variables.c:186
#define putenv(x)
Definition: win32.h:411
static char * read_connect_arg(PsqlScanState scan_state)
Definition: command.c:2730
int PQntuples(const PGresult *res)
Definition: fe-exec.c:2673
bool listSchemas(const char *pattern, bool verbose, bool showSystem)
Definition: describe.c:3940
void conditional_stack_set_paren_depth(ConditionalStack cstack, int depth)
Definition: conditional.c:137
#define PG_BINARY_R
Definition: c.h:1040
bool separator_zero
Definition: print.h:93
static int fd(const char *x, int i)
Definition: preproc-init.c:105
unicode_linestyle unicode_border_linestyle
Definition: print.h:121
int PQclientEncoding(const PGconn *conn)
Definition: fe-connect.c:6074
ExecStatusType PQresultStatus(const PGresult *res)
Definition: fe-exec.c:2596
bool describeTablespaces(const char *pattern, bool verbose)
Definition: describe.c:205
PGconn * PQconnectdbParams(const char *const *keywords, const char *const *values, int expand_dbname)
Definition: fe-connect.c:510
void UnsyncVariables(void)
Definition: command.c:3354
char * PQuser(const PGconn *conn)
Definition: fe-connect.c:5890
sigjmp_buf sigint_interrupt_jmp
Definition: common.c:275
static backslashResult exec_command_z(PsqlScanState scan_state, bool active_branch)
Definition: command.c:2655
bool describeSubscriptions(const char *pattern, bool verbose)
Definition: describe.c:5236
static int count_lines_in_buf(PQExpBuffer buf)
Definition: command.c:4772
volatile bool cancel_pressed
Definition: print.c:46
static backslashResult exec_command_g(PsqlScanState scan_state, bool active_branch, const char *cmd)
Definition: command.c:1303
int pg_strncasecmp(const char *s1, const char *s2, size_t n)
Definition: pgstrcasecmp.c:69
void pg_usleep(long microsec)
Definition: signal.c:53
void destroyPQExpBuffer(PQExpBuffer str)
Definition: pqexpbuffer.c:113
unsigned short int border
Definition: print.h:101
char * ctv_args[4]
Definition: settings.h:98
bool has_drive_prefix(const char *filename)
Definition: path.c:87
static backslashResult exec_command_watch(PsqlScanState scan_state, bool active_branch, PQExpBuffer query_buf, PQExpBuffer previous_buf)
Definition: command.c:2594
bool describeAggregates(const char *pattern, bool verbose, bool showSystem)
Definition: describe.c:61
unsigned short int expanded
Definition: print.h:99
static backslashResult exec_command(const char *cmd, PsqlScanState scan_state, ConditionalStack cstack, PQExpBuffer query_buf, PQExpBuffer previous_buf)
Definition: command.c:276
bool cur_cmd_interactive
Definition: settings.h:105
PSQL_ECHO_HIDDEN echo_hidden
Definition: settings.h:132
FILE * PageOutput(int lines, const printTableOpt *topt)
Definition: print.c:2851
static backslashResult exec_command_shell_escape(PsqlScanState scan_state, bool active_branch)
Definition: command.c:2678
static bool printPsetInfo(const char *param, struct printQueryOpt *popt)
Definition: command.c:4009
static backslashResult exec_command_setenv(PsqlScanState scan_state, bool active_branch, const char *cmd)
Definition: command.c:2160
void expand_tilde(char **filename)
Definition: common.c:2103
static const char * pset_bool_string(bool val)
Definition: command.c:4185
static bool do_watch(PQExpBuffer query_buf, double sleep)
Definition: command.c:4343
char * psql_scan_slash_option(PsqlScanState state, enum slash_option_type type, char *quote, bool semicolon)
#define MAXPGPATH
unicode_linestyle unicode_column_linestyle
Definition: print.h:122
bool listTables(const char *tabtypes, const char *pattern, bool verbose, bool showSystem)
Definition: describe.c:3297
static struct @121 value
void appendPQExpBuffer(PQExpBuffer str, const char *fmt,...)
Definition: pqexpbuffer.c:262
static backslashResult exec_command_conninfo(PsqlScanState scan_state, bool active_branch)
Definition: command.c:589
bool describeTableDetails(const char *pattern, bool verbose, bool showSystem)
Definition: describe.c:1287
bool tuples_only
Definition: print.h:107
static bool success
Definition: pg_basebackup.c:96
char * PQresultVerboseErrorMessage(const PGresult *res, PGVerbosity verbosity, PGContextVisibility show_context)
Definition: fe-exec.c:2620
char * c
static char * buf
Definition: pg_test_fsync.c:66
bool listConversions(const char *pattern, bool verbose, bool showSystem)
Definition: describe.c:3615
static void ignore_slash_filepipe(PsqlScanState scan_state)
Definition: command.c:2847
void simple_prompt(const char *prompt, char *destination, size_t destlen, bool echo)
Definition: sprompt.c:37
void psql_scan_reset(PsqlScanState state)
void PQconninfoFree(PQconninfoOption *connOptions)
Definition: fe-connect.c:5864
#define is_absolute_path(filename)
Definition: port.h:77
static backslashResult exec_command_elif(PsqlScanState scan_state, ConditionalStack cstack, PQExpBuffer query_buf)
Definition: command.c:1517
bool appendReloptionsArray(PQExpBuffer buffer, const char *reloptions, const char *prefix, int encoding, bool std_strings)
Definition: string_utils.c:747
void get_parent_directory(char *path)
Definition: path.c:854
#define PG_DIAG_SEVERITY
Definition: postgres_ext.h:55
char * pg_strdup(const char *in)
Definition: fe_memutils.c:85
bool g_expanded
Definition: settings.h:94
char * PQpass(const PGconn *conn)
Definition: fe-connect.c:5898
PQconninfoOption * PQconninfo(PGconn *conn)
Definition: fe-connect.c:5823
bool do_pset(const char *param, const char *value, printQueryOpt *popt, bool quiet)
Definition: command.c:3737
char * tableAttr
Definition: print.h:117
static bool editFile(const char *fname, int lineno)
Definition: command.c:3371
static char * pset_value_string(const char *param, struct printQueryOpt *popt)
Definition: command.c:4230
static backslashResult exec_command_ef(PsqlScanState scan_state, bool active_branch, PQExpBuffer query_buf)
Definition: command.c:980
static backslashResult exec_command_crosstabview(PsqlScanState scan_state, bool active_branch)
Definition: command.c:673
void * pg_realloc(void *ptr, size_t size)
Definition: fe_memutils.c:65
bool do_lo_import(const char *filename_arg, const char *comment_arg)
Definition: large_obj.c:175
#define atooid(x)
Definition: postgres_ext.h:42
static PQExpBuffer gather_boolean_expression(PsqlScanState scan_state)
Definition: command.c:2767
static char * prompt_for_password(const char *username)
Definition: command.c:2948
void restore_sigpipe_trap(void)
Definition: print.c:2824
static backslashResult exec_command_connect(PsqlScanState scan_state, bool active_branch)
Definition: command.c:478
static backslashResult exec_command_gset(PsqlScanState scan_state, bool active_branch)
Definition: command.c:1351
bool listForeignTables(const char *pattern, bool verbose)
Definition: describe.c:4804
static int port
Definition: pg_regress.c:89
#define DEFAULT_EDITOR
Definition: settings.h:22
static backslashResult exec_command_endif(PsqlScanState scan_state, ConditionalStack cstack, PQExpBuffer query_buf)
Definition: command.c:1658
bool describePublications(const char *pattern)
Definition: describe.c:5115
static backslashResult exec_command_set(PsqlScanState scan_state, bool active_branch)
Definition: command.c:2107
trivalue
Definition: vacuumlo.c:31
#define PARAMS_ARRAY_SIZE
#define ngettext(s, p, n)
Definition: c.h:127
static backslashResult exec_command_if(PsqlScanState scan_state, ConditionalStack cstack, PQExpBuffer query_buf)
Definition: command.c:1471
static backslashResult exec_command_gexec(PsqlScanState scan_state, bool active_branch)
Definition: command.c:1334
PGContextVisibility show_context
Definition: settings.h:140
void psql_error(const char *fmt,...)
Definition: common.c:220
char * gfname
Definition: settings.h:93
void helpVariables(unsigned short int pager)
Definition: help.c:327
bool listTSDictionaries(const char *pattern, bool verbose)
Definition: describe.c:4235
bool setQFout(const char *fname)
Definition: common.c:84
PQExpBuffer createPQExpBuffer(void)
Definition: pqexpbuffer.c:71
static backslashResult exec_command_timing(PsqlScanState scan_state, bool active_branch)
Definition: command.c:2443
void appendPQExpBufferChar(PQExpBuffer str, char ch)
Definition: pqexpbuffer.c:396
static void discard_query_text(PsqlScanState scan_state, ConditionalStack cstack, PQExpBuffer query_buf)
Definition: command.c:2913
int PQsetClientEncoding(PGconn *conn, const char *encoding)
Definition: fe-connect.c:6082
PGresult * last_error_result
Definition: settings.h:89
static bool do_edit(const char *filename_arg, PQExpBuffer query_buf, int lineno, bool *edited)
Definition: command.c:3439
FILE * logfile
Definition: settings.h:114
PGContextVisibility PQsetErrorContextVisibility(PGconn *conn, PGContextVisibility show_context)
Definition: fe-connect.c:6140
bool listPublications(const char *pattern)
Definition: describe.c:5049
bool listForeignServers(const char *pattern, bool verbose)
Definition: describe.c:4661
ifState conditional_stack_peek(ConditionalStack cstack)
Definition: conditional.c:70
unsigned short int pager
Definition: print.h:103
static char * username
Definition: initdb.c:131
static backslashResult exec_command_encoding(PsqlScanState scan_state, bool active_branch)
Definition: command.c:1212
#define InvalidOid
Definition: postgres_ext.h:36
PGVerbosity verbosity
Definition: settings.h:139
char * PQhost(const PGconn *conn)
Definition: fe-connect.c:5915
int process_file(char *filename, bool use_relative_path)
Definition: command.c:3603
int psql_scan_get_paren_depth(PsqlScanState state)
void PQclear(PGresult *res)
Definition: fe-exec.c:650
static char * encoding
Definition: initdb.c:122
bool standard_strings(void)
Definition: common.c:2058
#define free(a)
Definition: header.h:65
bool describeTypes(const char *pattern, bool verbose, bool showSystem)
Definition: describe.c:588
static backslashResult exec_command_html(PsqlScanState scan_state, bool active_branch)
Definition: command.c:1411
struct separator fieldSep
Definition: print.h:113
void NoticeProcessor(void *arg, const char *message)
Definition: common.c:241
enum _backslashResult backslashResult
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:607
bool describeAccessMethods(const char *pattern, bool verbose)
Definition: describe.c:138
char * PQdb(const PGconn *conn)
Definition: fe-connect.c:5882
const printTextFormat * get_line_style(const printTableOpt *opt)
Definition: print.c:3412
char * title
Definition: print.h:167
int pager_min_lines
Definition: print.h:105
char * PQresultErrorField(const PGresult *res, int fieldcode)
Definition: fe-exec.c:2658
bool default_footer
Definition: print.h:110
#define NULL
Definition: c.h:229
static int strip_lineno_from_objdesc(char *obj)
Definition: command.c:4714
bool SetVariable(VariableSpace space, const char *name, const char *value)
Definition: variables.c:211
#define Assert(condition)
Definition: c.h:675
bool listForeignDataWrappers(const char *pattern, bool verbose)
Definition: describe.c:4578
#define DEFAULT_EDITOR_LINENUMBER_ARG
Definition: settings.h:23
const char * progname
Definition: settings.h:107
bool conditional_stack_poke(ConditionalStack cstack, ifState new_state)
Definition: conditional.c:82
int MainLoop(FILE *source)
Definition: mainloop.c:35
printQueryOpt popt
Definition: settings.h:91
bool listUserMappings(const char *pattern, bool verbose)
Definition: describe.c:4743
static int server_version
Definition: pg_dumpall.c:82
enum trivalue getPassword
Definition: settings.h:102
static backslashResult exec_command_s(PsqlScanState scan_state, bool active_branch)
Definition: command.c:2080
char * gets_fromFile(FILE *source)
Definition: input.c:187
char * dbname
Definition: streamutil.c:38
static void copy_previous_query(PQExpBuffer query_buf, PQExpBuffer previous_buf)
Definition: command.c:2936
char * PQencryptPasswordConn(PGconn *conn, const char *passwd, const char *user, const char *algorithm)
Definition: fe-auth.c:1140
#define DEFAULT_SHELL
Definition: command.c:4289
#define newval
static bool set_unicode_line_style(const char *value, size_t vallen, unicode_linestyle *linestyle)
Definition: command.c:3705
#define unsetenv(x)
Definition: win32.h:412
void pg_free(void *ptr)
Definition: fe_memutils.c:105
void join_path_components(char *ret_path, const char *head, const char *tail)
Definition: path.c:218
static backslashResult exec_command_write(PsqlScanState scan_state, bool active_branch, const char *cmd, PQExpBuffer query_buf, PQExpBuffer previous_buf)
Definition: command.c:2505
bool describeFunctions(const char *functypes, const char *pattern, bool verbose, bool showSystem)
Definition: describe.c:299
const char * name
Definition: encode.c:521
static bool do_shell(const char *command)
Definition: command.c:4299
static backslashResult exec_command_quit(PsqlScanState scan_state, bool active_branch)
Definition: command.c:2048
bool do_lo_list(void)
Definition: large_obj.c:273
bool numericLocale
Definition: print.h:115
static const char * _align2string(enum printFormat in)
Definition: command.c:3665
bool ParseVariableBool(const char *value, const char *name, bool *result)
Definition: variables.c:107
bool listExtensions(const char *pattern)
Definition: describe.c:4882
static Datum values[MAXATTR]
Definition: bootstrap.c:163
static backslashResult exec_command_x(PsqlScanState scan_state, bool active_branch)
Definition: command.c:2633
static char * filename
Definition: pg_dumpall.c:89
void appendStringLiteralConn(PQExpBuffer buf, const char *str, PGconn *conn)
Definition: string_utils.c:298
int PQconnectionNeedsPassword(const PGconn *conn)
Definition: fe-connect.c:6048
static char * user
Definition: pg_regress.c:92
bool describeOperators(const char *pattern, bool verbose, bool showSystem)
Definition: describe.c:703
static bool get_create_object_cmd(EditableObjectType obj_type, Oid oid, PQExpBuffer buf)
Definition: command.c:4541
static void ignore_slash_options(PsqlScanState scan_state)
Definition: command.c:2830
static backslashResult exec_command_cd(PsqlScanState scan_state, bool active_branch, const char *cmd)
Definition: command.c:531
int conditional_stack_get_paren_depth(ConditionalStack cstack)
Definition: conditional.c:148
bool listCasts(const char *pattern, bool verbose)
Definition: describe.c:3757
#define RELKIND_VIEW
Definition: pg_class.h:164
void helpSQL(const char *topic, unsigned short int pager)
Definition: help.c:439
int PQsslInUse(PGconn *conn)
int i
const char * strerror(int errnum)
Definition: strerror.c:19
static backslashResult exec_command_copyright(PsqlScanState scan_state, bool active_branch)
Definition: command.c:661
void refresh_utf8format(const printTableOpt *opt)
Definition: print.c:3426
bool crosstab_flag
Definition: settings.h:97
#define relpath(rnode, forknum)
Definition: relpath.h:71
static backslashResult exec_command_lo(PsqlScanState scan_state, bool active_branch, const char *cmd)
Definition: command.c:1727
#define EXIT_FAILURE
Definition: settings.h:151
PGresult * PQexec(PGconn *conn, const char *query)
Definition: fe-exec.c:1846
void * arg
const printTextFormat pg_asciiformat
Definition: print.c:59
static backslashResult exec_command_T(PsqlScanState scan_state, bool active_branch)
Definition: command.c:2421
static backslashResult exec_command_out(PsqlScanState scan_state, bool active_branch)
Definition: command.c:1803
char * separator
Definition: print.h:92
bool listDefaultACLs(const char *pattern)
Definition: describe.c:1010
static backslashResult exec_command_copy(PsqlScanState scan_state, bool active_branch)
Definition: command.c:639
printFormat
Definition: print.h:26
void connection_warnings(bool in_startup)
Definition: command.c:3223
static backslashResult exec_command_sf(PsqlScanState scan_state, bool active_branch, const char *cmd)
Definition: command.c:2217
bool permissionsList(const char *pattern)
Definition: describe.c:850
struct separator recordSep
Definition: print.h:114
static void printSSLInfo(void)
Definition: command.c:3275
backslashResult HandleSlashCmds(PsqlScanState scan_state, ConditionalStack cstack, PQExpBuffer query_buf, PQExpBuffer previous_buf)
Definition: command.c:202
void resetPQExpBuffer(PQExpBuffer str)
Definition: pqexpbuffer.c:145
int encoding
Definition: settings.h:83
static void static void status(const char *fmt,...) pg_attribute_printf(1
Definition: pg_regress.c:224
static bool echo_hidden_command(const char *query)
Definition: command.c:4449
ConnStatusType PQstatus(const PGconn *conn)
Definition: fe-connect.c:5961
bool listDbRoleSettings(const char *pattern, const char *pattern2)
Definition: describe.c:3223
bool listTSTemplates(const char *pattern, bool verbose)
Definition: describe.c:4306
static backslashResult exec_command_reset(PsqlScanState scan_state, bool active_branch, PQExpBuffer query_buf)
Definition: command.c:2062
bool describeRoles(const char *pattern, bool verbose, bool showSystem)
Definition: describe.c:3052
static backslashResult exec_command_C(PsqlScanState scan_state, bool active_branch)
Definition: command.c:445
int columns
Definition: print.h:120
PGVerbosity PQsetErrorVerbosity(PGconn *conn, PGVerbosity verbosity)
Definition: fe-connect.c:6128
#define _(x)
Definition: elog.c:84
bool listTSParsers(const char *pattern, bool verbose)
Definition: describe.c:3997
void PQfreemem(void *ptr)
Definition: fe-exec.c:3200
long val
Definition: informix.c:689
void slashUsage(unsigned short int pager)
Definition: help.c:158
bool listAllDbs(const char *pattern, bool verbose)
Definition: describe.c:780
void initPQExpBuffer(PQExpBuffer str)
Definition: pqexpbuffer.c:89
static bool do_connect(enum trivalue reuse_previous_specification, char *dbname, char *user, char *host, char *port)
Definition: command.c:2990
char * formatPGVersionNumber(int version_number, bool include_minor, char *buf, size_t buflen)
Definition: string_utils.c:182
static char * pset_quoted_string(const char *str)
Definition: command.c:4192
static void ignore_slash_whole_line(PsqlScanState scan_state)
Definition: command.c:2864
bool printHistory(const char *fname, unsigned short int pager)
Definition: input.c:490
PGresult * PSQLexec(const char *query)
Definition: common.c:642
VariableSpace vars
Definition: settings.h:116
static char * connstr
Definition: pg_dumpall.c:64
static backslashResult exec_command_d(PsqlScanState scan_state, bool active_branch, const char *cmd)
Definition: command.c:697