27 #include "catalog/pg_class_d.h"
79 bool show_verbose,
bool show_system);
131 const char *cmd,
bool is_func);
163 int lineno,
bool discard_on_quit,
bool *edited);
164 static bool do_shell(
const char *command);
181 static void checkWin32Codepage(
void);
223 Assert(scan_state != NULL);
230 status =
exec_command(cmd, scan_state, cstack, query_buf, previous_buf);
306 pg_log_warning(
"\\%s command ignored; use \\endif or Ctrl-C to exit current \\if block",
310 if (strcmp(cmd,
"a") == 0)
312 else if (strcmp(cmd,
"bind") == 0)
314 else if (strcmp(cmd,
"C") == 0)
316 else if (strcmp(cmd,
"c") == 0 || strcmp(cmd,
"connect") == 0)
318 else if (strcmp(cmd,
"cd") == 0)
320 else if (strcmp(cmd,
"conninfo") == 0)
324 else if (strcmp(cmd,
"copyright") == 0)
326 else if (strcmp(cmd,
"crosstabview") == 0)
328 else if (cmd[0] ==
'd')
330 else if (strcmp(cmd,
"e") == 0 || strcmp(cmd,
"edit") == 0)
332 query_buf, previous_buf);
333 else if (strcmp(cmd,
"ef") == 0)
335 else if (strcmp(cmd,
"ev") == 0)
337 else if (strcmp(cmd,
"echo") == 0 || strcmp(cmd,
"qecho") == 0 ||
338 strcmp(cmd,
"warn") == 0)
340 else if (strcmp(cmd,
"elif") == 0)
342 else if (strcmp(cmd,
"else") == 0)
344 else if (strcmp(cmd,
"endif") == 0)
346 else if (strcmp(cmd,
"encoding") == 0)
348 else if (strcmp(cmd,
"errverbose") == 0)
350 else if (strcmp(cmd,
"f") == 0)
352 else if (strcmp(cmd,
"g") == 0 || strcmp(cmd,
"gx") == 0)
354 else if (strcmp(cmd,
"gdesc") == 0)
356 else if (strcmp(cmd,
"getenv") == 0)
358 else if (strcmp(cmd,
"gexec") == 0)
360 else if (strcmp(cmd,
"gset") == 0)
362 else if (strcmp(cmd,
"h") == 0 || strcmp(cmd,
"help") == 0)
364 else if (strcmp(cmd,
"H") == 0 || strcmp(cmd,
"html") == 0)
366 else if (strcmp(cmd,
"i") == 0 || strcmp(cmd,
"include") == 0 ||
367 strcmp(cmd,
"ir") == 0 || strcmp(cmd,
"include_relative") == 0)
369 else if (strcmp(cmd,
"if") == 0)
371 else if (strcmp(cmd,
"l") == 0 || strcmp(cmd,
"list") == 0 ||
372 strcmp(cmd,
"l+") == 0 || strcmp(cmd,
"list+") == 0)
374 else if (strncmp(cmd,
"lo_", 3) == 0)
376 else if (strcmp(cmd,
"o") == 0 || strcmp(cmd,
"out") == 0)
378 else if (strcmp(cmd,
"p") == 0 || strcmp(cmd,
"print") == 0)
380 query_buf, previous_buf);
381 else if (strcmp(cmd,
"password") == 0)
383 else if (strcmp(cmd,
"prompt") == 0)
385 else if (strcmp(cmd,
"pset") == 0)
387 else if (strcmp(cmd,
"q") == 0 || strcmp(cmd,
"quit") == 0)
389 else if (strcmp(cmd,
"r") == 0 || strcmp(cmd,
"reset") == 0)
391 else if (strcmp(cmd,
"s") == 0)
393 else if (strcmp(cmd,
"set") == 0)
395 else if (strcmp(cmd,
"setenv") == 0)
397 else if (strcmp(cmd,
"sf") == 0 || strcmp(cmd,
"sf+") == 0)
399 else if (strcmp(cmd,
"sv") == 0 || strcmp(cmd,
"sv+") == 0)
401 else if (strcmp(cmd,
"t") == 0)
403 else if (strcmp(cmd,
"T") == 0)
405 else if (strcmp(cmd,
"timing") == 0)
407 else if (strcmp(cmd,
"unset") == 0)
409 else if (strcmp(cmd,
"w") == 0 || strcmp(cmd,
"write") == 0)
411 query_buf, previous_buf);
412 else if (strcmp(cmd,
"watch") == 0)
414 query_buf, previous_buf);
415 else if (strcmp(cmd,
"x") == 0)
417 else if (strcmp(cmd,
"z") == 0 || strcmp(cmd,
"zS") == 0)
419 else if (strcmp(cmd,
"!") == 0)
421 else if (strcmp(cmd,
"?") == 0)
478 if (nparams > nalloc)
480 nalloc = nalloc ? nalloc * 2 : 1;
536 static const char prefix[] =
"-reuse-previous=";
544 if (opt1 != NULL && strncmp(opt1, prefix,
sizeof(prefix) - 1) == 0)
599 dir = getenv(
"HOME");
600 if (dir == NULL || dir[0] ==
'\0')
602 uid_t user_id = geteuid();
606 pw = getpwuid(user_id);
611 pg_log_error(
"could not get home directory for user ID %ld: %s",
613 errno ?
strerror(errno) :
_(
"user does not exist"));
630 pg_log_error(
"\\%s: could not change directory to \"%s\": %m",
654 printf(
_(
"You are currently not connected to a database.\n"));
663 if (hostaddr && *hostaddr)
664 printf(
_(
"You are connected to database \"%s\" as user \"%s\" on address \"%s\" at port \"%s\".\n"),
667 printf(
_(
"You are connected to database \"%s\" as user \"%s\" via socket in \"%s\" at port \"%s\".\n"),
672 if (hostaddr && *hostaddr && strcmp(host, hostaddr) != 0)
673 printf(
_(
"You are connected to database \"%s\" as user \"%s\" on host \"%s\" (address \"%s\") at port \"%s\".\n"),
676 printf(
_(
"You are connected to database \"%s\" as user \"%s\" on host \"%s\" at port \"%s\".\n"),
764 show_verbose = strchr(cmd,
'+') ?
true :
false;
765 show_system = strchr(cmd,
'S') ?
true :
false;
780 char *pattern2 = NULL;
782 if (pattern && cmd[2] !=
'\0' && cmd[2] !=
'+')
818 if (strncmp(cmd,
"dconfig", 7) == 0)
831 if (strncmp(cmd,
"ddp", 3) == 0)
851 show_verbose, show_system);
873 show_verbose, show_system);
910 if (cmd[2] ==
'd' && cmd[3] ==
's')
912 char *pattern2 = NULL;
921 else if (cmd[2] ==
'g')
1016 const char *pattern,
1017 bool show_verbose,
bool show_system)
1021 int num_arg_patterns = 0;
1031 arg_patterns[num_arg_patterns++] = ap;
1039 arg_patterns, num_arg_patterns,
1040 show_verbose, show_system);
1043 arg_patterns, num_arg_patterns,
1044 show_verbose, show_system);
1046 while (--num_arg_patterns >= 0)
1047 free(arg_patterns[num_arg_patterns]);
1086 strspn(fname,
"0123456789") == strlen(fname))
1105 bool discard_on_quit;
1112 discard_on_quit =
true;
1125 if (
do_edit(fname, query_buf, lineno, discard_on_quit, NULL))
1187 "CREATE FUNCTION ( )\n"
1190 " -- common options: IMMUTABLE STABLE STRICT SECURITY DEFINER\n"
1197 " -- something...\n");
1209 else if (is_func && lineno > 0)
1220 const char *lines = query_buf->
data;
1222 while (*lines !=
'\0')
1224 if (strncmp(lines,
"AS ", 3) == 0 ||
1225 strncmp(lines,
"BEGIN ", 6) == 0 ||
1226 strncmp(lines,
"RETURN ", 7) == 0)
1230 lines = strchr(lines,
'\n');
1240 bool edited =
false;
1242 if (!
do_edit(NULL, query_buf, lineno,
true, &edited))
1245 puts(
_(
"No changes"));
1275 bool no_newline =
false;
1279 if (strcmp(cmd,
"qecho") == 0)
1281 else if (strcmp(cmd,
"warn") == 0)
1289 if (first && !no_newline && !quoted && strcmp(
value,
"-n") == 0)
1369 puts(
_(
"out of memory"));
1372 puts(
_(
"There is no previous error."));
1422 if (fname && fname[0] ==
'(')
1426 active_branch, cmd);
1442 if (strcmp(cmd,
"gx") == 0)
1464 bool active_branch,
const char *cmd)
1467 bool found_r_paren =
false;
1494 if (optlen > 0 &&
option[optlen - 1] ==
')')
1497 found_r_paren =
true;
1504 char *valptr = strchr(
option,
'=');
1519 first_option = NULL;
1522 }
while (!found_r_paren);
1567 if (!myvar || !envvar)
1574 char *envval = getenv(envvar);
1651 (isspace((
unsigned char) opt[
len - 1])
1652 || opt[
len - 1] ==
';'))
1704 bool include_relative;
1706 include_relative = (strcmp(cmd,
"ir") == 0
1707 || strcmp(cmd,
"include_relative") == 0);
1968 show_verbose = strchr(cmd,
'+') ?
true :
false;
1999 if (strcmp(cmd + 3,
"export") == 0)
2013 else if (strcmp(cmd + 3,
"import") == 0)
2027 else if (strcmp(cmd + 3,
"list") == 0)
2029 else if (strcmp(cmd + 3,
"list+") == 0)
2032 else if (strcmp(cmd + 3,
"unlink") == 0)
2095 if (query_buf && query_buf->
len > 0)
2096 puts(query_buf->
data);
2097 else if (previous_buf && previous_buf->
len > 0)
2098 puts(previous_buf->
data);
2100 puts(
_(
"Query buffer is empty."));
2154 else if (strcmp(pw1, pw2) != 0)
2161 char *encrypted_password;
2165 if (!encrypted_password)
2209 *prompt_text = NULL;
2247 fputs(prompt_text,
stdout);
2253 pg_log_error(
"\\%s: could not read value for variable",
2294 static const char *
const my_list[] = {
2295 "border",
"columns",
"csv_fieldsep",
"expanded",
"fieldsep",
2296 "fieldsep_zero",
"footer",
"format",
"linestyle",
"null",
2297 "numericlocale",
"pager",
"pager_min_lines",
2298 "recordsep",
"recordsep_zero",
2299 "tableattr",
"title",
"tuples_only",
2300 "unicode_border_linestyle",
2301 "unicode_column_linestyle",
2302 "unicode_header_linestyle",
2307 for (
i = 0; my_list[
i] != NULL;
i++)
2355 puts(
_(
"Query buffer reset (cleared)."));
2377 printf(
_(
"Wrote history to file \"%s\".\n"), fname);
2462 else if (strchr(envvar,
'=') != NULL)
2464 pg_log_error(
"\\%s: environment variable name must not contain \"=\"",
2477 setenv(envvar, envval, 1);
2494 const char *cmd,
bool is_func)
2500 bool show_linenumbers = (strchr(cmd,
'+') != NULL);
2548 if (show_linenumbers)
2636 puts(
_(
"Timing is on."));
2638 puts(
_(
"Timing is off."));
2693 bool is_pipe =
false;
2710 if (fname[0] ==
'|')
2715 fd = popen(&fname[1],
"w");
2720 fd = fopen(fname,
"w");
2740 if (query_buf && query_buf->
len > 0)
2742 else if (previous_buf && previous_buf->
len > 0)
2747 result = pclose(
fd);
2758 result = fclose(
fd);
2791 bool have_sleep =
false;
2792 bool have_iter =
false;
2793 bool have_min_rows =
false;
2813 valptr = strchr(opt,
'=');
2818 if (strncmp(
"i=", opt, strlen(
"i=")) == 0 ||
2819 strncmp(
"interval=", opt, strlen(
"interval=")) == 0)
2823 pg_log_error(
"\\watch: interval value is specified more than once");
2830 sleep = strtod(valptr, &opt_end);
2831 if (sleep < 0 || *opt_end || errno == ERANGE)
2833 pg_log_error(
"\\watch: incorrect interval value \"%s\"", valptr);
2838 else if (strncmp(
"c=", opt, strlen(
"c=")) == 0 ||
2839 strncmp(
"count=", opt, strlen(
"count=")) == 0)
2843 pg_log_error(
"\\watch: iteration count is specified more than once");
2850 iter =
strtoint(valptr, &opt_end, 10);
2851 if (iter <= 0 || *opt_end || errno == ERANGE)
2853 pg_log_error(
"\\watch: incorrect iteration count \"%s\"", valptr);
2858 else if (strncmp(
"m=", opt, strlen(
"m=")) == 0 ||
2859 strncmp(
"min_rows=", opt, strlen(
"min_rows=")) == 0)
2863 pg_log_error(
"\\watch: minimum row count specified more than once");
2868 have_min_rows =
true;
2870 min_rows =
strtoint(valptr, &opt_end, 10);
2871 if (min_rows <= 0 || *opt_end || errno == ERANGE)
2873 pg_log_error(
"\\watch: incorrect minimum row count \"%s\"", valptr);
2880 pg_log_error(
"\\watch: unrecognized parameter \"%s\"", opt);
2889 pg_log_error(
"\\watch: interval value is specified more than once");
2896 sleep = strtod(opt, &opt_end);
2897 if (sleep < 0 || *opt_end || errno == ERANGE)
2899 pg_log_error(
"\\watch: incorrect interval value \"%s\"", opt);
2965 show_system = strchr(cmd,
'S') ?
true :
false;
3010 if (!opt0 || strcmp(opt0,
"commands") == 0)
3012 else if (strcmp(opt0,
"options") == 0)
3014 else if (strcmp(opt0,
"variables") == 0)
3056 if (*result ==
'\0' || strcmp(result,
"-") == 0)
3077 int num_options = 0;
3085 if (num_options > 0)
3184 return (strcmp(cmd,
"if") == 0 ||
3185 strcmp(cmd,
"elif") == 0 ||
3186 strcmp(cmd,
"else") == 0 ||
3187 strcmp(cmd,
"endif") == 0);
3225 Assert(new_len >= 0 && new_len <= query_buf->
len);
3226 query_buf->
len = new_len;
3227 query_buf->
data[new_len] =
'\0';
3246 if (query_buf && query_buf->
len == 0)
3292 if (new_val == NULL)
3295 if (old_val == NULL || strcmp(old_val, new_val) != 0)
3320 bool same_host =
false;
3322 char *client_encoding;
3324 bool keep_password =
true;
3325 bool has_connection_string;
3326 bool reuse_previous;
3328 has_connection_string =
dbname ?
3332 if (has_connection_string && (
user || host ||
port))
3334 pg_log_error(
"Do not give user, host, or port separately when using a connection string");
3338 switch (reuse_previous_specification)
3341 reuse_previous =
true;
3344 reuse_previous =
false;
3347 reuse_previous = !has_connection_string;
3369 pg_log_error(
"No database connection exists to re-use parameters from");
3378 if (has_connection_string)
3389 bool have_password =
false;
3391 for (ci = cinfo, replci = replcinfo;
3404 char *swap = replci->
val;
3416 if (replci->
val == NULL ||
3417 strcmp(ci->
val, replci->
val) != 0)
3419 if (strcmp(replci->
keyword,
"user") == 0 ||
3420 strcmp(replci->
keyword,
"host") == 0 ||
3421 strcmp(replci->
keyword,
"hostaddr") == 0 ||
3422 strcmp(replci->
keyword,
"port") == 0)
3423 keep_password =
false;
3426 if (strcmp(replci->
keyword,
"password") == 0)
3427 have_password =
true;
3429 else if (!reuse_previous)
3452 nconnopts = ci - cinfo;
3462 keep_password =
true;
3497 for (ci = cinfo; ci->
keyword; ci++)
3501 if (!(ci->
val && strcmp(
user, ci->
val) == 0))
3502 keep_password =
false;
3504 else if (host && strcmp(ci->
keyword,
"host") == 0)
3506 if (ci->
val && strcmp(host, ci->
val) == 0)
3509 keep_password =
false;
3511 else if (
port && strcmp(ci->
keyword,
"port") == 0)
3513 if (!(ci->
val && strcmp(
port, ci->
val) == 0))
3514 keep_password =
false;
3519 nconnopts = ci - cinfo;
3541 bool canceled =
false;
3560 if (
pset.
notty || getenv(
"PGCLIENTENCODING"))
3561 client_encoding = NULL;
3563 client_encoding =
"auto";
3568 const char **keywords =
pg_malloc((nconnopts + 1) *
sizeof(*keywords));
3582 for (ci = cinfo; ci->
keyword; ci++)
3584 keywords[paramnum] = ci->
keyword;
3588 else if (
user && strcmp(ci->
keyword,
"user") == 0)
3590 else if (host && strcmp(ci->
keyword,
"host") == 0)
3591 values[paramnum++] = host;
3592 else if (host && !same_host && strcmp(ci->
keyword,
"hostaddr") == 0)
3595 values[paramnum++] = NULL;
3597 else if (
port && strcmp(ci->
keyword,
"port") == 0)
3600 else if ((
password || !keep_password) &&
3601 strcmp(ci->
keyword,
"password") == 0)
3603 else if (strcmp(ci->
keyword,
"fallback_application_name") == 0)
3605 else if (client_encoding &&
3606 strcmp(ci->
keyword,
"client_encoding") == 0)
3607 values[paramnum++] = client_encoding;
3613 keywords[paramnum] = NULL;
3631 bool canceled =
false;
3736 if (hostaddr && *hostaddr)
3737 printf(
_(
"You are now connected to database \"%s\" as user \"%s\" on address \"%s\" at port \"%s\".\n"),
3740 printf(
_(
"You are now connected to database \"%s\" as user \"%s\" via socket in \"%s\" at port \"%s\".\n"),
3745 if (hostaddr && *hostaddr && strcmp(connhost, hostaddr) != 0)
3746 printf(
_(
"You are now connected to database \"%s\" as user \"%s\" on host \"%s\" (address \"%s\") at port \"%s\".\n"),
3749 printf(
_(
"You are now connected to database \"%s\" as user \"%s\" on host \"%s\" at port \"%s\".\n"),
3754 printf(
_(
"You are now connected to database \"%s\" as user \"%s\".\n"),
3776 int client_ver = PG_VERSION_NUM;
3790 sverbuf,
sizeof(sverbuf));
3794 printf(
_(
"%s (%s, server %s)\n"),
3798 else if (in_startup)
3807 printf(
_(
"WARNING: %s major version %s, server major version %s.\n"
3808 " Some psql features might not work.\n"),
3811 cverbuf,
sizeof(cverbuf)),
3813 sverbuf,
sizeof(sverbuf)));
3817 checkWin32Codepage();
3833 const char *protocol;
3835 const char *compression;
3844 printf(
_(
"SSL connection (protocol: %s, cipher: %s, compression: %s)\n"),
3845 protocol ? protocol :
_(
"unknown"),
3846 cipher ? cipher :
_(
"unknown"),
3847 (compression && strcmp(compression,
"off") != 0) ?
_(
"on") :
_(
"off"));
3861 printf(
_(
"GSSAPI-encrypted connection\n"));
3872 checkWin32Codepage(
void)
3878 concp = GetConsoleCP();
3881 printf(
_(
"WARNING: Console code page (%u) differs from Windows code page (%u)\n"
3882 " 8-bit characters might not work correctly. See psql reference\n"
3883 " page \"Notes for Windows users\" for details.\n"),
3960 const char *editorName;
3961 const char *editor_lineno_arg = NULL;
3968 editorName = getenv(
"PSQL_EDITOR");
3970 editorName = getenv(
"EDITOR");
3972 editorName = getenv(
"VISUAL");
3979 editor_lineno_arg = getenv(
"PSQL_EDITOR_LINENUMBER_ARG");
3980 #ifdef DEFAULT_EDITOR_LINENUMBER_ARG
3981 if (!editor_lineno_arg)
3984 if (!editor_lineno_arg)
3986 pg_log_error(
"environment variable PSQL_EDITOR_LINENUMBER_ARG must be set to specify a line number");
4000 sys =
psprintf(
"exec %s %s%d '%s'",
4001 editorName, editor_lineno_arg, lineno, fname);
4007 sys =
psprintf(
"\"%s\" %s%d \"%s\"",
4008 editorName, editor_lineno_arg, lineno, fname);
4014 result = system(sys);
4016 pg_log_error(
"could not start editor \"%s\"", editorName);
4017 else if (result == 127)
4041 int lineno,
bool discard_on_quit,
bool *edited)
4044 FILE *stream = NULL;
4052 fname = filename_arg;
4057 const char *tmpdir = getenv(
"TMPDIR");
4068 pg_log_error(
"could not locate temporary directory: %s",
4080 snprintf(fnametmp,
sizeof(fnametmp),
"%s%spsql.edit.%d.sql", tmpdir,
4081 "/", (
int) getpid());
4083 snprintf(fnametmp,
sizeof(fnametmp),
"%s%spsql.edit.%d.sql", tmpdir,
4084 "" , (
int) getpid());
4087 fname = (
const char *) fnametmp;
4089 fd = open(fname, O_WRONLY | O_CREAT | O_EXCL, 0600);
4091 stream = fdopen(
fd,
"w");
4093 if (
fd == -1 || !stream)
4095 pg_log_error(
"could not open temporary file \"%s\": %m", fname);
4100 unsigned int ql = query_buf->
len;
4103 if (ql > 0 && query_buf->
data[ql - 1] !=
'\n')
4109 if (fwrite(query_buf->
data, 1, ql, stream) != ql)
4113 if (fclose(stream) != 0)
4116 if (remove(fname) != 0)
4121 else if (fclose(stream) != 0)
4124 if (remove(fname) != 0)
4143 ut.modtime = ut.actime = time(NULL) - 2;
4144 (void) utime(fname, &ut);
4182 while (fgets(line,
sizeof(line), stream) != NULL)
4205 if (discard_on_quit)
4212 if (remove(fname) == -1)
4247 else if (strcmp(
filename,
"-") != 0)
4325 return "latex-longtable";
4395 vallen = strlen(
value);
4398 if (strcmp(param,
"format") == 0)
4400 static const struct fmt
4431 pg_log_error(
"\\pset: ambiguous abbreviation \"%s\" matches both \"%s\" and \"%s\"",
4433 formats[match_pos].
name, formats[
i].
name);
4439 popt->
topt.
format = formats[match_pos].number;
4451 pg_log_error(
"\\pset: allowed formats are aligned, asciidoc, csv, html, latex, latex-longtable, troff-ms, unaligned, wrapped");
4458 else if (strcmp(param,
"linestyle") == 0)
4470 pg_log_error(
"\\pset: allowed line styles are ascii, old-ascii, unicode");
4476 else if (strcmp(param,
"unicode_border_linestyle") == 0)
4485 pg_log_error(
"\\pset: allowed Unicode border line styles are single, double");
4491 else if (strcmp(param,
"unicode_column_linestyle") == 0)
4500 pg_log_error(
"\\pset: allowed Unicode column line styles are single, double");
4506 else if (strcmp(param,
"unicode_header_linestyle") == 0)
4515 pg_log_error(
"\\pset: allowed Unicode header line styles are single, double");
4521 else if (strcmp(param,
"border") == 0)
4528 else if (strcmp(param,
"x") == 0 ||
4529 strcmp(param,
"expanded") == 0 ||
4530 strcmp(param,
"vertical") == 0)
4551 else if (strcmp(param,
"xheader_width") == 0)
4563 int intval = atoi(
value);
4567 pg_log_error(
"\\pset: allowed xheader_width values are \"%s\" (default), \"%s\", \"%s\", or a number specifying the exact width",
"full",
"column",
"page");
4577 else if (strcmp(param,
"csv_fieldsep") == 0)
4582 if (strlen(
value) != 1)
4584 pg_log_error(
"\\pset: csv_fieldsep must be a single one-byte character");
4589 pg_log_error(
"\\pset: csv_fieldsep cannot be a double quote, a newline, or a carriage return");
4597 else if (strcmp(param,
"numericlocale") == 0)
4606 else if (strcmp(param,
"null") == 0)
4616 else if (strcmp(param,
"fieldsep") == 0)
4626 else if (strcmp(param,
"fieldsep_zero") == 0)
4634 else if (strcmp(param,
"recordsep") == 0)
4644 else if (strcmp(param,
"recordsep_zero") == 0)
4652 else if (strcmp(param,
"t") == 0 || strcmp(param,
"tuples_only") == 0)
4661 else if (strcmp(param,
"C") == 0 || strcmp(param,
"title") == 0)
4671 else if (strcmp(param,
"T") == 0 || strcmp(param,
"tableattr") == 0)
4681 else if (strcmp(param,
"pager") == 0)
4703 else if (strcmp(param,
"pager_min_lines") == 0)
4711 else if (strcmp(param,
"footer") == 0)
4720 else if (strcmp(param,
"columns") == 0)
4746 if (strcmp(param,
"border") == 0)
4750 else if (strcmp(param,
"columns") == 0)
4753 printf(
_(
"Target width is unset.\n"));
4759 else if (strcmp(param,
"x") == 0 || strcmp(param,
"expanded") == 0 || strcmp(param,
"vertical") == 0)
4762 printf(
_(
"Expanded display is on.\n"));
4764 printf(
_(
"Expanded display is used automatically.\n"));
4766 printf(
_(
"Expanded display is off.\n"));
4770 else if (strcmp(param,
"xheader_width") == 0)
4773 printf(
_(
"Expanded header width is \"%s\".\n"),
"full");
4775 printf(
_(
"Expanded header width is \"%s\".\n"),
"column");
4777 printf(
_(
"Expanded header width is \"%s\".\n"),
"page");
4783 else if (strcmp(param,
"csv_fieldsep") == 0)
4785 printf(
_(
"Field separator for CSV is \"%s\".\n"),
4790 else if (strcmp(param,
"fieldsep") == 0)
4793 printf(
_(
"Field separator is zero byte.\n"));
4795 printf(
_(
"Field separator is \"%s\".\n"),
4799 else if (strcmp(param,
"fieldsep_zero") == 0)
4801 printf(
_(
"Field separator is zero byte.\n"));
4805 else if (strcmp(param,
"footer") == 0)
4808 printf(
_(
"Default footer is on.\n"));
4810 printf(
_(
"Default footer is off.\n"));
4814 else if (strcmp(param,
"format") == 0)
4820 else if (strcmp(param,
"linestyle") == 0)
4822 printf(
_(
"Line style is %s.\n"),
4827 else if (strcmp(param,
"null") == 0)
4829 printf(
_(
"Null display is \"%s\".\n"),
4834 else if (strcmp(param,
"numericlocale") == 0)
4837 printf(
_(
"Locale-adjusted numeric output is on.\n"));
4839 printf(
_(
"Locale-adjusted numeric output is off.\n"));
4843 else if (strcmp(param,
"pager") == 0)
4846 printf(
_(
"Pager is used for long output.\n"));
4848 printf(
_(
"Pager is always used.\n"));
4850 printf(
_(
"Pager usage is off.\n"));
4854 else if (strcmp(param,
"pager_min_lines") == 0)
4857 "Pager won't be used for less than %d lines.\n",
4863 else if (strcmp(param,
"recordsep") == 0)
4866 printf(
_(
"Record separator is zero byte.\n"));
4868 printf(
_(
"Record separator is <newline>.\n"));
4870 printf(
_(
"Record separator is \"%s\".\n"),
4874 else if (strcmp(param,
"recordsep_zero") == 0)
4876 printf(
_(
"Record separator is zero byte.\n"));
4880 else if (strcmp(param,
"T") == 0 || strcmp(param,
"tableattr") == 0)
4883 printf(
_(
"Table attributes are \"%s\".\n"),
4886 printf(
_(
"Table attributes unset.\n"));
4890 else if (strcmp(param,
"C") == 0 || strcmp(param,
"title") == 0)
4895 printf(
_(
"Title is unset.\n"));
4899 else if (strcmp(param,
"t") == 0 || strcmp(param,
"tuples_only") == 0)
4902 printf(
_(
"Tuples only is on.\n"));
4904 printf(
_(
"Tuples only is off.\n"));
4908 else if (strcmp(param,
"unicode_border_linestyle") == 0)
4910 printf(
_(
"Unicode border line style is \"%s\".\n"),
4914 else if (strcmp(param,
"unicode_column_linestyle") == 0)
4916 printf(
_(
"Unicode column line style is \"%s\".\n"),
4920 else if (strcmp(param,
"unicode_header_linestyle") == 0)
4922 printf(
_(
"Unicode header line style is \"%s\".\n"),
5005 return val ?
"on" :
"off";
5024 else if (*
str ==
'\'')
5052 if (strcmp(param,
"border") == 0)
5054 else if (strcmp(param,
"columns") == 0)
5056 else if (strcmp(param,
"csv_fieldsep") == 0)
5058 else if (strcmp(param,
"expanded") == 0)
5062 else if (strcmp(param,
"fieldsep") == 0)
5066 else if (strcmp(param,
"fieldsep_zero") == 0)
5068 else if (strcmp(param,
"footer") == 0)
5070 else if (strcmp(param,
"format") == 0)
5072 else if (strcmp(param,
"linestyle") == 0)
5074 else if (strcmp(param,
"null") == 0)
5078 else if (strcmp(param,
"numericlocale") == 0)
5080 else if (strcmp(param,
"pager") == 0)
5082 else if (strcmp(param,
"pager_min_lines") == 0)
5084 else if (strcmp(param,
"recordsep") == 0)
5088 else if (strcmp(param,
"recordsep_zero") == 0)
5090 else if (strcmp(param,
"tableattr") == 0)
5092 else if (strcmp(param,
"title") == 0)
5094 else if (strcmp(param,
"tuples_only") == 0)
5096 else if (strcmp(param,
"unicode_border_linestyle") == 0)
5098 else if (strcmp(param,
"unicode_column_linestyle") == 0)
5100 else if (strcmp(param,
"unicode_header_linestyle") == 0)
5102 else if (strcmp(param,
"xheader_width") == 0)
5115 snprintf(wbuff,
sizeof(wbuff),
"%d",
5127 #define DEFAULT_SHELL "/bin/sh"
5133 #define DEFAULT_SHELL "cmd.exe"
5145 const char *shellName;
5147 shellName = getenv(
"SHELL");
5149 if (shellName == NULL)
5150 shellName = getenv(
"COMSPEC");
5152 if (shellName == NULL)
5157 sys =
psprintf(
"exec %s", shellName);
5159 sys =
psprintf(
"\"%s\"", shellName);
5161 result = system(sys);
5165 result = system(command);
5169 if (result == 127 || result == -1)
5186 long sleep_ms = (long) (sleep * 1000);
5188 const char *strftime_fmt;
5189 const char *user_title;
5191 const char *pagerprog = NULL;
5192 FILE *pagerpipe = NULL;
5196 sigset_t sigalrm_sigchld_sigint;
5197 sigset_t sigalrm_sigchld;
5203 if (!query_buf || query_buf->
len <= 0)
5205 pg_log_error(
"\\watch cannot be used with an empty query");
5210 sigemptyset(&sigalrm_sigchld_sigint);
5211 sigaddset(&sigalrm_sigchld_sigint,
SIGCHLD);
5212 sigaddset(&sigalrm_sigchld_sigint,
SIGALRM);
5213 sigaddset(&sigalrm_sigchld_sigint, SIGINT);
5215 sigemptyset(&sigalrm_sigchld);
5216 sigaddset(&sigalrm_sigchld,
SIGCHLD);
5217 sigaddset(&sigalrm_sigchld,
SIGALRM);
5219 sigemptyset(&sigint);
5220 sigaddset(&sigint, SIGINT);
5226 sigprocmask(SIG_BLOCK, &sigalrm_sigchld, NULL);
5232 interval.it_value.tv_sec = sleep_ms / 1000;
5233 interval.it_value.tv_usec = (sleep_ms % 1000) * 1000;
5251 pagerprog = getenv(
"PSQL_WATCH_PAGER");
5253 if (pagerprog && strspn(pagerprog,
" \t\r\n") == strlen(pagerprog))
5257 isatty(fileno(stdin)) && isatty(fileno(
stdout)))
5261 pagerpipe = popen(pagerprog,
"w");
5273 strftime_fmt =
"%c";
5288 user_title = myopt.
title;
5289 title_len = (user_title ? strlen(user_title) : 0) + 256;
5303 strftime(timebuf,
sizeof(timebuf), strftime_fmt, localtime(&timer));
5306 snprintf(title, title_len,
_(
"%s\t%s (every %gs)\n"),
5307 user_title, timebuf, sleep);
5309 snprintf(title, title_len,
_(
"%s (every %gs)\n"),
5311 myopt.
title = title;
5324 if (iter && (--iter <= 0))
5327 if (pagerpipe && ferror(pagerpipe))
5348 for (
long i = sleep_ms;
i > 0;)
5350 long s =
Min(
i, 1000L);
5360 sigprocmask(SIG_BLOCK, &sigint, NULL);
5367 int signal_received;
5369 errno = sigwait(&sigalrm_sigchld_sigint, &signal_received);
5383 if (signal_received == SIGINT || signal_received ==
SIGCHLD)
5390 sigprocmask(SIG_UNBLOCK, &sigint, NULL);
5419 sigprocmask(SIG_UNBLOCK, &sigalrm_sigchld_sigint, NULL);
5435 printf(
_(
"/******** QUERY *********/\n"
5437 "/************************/\n\n"), query);
5442 _(
"/******** QUERY *********/\n"
5444 "/************************/\n\n"), query);
5482 strchr(desc,
'(') ?
"regprocedure" :
"regproc");