static void setup(char *argv0, bool live_check) { char exec_path[MAXPGPATH]; /* full path to my executable */ /* * make sure the user has a clean environment, otherwise, we may confuse * libpq when we connect to one (or both) of the servers. */ check_pghost_envvar(); verify_directories(); /* no postmasters should be running */ if (!live_check && is_server_running(old_cluster.pgdata)) pg_log(PG_FATAL, "There seems to be a postmaster servicing the old cluster.\n" "Please shutdown that postmaster and try again.\n"); /* same goes for the new postmaster */ if (is_server_running(new_cluster.pgdata)) pg_log(PG_FATAL, "There seems to be a postmaster servicing the new cluster.\n" "Please shutdown that postmaster and try again.\n"); /* get path to pg_upgrade executable */ if (find_my_exec(argv0, exec_path) < 0) pg_log(PG_FATAL, "Could not get pathname to pg_upgrade: %s\n", getErrorText(errno)); /* Trim off program name and keep just path */ *last_dir_separator(exec_path) = '\0'; canonicalize_path(exec_path); os_info.exec_path = pg_strdup(exec_path); }
static char * find_other_exec_or_die(const char *argv0, const char *target, const char *versionstr) { int ret; char *found_path; found_path = pg_malloc(MAXPGPATH); if ((ret = find_other_exec(argv0, target, versionstr, found_path)) < 0) { char full_path[MAXPGPATH]; if (find_my_exec(argv0, full_path) < 0) strlcpy(full_path, progname, sizeof(full_path)); if (ret == -1) write_stderr(_("The program \"%s\" is needed by %s " "but was not found in the\n" "same directory as \"%s\".\n" "Check your installation.\n"), target, progname, full_path); else write_stderr(_("The program \"%s\" was found by \"%s\"\n" "but was not the same version as %s.\n" "Check your installation.\n"), target, full_path, progname); exit(1); } return found_path; }
/* * Load .psqlrc file, if found. */ static void process_psqlrc(char *argv0) { char home[MAXPGPATH]; char rc_file[MAXPGPATH]; char my_exec_path[MAXPGPATH]; char etc_path[MAXPGPATH]; char *envrc; find_my_exec(argv0, my_exec_path); get_etc_path(my_exec_path, etc_path); snprintf(rc_file, MAXPGPATH, "%s/%s", etc_path, SYSPSQLRC); process_psqlrc_file(rc_file); envrc = getenv("PSQLRC"); if (envrc != NULL && strlen(envrc) > 0) { expand_tilde(&envrc); process_psqlrc_file(envrc); } else if (get_home_path(home)) { snprintf(rc_file, MAXPGPATH, "%s/%s", home, PSQLRC); process_psqlrc_file(rc_file); } }
/* * Find another program in our binary's directory, * then make sure it is the proper version. */ int find_other_exec(const char *argv0, const char *target, const char *versionstr, char *retpath) { char cmd[MAXPGPATH]; char line[100]; if (find_my_exec(argv0, retpath) < 0) return -1; /* Trim off program name and keep just directory */ *last_dir_separator(retpath) = '\0'; canonicalize_path(retpath); /* Now append the other program's name */ snprintf(retpath + strlen(retpath), MAXPGPATH - strlen(retpath), "/%s%s", target, EXE); if (validate_exec(retpath) != 0) return -1; snprintf(cmd, sizeof(cmd), "\"%s\" -V 2>%s", retpath, DEVNULL); if (!pipe_read_line(cmd, line, sizeof(line))) return -1; if (strcmp(line, versionstr) != 0) return -2; return 0; }
/* * Load .psqlrc file, if found. */ static void process_psqlrc(char *argv0) { char home[MAXPGPATH]; char rc_file[MAXPGPATH]; char my_exec_path[MAXPGPATH]; char etc_path[MAXPGPATH]; char *envrc = getenv("PSQLRC"); if (find_my_exec(argv0, my_exec_path) < 0) { fprintf(stderr, _("%s: could not find own program executable\n"), argv0); exit(EXIT_FAILURE); } get_etc_path(my_exec_path, etc_path); snprintf(rc_file, MAXPGPATH, "%s/%s", etc_path, SYSPSQLRC); process_psqlrc_file(rc_file); if (envrc != NULL && strlen(envrc) > 0) { /* might need to free() this */ char *envrc_alloc = pstrdup(envrc); expand_tilde(&envrc_alloc); process_psqlrc_file(envrc_alloc); } else if (get_home_path(home)) { snprintf(rc_file, MAXPGPATH, "%s/%s", home, PSQLRC); process_psqlrc_file(rc_file); } }
/* * load_config() * * Set default options and overwrite with values from provided configuration * file. * * Returns true if a configuration file could be parsed, otherwise false. * * Any configuration options changed in this function must also be changed in * reload_config() */ bool load_config(const char *config_file, t_configuration_options *options, char *argv0) { struct stat config; /* Sanity checks */ /* * If a configuration file was provided, check it exists, otherwise * emit an error and terminate */ if (config_file[0]) { strncpy(config_file_path, config_file, MAXPGPATH); canonicalize_path(config_file_path); if (stat(config_file_path, &config) != 0) { log_err(_("provided configuration file '%s' not found: %s\n"), config_file, strerror(errno) ); exit(ERR_BAD_CONFIG); } config_file_provided = true; } /* * If no configuration file was provided, attempt to find a default file */ if (config_file_provided == false) { char my_exec_path[MAXPGPATH]; char etc_path[MAXPGPATH]; /* First check if one is in the default sysconfdir */ if (find_my_exec(argv0, my_exec_path) < 0) { fprintf(stderr, _("%s: could not find own program executable\n"), argv0); exit(EXIT_FAILURE); } get_etc_path(my_exec_path, etc_path); snprintf(config_file_path, MAXPGPATH, "%s/repmgr.conf", etc_path); log_debug(_("Looking for configuration file in %s\n"), etc_path); if (stat(config_file_path, &config) != 0) { /* Not found - default to ./repmgr.conf */ strncpy(config_file_path, DEFAULT_CONFIG_FILE, MAXPGPATH); canonicalize_path(config_file_path); log_debug(_("Looking for configuration file in %s\n"), config_file_path); } } return parse_config(options); }
int main(int argc, char **argv) { int i; int j; int ret; set_pglocale_pgservice(argv[0], PG_TEXTDOMAIN("pg_config")); progname = get_progname(argv[0]); /* check for --help */ for (i = 1; i < argc; i++) { if (strcmp(argv[i], "--help") == 0 || strcmp(argv[i], "-?") == 0) { help(); exit(0); } } ret = find_my_exec(argv[0], mypath); if (ret) { fprintf(stderr, _("%s: could not find own program executable\n"), progname); exit(1); } /* no arguments -> print everything */ if (argc < 2) { show_all(); exit(0); } for (i = 1; i < argc; i++) { for (j = 0; info_items[j].switchname != NULL; j++) { if (strcmp(argv[i], info_items[j].switchname) == 0) { (*info_items[j].show_func) (false); break; } } if (info_items[j].switchname == NULL) { fprintf(stderr, _("%s: invalid argument: %s\n"), progname, argv[i]); advice(); exit(1); } } return 0; }
/* * set_pglocale_pgservice * * Set application-specific locale and service directory * * This function takes the value of argv[0] rather than a full path. * * (You may be wondering why this is in exec.c. It requires this module's * services and doesn't introduce any new dependencies, so this seems as * good as anyplace.) */ void set_pglocale_pgservice(const char *argv0, const char *app) { char path[MAXPGPATH]; char my_exec_path[MAXPGPATH]; char env_path[MAXPGPATH + sizeof("PGSYSCONFDIR=")]; /* longer than * PGLOCALEDIR */ char *dup_path; /* don't set LC_ALL in the backend */ if (strcmp(app, PG_TEXTDOMAIN("postgres")) != 0) { setlocale(LC_ALL, ""); /* * One could make a case for reproducing here PostmasterMain()'s test * for whether the process is multithreaded. Unlike the postmaster, * no frontend program calls sigprocmask() or otherwise provides for * mutual exclusion between signal handlers. While frontends using * fork(), if multithreaded, are formally exposed to undefined * behavior, we have not witnessed a concrete bug. Therefore, * complaining about multithreading here may be mere pedantry. */ } if (find_my_exec(argv0, my_exec_path) < 0) return; #ifdef ENABLE_NLS get_locale_path(my_exec_path, path); bindtextdomain(app, path); textdomain(app); if (getenv("PGLOCALEDIR") == NULL) { /* set for libpq to use */ snprintf(env_path, sizeof(env_path), "PGLOCALEDIR=%s", path); canonicalize_path(env_path + 12); dup_path = strdup(env_path); if (dup_path) putenv(dup_path); } #endif if (getenv("PGSYSCONFDIR") == NULL) { get_etc_path(my_exec_path, path); /* set for libpq to use */ snprintf(env_path, sizeof(env_path), "PGSYSCONFDIR=%s", path); canonicalize_path(env_path + 13); dup_path = strdup(env_path); if (dup_path) putenv(dup_path); } }
static void setup(char *argv0, bool *live_check) { char exec_path[MAXPGPATH]; /* full path to my executable */ /* * make sure the user has a clean environment, otherwise, we may confuse * libpq when we connect to one (or both) of the servers. */ check_pghost_envvar(); verify_directories(); /* no postmasters should be running, except for a live check */ if (pid_lock_file_exists(old_cluster.pgdata)) { /* * If we have a postmaster.pid file, try to start the server. If it * starts, the pid file was stale, so stop the server. If it doesn't * start, assume the server is running. If the pid file is left over * from a server crash, this also allows any committed transactions * stored in the WAL to be replayed so they are not lost, because WAL * files are not transferred from old to new servers. We later check * for a clean shutdown. */ if (start_postmaster(&old_cluster, false)) stop_postmaster(false); else { if (!user_opts.check) pg_fatal("There seems to be a postmaster servicing the old cluster.\n" "Please shutdown that postmaster and try again.\n"); else *live_check = true; } } /* same goes for the new postmaster */ if (pid_lock_file_exists(new_cluster.pgdata)) { if (start_postmaster(&new_cluster, false)) stop_postmaster(false); else pg_fatal("There seems to be a postmaster servicing the new cluster.\n" "Please shutdown that postmaster and try again.\n"); } /* get path to pg_upgrade executable */ if (find_my_exec(argv0, exec_path) < 0) pg_fatal("%s: could not find own program executable\n", argv0); /* Trim off program name and keep just path */ *last_dir_separator(exec_path) = '\0'; canonicalize_path(exec_path); os_info.exec_path = pg_strdup(exec_path); }
/* * Load .psqlrc file, if found. */ static void process_psqlrc(char *argv0) { char home[MAX_PG_PATH]; char rc_file[MAX_PG_PATH]; char my_exec_path[MAX_PG_PATH]; char etc_path[MAX_PG_PATH]; find_my_exec(argv0, my_exec_path); get_etc_path(my_exec_path, etc_path); snprintf(rc_file, MAX_PG_PATH, "%s/%s", etc_path, SYSPSQLRC); process_psqlrc_file(rc_file); if (get_home_path(home)) { snprintf(rc_file, MAX_PG_PATH, "%s/%s", home, PSQLRC); process_psqlrc_file(rc_file); } }
/* * Find another program in our binary's directory, * then make sure it is the proper version. */ int find_other_exec(const char *argv0, const char *target, const char *versionstr, char *retpath) { char cmd[MAXPGPATH]; char line[100]; if (find_my_exec(argv0, retpath) < 0) return -1; /* Trim off program name and keep just directory */ *last_dir_separator(retpath) = '\0'; canonicalize_path(retpath); /* Now append the other program's name */ snprintf(retpath + strlen(retpath), MAXPGPATH - strlen(retpath), "/%s%s", target, EXE); if (validate_exec(retpath) != 0) return -1; /* * In PostgreSQL, the version check is always performed. In GPDB, this * is also used to find scripts that don't necessarily have the same * version output (in particular, pg_regress uses this to find gpdiff.pl) */ if (versionstr) { snprintf(cmd, sizeof(cmd), "\"%s\" -V 2>%s", retpath, DEVNULL); if (!pipe_read_line(cmd, line, sizeof(line))) return -1; if (strcmp(line, versionstr) != 0) return -2; } return 0; }
/* * set_pglocale_pgservice * * Set application-specific locale and service directory * * This function takes an argv[0] rather than a full path. */ void set_pglocale_pgservice(const char *argv0, const char *app) { char path[MAXPGPATH]; char my_exec_path[MAXPGPATH]; char env_path[MAXPGPATH + sizeof("PGSYSCONFDIR=")]; /* longer than * PGLOCALEDIR */ /* don't set LC_ALL in the backend */ if (strcmp(app, "postgres") != 0) setlocale(LC_ALL, ""); if (find_my_exec(argv0, my_exec_path) < 0) return; #ifdef ENABLE_NLS get_locale_path(my_exec_path, path); bindtextdomain(app, path); textdomain(app); if (getenv("PGLOCALEDIR") == NULL) { /* set for libpq to use */ snprintf(env_path, sizeof(env_path), "PGLOCALEDIR=%s", path); canonicalize_path(env_path + 12); putenv(strdup(env_path)); } #endif if (getenv("PGSYSCONFDIR") == NULL) { get_etc_path(my_exec_path, path); /* set for libpq to use */ snprintf(env_path, sizeof(env_path), "PGSYSCONFDIR=%s", path); canonicalize_path(env_path + 13); putenv(strdup(env_path)); } }
/* * load_config() * * Set default options and overwrite with values from provided configuration * file. * * Returns true if a configuration file could be parsed, otherwise false. * * Any *repmgrd-specific* configuration options added/changed in this function must also be * added/changed in reload_config() * * NOTE: this function is called before the logger is set up, so we need * to handle the verbose option ourselves; also the default log level is NOTICE, * so we can't use DEBUG. */ bool load_config(const char *config_file, bool verbose, t_configuration_options *options, char *argv0) { struct stat stat_config; /* * If a configuration file was provided, check it exists, otherwise * emit an error and terminate. We assume that if a user explicitly * provides a configuration file, they'll want to make sure it's * used and not fall back to any of the defaults. */ if (config_file[0]) { strncpy(config_file_path, config_file, MAXPGPATH); canonicalize_path(config_file_path); if (stat(config_file_path, &stat_config) != 0) { log_err(_("provided configuration file \"%s\" not found: %s\n"), config_file, strerror(errno) ); exit(ERR_BAD_CONFIG); } if (verbose == true) { log_notice(_("using configuration file \"%s\"\n"), config_file); } config_file_provided = true; config_file_found = true; } /* * If no configuration file was provided, attempt to find a default file * in this order: * - current directory * - /etc/repmgr.conf * - default sysconfdir * * here we just check for the existence of the file; parse_config() * will handle read errors etc. */ if (config_file_provided == false) { char my_exec_path[MAXPGPATH]; char sysconf_etc_path[MAXPGPATH]; /* 1. "./repmgr.conf" */ if (verbose == true) { log_notice(_("looking for configuration file in current directory\n")); } snprintf(config_file_path, MAXPGPATH, "./%s", CONFIG_FILE_NAME); canonicalize_path(config_file_path); if (stat(config_file_path, &stat_config) == 0) { config_file_found = true; goto end_search; } /* 2. "/etc/repmgr.conf" */ if (verbose == true) { log_notice(_("looking for configuration file in /etc\n")); } snprintf(config_file_path, MAXPGPATH, "/etc/%s", CONFIG_FILE_NAME); if (stat(config_file_path, &stat_config) == 0) { config_file_found = true; goto end_search; } /* 3. default sysconfdir */ if (find_my_exec(argv0, my_exec_path) < 0) { fprintf(stderr, _("%s: could not find own program executable\n"), argv0); exit(EXIT_FAILURE); } get_etc_path(my_exec_path, sysconf_etc_path); if (verbose == true) { log_notice(_("looking for configuration file in %s\n"), sysconf_etc_path); } snprintf(config_file_path, MAXPGPATH, "%s/%s", sysconf_etc_path, CONFIG_FILE_NAME); if (stat(config_file_path, &stat_config) == 0) { config_file_found = true; goto end_search; } end_search: if (config_file_found == true) { if (verbose == true) { log_notice(_("configuration file found at: %s\n"), config_file_path); } } else { if (verbose == true) { log_notice(_("no configuration file provided or found\n")); } } } return parse_config(options); }
int main(int argc, char **argv) { int i; int ret; char mypath[MAXPGPATH]; char otherpath[MAXPGPATH]; set_pglocale_pgservice(argv[0], "pg_config"); progname = get_progname(argv[0]); if (argc < 2) { fprintf(stderr, _("%s: argument required\n"), progname); advice(); exit(1); } for (i = 1; i < argc; i++) { if (strcmp(argv[i], "--bindir") == 0 || strcmp(argv[i], "--includedir") == 0 || strcmp(argv[i], "--includedir-server") == 0 || strcmp(argv[i], "--libdir") == 0 || strcmp(argv[i], "--pkglibdir") == 0 || strcmp(argv[i], "--pgxs") == 0 || strcmp(argv[i], "--configure") == 0) { /* come back to these later */ continue; } if (strcmp(argv[i], "--version") == 0) { printf("PostgreSQL " PG_VERSION "\n"); exit(0); } if (strcmp(argv[i], "--help") == 0 || strcmp(argv[i], "-?") == 0) { help(); exit(0); } fprintf(stderr, _("%s: invalid argument: %s\n"), progname, argv[i]); advice(); exit(1); } ret = find_my_exec(argv[0], mypath); if (ret) { fprintf(stderr, _("%s: could not find own executable\n"), progname); exit(1); } for (i = 1; i < argc; i++) { if (strcmp(argv[i], "--configure") == 0) { /* the VAL_CONFIGURE macro must be defined by the Makefile */ printf("%s\n", VAL_CONFIGURE); continue; } if (strcmp(argv[i], "--bindir") == 0) { /* assume we are located in the bindir */ char *lastsep; strcpy(otherpath, mypath); lastsep = strrchr(otherpath, '/'); if (lastsep) *lastsep = '\0'; } else if (strcmp(argv[i], "--includedir") == 0) get_include_path(mypath, otherpath); else if (strcmp(argv[i], "--includedir-server") == 0) get_includeserver_path(mypath, otherpath); else if (strcmp(argv[i], "--libdir") == 0) get_lib_path(mypath, otherpath); else if (strcmp(argv[i], "--pkglibdir") == 0) get_pkglib_path(mypath, otherpath); else if (strcmp(argv[i], "--pgxs") == 0) { get_pkglib_path(mypath, otherpath); strncat(otherpath, "/pgxs/src/makefiles/pgxs.mk", MAXPGPATH - 1); } printf("%s\n", otherpath); } return 0; }
static void do_start(void) { pgpid_t pid; pgpid_t old_pid = 0; int exitcode; if (ctl_command != RESTART_COMMAND) { old_pid = get_pgpid(); if (old_pid != 0) write_stderr(_("%s: another server might be running; " "trying to start server anyway\n"), progname); } read_post_opts(); /* No -D or -D already added during server start */ if (ctl_command == RESTART_COMMAND || pgdata_opt == NULL) pgdata_opt = ""; if (postgres_path == NULL) { char *postmaster_path; int ret; postmaster_path = pg_malloc(MAXPGPATH); if ((ret = find_other_exec(argv0, "postgres", PM_VERSIONSTR, postmaster_path)) < 0) { char full_path[MAXPGPATH]; if (find_my_exec(argv0, full_path) < 0) strlcpy(full_path, progname, sizeof(full_path)); if (ret == -1) write_stderr(_("The program \"postgres\" is needed by %s " "but was not found in the\n" "same directory as \"%s\".\n" "Check your installation.\n"), progname, full_path); else write_stderr(_("The program \"postgres\" was found by \"%s\"\n" "but was not the same version as %s.\n" "Check your installation.\n"), full_path, progname); exit(1); } postgres_path = postmaster_path; } #if defined(HAVE_GETRLIMIT) && defined(RLIMIT_CORE) if (allow_core_files) unlimit_core_size(); #endif exitcode = start_postmaster(); if (exitcode != 0) { write_stderr(_("%s: could not start server: exit code was %d\n"), progname, exitcode); exit(1); } if (old_pid != 0) { pg_usleep(1000000); pid = get_pgpid(); if (pid == old_pid) { write_stderr(_("%s: could not start server\n" "Examine the log output.\n"), progname); exit(1); } } if (do_wait) { print_msg(_("waiting for server to start...")); if (test_postmaster_connection(false) == false) { printf(_("could not start server\n")); exit(1); } else { print_msg(_(" done\n")); print_msg(_("server started\n")); } } else print_msg(_("server starting\n")); }
int main(int argc, char **argv) { ConfigData *configdata; size_t configdata_len; char my_exec_path[MAXPGPATH]; int i; int j; set_pglocale_pgservice(argv[0], PG_TEXTDOMAIN("pg_config")); progname = get_progname(argv[0]); /* check for --help */ for (i = 1; i < argc; i++) { if (strcmp(argv[i], "--help") == 0 || strcmp(argv[i], "-?") == 0) { help(); exit(0); } } if (find_my_exec(argv[0], my_exec_path) < 0) { fprintf(stderr, _("%s: could not find own program executable\n"), progname); exit(1); } configdata = get_configdata(my_exec_path, &configdata_len); /* no arguments -> print everything */ if (argc < 2) { for (i = 0; i < configdata_len; i++) printf("%s = %s\n", configdata[i].name, configdata[i].setting); exit(0); } /* otherwise print requested items */ for (i = 1; i < argc; i++) { for (j = 0; info_items[j].switchname != NULL; j++) { if (strcmp(argv[i], info_items[j].switchname) == 0) { show_item(info_items[j].configname, configdata, configdata_len); break; } } if (info_items[j].switchname == NULL) { fprintf(stderr, _("%s: invalid argument: %s\n"), progname, argv[i]); advice(); exit(1); } } return 0; }
static char * pgwin32_CommandLine(bool registration) { static char cmdLine[MAXPGPATH]; int ret; #ifdef __CYGWIN__ char buf[MAXPGPATH]; #endif if (registration) { ret = find_my_exec(argv0, cmdLine); if (ret != 0) { write_stderr(_("%s: could not find own program executable\n"), progname); exit(1); } } else { ret = find_other_exec(argv0, "postgres", PG_BACKEND_VERSIONSTR, cmdLine); if (ret != 0) { write_stderr(_("%s: could not find postgres program executable\n"), progname); exit(1); } } #ifdef __CYGWIN__ /* need to convert to windows path */ #if CYGWIN_VERSION_DLL_MAJOR >= 1007 cygwin_conv_path(CCP_POSIX_TO_WIN_A, cmdLine, buf, sizeof(buf)); #else cygwin_conv_to_full_win32_path(cmdLine, buf); #endif strcpy(cmdLine, buf); #endif if (registration) { if (pg_strcasecmp(cmdLine + strlen(cmdLine) - 4, ".exe")) { /* If commandline does not end in .exe, append it */ strcat(cmdLine, ".exe"); } strcat(cmdLine, " runservice -N \""); strcat(cmdLine, register_servicename); strcat(cmdLine, "\""); } if (pg_data) { strcat(cmdLine, " -D \""); strcat(cmdLine, pg_data); strcat(cmdLine, "\""); } if (registration && do_wait) strcat(cmdLine, " -w"); if (registration && wait_seconds != DEFAULT_WAIT) /* concatenate */ sprintf(cmdLine + strlen(cmdLine), " -t %d", wait_seconds); if (post_opts) { strcat(cmdLine, " "); if (registration) strcat(cmdLine, " -o \""); strcat(cmdLine, post_opts); if (registration) strcat(cmdLine, "\""); } return cmdLine; }
int main(int argc, char *argv[]) { /* * options with no short version return a low integer, the rest return * their short version value */ static struct option long_options[] = { {"pgdata", required_argument, NULL, 'D'}, {"help", no_argument, NULL, '?'}, {"version", no_argument, NULL, 'V'}, {"debug", no_argument, NULL, 'd'}, {"show", no_argument, NULL, 's'}, {"noclean", no_argument, NULL, 'n'}, {NULL, 0, NULL, 0} }; int c, ret; int option_index; char *effective_user; char bin_dir[MAXPGPATH]; char *pg_data_native; bool node_type_specified = false; progname = get_progname(argv[0]); set_pglocale_pgservice(argv[0], PG_TEXTDOMAIN("initgtm")); if (argc > 1) { if (strcmp(argv[1], "--help") == 0 || strcmp(argv[1], "-?") == 0) { usage(progname); exit(0); } if (strcmp(argv[1], "--version") == 0 || strcmp(argv[1], "-V") == 0) { puts("initgtm (Postgres-XL) " PGXC_VERSION); exit(0); } } /* process command-line options */ while ((c = getopt_long(argc, argv, "dD:nsZ:", long_options, &option_index)) != -1) { switch (c) { case 'D': pg_data = xstrdup(optarg); break; case 'd': debug = true; printf(_("Running in debug mode.\n")); break; case 'n': noclean = true; printf(_("Running in noclean mode. Mistakes will not be cleaned up.\n")); break; case 's': show_setting = true; break; case 'Z': if (strcmp(xstrdup(optarg), "gtm") == 0) is_gtm = true; else if (strcmp(xstrdup(optarg), "gtm_proxy") == 0) is_gtm = false; else { fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } node_type_specified = true; break; default: /* getopt_long already emitted a complaint */ fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } } /* Non-option argument specifies data directory */ if (optind < argc) { pg_data = xstrdup(argv[optind]); optind++; } if (optind < argc) { fprintf(stderr, _("%s: too many command-line arguments (first is \"%s\")\n"), progname, argv[optind + 1]); fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } /* Check on definition of GTM data folder */ if (strlen(pg_data) == 0) { fprintf(stderr, _("%s: no data directory specified\n" "You must identify the directory where the data for this GTM system\n" "will reside. Do this with either the invocation option -D or the\n" "environment variable PGDATA.\n"), progname); exit(1); } if (!node_type_specified) { fprintf(stderr, _("%s: no node type specified\n" "You must identify the node type chosen for initialization.\n" "Do this with the invocation option -Z by choosing \"gtm\" or" "\"gtm_proxy\"\n"), progname); exit(1); } pg_data_native = pg_data; canonicalize_path(pg_data); #ifdef WIN32 /* * Before we execute another program, make sure that we are running with a * restricted token. If not, re-execute ourselves with one. */ if ((restrict_env = getenv("PG_RESTRICT_EXEC")) == NULL || strcmp(restrict_env, "1") != 0) { PROCESS_INFORMATION pi; char *cmdline; ZeroMemory(&pi, sizeof(pi)); cmdline = xstrdup(GetCommandLine()); putenv("PG_RESTRICT_EXEC=1"); if (!CreateRestrictedProcess(cmdline, &pi)) { fprintf(stderr, "Failed to re-exec with restricted token: %lu.\n", GetLastError()); } else { /* * Successfully re-execed. Now wait for child process to capture * exitcode. */ DWORD x; CloseHandle(pi.hThread); WaitForSingleObject(pi.hProcess, INFINITE); if (!GetExitCodeProcess(pi.hProcess, &x)) { fprintf(stderr, "Failed to get exit code from subprocess: %lu\n", GetLastError()); exit(1); } exit(x); } } #endif /* Like for initdb, check if a valid version of Postgres is running */ if ((ret = find_other_exec(argv[0], "postgres", PG_BACKEND_VERSIONSTR, backend_exec)) < 0) { char full_path[MAXPGPATH]; if (find_my_exec(argv[0], full_path) < 0) strlcpy(full_path, progname, sizeof(full_path)); if (ret == -1) fprintf(stderr, _("The program \"postgres\" is needed by %s " "but was not found in the\n" "same directory as \"%s\".\n" "Check your installation.\n"), progname, full_path); else fprintf(stderr, _("The program \"postgres\" was found by \"%s\"\n" "but was not the same version as %s.\n" "Check your installation.\n"), full_path, progname); exit(1); } /* store binary directory */ strcpy(bin_path, backend_exec); *last_dir_separator(bin_path) = '\0'; canonicalize_path(bin_path); if (!share_path) { share_path = pg_malloc(MAXPGPATH); get_share_path(backend_exec, share_path); } else if (!is_absolute_path(share_path)) { fprintf(stderr, _("%s: input file location must be an absolute path\n"), progname); exit(1); } canonicalize_path(share_path); effective_user = get_id(); /* Take into account GTM and GTM-proxy cases */ if (is_gtm) set_input(&conf_file, "gtm.conf.sample"); else set_input(&conf_file, "gtm_proxy.conf.sample"); if (show_setting || debug) { fprintf(stderr, "VERSION=%s\n" "GTMDATA=%s\nshare_path=%s\nGTMPATH=%s\n" "GTM_CONF_SAMPLE=%s\n", PGXC_VERSION, pg_data, share_path, bin_path, conf_file); if (show_setting) exit(0); } check_input(conf_file); printf(_("The files belonging to this GTM system will be owned " "by user \"%s\".\n" "This user must also own the server process.\n\n"), effective_user); printf("\n"); umask(S_IRWXG | S_IRWXO); /* * now we are starting to do real work, trap signals so we can clean up */ /* some of these are not valid on Windows */ #ifdef SIGHUP pqsignal(SIGHUP, trapsig); #endif #ifdef SIGINT pqsignal(SIGINT, trapsig); #endif #ifdef SIGQUIT pqsignal(SIGQUIT, trapsig); #endif #ifdef SIGTERM pqsignal(SIGTERM, trapsig); #endif /* Ignore SIGPIPE when writing to backend, so we can clean up */ #ifdef SIGPIPE pqsignal(SIGPIPE, SIG_IGN); #endif switch (pg_check_dir(pg_data)) { case 0: /* PGDATA not there, must create it */ printf(_("creating directory %s ... "), pg_data); fflush(stdout); if (!mkdatadir(NULL)) exit_nicely(); else check_ok(); made_new_pgdata = true; break; case 1: /* Present but empty, fix permissions and use it */ printf(_("fixing permissions on existing directory %s ... "), pg_data); fflush(stdout); if (chmod(pg_data, S_IRWXU) != 0) { fprintf(stderr, _("%s: could not change permissions of directory \"%s\": %s\n"), progname, pg_data, strerror(errno)); exit_nicely(); } else check_ok(); found_existing_pgdata = true; break; case 2: /* Present and not empty */ fprintf(stderr, _("%s: directory \"%s\" exists but is not empty\n"), progname, pg_data); fprintf(stderr, _("If you want to create a new GTM system, either remove or empty\n" "the directory \"%s\" or run %s\n" "with an argument other than \"%s\".\n"), pg_data, progname, pg_data); exit(1); /* no further message needed */ default: /* Trouble accessing directory */ fprintf(stderr, _("%s: could not access directory \"%s\": %s\n"), progname, pg_data, strerror(errno)); exit_nicely(); } /* Select suitable configuration settings */ set_null_conf(); /* Now create all the text config files */ setup_config(); /* Get directory specification used to start this executable */ strcpy(bin_dir, argv[0]); get_parent_directory(bin_dir); if (is_gtm) printf(_("\nSuccess. You can now start the GTM server using:\n\n" " %s%s%sgtm%s -D %s%s%s\n" "or\n" " %s%s%sgtm_ctl%s -Z gtm -D %s%s%s -l logfile start\n\n"), QUOTE_PATH, bin_dir, (strlen(bin_dir) > 0) ? DIR_SEP : "", QUOTE_PATH, QUOTE_PATH, pg_data_native, QUOTE_PATH, QUOTE_PATH, bin_dir, (strlen(bin_dir) > 0) ? DIR_SEP : "", QUOTE_PATH, QUOTE_PATH, pg_data_native, QUOTE_PATH); else printf(_("\nSuccess. You can now start the GTM proxy server using:\n\n" " %s%s%sgtm_proxy%s -D %s%s%s\n" "or\n" " %s%s%sgtm_ctl%s -Z gtm_proxy -D %s%s%s -l logfile start\n\n"), QUOTE_PATH, bin_dir, (strlen(bin_dir) > 0) ? DIR_SEP : "", QUOTE_PATH, QUOTE_PATH, pg_data_native, QUOTE_PATH, QUOTE_PATH, bin_dir, (strlen(bin_dir) > 0) ? DIR_SEP : "", QUOTE_PATH, QUOTE_PATH, pg_data_native, QUOTE_PATH); return 0; }
int main(int argc, char *argv[]) { char *pghost = NULL; char *pgport = NULL; char *pguser = NULL; char *pgdb = NULL; enum trivalue prompt_password = TRI_DEFAULT; bool data_only = false; bool globals_only = false; bool schema_only = false; static int gp_migrator = 0; bool gp_syntax = false; bool no_gp_syntax = false; PGconn *conn; int encoding; const char *std_strings; int c, ret; static struct option long_options[] = { {"data-only", no_argument, NULL, 'a'}, {"clean", no_argument, NULL, 'c'}, {"inserts", no_argument, NULL, 'd'}, {"attribute-inserts", no_argument, NULL, 'D'}, {"column-inserts", no_argument, NULL, 'D'}, {"file", required_argument, NULL, 'f'}, {"globals-only", no_argument, NULL, 'g'}, {"host", required_argument, NULL, 'h'}, {"ignore-version", no_argument, NULL, 'i'}, {"database", required_argument, NULL, 'l'}, {"oids", no_argument, NULL, 'o'}, {"no-owner", no_argument, NULL, 'O'}, {"port", required_argument, NULL, 'p'}, {"schema-only", no_argument, NULL, 's'}, {"superuser", required_argument, NULL, 'S'}, {"username", required_argument, NULL, 'U'}, {"verbose", no_argument, NULL, 'v'}, {"no-password", no_argument, NULL, 'w'}, {"password", no_argument, NULL, 'W'}, {"no-privileges", no_argument, NULL, 'x'}, {"no-acl", no_argument, NULL, 'x'}, {"resource-queues", no_argument, NULL, 'r'}, {"filespaces", no_argument, NULL, 'F'}, /* * the following options don't have an equivalent short option letter */ {"disable-dollar-quoting", no_argument, &disable_dollar_quoting, 1}, {"disable-triggers", no_argument, &disable_triggers, 1}, {"use-set-session-authorization", no_argument, &use_setsessauth, 1}, /* START MPP ADDITION */ {"gp-syntax", no_argument, NULL, 1}, {"no-gp-syntax", no_argument, NULL, 2}, {"gp-migrator", no_argument, &gp_migrator, 1}, /* END MPP ADDITION */ {NULL, 0, NULL, 0} }; int optindex; set_pglocale_pgservice(argv[0], "pg_dump"); progname = get_progname(argv[0]); if (argc > 1) { if (strcmp(argv[1], "--help") == 0 || strcmp(argv[1], "-?") == 0) { help(); exit(0); } if (strcmp(argv[1], "--version") == 0 || strcmp(argv[1], "-V") == 0) { puts("pg_dumpall (PostgreSQL) " PG_VERSION); exit(0); } } if ((ret = find_other_exec(argv[0], "pg_dump", PGDUMP_VERSIONSTR, pg_dump_bin)) < 0) { char full_path[MAXPGPATH]; if (find_my_exec(argv[0], full_path) < 0) strlcpy(full_path, progname, sizeof(full_path)); if (ret == -1) fprintf(stderr, _("The program \"pg_dump\" is needed by %s " "but was not found in the\n" "same directory as \"%s\".\n" "Check your installation.\n"), progname, full_path); else fprintf(stderr, _("The program \"pg_dump\" was found by \"%s\"\n" "but was not the same version as %s.\n" "Check your installation.\n"), full_path, progname); exit(1); } pgdumpopts = createPQExpBuffer(); while ((c = getopt_long(argc, argv, "acdDf:Fgh:il:oOp:rsS:U:vwWxX:", long_options, &optindex)) != -1) { switch (c) { case 'a': data_only = true; appendPQExpBuffer(pgdumpopts, " -a"); break; case 'c': output_clean = true; break; case 'd': case 'D': appendPQExpBuffer(pgdumpopts, " -%c", c); break; case 'f': filename = optarg; #ifndef WIN32 appendPQExpBuffer(pgdumpopts, " -f '%s'", filename); #else appendPQExpBuffer(pgdumpopts, " -f \"%s\"", filename); #endif break; case 'g': globals_only = true; break; case 'h': pghost = optarg; #ifndef WIN32 appendPQExpBuffer(pgdumpopts, " -h '%s'", pghost); #else appendPQExpBuffer(pgdumpopts, " -h \"%s\"", pghost); #endif break; case 'i': /* ignored, deprecated option */ break; case 'l': pgdb = optarg; break; case 'o': appendPQExpBuffer(pgdumpopts, " -o"); break; case 'O': appendPQExpBuffer(pgdumpopts, " -O"); break; case 'p': pgport = optarg; #ifndef WIN32 appendPQExpBuffer(pgdumpopts, " -p '%s'", pgport); #else appendPQExpBuffer(pgdumpopts, " -p \"%s\"", pgport); #endif break; case 'r': resource_queues = true; break; case 'F': filespaces = true; break; case 's': schema_only = true; appendPQExpBuffer(pgdumpopts, " -s"); break; case 'S': #ifndef WIN32 appendPQExpBuffer(pgdumpopts, " -S '%s'", optarg); #else appendPQExpBuffer(pgdumpopts, " -S \"%s\"", optarg); #endif break; case 'U': pguser = optarg; #ifndef WIN32 appendPQExpBuffer(pgdumpopts, " -U '%s'", pguser); #else appendPQExpBuffer(pgdumpopts, " -U \"%s\"", pguser); #endif break; case 'v': verbose = true; appendPQExpBuffer(pgdumpopts, " -v"); break; case 'w': prompt_password = TRI_NO; appendPQExpBuffer(pgdumpopts, " -w"); break; case 'W': prompt_password = TRI_YES; appendPQExpBuffer(pgdumpopts, " -W"); break; case 'x': skip_acls = true; appendPQExpBuffer(pgdumpopts, " -x"); break; case 'X': /* -X is a deprecated alternative to long options */ if (strcmp(optarg, "disable-dollar-quoting") == 0) appendPQExpBuffer(pgdumpopts, " --disable-dollar-quoting"); else if (strcmp(optarg, "disable-triggers") == 0) appendPQExpBuffer(pgdumpopts, " --disable-triggers"); else if (strcmp(optarg, "use-set-session-authorization") == 0) /* no-op, still allowed for compatibility */ ; else { fprintf(stderr, _("%s: invalid -X option -- %s\n"), progname, optarg); fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } break; case 0: break; /* START MPP ADDITION */ case 1: /* gp-format */ appendPQExpBuffer(pgdumpopts, " --gp-syntax"); gp_syntax = true; resource_queues = true; /* -r is implied by --gp-syntax */ break; case 2: /* no-gp-format */ appendPQExpBuffer(pgdumpopts, " --no-gp-syntax"); no_gp_syntax = true; break; /* END MPP ADDITION */ default: fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } } /* Add long options to the pg_dump argument list */ if (disable_dollar_quoting) appendPQExpBuffer(pgdumpopts, " --disable-dollar-quoting"); if (disable_triggers) appendPQExpBuffer(pgdumpopts, " --disable-triggers"); if (use_setsessauth) appendPQExpBuffer(pgdumpopts, " --use-set-session-authorization"); /* Complain if any arguments remain */ if (optind < argc) { fprintf(stderr, _("%s: too many command-line arguments (first is \"%s\")\n"), progname, argv[optind]); fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } if (gp_syntax && no_gp_syntax) { fprintf(stderr, _("%s: options \"--gp-syntax\" and \"--no-gp-syntax\" cannot be used together\n"), progname); exit(1); } /* * If there was a database specified on the command line, use that, * otherwise try to connect to database "postgres", and failing that * "template1". "postgres" is the preferred choice for 8.1 and later * servers, but it usually will not exist on older ones. */ if (pgdb) { conn = connectDatabase(pgdb, pghost, pgport, pguser, prompt_password, false); if (!conn) { fprintf(stderr, _("%s: could not connect to database \"%s\"\n"), progname, pgdb); exit(1); } } else { conn = connectDatabase("postgres", pghost, pgport, pguser, prompt_password, false); if (!conn) conn = connectDatabase("template1", pghost, pgport, pguser, prompt_password, true); if (!conn) { fprintf(stderr, _("%s: could not connect to databases \"postgres\" or \"template1\"\n" "Please specify an alternative database.\n"), progname); fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } } /* * Open the output file if required, otherwise use stdout */ if (filename) { OPF = fopen(filename, PG_BINARY_W); if (!OPF) { fprintf(stderr, _("%s: could not open the output file \"%s\": %s\n"), progname, filename, strerror(errno)); exit(1); } } else OPF = stdout; /* * Get the active encoding and the standard_conforming_strings setting, so * we know how to escape strings. */ encoding = PQclientEncoding(conn); std_strings = PQparameterStatus(conn, "standard_conforming_strings"); if (!std_strings) std_strings = "off"; fprintf(OPF,"--\n-- Greenplum Database cluster dump\n--\n\n"); if (verbose) dumpTimestamp("Started on"); fprintf(OPF, "\\connect postgres\n\n"); if (!data_only) { /* Replicate encoding and std_strings in output */ fprintf(OPF, "SET client_encoding = '%s';\n", pg_encoding_to_char(encoding)); fprintf(OPF, "SET standard_conforming_strings = %s;\n", std_strings); if (strcmp(std_strings, "off") == 0) fprintf(OPF, "SET escape_string_warning = 'off';\n"); fprintf(OPF, "\n"); /* Dump Resource Queues */ if (resource_queues) dumpResQueues(conn); /* Dump roles (users) */ dumpRoles(conn); /* Dump role memberships */ dumpRoleMembership(conn); /* Dump role constraints */ dumpRoleConstraints(conn); /* Dump filespaces and tablespaces */ if (filespaces) { dumpFilespaces(conn); dumpTablespaces(conn); } /* Dump CREATE DATABASE commands */ if (!globals_only) dumpCreateDB(conn); } if (!globals_only) dumpDatabases(conn); PQfinish(conn); if (verbose) dumpTimestamp("Completed on"); fprintf(OPF, "--\n-- PostgreSQL database cluster dump complete\n--\n\n"); if (filename) fclose(OPF); exit(0); }
int main(int argc, char *argv[]) { char *pghost = NULL; char *pgport = NULL; char *pguser = NULL; char *pgdb = NULL; char *use_role = NULL; enum trivalue prompt_password = TRI_DEFAULT; bool data_only = false; bool globals_only = false; bool output_clean = false; bool roles_only = false; bool tablespaces_only = false; bool schema_only = false; PGconn *conn; int encoding; const char *std_strings; int c, ret; int optindex; static struct option long_options[] = { {"data-only", no_argument, NULL, 'a'}, {"clean", no_argument, NULL, 'c'}, {"file", required_argument, NULL, 'f'}, {"globals-only", no_argument, NULL, 'g'}, {"host", required_argument, NULL, 'h'}, {"ignore-version", no_argument, NULL, 'i'}, {"database", required_argument, NULL, 'l'}, {"oids", no_argument, NULL, 'o'}, {"no-owner", no_argument, NULL, 'O'}, {"port", required_argument, NULL, 'p'}, {"roles-only", no_argument, NULL, 'r'}, {"schema-only", no_argument, NULL, 's'}, {"superuser", required_argument, NULL, 'S'}, {"tablespaces-only", no_argument, NULL, 't'}, {"username", required_argument, NULL, 'U'}, {"verbose", no_argument, NULL, 'v'}, {"no-password", no_argument, NULL, 'w'}, {"password", no_argument, NULL, 'W'}, {"no-privileges", no_argument, NULL, 'x'}, {"no-acl", no_argument, NULL, 'x'}, /* * the following options don't have an equivalent short option letter */ {"attribute-inserts", no_argument, &column_inserts, 1}, {"binary-upgrade", no_argument, &binary_upgrade, 1}, {"column-inserts", no_argument, &column_inserts, 1}, {"disable-dollar-quoting", no_argument, &disable_dollar_quoting, 1}, {"disable-triggers", no_argument, &disable_triggers, 1}, {"inserts", no_argument, &inserts, 1}, {"lock-wait-timeout", required_argument, NULL, 2}, {"no-tablespaces", no_argument, &no_tablespaces, 1}, {"role", required_argument, NULL, 3}, {"use-set-session-authorization", no_argument, &use_setsessauth, 1}, {NULL, 0, NULL, 0} }; set_pglocale_pgservice(argv[0], PG_TEXTDOMAIN("pg_dump")); progname = get_progname(argv[0]); if (argc > 1) { if (strcmp(argv[1], "--help") == 0 || strcmp(argv[1], "-?") == 0) { help(); exit(0); } if (strcmp(argv[1], "--version") == 0 || strcmp(argv[1], "-V") == 0) { puts("pg_dumpall (PostgreSQL) " PG_VERSION); exit(0); } } if ((ret = find_other_exec(argv[0], "pg_dump", PGDUMP_VERSIONSTR, pg_dump_bin)) < 0) { char full_path[MAXPGPATH]; if (find_my_exec(argv[0], full_path) < 0) strlcpy(full_path, progname, sizeof(full_path)); if (ret == -1) fprintf(stderr, _("The program \"pg_dump\" is needed by %s " "but was not found in the\n" "same directory as \"%s\".\n" "Check your installation.\n"), progname, full_path); else fprintf(stderr, _("The program \"pg_dump\" was found by \"%s\"\n" "but was not the same version as %s.\n" "Check your installation.\n"), full_path, progname); exit(1); } pgdumpopts = createPQExpBuffer(); while ((c = getopt_long(argc, argv, "acf:gh:il:oOp:rsS:tU:vwWxX:", long_options, &optindex)) != -1) { switch (c) { case 'a': data_only = true; appendPQExpBuffer(pgdumpopts, " -a"); break; case 'c': output_clean = true; break; case 'f': filename = optarg; appendPQExpBuffer(pgdumpopts, " -f "); doShellQuoting(pgdumpopts, filename); break; case 'g': globals_only = true; break; case 'h': pghost = optarg; appendPQExpBuffer(pgdumpopts, " -h "); doShellQuoting(pgdumpopts, pghost); break; case 'i': /* ignored, deprecated option */ break; case 'l': pgdb = optarg; break; case 'o': appendPQExpBuffer(pgdumpopts, " -o"); break; case 'O': appendPQExpBuffer(pgdumpopts, " -O"); break; case 'p': pgport = optarg; appendPQExpBuffer(pgdumpopts, " -p "); doShellQuoting(pgdumpopts, pgport); break; case 'r': roles_only = true; break; case 's': schema_only = true; appendPQExpBuffer(pgdumpopts, " -s"); break; case 'S': appendPQExpBuffer(pgdumpopts, " -S "); doShellQuoting(pgdumpopts, optarg); break; case 't': tablespaces_only = true; break; case 'U': pguser = optarg; appendPQExpBuffer(pgdumpopts, " -U "); doShellQuoting(pgdumpopts, pguser); break; case 'v': verbose = true; appendPQExpBuffer(pgdumpopts, " -v"); break; case 'w': prompt_password = TRI_NO; appendPQExpBuffer(pgdumpopts, " -w"); break; case 'W': prompt_password = TRI_YES; appendPQExpBuffer(pgdumpopts, " -W"); break; case 'x': skip_acls = true; appendPQExpBuffer(pgdumpopts, " -x"); break; case 'X': /* -X is a deprecated alternative to long options */ if (strcmp(optarg, "disable-dollar-quoting") == 0) disable_dollar_quoting = 1; else if (strcmp(optarg, "disable-triggers") == 0) disable_triggers = 1; else if (strcmp(optarg, "no-tablespaces") == 0) no_tablespaces = 1; else if (strcmp(optarg, "use-set-session-authorization") == 0) use_setsessauth = 1; else { fprintf(stderr, _("%s: invalid -X option -- %s\n"), progname, optarg); fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } break; case 0: break; case 2: appendPQExpBuffer(pgdumpopts, " --lock-wait-timeout "); doShellQuoting(pgdumpopts, optarg); break; case 3: use_role = optarg; appendPQExpBuffer(pgdumpopts, " --role "); doShellQuoting(pgdumpopts, use_role); break; default: fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } } /* Add long options to the pg_dump argument list */ if (binary_upgrade) appendPQExpBuffer(pgdumpopts, " --binary-upgrade"); if (column_inserts) appendPQExpBuffer(pgdumpopts, " --column-inserts"); if (disable_dollar_quoting) appendPQExpBuffer(pgdumpopts, " --disable-dollar-quoting"); if (disable_triggers) appendPQExpBuffer(pgdumpopts, " --disable-triggers"); if (inserts) appendPQExpBuffer(pgdumpopts, " --inserts"); if (no_tablespaces) appendPQExpBuffer(pgdumpopts, " --no-tablespaces"); if (use_setsessauth) appendPQExpBuffer(pgdumpopts, " --use-set-session-authorization"); if (optind < argc) { fprintf(stderr, _("%s: too many command-line arguments (first is \"%s\")\n"), progname, argv[optind]); fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } /* Make sure the user hasn't specified a mix of globals-only options */ if (globals_only && roles_only) { fprintf(stderr, _("%s: options -g/--globals-only and -r/--roles-only cannot be used together\n"), progname); fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } if (globals_only && tablespaces_only) { fprintf(stderr, _("%s: options -g/--globals-only and -t/--tablespaces-only cannot be used together\n"), progname); fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } if (roles_only && tablespaces_only) { fprintf(stderr, _("%s: options -r/--roles-only and -t/--tablespaces-only cannot be used together\n"), progname); fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } /* * If there was a database specified on the command line, use that, * otherwise try to connect to database "postgres", and failing that * "template1". "postgres" is the preferred choice for 8.1 and later * servers, but it usually will not exist on older ones. */ if (pgdb) { conn = connectDatabase(pgdb, pghost, pgport, pguser, prompt_password, false); if (!conn) { fprintf(stderr, _("%s: could not connect to database \"%s\"\n"), progname, pgdb); exit(1); } } else { conn = connectDatabase("postgres", pghost, pgport, pguser, prompt_password, false); if (!conn) conn = connectDatabase("template1", pghost, pgport, pguser, prompt_password, true); if (!conn) { fprintf(stderr, _("%s: could not connect to databases \"postgres\" or \"template1\"\n" "Please specify an alternative database.\n"), progname); fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } } /* * Open the output file if required, otherwise use stdout */ if (filename) { OPF = fopen(filename, PG_BINARY_W); if (!OPF) { fprintf(stderr, _("%s: could not open the output file \"%s\": %s\n"), progname, filename, strerror(errno)); exit(1); } } else OPF = stdout; /* * Get the active encoding and the standard_conforming_strings setting, so * we know how to escape strings. */ encoding = PQclientEncoding(conn); std_strings = PQparameterStatus(conn, "standard_conforming_strings"); if (!std_strings) std_strings = "off"; /* Set the role if requested */ if (use_role && server_version >= 80100) { PQExpBuffer query = createPQExpBuffer(); appendPQExpBuffer(query, "SET ROLE %s", fmtId(use_role)); executeCommand(conn, query->data); destroyPQExpBuffer(query); } fprintf(OPF, "--\n-- PostgreSQL database cluster dump\n--\n\n"); if (verbose) dumpTimestamp("Started on"); fprintf(OPF, "\\connect postgres\n\n"); /* Replicate encoding and std_strings in output */ fprintf(OPF, "SET client_encoding = '%s';\n", pg_encoding_to_char(encoding)); fprintf(OPF, "SET standard_conforming_strings = %s;\n", std_strings); if (strcmp(std_strings, "off") == 0) fprintf(OPF, "SET escape_string_warning = off;\n"); fprintf(OPF, "\n"); if (!data_only) { /* * If asked to --clean, do that first. We can avoid detailed * dependency analysis because databases never depend on each other, * and tablespaces never depend on each other. Roles could have * grants to each other, but DROP ROLE will clean those up silently. */ if (output_clean) { if (!globals_only && !roles_only && !tablespaces_only) dropDBs(conn); if (!roles_only && !no_tablespaces) { if (server_version >= 80000) dropTablespaces(conn); } if (!tablespaces_only) dropRoles(conn); } /* * Now create objects as requested. Be careful that option logic here * is the same as for drops above. */ if (!tablespaces_only) { /* Dump roles (users) */ dumpRoles(conn); /* Dump role memberships --- need different method for pre-8.1 */ if (server_version >= 80100) dumpRoleMembership(conn); else dumpGroups(conn); } if (!roles_only && !no_tablespaces) { /* Dump tablespaces */ if (server_version >= 80000) dumpTablespaces(conn); } /* Dump CREATE DATABASE commands */ if (!globals_only && !roles_only && !tablespaces_only) dumpCreateDB(conn); /* Dump role/database settings */ if (!tablespaces_only && !roles_only) { if (server_version >= 90000) dumpDbRoleConfig(conn); } } if (!globals_only && !roles_only && !tablespaces_only) dumpDatabases(conn); PQfinish(conn); if (verbose) dumpTimestamp("Completed on"); fprintf(OPF, "--\n-- PostgreSQL database cluster dump complete\n--\n\n"); if (filename) fclose(OPF); exit(0); }
int main(int argc, char *argv[]) { char *pghost = NULL; char *pgport = NULL; char *pguser = NULL; bool force_password = false; bool data_only = false; bool globals_only = false; bool schema_only = false; PGconn *conn; int c, ret; static struct option long_options[] = { {"data-only", no_argument, NULL, 'a'}, {"clean", no_argument, NULL, 'c'}, {"inserts", no_argument, NULL, 'd'}, {"attribute-inserts", no_argument, NULL, 'D'}, {"column-inserts", no_argument, NULL, 'D'}, {"globals-only", no_argument, NULL, 'g'}, {"host", required_argument, NULL, 'h'}, {"ignore-version", no_argument, NULL, 'i'}, {"oids", no_argument, NULL, 'o'}, {"no-owner", no_argument, NULL, 'O'}, {"port", required_argument, NULL, 'p'}, {"password", no_argument, NULL, 'W'}, {"schema-only", no_argument, NULL, 's'}, {"superuser", required_argument, NULL, 'S'}, {"username", required_argument, NULL, 'U'}, {"verbose", no_argument, NULL, 'v'}, {"no-privileges", no_argument, NULL, 'x'}, {"no-acl", no_argument, NULL, 'x'}, /* * the following options don't have an equivalent short option letter, * but are available as '-X long-name' */ {"disable-dollar-quoting", no_argument, &disable_dollar_quoting, 1}, {"disable-triggers", no_argument, &disable_triggers, 1}, {"use-set-session-authorization", no_argument, &use_setsessauth, 1}, {NULL, 0, NULL, 0} }; int optindex; set_pglocale_pgservice(argv[0], "pg_dump"); progname = get_progname(argv[0]); if (argc > 1) { if (strcmp(argv[1], "--help") == 0 || strcmp(argv[1], "-?") == 0) { help(); exit(0); } if (strcmp(argv[1], "--version") == 0 || strcmp(argv[1], "-V") == 0) { puts("pg_dumpall (PostgreSQL) " PG_VERSION); exit(0); } } if ((ret = find_other_exec(argv[0], "pg_dump", PG_VERSIONSTR, pg_dump_bin)) < 0) { char full_path[MAXPGPATH]; if (find_my_exec(argv[0], full_path) < 0) StrNCpy(full_path, progname, MAXPGPATH); if (ret == -1) fprintf(stderr, _("The program \"pg_dump\" is needed by %s " "but was not found in the\n" "same directory as \"%s\".\n" "Check your installation.\n"), progname, full_path); else fprintf(stderr, _("The program \"pg_dump\" was found by \"%s\"\n" "but was not the same version as %s.\n" "Check your installation.\n"), full_path, progname); exit(1); } pgdumpopts = createPQExpBuffer(); while ((c = getopt_long(argc, argv, "acdDgh:ioOp:sS:U:vWxX:", long_options, &optindex)) != -1) { switch (c) { case 'a': data_only = true; appendPQExpBuffer(pgdumpopts, " -a"); break; case 'c': output_clean = true; break; case 'd': case 'D': appendPQExpBuffer(pgdumpopts, " -%c", c); break; case 'g': globals_only = true; break; case 'h': pghost = optarg; #ifndef WIN32 appendPQExpBuffer(pgdumpopts, " -h '%s'", pghost); #else appendPQExpBuffer(pgdumpopts, " -h \"%s\"", pghost); #endif break; case 'i': ignoreVersion = true; appendPQExpBuffer(pgdumpopts, " -i"); break; case 'o': appendPQExpBuffer(pgdumpopts, " -o"); break; case 'O': appendPQExpBuffer(pgdumpopts, " -O"); break; case 'p': pgport = optarg; #ifndef WIN32 appendPQExpBuffer(pgdumpopts, " -p '%s'", pgport); #else appendPQExpBuffer(pgdumpopts, " -p \"%s\"", pgport); #endif break; case 's': schema_only = true; appendPQExpBuffer(pgdumpopts, " -s"); break; case 'S': #ifndef WIN32 appendPQExpBuffer(pgdumpopts, " -S '%s'", optarg); #else appendPQExpBuffer(pgdumpopts, " -S \"%s\"", optarg); #endif break; case 'U': pguser = optarg; #ifndef WIN32 appendPQExpBuffer(pgdumpopts, " -U '%s'", pguser); #else appendPQExpBuffer(pgdumpopts, " -U \"%s\"", pguser); #endif break; case 'v': verbose = true; appendPQExpBuffer(pgdumpopts, " -v"); break; case 'W': force_password = true; appendPQExpBuffer(pgdumpopts, " -W"); break; case 'x': skip_acls = true; appendPQExpBuffer(pgdumpopts, " -x"); break; case 'X': if (strcmp(optarg, "disable-dollar-quoting") == 0) appendPQExpBuffer(pgdumpopts, " -X disable-dollar-quoting"); else if (strcmp(optarg, "disable-triggers") == 0) appendPQExpBuffer(pgdumpopts, " -X disable-triggers"); else if (strcmp(optarg, "use-set-session-authorization") == 0) /* no-op, still allowed for compatibility */ ; else { fprintf(stderr, _("%s: invalid -X option -- %s\n"), progname, optarg); fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } break; case 0: break; default: fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } } /* Add long options to the pg_dump argument list */ if (disable_dollar_quoting) appendPQExpBuffer(pgdumpopts, " -X disable-dollar-quoting"); if (disable_triggers) appendPQExpBuffer(pgdumpopts, " -X disable-triggers"); if (use_setsessauth) appendPQExpBuffer(pgdumpopts, " -X use-set-session-authorization"); if (optind < argc) { fprintf(stderr, _("%s: too many command-line arguments (first is \"%s\")\n"), progname, argv[optind]); fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit(1); } /* * First try to connect to database "postgres", and failing that * "template1". "postgres" is the preferred choice for 8.1 and later * servers, but it usually will not exist on older ones. */ conn = connectDatabase("postgres", pghost, pgport, pguser, force_password, false); if (!conn) conn = connectDatabase("template1", pghost, pgport, pguser, force_password, true); printf("--\n-- PostgreSQL database cluster dump\n--\n\n"); if (verbose) dumpTimestamp("Started on"); printf("\\connect postgres\n\n"); if (!data_only) { /* Dump roles (users) */ dumpRoles(conn); /* Dump role memberships --- need different method for pre-8.1 */ if (server_version >= 80100) dumpRoleMembership(conn); else dumpGroups(conn); /* Dump tablespaces */ if (server_version >= 80000) dumpTablespaces(conn); /* Dump CREATE DATABASE commands */ if (!globals_only) dumpCreateDB(conn); } if (!globals_only) dumpDatabases(conn); PQfinish(conn); if (verbose) dumpTimestamp("Completed on"); printf("--\n-- PostgreSQL database cluster dump complete\n--\n\n"); exit(0); }
static void do_start(void) { pgpid_t pid; pgpid_t old_pid = 0; int exitcode; if (ctl_command != RESTART_COMMAND) { old_pid = get_pgpid(); if (old_pid != 0) write_stderr(_("%s: another server might be running; " "trying to start server anyway\n"), progname); } read_gtm_opts(); /* The binary for both gtm and gtm_standby is the same */ if (strcmp(gtm_app, "gtm_standby") == 0) gtm_app = "gtm"; if (gtm_path == NULL) { int ret; char *found_path; char version_str[MAXPGPATH]; found_path = pg_malloc(MAXPGPATH); sprintf(version_str, "%s (Postgres-XC) %s\n", gtm_app, PGXC_VERSION); if ((ret = find_other_exec(argv0, gtm_app, version_str, found_path)) < 0) { char full_path[MAXPGPATH]; if (find_my_exec(argv0, full_path) < 0) strlcpy(full_path, progname, sizeof(full_path)); if (ret == -1) write_stderr(_("The program \"%s\" is needed by gtm_ctl " "but was not found in the\n" "same directory as \"%s\".\n" "Check your installation.\n"), gtm_app, full_path); else write_stderr(_("The program \"%s\" was found by \"%s\"\n" "but was not the same version as gtm_ctl.\n" "Check your installation.\n"), gtm_app, full_path); exit(1); } *last_dir_separator(found_path) = '\0'; gtm_path = found_path; } exitcode = start_gtm(); if (exitcode != 0) { write_stderr(_("%s: could not start server: exit code was %d\n"), progname, exitcode); exit(1); } if (old_pid != 0) { sleep(1); pid = get_pgpid(); if (pid == old_pid) { write_stderr(_("%s: could not start server\n" "Examine the log output.\n"), progname); exit(1); } } if (do_wait) { print_msg(_("waiting for server to start...")); if (test_gtm_connection() == false) { printf(_("could not start server\n")); exit(1); } else { print_msg(_(" done\n")); print_msg(_("server started\n")); } } else print_msg(_("server starting\n")); }