From cf1cf8964925cd36dc7bf034a968a4e44ede382a Mon Sep 17 00:00:00 2001 From: Peter Eisentraut Date: Tue, 18 Mar 2003 22:15:44 +0000 Subject: [PATCH] Make the printing code somewhat more independent by not relying on functions and global variables from the rest of psql. Also clean up some data type mismatches created by the last pager patch. --- src/bin/psql/command.c | 4 ++- src/bin/psql/common.c | 53 +--------------------------- src/bin/psql/common.h | 4 +-- src/bin/psql/help.c | 4 +-- src/bin/psql/help.h | 4 +-- src/bin/psql/mbprint.c | 11 +++--- src/bin/psql/mbprint.h | 6 ++-- src/bin/psql/print.c | 80 ++++++++++++++++++++++++++++++++---------- src/bin/psql/print.h | 7 +++- src/bin/psql/startup.c | 4 ++- 10 files changed, 88 insertions(+), 89 deletions(-) diff --git a/src/bin/psql/command.c b/src/bin/psql/command.c index feb6ba32a9..66a8553e21 100644 --- a/src/bin/psql/command.c +++ b/src/bin/psql/command.c @@ -3,7 +3,7 @@ * * Copyright 2000-2002 by PostgreSQL Global Development Group * - * $Header: /cvsroot/pgsql/src/bin/psql/command.c,v 1.91 2003/03/10 15:46:01 momjian Exp $ + * $Header: /cvsroot/pgsql/src/bin/psql/command.c,v 1.92 2003/03/18 22:15:43 petere Exp $ */ #include "postgres_fe.h" #include "command.h" @@ -471,6 +471,7 @@ exec_command(const char *cmd, { /* save encoding info into psql internal data */ pset.encoding = PQclientEncoding(pset.db); + pset.popt.topt.encoding = PQclientEncoding(pset.db); SetVariable(pset.vars, "ENCODING", pg_encoding_to_char(pset.encoding)); } free(encoding); @@ -1445,6 +1446,7 @@ do_connect(const char *new_dbname, const char *new_user) PQsetNoticeProcessor(pset.db, NoticeProcessor, NULL); pset.encoding = PQclientEncoding(pset.db); + pset.popt.topt.encoding = PQclientEncoding(pset.db); /* Update variables */ SetVariable(pset.vars, "DBNAME", PQdb(pset.db)); diff --git a/src/bin/psql/common.c b/src/bin/psql/common.c index 0caaf1ef64..5d7180f993 100644 --- a/src/bin/psql/common.c +++ b/src/bin/psql/common.c @@ -3,7 +3,7 @@ * * Copyright 2000 by PostgreSQL Global Development Group * - * $Header: /cvsroot/pgsql/src/bin/psql/common.c,v 1.56 2003/03/10 22:28:19 tgl Exp $ + * $Header: /cvsroot/pgsql/src/bin/psql/common.c,v 1.57 2003/03/18 22:15:44 petere Exp $ */ #include "postgres_fe.h" #include "common.h" @@ -24,14 +24,6 @@ #include /* for _ftime() */ #endif -#ifndef WIN32 -#include /* for ioctl() */ -#endif - -#ifdef HAVE_TERMIOS_H -#include -#endif - #include "libpq-fe.h" #include "pqsignal.h" @@ -522,46 +514,3 @@ SendQuery(const char *query) return success; } - - -/* - * PageOutput - * - * Tests if pager is needed and returns appropriate FILE pointer. - */ -FILE * -PageOutput(int lines, bool pager) -{ - /* check whether we need / can / are supposed to use pager */ - if (pager -#ifndef WIN32 - && - isatty(fileno(stdin)) && - isatty(fileno(stdout)) -#endif - ) - { - const char *pagerprog; - -#ifdef TIOCGWINSZ - int result; - struct winsize screen_size; - - result = ioctl(fileno(stdout), TIOCGWINSZ, &screen_size); - if (result == -1 || lines > screen_size.ws_row || pager > 1) - { -#endif - pagerprog = getenv("PAGER"); - if (!pagerprog) - pagerprog = DEFAULT_PAGER; -#ifndef WIN32 - pqsignal(SIGPIPE, SIG_IGN); -#endif - return popen(pagerprog, "w"); -#ifdef TIOCGWINSZ - } -#endif - } - - return stdout; -} diff --git a/src/bin/psql/common.h b/src/bin/psql/common.h index 3b0c7d8b56..fdfcdc05eb 100644 --- a/src/bin/psql/common.h +++ b/src/bin/psql/common.h @@ -3,7 +3,7 @@ * * Copyright 2000 by PostgreSQL Global Development Group * - * $Header: /cvsroot/pgsql/src/bin/psql/common.h,v 1.21 2002/10/29 19:35:33 momjian Exp $ + * $Header: /cvsroot/pgsql/src/bin/psql/common.h,v 1.22 2003/03/18 22:15:44 petere Exp $ */ #ifndef COMMON_H #define COMMON_H @@ -37,8 +37,6 @@ extern PGresult *PSQLexec(const char *query, bool ignore_command_ok); extern bool SendQuery(const char *query); -extern FILE *PageOutput(int lines, bool pager); - /* sprompt.h */ extern char *simple_prompt(const char *prompt, int maxlen, bool echo); diff --git a/src/bin/psql/help.c b/src/bin/psql/help.c index d1a30e40ae..1a55640afa 100644 --- a/src/bin/psql/help.c +++ b/src/bin/psql/help.c @@ -3,7 +3,7 @@ * * Copyright 2000 by PostgreSQL Global Development Group * - * $Header: /cvsroot/pgsql/src/bin/psql/help.c,v 1.70 2003/03/10 15:46:03 momjian Exp $ + * $Header: /cvsroot/pgsql/src/bin/psql/help.c,v 1.71 2003/03/18 22:15:44 petere Exp $ */ #include "postgres_fe.h" #include "common.h" @@ -262,7 +262,7 @@ slashUsage(unsigned short int pager) * */ void -helpSQL(const char *topic, bool pager) +helpSQL(const char *topic, unsigned short int pager) { #define VALUE_OR_NULL(a) ((a) ? (a) : "") diff --git a/src/bin/psql/help.h b/src/bin/psql/help.h index 7b3078dd85..8b247d0fed 100644 --- a/src/bin/psql/help.h +++ b/src/bin/psql/help.h @@ -3,7 +3,7 @@ * * Copyright 2000 by PostgreSQL Global Development Group * - * $Header: /cvsroot/pgsql/src/bin/psql/help.h,v 1.11 2002/11/08 19:12:21 momjian Exp $ + * $Header: /cvsroot/pgsql/src/bin/psql/help.h,v 1.12 2003/03/18 22:15:44 petere Exp $ */ #ifndef HELP_H #define HELP_H @@ -12,7 +12,7 @@ void usage(void); void slashUsage(unsigned short int pager); -void helpSQL(const char *topic, bool pager); +void helpSQL(const char *topic, unsigned short int pager); void print_copyright(void); diff --git a/src/bin/psql/mbprint.c b/src/bin/psql/mbprint.c index c91b71c9c5..692f60bf77 100644 --- a/src/bin/psql/mbprint.c +++ b/src/bin/psql/mbprint.c @@ -3,14 +3,13 @@ * * Copyright 2000 by PostgreSQL Global Development Group * - * $Header: /cvsroot/pgsql/src/bin/psql/mbprint.c,v 1.5 2002/10/03 17:09:42 momjian Exp $ + * $Header: /cvsroot/pgsql/src/bin/psql/mbprint.c,v 1.6 2003/03/18 22:15:44 petere Exp $ */ #include "postgres_fe.h" #include "mbprint.h" #include "mb/pg_wchar.h" -#include "settings.h" /* * This is an implementation of wcwidth() and wcswidth() as defined in @@ -310,9 +309,9 @@ mb_utf_validate(unsigned char *pwcs) */ int -pg_wcswidth(unsigned char *pwcs, size_t len) +pg_wcswidth(unsigned char *pwcs, size_t len, int encoding) { - if (pset.encoding == PG_UTF8) + if (encoding == PG_UTF8) return mb_utf_wcswidth(pwcs, len); else { @@ -325,9 +324,9 @@ pg_wcswidth(unsigned char *pwcs, size_t len) } unsigned char * -mbvalidate(unsigned char *pwcs) +mbvalidate(unsigned char *pwcs, int encoding) { - if (pset.encoding == PG_UTF8) + if (encoding == PG_UTF8) return mb_utf_validate(pwcs); else { diff --git a/src/bin/psql/mbprint.h b/src/bin/psql/mbprint.h index 826b71c84a..7624a34793 100644 --- a/src/bin/psql/mbprint.h +++ b/src/bin/psql/mbprint.h @@ -1,4 +1,4 @@ -/* $Id: mbprint.h,v 1.5 2002/08/27 20:16:48 petere Exp $ */ +/* $Id: mbprint.h,v 1.6 2003/03/18 22:15:44 petere Exp $ */ #ifndef MBPRINT_H #define MBPRINT_H @@ -6,8 +6,8 @@ pg_wchar utf2ucs(const unsigned char *c); -unsigned char *mbvalidate(unsigned char *pwcs); +unsigned char *mbvalidate(unsigned char *pwcs, int encoding); -int pg_wcswidth(unsigned char *pwcs, size_t len); +int pg_wcswidth(unsigned char *pwcs, size_t len, int encoding); #endif /* MBPRINT_H */ diff --git a/src/bin/psql/print.c b/src/bin/psql/print.c index 4c76d06f8f..7ac365647d 100644 --- a/src/bin/psql/print.c +++ b/src/bin/psql/print.c @@ -3,7 +3,7 @@ * * Copyright 2000 by PostgreSQL Global Development Group * - * $Header: /cvsroot/pgsql/src/bin/psql/print.c,v 1.35 2002/11/01 15:12:19 tgl Exp $ + * $Header: /cvsroot/pgsql/src/bin/psql/print.c,v 1.36 2003/03/18 22:15:44 petere Exp $ */ #include "postgres_fe.h" #include "common.h" @@ -11,12 +11,15 @@ #include #include +#include + +#ifndef WIN32 +#include /* for ioctl() */ +#endif #include "pqsignal.h" #include "libpq-fe.h" -#include "settings.h" - #include "mbprint.h" /*************************/ @@ -195,7 +198,7 @@ static void print_aligned_text(const char *title, const char *const * headers, const char *const * cells, const char *const * footers, const char *opt_align, bool opt_barebones, - unsigned short int opt_border, + unsigned short int opt_border, int encoding, FILE *fout) { unsigned int col_count = 0; @@ -253,7 +256,7 @@ print_aligned_text(const char *title, const char *const * headers, /* calc column widths */ for (i = 0; i < col_count; i++) { - tmp = pg_wcswidth((unsigned char *) headers[i], strlen(headers[i])); + tmp = pg_wcswidth((unsigned char *) headers[i], strlen(headers[i]), encoding); if (tmp > widths[i]) widths[i] = tmp; head_w[i] = tmp; @@ -261,7 +264,7 @@ print_aligned_text(const char *title, const char *const * headers, for (i = 0, ptr = cells; *ptr; ptr++, i++) { - tmp = pg_wcswidth((unsigned char *) *ptr, strlen(*ptr)); + tmp = pg_wcswidth((unsigned char *) *ptr, strlen(*ptr), encoding); if (tmp > widths[i % col_count]) widths[i % col_count] = tmp; cell_w[i] = tmp; @@ -282,7 +285,7 @@ print_aligned_text(const char *title, const char *const * headers, { int tlen; - tlen = pg_wcswidth((unsigned char *) title, strlen(title)); + tlen = pg_wcswidth((unsigned char *) title, strlen(title), encoding); if (tlen >= (int) total_w) fprintf(fout, "%s\n", title); else @@ -392,9 +395,9 @@ print_aligned_text(const char *title, const char *const * headers, static void print_aligned_vertical(const char *title, const char *const * headers, - const char *const * cells, const char *const * footers, + const char *const * cells, const char *const * footers, bool opt_barebones, unsigned short int opt_border, - FILE *fout) + int encoding, FILE *fout) { unsigned int col_count = 0; unsigned int record = 1; @@ -425,7 +428,7 @@ print_aligned_vertical(const char *title, const char *const * headers, } for (i = 0; i < col_count; i++) { - if ((tmp = pg_wcswidth((unsigned char *) headers[i], strlen(headers[i]))) > hwidth) + if ((tmp = pg_wcswidth((unsigned char *) headers[i], strlen(headers[i]), encoding)) > hwidth) hwidth = tmp; head_w[i] = tmp; } @@ -447,7 +450,7 @@ print_aligned_vertical(const char *title, const char *const * headers, /* find longest data cell */ for (i = 0, ptr = cells; *ptr; ptr++, i++) { - if ((tmp = pg_wcswidth((unsigned char *) *ptr, strlen(*ptr))) > dwidth) + if ((tmp = pg_wcswidth((unsigned char *) *ptr, strlen(*ptr), encoding)) > dwidth) dwidth = tmp; cell_w[i] = tmp; } @@ -953,14 +956,55 @@ const char *opt_align, bool opt_barebones, unsigned short int opt_border, - - - /********************************/ /* Public functions */ /********************************/ +/* + * PageOutput + * + * Tests if pager is needed and returns appropriate FILE pointer. + */ +FILE * +PageOutput(int lines, unsigned short int pager) +{ + /* check whether we need / can / are supposed to use pager */ + if (pager +#ifndef WIN32 + && + isatty(fileno(stdin)) && + isatty(fileno(stdout)) +#endif + ) + { + const char *pagerprog; + +#ifdef TIOCGWINSZ + int result; + struct winsize screen_size; + + result = ioctl(fileno(stdout), TIOCGWINSZ, &screen_size); + if (result == -1 || lines > screen_size.ws_row || pager > 1) + { +#endif + pagerprog = getenv("PAGER"); + if (!pagerprog) + pagerprog = DEFAULT_PAGER; +#ifndef WIN32 + pqsignal(SIGPIPE, SIG_IGN); +#endif + return popen(pagerprog, "w"); +#ifdef TIOCGWINSZ + } +#endif + } + + return stdout; +} + + + void printTable(const char *title, const char *const * headers, @@ -1023,9 +1067,9 @@ printTable(const char *title, break; case PRINT_ALIGNED: if (opt->expanded) - print_aligned_vertical(title, headers, cells, footers, opt->tuples_only, border, output); + print_aligned_vertical(title, headers, cells, footers, opt->tuples_only, border, opt->encoding, output); else - print_aligned_text(title, headers, cells, footers, align, opt->tuples_only, border, output); + print_aligned_text(title, headers, cells, footers, align, opt->tuples_only, border, opt->encoding, output); break; case PRINT_HTML: if (opt->expanded) @@ -1077,7 +1121,7 @@ printQuery(const PGresult *result, const printQueryOpt *opt, FILE *fout) } for (i = 0; i < nfields; i++) - headers[i] = mbvalidate(PQfname(result, i)); + headers[i] = mbvalidate(PQfname(result, i), opt->topt.encoding); /* set cells */ @@ -1093,7 +1137,7 @@ printQuery(const PGresult *result, const printQueryOpt *opt, FILE *fout) if (PQgetisnull(result, i / nfields, i % nfields)) cells[i] = opt->nullPrint ? opt->nullPrint : ""; else - cells[i] = mbvalidate(PQgetvalue(result, i / nfields, i % nfields)); + cells[i] = mbvalidate(PQgetvalue(result, i / nfields, i % nfields), opt->topt.encoding); } /* set footers */ diff --git a/src/bin/psql/print.h b/src/bin/psql/print.h index f97bf9ead5..e0ce3401d3 100644 --- a/src/bin/psql/print.h +++ b/src/bin/psql/print.h @@ -3,13 +3,17 @@ * * Copyright 2000 by PostgreSQL Global Development Group * - * $Header: /cvsroot/pgsql/src/bin/psql/print.h,v 1.15 2002/11/08 19:12:21 momjian Exp $ + * $Header: /cvsroot/pgsql/src/bin/psql/print.h,v 1.16 2003/03/18 22:15:44 petere Exp $ */ #ifndef PRINT_H #define PRINT_H #include "libpq-fe.h" + +extern FILE *PageOutput(int lines, unsigned short int pager); + + enum printFormat { PRINT_NOTHING = 0, /* to make sure someone initializes this */ @@ -36,6 +40,7 @@ typedef struct _printTableOpt char *recordSep; /* record separator for unaligned text * mode */ char *tableAttr; /* attributes for HTML */ + int encoding; /* character encoding */ } printTableOpt; diff --git a/src/bin/psql/startup.c b/src/bin/psql/startup.c index 28bbf3cc5e..39c22dfc69 100644 --- a/src/bin/psql/startup.c +++ b/src/bin/psql/startup.c @@ -3,7 +3,7 @@ * * Copyright 2000 by PostgreSQL Global Development Group * - * $Header: /cvsroot/pgsql/src/bin/psql/startup.c,v 1.70 2003/01/06 18:53:25 petere Exp $ + * $Header: /cvsroot/pgsql/src/bin/psql/startup.c,v 1.71 2003/03/18 22:15:44 petere Exp $ */ #include "postgres_fe.h" @@ -231,6 +231,8 @@ main(int argc, char *argv[]) SetVariable(pset.vars, "PORT", PQport(pset.db)); SetVariable(pset.vars, "ENCODING", pg_encoding_to_char(pset.encoding)); + pset.popt.topt.encoding = pset.encoding; + /* * Now find something to do */