PostgreSQL Source Code git master
vacuumdb.c File Reference
#include "postgres_fe.h"
#include <limits.h>
#include "common.h"
#include "common/logging.h"
#include "fe_utils/option_utils.h"
#include "vacuuming.h"
Include dependency graph for vacuumdb.c:

Go to the source code of this file.

Functions

static void help (const char *progname)
 
static void check_objfilter (bits32 objfilter)
 
int main (int argc, char *argv[])
 

Function Documentation

◆ check_objfilter()

void check_objfilter ( bits32  objfilter)
static

Definition at line 325 of file vacuumdb.c.

326{
327 if ((objfilter & OBJFILTER_ALL_DBS) &&
328 (objfilter & OBJFILTER_DATABASE))
329 pg_fatal("cannot vacuum all databases and a specific one at the same time");
330
331 if ((objfilter & OBJFILTER_TABLE) &&
332 (objfilter & OBJFILTER_SCHEMA))
333 pg_fatal("cannot vacuum all tables in schema(s) and specific table(s) at the same time");
334
335 if ((objfilter & OBJFILTER_TABLE) &&
336 (objfilter & OBJFILTER_SCHEMA_EXCLUDE))
337 pg_fatal("cannot vacuum specific table(s) and exclude schema(s) at the same time");
338
339 if ((objfilter & OBJFILTER_SCHEMA) &&
340 (objfilter & OBJFILTER_SCHEMA_EXCLUDE))
341 pg_fatal("cannot vacuum all tables in schema(s) and exclude schema(s) at the same time");
342}
#define pg_fatal(...)
#define OBJFILTER_ALL_DBS
Definition: vacuuming.h:60
#define OBJFILTER_SCHEMA_EXCLUDE
Definition: vacuuming.h:64
#define OBJFILTER_TABLE
Definition: vacuuming.h:62
#define OBJFILTER_DATABASE
Definition: vacuuming.h:61
#define OBJFILTER_SCHEMA
Definition: vacuuming.h:63

References OBJFILTER_ALL_DBS, OBJFILTER_DATABASE, OBJFILTER_SCHEMA, OBJFILTER_SCHEMA_EXCLUDE, OBJFILTER_TABLE, and pg_fatal.

Referenced by main().

◆ help()

static void help ( const char *  progname)
static

Definition at line 346 of file vacuumdb.c.

347{
348 printf(_("%s cleans and analyzes a PostgreSQL database.\n\n"), progname);
349 printf(_("Usage:\n"));
350 printf(_(" %s [OPTION]... [DBNAME]\n"), progname);
351 printf(_("\nOptions:\n"));
352 printf(_(" -a, --all vacuum all databases\n"));
353 printf(_(" --buffer-usage-limit=SIZE size of ring buffer used for vacuum\n"));
354 printf(_(" -d, --dbname=DBNAME database to vacuum\n"));
355 printf(_(" --disable-page-skipping disable all page-skipping behavior\n"));
356 printf(_(" --dry-run show the commands that would be sent to the server\n"));
357 printf(_(" -e, --echo show the commands being sent to the server\n"));
358 printf(_(" -f, --full do full vacuuming\n"));
359 printf(_(" -F, --freeze freeze row transaction information\n"));
360 printf(_(" --force-index-cleanup always remove index entries that point to dead tuples\n"));
361 printf(_(" -j, --jobs=NUM use this many concurrent connections to vacuum\n"));
362 printf(_(" --min-mxid-age=MXID_AGE minimum multixact ID age of tables to vacuum\n"));
363 printf(_(" --min-xid-age=XID_AGE minimum transaction ID age of tables to vacuum\n"));
364 printf(_(" --missing-stats-only only analyze relations with missing statistics\n"));
365 printf(_(" --no-index-cleanup don't remove index entries that point to dead tuples\n"));
366 printf(_(" --no-process-main skip the main relation\n"));
367 printf(_(" --no-process-toast skip the TOAST table associated with the table to vacuum\n"));
368 printf(_(" --no-truncate don't truncate empty pages at the end of the table\n"));
369 printf(_(" -n, --schema=SCHEMA vacuum tables in the specified schema(s) only\n"));
370 printf(_(" -N, --exclude-schema=SCHEMA do not vacuum tables in the specified schema(s)\n"));
371 printf(_(" -P, --parallel=PARALLEL_WORKERS use this many background workers for vacuum, if available\n"));
372 printf(_(" -q, --quiet don't write any messages\n"));
373 printf(_(" --skip-locked skip relations that cannot be immediately locked\n"));
374 printf(_(" -t, --table='TABLE[(COLUMNS)]' vacuum specific table(s) only\n"));
375 printf(_(" -v, --verbose write a lot of output\n"));
376 printf(_(" -V, --version output version information, then exit\n"));
377 printf(_(" -z, --analyze update optimizer statistics\n"));
378 printf(_(" -Z, --analyze-only only update optimizer statistics; no vacuum\n"));
379 printf(_(" --analyze-in-stages only update optimizer statistics, in multiple\n"
380 " stages for faster results; no vacuum\n"));
381 printf(_(" -?, --help show this help, then exit\n"));
382 printf(_("\nConnection options:\n"));
383 printf(_(" -h, --host=HOSTNAME database server host or socket directory\n"));
384 printf(_(" -p, --port=PORT database server port\n"));
385 printf(_(" -U, --username=USERNAME user name to connect as\n"));
386 printf(_(" -w, --no-password never prompt for password\n"));
387 printf(_(" -W, --password force password prompt\n"));
388 printf(_(" --maintenance-db=DBNAME alternate maintenance database\n"));
389 printf(_("\nRead the description of the SQL command VACUUM for details.\n"));
390 printf(_("\nReport bugs to <%s>.\n"), PACKAGE_BUGREPORT);
391 printf(_("%s home page: <%s>\n"), PACKAGE_NAME, PACKAGE_URL);
392}
#define _(x)
Definition: elog.c:91
const char * progname
Definition: main.c:44
#define printf(...)
Definition: port.h:266

References _, printf, and progname.

Referenced by main().

◆ main()

int main ( int  argc,
char *  argv[] 
)

Definition at line 27 of file vacuumdb.c.

28{
29 static struct option long_options[] = {
30 {"host", required_argument, NULL, 'h'},
31 {"port", required_argument, NULL, 'p'},
32 {"username", required_argument, NULL, 'U'},
33 {"no-password", no_argument, NULL, 'w'},
34 {"password", no_argument, NULL, 'W'},
35 {"echo", no_argument, NULL, 'e'},
36 {"quiet", no_argument, NULL, 'q'},
37 {"dbname", required_argument, NULL, 'd'},
38 {"analyze", no_argument, NULL, 'z'},
39 {"analyze-only", no_argument, NULL, 'Z'},
40 {"freeze", no_argument, NULL, 'F'},
41 {"all", no_argument, NULL, 'a'},
42 {"table", required_argument, NULL, 't'},
43 {"full", no_argument, NULL, 'f'},
44 {"verbose", no_argument, NULL, 'v'},
45 {"jobs", required_argument, NULL, 'j'},
46 {"parallel", required_argument, NULL, 'P'},
47 {"schema", required_argument, NULL, 'n'},
48 {"exclude-schema", required_argument, NULL, 'N'},
49 {"maintenance-db", required_argument, NULL, 2},
50 {"analyze-in-stages", no_argument, NULL, 3},
51 {"disable-page-skipping", no_argument, NULL, 4},
52 {"skip-locked", no_argument, NULL, 5},
53 {"min-xid-age", required_argument, NULL, 6},
54 {"min-mxid-age", required_argument, NULL, 7},
55 {"no-index-cleanup", no_argument, NULL, 8},
56 {"force-index-cleanup", no_argument, NULL, 9},
57 {"no-truncate", no_argument, NULL, 10},
58 {"no-process-toast", no_argument, NULL, 11},
59 {"no-process-main", no_argument, NULL, 12},
60 {"buffer-usage-limit", required_argument, NULL, 13},
61 {"missing-stats-only", no_argument, NULL, 14},
62 {"dry-run", no_argument, NULL, 15},
63 {NULL, 0, NULL, 0}
64 };
65
66 const char *progname;
67 int optindex;
68 int c;
69 const char *dbname = NULL;
70 const char *maintenance_db = NULL;
71 ConnParams cparams;
72 vacuumingOptions vacopts;
73 SimpleStringList objects = {NULL, NULL};
74 int concurrentCons = 1;
75 unsigned int tbl_count = 0;
76 int ret;
77
78 /* initialize options */
79 memset(&vacopts, 0, sizeof(vacopts));
80 vacopts.parallel_workers = -1;
81 vacopts.do_truncate = true;
82 vacopts.process_main = true;
83 vacopts.process_toast = true;
84
85 /* the same for connection parameters */
86 memset(&cparams, 0, sizeof(cparams));
88
89 pg_logging_init(argv[0]);
90 progname = get_progname(argv[0]);
91 set_pglocale_pgservice(argv[0], PG_TEXTDOMAIN("pgscripts"));
92
93 handle_help_version_opts(argc, argv, "vacuumdb", help);
94
95 while ((c = getopt_long(argc, argv, "ad:efFh:j:n:N:p:P:qt:U:vwWzZ",
96 long_options, &optindex)) != -1)
97 {
98 switch (c)
99 {
100 case 'a':
101 vacopts.objfilter |= OBJFILTER_ALL_DBS;
102 break;
103 case 'd':
104 vacopts.objfilter |= OBJFILTER_DATABASE;
106 break;
107 case 'e':
108 vacopts.echo = true;
109 break;
110 case 'f':
111 vacopts.full = true;
112 break;
113 case 'F':
114 vacopts.freeze = true;
115 break;
116 case 'h':
117 cparams.pghost = pg_strdup(optarg);
118 break;
119 case 'j':
120 if (!option_parse_int(optarg, "-j/--jobs", 1, INT_MAX,
121 &concurrentCons))
122 exit(1);
123 break;
124 case 'n':
125 vacopts.objfilter |= OBJFILTER_SCHEMA;
127 break;
128 case 'N':
131 break;
132 case 'p':
133 cparams.pgport = pg_strdup(optarg);
134 break;
135 case 'P':
136 if (!option_parse_int(optarg, "-P/--parallel", 0, INT_MAX,
137 &vacopts.parallel_workers))
138 exit(1);
139 break;
140 case 'q':
141 vacopts.quiet = true;
142 break;
143 case 't':
144 vacopts.objfilter |= OBJFILTER_TABLE;
146 tbl_count++;
147 break;
148 case 'U':
149 cparams.pguser = pg_strdup(optarg);
150 break;
151 case 'v':
152 vacopts.verbose = true;
153 break;
154 case 'w':
155 cparams.prompt_password = TRI_NO;
156 break;
157 case 'W':
158 cparams.prompt_password = TRI_YES;
159 break;
160 case 'z':
161 vacopts.and_analyze = true;
162 break;
163 case 'Z':
164 /* if analyze-in-stages is given, don't override it */
165 if (vacopts.mode != MODE_ANALYZE_IN_STAGES)
166 vacopts.mode = MODE_ANALYZE;
167 break;
168 case 2:
169 maintenance_db = pg_strdup(optarg);
170 break;
171 case 3:
173 break;
174 case 4:
175 vacopts.disable_page_skipping = true;
176 break;
177 case 5:
178 vacopts.skip_locked = true;
179 break;
180 case 6:
181 if (!option_parse_int(optarg, "--min-xid-age", 1, INT_MAX,
182 &vacopts.min_xid_age))
183 exit(1);
184 break;
185 case 7:
186 if (!option_parse_int(optarg, "--min-mxid-age", 1, INT_MAX,
187 &vacopts.min_mxid_age))
188 exit(1);
189 break;
190 case 8:
191 vacopts.no_index_cleanup = true;
192 break;
193 case 9:
194 vacopts.force_index_cleanup = true;
195 break;
196 case 10:
197 vacopts.do_truncate = false;
198 break;
199 case 11:
200 vacopts.process_toast = false;
201 break;
202 case 12:
203 vacopts.process_main = false;
204 break;
205 case 13:
207 break;
208 case 14:
209 vacopts.missing_stats_only = true;
210 break;
211 case 15:
212 vacopts.dry_run = true;
213 break;
214 default:
215 /* getopt_long already emitted a complaint */
216 pg_log_error_hint("Try \"%s --help\" for more information.", progname);
217 exit(1);
218 }
219 }
220
221 /*
222 * Non-option argument specifies database name as long as it wasn't
223 * already specified with -d / --dbname
224 */
225 if (optind < argc && dbname == NULL)
226 {
227 vacopts.objfilter |= OBJFILTER_DATABASE;
228 dbname = argv[optind];
229 optind++;
230 }
231
232 if (optind < argc)
233 {
234 pg_log_error("too many command-line arguments (first is \"%s\")",
235 argv[optind]);
236 pg_log_error_hint("Try \"%s --help\" for more information.", progname);
237 exit(1);
238 }
239
240 /*
241 * Validate the combination of filters specified in the command-line
242 * options.
243 */
244 check_objfilter(vacopts.objfilter);
245
246 if (vacopts.mode == MODE_ANALYZE ||
247 vacopts.mode == MODE_ANALYZE_IN_STAGES)
248 {
249 if (vacopts.full)
250 pg_fatal("cannot use the \"%s\" option when performing only analyze",
251 "full");
252 if (vacopts.freeze)
253 pg_fatal("cannot use the \"%s\" option when performing only analyze",
254 "freeze");
255 if (vacopts.disable_page_skipping)
256 pg_fatal("cannot use the \"%s\" option when performing only analyze",
257 "disable-page-skipping");
258 if (vacopts.no_index_cleanup)
259 pg_fatal("cannot use the \"%s\" option when performing only analyze",
260 "no-index-cleanup");
261 if (vacopts.force_index_cleanup)
262 pg_fatal("cannot use the \"%s\" option when performing only analyze",
263 "force-index-cleanup");
264 if (!vacopts.do_truncate)
265 pg_fatal("cannot use the \"%s\" option when performing only analyze",
266 "no-truncate");
267 if (!vacopts.process_main)
268 pg_fatal("cannot use the \"%s\" option when performing only analyze",
269 "no-process-main");
270 if (!vacopts.process_toast)
271 pg_fatal("cannot use the \"%s\" option when performing only analyze",
272 "no-process-toast");
273 /* allow 'and_analyze' with 'analyze_only' */
274 }
275
276 /* Prohibit full and analyze_only options with parallel option */
277 if (vacopts.parallel_workers >= 0)
278 {
279 if (vacopts.mode == MODE_ANALYZE ||
280 vacopts.mode == MODE_ANALYZE_IN_STAGES)
281 pg_fatal("cannot use the \"%s\" option when performing only analyze",
282 "parallel");
283 if (vacopts.full)
284 pg_fatal("cannot use the \"%s\" option when performing full vacuum",
285 "parallel");
286 }
287
288 /* Prohibit --no-index-cleanup and --force-index-cleanup together */
289 if (vacopts.no_index_cleanup && vacopts.force_index_cleanup)
290 pg_fatal("cannot use the \"%s\" option with the \"%s\" option",
291 "no-index-cleanup", "force-index-cleanup");
292
293 /*
294 * buffer-usage-limit is not allowed with VACUUM FULL unless ANALYZE is
295 * included too.
296 */
297 if (vacopts.buffer_usage_limit && vacopts.full && !vacopts.and_analyze)
298 pg_fatal("cannot use the \"%s\" option with the \"%s\" option",
299 "buffer-usage-limit", "full");
300
301 /*
302 * Prohibit --missing-stats-only without --analyze-only or
303 * --analyze-in-stages.
304 */
305 if (vacopts.missing_stats_only && (vacopts.mode != MODE_ANALYZE &&
306 vacopts.mode != MODE_ANALYZE_IN_STAGES))
307 pg_fatal("cannot use the \"%s\" option without \"%s\" or \"%s\"",
308 "missing-stats-only", "analyze-only", "analyze-in-stages");
309
310 if (vacopts.dry_run && !vacopts.quiet)
311 pg_log_info("Executing in dry-run mode.\n"
312 "No commands will be sent to the server.");
313
314 ret = vacuuming_main(&cparams, dbname, maintenance_db, &vacopts,
315 &objects, tbl_count,
316 concurrentCons,
317 progname);
318 exit(ret);
319}
#define PG_TEXTDOMAIN(domain)
Definition: c.h:1212
void set_pglocale_pgservice(const char *argv0, const char *app)
Definition: exec.c:430
char * pg_strdup(const char *in)
Definition: fe_memutils.c:85
int getopt_long(int argc, char *const argv[], const char *optstring, const struct option *longopts, int *longindex)
Definition: getopt_long.c:60
#define no_argument
Definition: getopt_long.h:25
#define required_argument
Definition: getopt_long.h:26
static char * escape_quotes(const char *src)
Definition: initdb.c:406
void pg_logging_init(const char *argv0)
Definition: logging.c:83
#define pg_log_error(...)
Definition: logging.h:106
#define pg_log_error_hint(...)
Definition: logging.h:112
#define pg_log_info(...)
Definition: logging.h:124
bool option_parse_int(const char *optarg, const char *optname, int min_range, int max_range, int *result)
Definition: option_utils.c:50
void handle_help_version_opts(int argc, char *argv[], const char *fixed_progname, help_handler hlp)
Definition: option_utils.c:24
PGDLLIMPORT int optind
Definition: getopt.c:51
PGDLLIMPORT char * optarg
Definition: getopt.c:53
const char * get_progname(const char *argv0)
Definition: path.c:652
char * c
void simple_string_list_append(SimpleStringList *list, const char *val)
Definition: simple_list.c:63
char * dbname
Definition: streamutil.c:49
const char * pguser
Definition: connect_utils.h:31
char * pgport
Definition: pg_backup.h:87
char * pghost
Definition: pg_backup.h:88
enum trivalue prompt_password
Definition: connect_utils.h:32
bool force_index_cleanup
Definition: vacuuming.h:47
RunMode mode
Definition: vacuuming.h:34
bool no_index_cleanup
Definition: vacuuming.h:46
bits32 objfilter
Definition: vacuuming.h:35
int parallel_workers
Definition: vacuuming.h:44
bool disable_page_skipping
Definition: vacuuming.h:40
bool process_toast
Definition: vacuuming.h:50
char * buffer_usage_limit
Definition: vacuuming.h:52
bool missing_stats_only
Definition: vacuuming.h:53
static void help(const char *progname)
Definition: vacuumdb.c:346
static void check_objfilter(bits32 objfilter)
Definition: vacuumdb.c:325
int vacuuming_main(ConnParams *cparams, const char *dbname, const char *maintenance_db, vacuumingOptions *vacopts, SimpleStringList *objects, unsigned int tbl_count, int concurrentCons, const char *progname)
Definition: vacuuming.c:55
@ MODE_ANALYZE
Definition: vacuuming.h:23
@ MODE_ANALYZE_IN_STAGES
Definition: vacuuming.h:24
@ TRI_YES
Definition: vacuumlo.c:38
@ TRI_DEFAULT
Definition: vacuumlo.c:36
@ TRI_NO
Definition: vacuumlo.c:37

References vacuumingOptions::and_analyze, vacuumingOptions::buffer_usage_limit, check_objfilter(), dbname, vacuumingOptions::disable_page_skipping, vacuumingOptions::do_truncate, vacuumingOptions::dry_run, vacuumingOptions::echo, escape_quotes(), vacuumingOptions::force_index_cleanup, vacuumingOptions::freeze, vacuumingOptions::full, get_progname(), getopt_long(), handle_help_version_opts(), help(), vacuumingOptions::min_mxid_age, vacuumingOptions::min_xid_age, vacuumingOptions::missing_stats_only, vacuumingOptions::mode, MODE_ANALYZE, MODE_ANALYZE_IN_STAGES, no_argument, vacuumingOptions::no_index_cleanup, vacuumingOptions::objfilter, OBJFILTER_ALL_DBS, OBJFILTER_DATABASE, OBJFILTER_SCHEMA, OBJFILTER_SCHEMA_EXCLUDE, OBJFILTER_TABLE, optarg, optind, option_parse_int(), vacuumingOptions::parallel_workers, pg_fatal, pg_log_error, pg_log_error_hint, pg_log_info, pg_logging_init(), pg_strdup(), PG_TEXTDOMAIN, _connParams::pghost, _connParams::pgport, _connParams::pguser, vacuumingOptions::process_main, vacuumingOptions::process_toast, progname, _connParams::prompt_password, vacuumingOptions::quiet, required_argument, set_pglocale_pgservice(), simple_string_list_append(), vacuumingOptions::skip_locked, TRI_DEFAULT, TRI_NO, TRI_YES, vacuuming_main(), and vacuumingOptions::verbose.