PostgreSQL Source Code  git master
pg_ctl.c
Go to the documentation of this file.
1 /*-------------------------------------------------------------------------
2  *
3  * pg_ctl --- start/stops/restarts the PostgreSQL server
4  *
5  * Portions Copyright (c) 1996-2023, PostgreSQL Global Development Group
6  *
7  * src/bin/pg_ctl/pg_ctl.c
8  *
9  *-------------------------------------------------------------------------
10  */
11 
12 #include "postgres_fe.h"
13 
14 #include <fcntl.h>
15 #include <signal.h>
16 #include <time.h>
17 #include <sys/resource.h>
18 #include <sys/stat.h>
19 #include <sys/time.h>
20 #include <sys/wait.h>
21 #include <unistd.h>
22 
23 
24 #include "catalog/pg_control.h"
26 #include "common/file_perm.h"
27 #include "common/logging.h"
28 #include "common/string.h"
29 #include "getopt_long.h"
30 #include "utils/pidfile.h"
31 
32 #ifdef WIN32 /* on Unix, we don't need libpq */
33 #include "pqexpbuffer.h"
34 #endif
35 
36 
37 typedef enum
38 {
43 
44 typedef enum
45 {
50 
51 typedef enum
52 {
67 
68 #define DEFAULT_WAIT 60
69 
70 #define USEC_PER_SEC 1000000
71 
72 #define WAITS_PER_SEC 10 /* should divide USEC_PER_SEC evenly */
73 
74 static bool do_wait = true;
76 static bool wait_seconds_arg = false;
77 static bool silent_mode = false;
79 static int sig = SIGINT; /* default */
81 static char *pg_data = NULL;
82 static char *pg_config = NULL;
83 static char *pgdata_opt = NULL;
84 static char *post_opts = NULL;
85 static const char *progname;
86 static char *log_file = NULL;
87 static char *exec_path = NULL;
88 static char *event_source = NULL;
89 static char *register_servicename = "PostgreSQL"; /* FIXME: + version ID? */
90 static char *register_username = NULL;
91 static char *register_password = NULL;
92 static char *argv0 = NULL;
93 static bool allow_core_files = false;
94 static time_t start_time;
95 
96 static char postopts_file[MAXPGPATH];
97 static char version_file[MAXPGPATH];
98 static char pid_file[MAXPGPATH];
99 static char backup_file[MAXPGPATH];
100 static char promote_file[MAXPGPATH];
102 
103 static volatile pid_t postmasterPID = -1;
104 
105 #ifdef WIN32
106 static DWORD pgctl_start_type = SERVICE_AUTO_START;
107 static SERVICE_STATUS status;
108 static SERVICE_STATUS_HANDLE hStatus = (SERVICE_STATUS_HANDLE) 0;
109 static HANDLE shutdownHandles[2];
110 
111 #define shutdownEvent shutdownHandles[0]
112 #define postmasterProcess shutdownHandles[1]
113 #endif
114 
115 
116 static void write_stderr(const char *fmt,...) pg_attribute_printf(1, 2);
117 static void do_advice(void);
118 static void do_help(void);
119 static void set_mode(char *modeopt);
120 static void set_sig(char *signame);
121 static void do_init(void);
122 static void do_start(void);
123 static void do_stop(void);
124 static void do_restart(void);
125 static void do_reload(void);
126 static void do_status(void);
127 static void do_promote(void);
128 static void do_logrotate(void);
129 static void do_kill(pid_t pid);
130 static void print_msg(const char *msg);
131 static void adjust_data_dir(void);
132 
133 #ifdef WIN32
134 #include <versionhelpers.h>
135 static bool pgwin32_IsInstalled(SC_HANDLE);
136 static char *pgwin32_CommandLine(bool);
137 static void pgwin32_doRegister(void);
138 static void pgwin32_doUnregister(void);
139 static void pgwin32_SetServiceStatus(DWORD);
140 static void WINAPI pgwin32_ServiceHandler(DWORD);
141 static void WINAPI pgwin32_ServiceMain(DWORD, LPTSTR *);
142 static void pgwin32_doRunAsService(void);
143 static int CreateRestrictedProcess(char *cmd, PROCESS_INFORMATION *processInfo, bool as_service);
144 static PTOKEN_PRIVILEGES GetPrivilegesToDelete(HANDLE hToken);
145 #endif
146 
147 static pid_t get_pgpid(bool is_status_request);
148 static char **readfile(const char *path, int *numlines);
149 static void free_readfile(char **optlines);
150 static pid_t start_postmaster(void);
151 static void read_post_opts(void);
152 
153 static WaitPMResult wait_for_postmaster_start(pid_t pm_pid, bool do_checkpoint);
154 static bool wait_for_postmaster_stop(void);
155 static bool wait_for_postmaster_promote(void);
156 static bool postmaster_is_alive(pid_t pid);
157 
158 #if defined(HAVE_GETRLIMIT)
159 static void unlimit_core_size(void);
160 #endif
161 
162 static DBState get_control_dbstate(void);
163 
164 
165 #ifdef WIN32
166 static void
167 write_eventlog(int level, const char *line)
168 {
169  static HANDLE evtHandle = INVALID_HANDLE_VALUE;
170 
171  if (silent_mode && level == EVENTLOG_INFORMATION_TYPE)
172  return;
173 
174  if (evtHandle == INVALID_HANDLE_VALUE)
175  {
176  evtHandle = RegisterEventSource(NULL,
178  if (evtHandle == NULL)
179  {
180  evtHandle = INVALID_HANDLE_VALUE;
181  return;
182  }
183  }
184 
185  ReportEvent(evtHandle,
186  level,
187  0,
188  0, /* All events are Id 0 */
189  NULL,
190  1,
191  0,
192  &line,
193  NULL);
194 }
195 #endif
196 
197 /*
198  * Write errors to stderr (or by equal means when stderr is
199  * not available).
200  */
201 static void
202 write_stderr(const char *fmt,...)
203 {
204  va_list ap;
205 
206  va_start(ap, fmt);
207 #ifndef WIN32
208  /* On Unix, we just fprintf to stderr */
209  vfprintf(stderr, fmt, ap);
210 #else
211 
212  /*
213  * On Win32, we print to stderr if running on a console, or write to
214  * eventlog if running as a service
215  */
216  if (pgwin32_is_service()) /* Running as a service */
217  {
218  char errbuf[2048]; /* Arbitrary size? */
219 
220  vsnprintf(errbuf, sizeof(errbuf), fmt, ap);
221 
222  write_eventlog(EVENTLOG_ERROR_TYPE, errbuf);
223  }
224  else
225  /* Not running as service, write to stderr */
226  vfprintf(stderr, fmt, ap);
227 #endif
228  va_end(ap);
229 }
230 
231 /*
232  * Given an already-localized string, print it to stdout unless the
233  * user has specified that no messages should be printed.
234  */
235 static void
236 print_msg(const char *msg)
237 {
238  if (!silent_mode)
239  {
240  fputs(msg, stdout);
241  fflush(stdout);
242  }
243 }
244 
245 static pid_t
246 get_pgpid(bool is_status_request)
247 {
248  FILE *pidf;
249  int pid;
250  struct stat statbuf;
251 
252  if (stat(pg_data, &statbuf) != 0)
253  {
254  if (errno == ENOENT)
255  write_stderr(_("%s: directory \"%s\" does not exist\n"), progname,
256  pg_data);
257  else
258  write_stderr(_("%s: could not access directory \"%s\": %s\n"), progname,
259  pg_data, strerror(errno));
260 
261  /*
262  * The Linux Standard Base Core Specification 3.1 says this should
263  * return '4, program or service status is unknown'
264  * https://refspecs.linuxbase.org/LSB_3.1.0/LSB-Core-generic/LSB-Core-generic/iniscrptact.html
265  */
266  exit(is_status_request ? 4 : 1);
267  }
268 
269  if (stat(version_file, &statbuf) != 0 && errno == ENOENT)
270  {
271  write_stderr(_("%s: directory \"%s\" is not a database cluster directory\n"),
272  progname, pg_data);
273  exit(is_status_request ? 4 : 1);
274  }
275 
276  pidf = fopen(pid_file, "r");
277  if (pidf == NULL)
278  {
279  /* No pid file, not an error on startup */
280  if (errno == ENOENT)
281  return 0;
282  else
283  {
284  write_stderr(_("%s: could not open PID file \"%s\": %s\n"),
285  progname, pid_file, strerror(errno));
286  exit(1);
287  }
288  }
289  if (fscanf(pidf, "%d", &pid) != 1)
290  {
291  /* Is the file empty? */
292  if (ftell(pidf) == 0 && feof(pidf))
293  write_stderr(_("%s: the PID file \"%s\" is empty\n"),
294  progname, pid_file);
295  else
296  write_stderr(_("%s: invalid data in PID file \"%s\"\n"),
297  progname, pid_file);
298  exit(1);
299  }
300  fclose(pidf);
301  return (pid_t) pid;
302 }
303 
304 
305 /*
306  * get the lines from a text file - return NULL if file can't be opened
307  *
308  * Trailing newlines are deleted from the lines (this is a change from pre-v10)
309  *
310  * *numlines is set to the number of line pointers returned; there is
311  * also an additional NULL pointer after the last real line.
312  */
313 static char **
314 readfile(const char *path, int *numlines)
315 {
316  int fd;
317  int nlines;
318  char **result;
319  char *buffer;
320  char *linebegin;
321  int i;
322  int n;
323  int len;
324  struct stat statbuf;
325 
326  *numlines = 0; /* in case of failure or empty file */
327 
328  /*
329  * Slurp the file into memory.
330  *
331  * The file can change concurrently, so we read the whole file into memory
332  * with a single read() call. That's not guaranteed to get an atomic
333  * snapshot, but in practice, for a small file, it's close enough for the
334  * current use.
335  */
336  fd = open(path, O_RDONLY | PG_BINARY, 0);
337  if (fd < 0)
338  return NULL;
339  if (fstat(fd, &statbuf) < 0)
340  {
341  close(fd);
342  return NULL;
343  }
344  if (statbuf.st_size == 0)
345  {
346  /* empty file */
347  close(fd);
348  result = (char **) pg_malloc(sizeof(char *));
349  *result = NULL;
350  return result;
351  }
352  buffer = pg_malloc(statbuf.st_size + 1);
353 
354  len = read(fd, buffer, statbuf.st_size + 1);
355  close(fd);
356  if (len != statbuf.st_size)
357  {
358  /* oops, the file size changed between fstat and read */
359  free(buffer);
360  return NULL;
361  }
362 
363  /*
364  * Count newlines. We expect there to be a newline after each full line,
365  * including one at the end of file. If there isn't a newline at the end,
366  * any characters after the last newline will be ignored.
367  */
368  nlines = 0;
369  for (i = 0; i < len; i++)
370  {
371  if (buffer[i] == '\n')
372  nlines++;
373  }
374 
375  /* set up the result buffer */
376  result = (char **) pg_malloc((nlines + 1) * sizeof(char *));
377  *numlines = nlines;
378 
379  /* now split the buffer into lines */
380  linebegin = buffer;
381  n = 0;
382  for (i = 0; i < len; i++)
383  {
384  if (buffer[i] == '\n')
385  {
386  int slen = &buffer[i] - linebegin;
387  char *linebuf = pg_malloc(slen + 1);
388 
389  memcpy(linebuf, linebegin, slen);
390  /* we already dropped the \n, but get rid of any \r too */
391  if (slen > 0 && linebuf[slen - 1] == '\r')
392  slen--;
393  linebuf[slen] = '\0';
394  result[n++] = linebuf;
395  linebegin = &buffer[i + 1];
396  }
397  }
398  result[n] = NULL;
399 
400  free(buffer);
401 
402  return result;
403 }
404 
405 
406 /*
407  * Free memory allocated for optlines through readfile()
408  */
409 static void
410 free_readfile(char **optlines)
411 {
412  char *curr_line = NULL;
413  int i = 0;
414 
415  if (!optlines)
416  return;
417 
418  while ((curr_line = optlines[i++]))
419  free(curr_line);
420 
421  free(optlines);
422 }
423 
424 /*
425  * start/test/stop routines
426  */
427 
428 /*
429  * Start the postmaster and return its PID.
430  *
431  * Currently, on Windows what we return is the PID of the shell process
432  * that launched the postmaster (and, we trust, is waiting for it to exit).
433  * So the PID is usable for "is the postmaster still running" checks,
434  * but cannot be compared directly to postmaster.pid.
435  *
436  * On Windows, we also save aside a handle to the shell process in
437  * "postmasterProcess", which the caller should close when done with it.
438  */
439 static pid_t
441 {
442  char *cmd;
443 
444 #ifndef WIN32
445  pid_t pm_pid;
446 
447  /* Flush stdio channels just before fork, to avoid double-output problems */
448  fflush(NULL);
449 
450 #ifdef EXEC_BACKEND
451  pg_disable_aslr();
452 #endif
453 
454  pm_pid = fork();
455  if (pm_pid < 0)
456  {
457  /* fork failed */
458  write_stderr(_("%s: could not start server: %s\n"),
459  progname, strerror(errno));
460  exit(1);
461  }
462  if (pm_pid > 0)
463  {
464  /* fork succeeded, in parent */
465  return pm_pid;
466  }
467 
468  /* fork succeeded, in child */
469 
470  /*
471  * If possible, detach the postmaster process from the launching process
472  * group and make it a group leader, so that it doesn't get signaled along
473  * with the current group that launched it.
474  */
475 #ifdef HAVE_SETSID
476  if (setsid() < 0)
477  {
478  write_stderr(_("%s: could not start server due to setsid() failure: %s\n"),
479  progname, strerror(errno));
480  exit(1);
481  }
482 #endif
483 
484  /*
485  * Since there might be quotes to handle here, it is easier simply to pass
486  * everything to a shell to process them. Use exec so that the postmaster
487  * has the same PID as the current child process.
488  */
489  if (log_file != NULL)
490  cmd = psprintf("exec \"%s\" %s%s < \"%s\" >> \"%s\" 2>&1",
492  DEVNULL, log_file);
493  else
494  cmd = psprintf("exec \"%s\" %s%s < \"%s\" 2>&1",
496 
497  (void) execl("/bin/sh", "/bin/sh", "-c", cmd, (char *) NULL);
498 
499  /* exec failed */
500  write_stderr(_("%s: could not start server: %s\n"),
501  progname, strerror(errno));
502  exit(1);
503 
504  return 0; /* keep dumb compilers quiet */
505 
506 #else /* WIN32 */
507 
508  /*
509  * As with the Unix case, it's easiest to use the shell (CMD.EXE) to
510  * handle redirection etc. Unfortunately CMD.EXE lacks any equivalent of
511  * "exec", so we don't get to find out the postmaster's PID immediately.
512  */
513  PROCESS_INFORMATION pi;
514  const char *comspec;
515 
516  /* Find CMD.EXE location using COMSPEC, if it's set */
517  comspec = getenv("COMSPEC");
518  if (comspec == NULL)
519  comspec = "CMD";
520 
521  if (log_file != NULL)
522  {
523  /*
524  * First, open the log file if it exists. The idea is that if the
525  * file is still locked by a previous postmaster run, we'll wait until
526  * it comes free, instead of failing with ERROR_SHARING_VIOLATION.
527  * (It'd be better to open the file in a sharing-friendly mode, but we
528  * can't use CMD.EXE to do that, so work around it. Note that the
529  * previous postmaster will still have the file open for a short time
530  * after removing postmaster.pid.)
531  *
532  * If the log file doesn't exist, we *must not* create it here. If we
533  * were launched with higher privileges than the restricted process
534  * will have, the log file might end up with permissions settings that
535  * prevent the postmaster from writing on it.
536  */
537  int fd = open(log_file, O_RDWR, 0);
538 
539  if (fd == -1)
540  {
541  /*
542  * ENOENT is expectable since we didn't use O_CREAT. Otherwise
543  * complain. We could just fall through and let CMD.EXE report
544  * the problem, but its error reporting is pretty miserable.
545  */
546  if (errno != ENOENT)
547  {
548  write_stderr(_("%s: could not open log file \"%s\": %s\n"),
549  progname, log_file, strerror(errno));
550  exit(1);
551  }
552  }
553  else
554  close(fd);
555 
556  cmd = psprintf("\"%s\" /C \"\"%s\" %s%s < \"%s\" >> \"%s\" 2>&1\"",
558  }
559  else
560  cmd = psprintf("\"%s\" /C \"\"%s\" %s%s < \"%s\" 2>&1\"",
561  comspec, exec_path, pgdata_opt, post_opts, DEVNULL);
562 
563  if (!CreateRestrictedProcess(cmd, &pi, false))
564  {
565  write_stderr(_("%s: could not start server: error code %lu\n"),
566  progname, (unsigned long) GetLastError());
567  exit(1);
568  }
569  /* Don't close command process handle here; caller must do so */
570  postmasterProcess = pi.hProcess;
571  CloseHandle(pi.hThread);
572  return pi.dwProcessId; /* Shell's PID, not postmaster's! */
573 #endif /* WIN32 */
574 }
575 
576 
577 
578 /*
579  * Wait for the postmaster to become ready.
580  *
581  * On Unix, pm_pid is the PID of the just-launched postmaster. On Windows,
582  * it may be the PID of an ancestor shell process, so we can't check the
583  * contents of postmaster.pid quite as carefully.
584  *
585  * On Windows, the static variable postmasterProcess is an implicit argument
586  * to this routine; it contains a handle to the postmaster process or an
587  * ancestor shell process thereof.
588  *
589  * Note that the checkpoint parameter enables a Windows service control
590  * manager checkpoint, it's got nothing to do with database checkpoints!!
591  */
592 static WaitPMResult
593 wait_for_postmaster_start(pid_t pm_pid, bool do_checkpoint)
594 {
595  int i;
596 
597  for (i = 0; i < wait_seconds * WAITS_PER_SEC; i++)
598  {
599  char **optlines;
600  int numlines;
601 
602  /*
603  * Try to read the postmaster.pid file. If it's not valid, or if the
604  * status line isn't there yet, just keep waiting.
605  */
606  if ((optlines = readfile(pid_file, &numlines)) != NULL &&
607  numlines >= LOCK_FILE_LINE_PM_STATUS)
608  {
609  /* File is complete enough for us, parse it */
610  pid_t pmpid;
611  time_t pmstart;
612 
613  /*
614  * Make sanity checks. If it's for the wrong PID, or the recorded
615  * start time is before pg_ctl started, then either we are looking
616  * at the wrong data directory, or this is a pre-existing pidfile
617  * that hasn't (yet?) been overwritten by our child postmaster.
618  * Allow 2 seconds slop for possible cross-process clock skew.
619  */
620  pmpid = atol(optlines[LOCK_FILE_LINE_PID - 1]);
621  pmstart = atol(optlines[LOCK_FILE_LINE_START_TIME - 1]);
622  if (pmstart >= start_time - 2 &&
623 #ifndef WIN32
624  pmpid == pm_pid
625 #else
626  /* Windows can only reject standalone-backend PIDs */
627  pmpid > 0
628 #endif
629  )
630  {
631  /*
632  * OK, seems to be a valid pidfile from our child. Check the
633  * status line (this assumes a v10 or later server).
634  */
635  char *pmstatus = optlines[LOCK_FILE_LINE_PM_STATUS - 1];
636 
637  if (strcmp(pmstatus, PM_STATUS_READY) == 0 ||
638  strcmp(pmstatus, PM_STATUS_STANDBY) == 0)
639  {
640  /* postmaster is done starting up */
641  free_readfile(optlines);
642  return POSTMASTER_READY;
643  }
644  }
645  }
646 
647  /*
648  * Free the results of readfile.
649  *
650  * This is safe to call even if optlines is NULL.
651  */
652  free_readfile(optlines);
653 
654  /*
655  * Check whether the child postmaster process is still alive. This
656  * lets us exit early if the postmaster fails during startup.
657  *
658  * On Windows, we may be checking the postmaster's parent shell, but
659  * that's fine for this purpose.
660  */
661 #ifndef WIN32
662  {
663  int exitstatus;
664 
665  if (waitpid(pm_pid, &exitstatus, WNOHANG) == pm_pid)
666  return POSTMASTER_FAILED;
667  }
668 #else
669  if (WaitForSingleObject(postmasterProcess, 0) == WAIT_OBJECT_0)
670  return POSTMASTER_FAILED;
671 #endif
672 
673  /* Startup still in process; wait, printing a dot once per second */
674  if (i % WAITS_PER_SEC == 0)
675  {
676 #ifdef WIN32
677  if (do_checkpoint)
678  {
679  /*
680  * Increment the wait hint by 6 secs (connection timeout +
681  * sleep). We must do this to indicate to the SCM that our
682  * startup time is changing, otherwise it'll usually send a
683  * stop signal after 20 seconds, despite incrementing the
684  * checkpoint counter.
685  */
686  status.dwWaitHint += 6000;
687  status.dwCheckPoint++;
688  SetServiceStatus(hStatus, (LPSERVICE_STATUS) &status);
689  }
690  else
691 #endif
692  print_msg(".");
693  }
694 
696  }
697 
698  /* out of patience; report that postmaster is still starting up */
700 }
701 
702 
703 /*
704  * Wait for the postmaster to stop.
705  *
706  * Returns true if the postmaster stopped cleanly (i.e., removed its pidfile).
707  * Returns false if the postmaster dies uncleanly, or if we time out.
708  */
709 static bool
711 {
712  int cnt;
713 
714  for (cnt = 0; cnt < wait_seconds * WAITS_PER_SEC; cnt++)
715  {
716  pid_t pid;
717 
718  if ((pid = get_pgpid(false)) == 0)
719  return true; /* pid file is gone */
720 
721  if (kill(pid, 0) != 0)
722  {
723  /*
724  * Postmaster seems to have died. Check the pid file once more to
725  * avoid a race condition, but give up waiting.
726  */
727  if (get_pgpid(false) == 0)
728  return true; /* pid file is gone */
729  return false; /* postmaster died untimely */
730  }
731 
732  if (cnt % WAITS_PER_SEC == 0)
733  print_msg(".");
735  }
736  return false; /* timeout reached */
737 }
738 
739 
740 /*
741  * Wait for the postmaster to promote.
742  *
743  * Returns true on success, else false.
744  * To avoid waiting uselessly, we check for postmaster death here too.
745  */
746 static bool
748 {
749  int cnt;
750 
751  for (cnt = 0; cnt < wait_seconds * WAITS_PER_SEC; cnt++)
752  {
753  pid_t pid;
754  DBState state;
755 
756  if ((pid = get_pgpid(false)) == 0)
757  return false; /* pid file is gone */
758  if (kill(pid, 0) != 0)
759  return false; /* postmaster died */
760 
762  if (state == DB_IN_PRODUCTION)
763  return true; /* successful promotion */
764 
765  if (cnt % WAITS_PER_SEC == 0)
766  print_msg(".");
768  }
769  return false; /* timeout reached */
770 }
771 
772 
773 #if defined(HAVE_GETRLIMIT)
774 static void
776 {
777  struct rlimit lim;
778 
779  getrlimit(RLIMIT_CORE, &lim);
780  if (lim.rlim_max == 0)
781  {
782  write_stderr(_("%s: cannot set core file size limit; disallowed by hard limit\n"),
783  progname);
784  return;
785  }
786  else if (lim.rlim_max == RLIM_INFINITY || lim.rlim_cur < lim.rlim_max)
787  {
788  lim.rlim_cur = lim.rlim_max;
789  setrlimit(RLIMIT_CORE, &lim);
790  }
791 }
792 #endif
793 
794 static void
796 {
797  if (post_opts == NULL)
798  {
799  post_opts = ""; /* default */
801  {
802  char **optlines;
803  int numlines;
804 
805  optlines = readfile(postopts_file, &numlines);
806  if (optlines == NULL)
807  {
808  write_stderr(_("%s: could not read file \"%s\"\n"), progname, postopts_file);
809  exit(1);
810  }
811  else if (numlines != 1)
812  {
813  write_stderr(_("%s: option file \"%s\" must have exactly one line\n"),
815  exit(1);
816  }
817  else
818  {
819  char *optline;
820  char *arg1;
821 
822  optline = optlines[0];
823 
824  /*
825  * Are we at the first option, as defined by space and
826  * double-quote?
827  */
828  if ((arg1 = strstr(optline, " \"")) != NULL)
829  {
830  *arg1 = '\0'; /* terminate so we get only program name */
831  post_opts = pg_strdup(arg1 + 1); /* point past whitespace */
832  }
833  if (exec_path == NULL)
834  exec_path = pg_strdup(optline);
835  }
836 
837  /* Free the results of readfile. */
838  free_readfile(optlines);
839  }
840  }
841 }
842 
843 /*
844  * SIGINT signal handler used while waiting for postmaster to start up.
845  * Forwards the SIGINT to the postmaster process, asking it to shut down,
846  * before terminating pg_ctl itself. This way, if the user hits CTRL-C while
847  * waiting for the server to start up, the server launch is aborted.
848  */
849 static void
851 {
852  if (postmasterPID != -1)
853  {
854  if (kill(postmasterPID, SIGINT) != 0)
855  write_stderr(_("%s: could not send stop signal (PID: %d): %s\n"),
856  progname, (int) postmasterPID, strerror(errno));
857  }
858 
859  /*
860  * Clear the signal handler, and send the signal again, to terminate the
861  * process as normal.
862  */
863  pqsignal(postgres_signal_arg, SIG_DFL);
864  raise(postgres_signal_arg);
865 }
866 
867 static char *
868 find_other_exec_or_die(const char *argv0, const char *target, const char *versionstr)
869 {
870  int ret;
871  char *found_path;
872 
873  found_path = pg_malloc(MAXPGPATH);
874 
875  if ((ret = find_other_exec(argv0, target, versionstr, found_path)) < 0)
876  {
877  char full_path[MAXPGPATH];
878 
879  if (find_my_exec(argv0, full_path) < 0)
880  strlcpy(full_path, progname, sizeof(full_path));
881 
882  if (ret == -1)
883  write_stderr(_("program \"%s\" is needed by %s but was not found in the same directory as \"%s\"\n"),
884  target, progname, full_path);
885  else
886  write_stderr(_("program \"%s\" was found by \"%s\" but was not the same version as %s\n"),
887  target, full_path, progname);
888  exit(1);
889  }
890 
891  return found_path;
892 }
893 
894 static void
895 do_init(void)
896 {
897  char *cmd;
898 
899  if (exec_path == NULL)
900  exec_path = find_other_exec_or_die(argv0, "initdb", "initdb (PostgreSQL) " PG_VERSION "\n");
901 
902  if (pgdata_opt == NULL)
903  pgdata_opt = "";
904 
905  if (post_opts == NULL)
906  post_opts = "";
907 
908  if (!silent_mode)
909  cmd = psprintf("\"%s\" %s%s",
911  else
912  cmd = psprintf("\"%s\" %s%s > \"%s\"",
914 
915  fflush(NULL);
916  if (system(cmd) != 0)
917  {
918  write_stderr(_("%s: database system initialization failed\n"), progname);
919  exit(1);
920  }
921 }
922 
923 static void
924 do_start(void)
925 {
926  pid_t old_pid = 0;
927  pid_t pm_pid;
928 
930  {
931  old_pid = get_pgpid(false);
932  if (old_pid != 0)
933  write_stderr(_("%s: another server might be running; "
934  "trying to start server anyway\n"),
935  progname);
936  }
937 
938  read_post_opts();
939 
940  /* No -D or -D already added during server start */
941  if (ctl_command == RESTART_COMMAND || pgdata_opt == NULL)
942  pgdata_opt = "";
943 
944  if (exec_path == NULL)
946 
947 #if defined(HAVE_GETRLIMIT)
948  if (allow_core_files)
950 #endif
951 
952  /*
953  * If possible, tell the postmaster our parent shell's PID (see the
954  * comments in CreateLockFile() for motivation). Windows hasn't got
955  * getppid() unfortunately.
956  */
957 #ifndef WIN32
958  {
959  char env_var[32];
960 
961  snprintf(env_var, sizeof(env_var), "%d", (int) getppid());
962  setenv("PG_GRANDPARENT_PID", env_var, 1);
963  }
964 #endif
965 
966  pm_pid = start_postmaster();
967 
968  if (do_wait)
969  {
970  /*
971  * If the user interrupts the startup (e.g. with CTRL-C), we'd like to
972  * abort the server launch. Install a signal handler that will
973  * forward SIGINT to the postmaster process, while we wait.
974  *
975  * (We don't bother to reset the signal handler after the launch, as
976  * we're about to exit, anyway.)
977  */
978  postmasterPID = pm_pid;
980 
981  print_msg(_("waiting for server to start..."));
982 
983  switch (wait_for_postmaster_start(pm_pid, false))
984  {
985  case POSTMASTER_READY:
986  print_msg(_(" done\n"));
987  print_msg(_("server started\n"));
988  break;
990  print_msg(_(" stopped waiting\n"));
991  write_stderr(_("%s: server did not start in time\n"),
992  progname);
993  exit(1);
994  break;
995  case POSTMASTER_FAILED:
996  print_msg(_(" stopped waiting\n"));
997  write_stderr(_("%s: could not start server\n"
998  "Examine the log output.\n"),
999  progname);
1000  exit(1);
1001  break;
1002  }
1003  }
1004  else
1005  print_msg(_("server starting\n"));
1006 
1007 #ifdef WIN32
1008  /* Now we don't need the handle to the shell process anymore */
1009  CloseHandle(postmasterProcess);
1010  postmasterProcess = INVALID_HANDLE_VALUE;
1011 #endif
1012 }
1013 
1014 
1015 static void
1016 do_stop(void)
1017 {
1018  pid_t pid;
1019 
1020  pid = get_pgpid(false);
1021 
1022  if (pid == 0) /* no pid file */
1023  {
1024  write_stderr(_("%s: PID file \"%s\" does not exist\n"), progname, pid_file);
1025  write_stderr(_("Is server running?\n"));
1026  exit(1);
1027  }
1028  else if (pid < 0) /* standalone backend, not postmaster */
1029  {
1030  pid = -pid;
1031  write_stderr(_("%s: cannot stop server; "
1032  "single-user server is running (PID: %d)\n"),
1033  progname, (int) pid);
1034  exit(1);
1035  }
1036 
1037  if (kill(pid, sig) != 0)
1038  {
1039  write_stderr(_("%s: could not send stop signal (PID: %d): %s\n"), progname, (int) pid,
1040  strerror(errno));
1041  exit(1);
1042  }
1043 
1044  if (!do_wait)
1045  {
1046  print_msg(_("server shutting down\n"));
1047  return;
1048  }
1049  else
1050  {
1051  print_msg(_("waiting for server to shut down..."));
1052 
1053  if (!wait_for_postmaster_stop())
1054  {
1055  print_msg(_(" failed\n"));
1056 
1057  write_stderr(_("%s: server does not shut down\n"), progname);
1058  if (shutdown_mode == SMART_MODE)
1059  write_stderr(_("HINT: The \"-m fast\" option immediately disconnects sessions rather than\n"
1060  "waiting for session-initiated disconnection.\n"));
1061  exit(1);
1062  }
1063  print_msg(_(" done\n"));
1064 
1065  print_msg(_("server stopped\n"));
1066  }
1067 }
1068 
1069 
1070 /*
1071  * restart/reload routines
1072  */
1073 
1074 static void
1076 {
1077  pid_t pid;
1078 
1079  pid = get_pgpid(false);
1080 
1081  if (pid == 0) /* no pid file */
1082  {
1083  write_stderr(_("%s: PID file \"%s\" does not exist\n"),
1084  progname, pid_file);
1085  write_stderr(_("Is server running?\n"));
1086  write_stderr(_("trying to start server anyway\n"));
1087  do_start();
1088  return;
1089  }
1090  else if (pid < 0) /* standalone backend, not postmaster */
1091  {
1092  pid = -pid;
1093  if (postmaster_is_alive(pid))
1094  {
1095  write_stderr(_("%s: cannot restart server; "
1096  "single-user server is running (PID: %d)\n"),
1097  progname, (int) pid);
1098  write_stderr(_("Please terminate the single-user server and try again.\n"));
1099  exit(1);
1100  }
1101  }
1102 
1103  if (postmaster_is_alive(pid))
1104  {
1105  if (kill(pid, sig) != 0)
1106  {
1107  write_stderr(_("%s: could not send stop signal (PID: %d): %s\n"), progname, (int) pid,
1108  strerror(errno));
1109  exit(1);
1110  }
1111 
1112  print_msg(_("waiting for server to shut down..."));
1113 
1114  /* always wait for restart */
1115  if (!wait_for_postmaster_stop())
1116  {
1117  print_msg(_(" failed\n"));
1118 
1119  write_stderr(_("%s: server does not shut down\n"), progname);
1120  if (shutdown_mode == SMART_MODE)
1121  write_stderr(_("HINT: The \"-m fast\" option immediately disconnects sessions rather than\n"
1122  "waiting for session-initiated disconnection.\n"));
1123  exit(1);
1124  }
1125 
1126  print_msg(_(" done\n"));
1127  print_msg(_("server stopped\n"));
1128  }
1129  else
1130  {
1131  write_stderr(_("%s: old server process (PID: %d) seems to be gone\n"),
1132  progname, (int) pid);
1133  write_stderr(_("starting server anyway\n"));
1134  }
1135 
1136  do_start();
1137 }
1138 
1139 static void
1141 {
1142  pid_t pid;
1143 
1144  pid = get_pgpid(false);
1145  if (pid == 0) /* no pid file */
1146  {
1147  write_stderr(_("%s: PID file \"%s\" does not exist\n"), progname, pid_file);
1148  write_stderr(_("Is server running?\n"));
1149  exit(1);
1150  }
1151  else if (pid < 0) /* standalone backend, not postmaster */
1152  {
1153  pid = -pid;
1154  write_stderr(_("%s: cannot reload server; "
1155  "single-user server is running (PID: %d)\n"),
1156  progname, (int) pid);
1157  write_stderr(_("Please terminate the single-user server and try again.\n"));
1158  exit(1);
1159  }
1160 
1161  if (kill(pid, sig) != 0)
1162  {
1163  write_stderr(_("%s: could not send reload signal (PID: %d): %s\n"),
1164  progname, (int) pid, strerror(errno));
1165  exit(1);
1166  }
1167 
1168  print_msg(_("server signaled\n"));
1169 }
1170 
1171 
1172 /*
1173  * promote
1174  */
1175 
1176 static void
1178 {
1179  FILE *prmfile;
1180  pid_t pid;
1181 
1182  pid = get_pgpid(false);
1183 
1184  if (pid == 0) /* no pid file */
1185  {
1186  write_stderr(_("%s: PID file \"%s\" does not exist\n"), progname, pid_file);
1187  write_stderr(_("Is server running?\n"));
1188  exit(1);
1189  }
1190  else if (pid < 0) /* standalone backend, not postmaster */
1191  {
1192  pid = -pid;
1193  write_stderr(_("%s: cannot promote server; "
1194  "single-user server is running (PID: %d)\n"),
1195  progname, (int) pid);
1196  exit(1);
1197  }
1198 
1200  {
1201  write_stderr(_("%s: cannot promote server; "
1202  "server is not in standby mode\n"),
1203  progname);
1204  exit(1);
1205  }
1206 
1207  snprintf(promote_file, MAXPGPATH, "%s/promote", pg_data);
1208 
1209  if ((prmfile = fopen(promote_file, "w")) == NULL)
1210  {
1211  write_stderr(_("%s: could not create promote signal file \"%s\": %s\n"),
1212  progname, promote_file, strerror(errno));
1213  exit(1);
1214  }
1215  if (fclose(prmfile))
1216  {
1217  write_stderr(_("%s: could not write promote signal file \"%s\": %s\n"),
1218  progname, promote_file, strerror(errno));
1219  exit(1);
1220  }
1221 
1222  sig = SIGUSR1;
1223  if (kill(pid, sig) != 0)
1224  {
1225  write_stderr(_("%s: could not send promote signal (PID: %d): %s\n"),
1226  progname, (int) pid, strerror(errno));
1227  if (unlink(promote_file) != 0)
1228  write_stderr(_("%s: could not remove promote signal file \"%s\": %s\n"),
1229  progname, promote_file, strerror(errno));
1230  exit(1);
1231  }
1232 
1233  if (do_wait)
1234  {
1235  print_msg(_("waiting for server to promote..."));
1237  {
1238  print_msg(_(" done\n"));
1239  print_msg(_("server promoted\n"));
1240  }
1241  else
1242  {
1243  print_msg(_(" stopped waiting\n"));
1244  write_stderr(_("%s: server did not promote in time\n"),
1245  progname);
1246  exit(1);
1247  }
1248  }
1249  else
1250  print_msg(_("server promoting\n"));
1251 }
1252 
1253 /*
1254  * log rotate
1255  */
1256 
1257 static void
1259 {
1260  FILE *logrotatefile;
1261  pid_t pid;
1262 
1263  pid = get_pgpid(false);
1264 
1265  if (pid == 0) /* no pid file */
1266  {
1267  write_stderr(_("%s: PID file \"%s\" does not exist\n"), progname, pid_file);
1268  write_stderr(_("Is server running?\n"));
1269  exit(1);
1270  }
1271  else if (pid < 0) /* standalone backend, not postmaster */
1272  {
1273  pid = -pid;
1274  write_stderr(_("%s: cannot rotate log file; "
1275  "single-user server is running (PID: %d)\n"),
1276  progname, (int) pid);
1277  exit(1);
1278  }
1279 
1280  snprintf(logrotate_file, MAXPGPATH, "%s/logrotate", pg_data);
1281 
1282  if ((logrotatefile = fopen(logrotate_file, "w")) == NULL)
1283  {
1284  write_stderr(_("%s: could not create log rotation signal file \"%s\": %s\n"),
1285  progname, logrotate_file, strerror(errno));
1286  exit(1);
1287  }
1288  if (fclose(logrotatefile))
1289  {
1290  write_stderr(_("%s: could not write log rotation signal file \"%s\": %s\n"),
1291  progname, logrotate_file, strerror(errno));
1292  exit(1);
1293  }
1294 
1295  sig = SIGUSR1;
1296  if (kill(pid, sig) != 0)
1297  {
1298  write_stderr(_("%s: could not send log rotation signal (PID: %d): %s\n"),
1299  progname, (int) pid, strerror(errno));
1300  if (unlink(logrotate_file) != 0)
1301  write_stderr(_("%s: could not remove log rotation signal file \"%s\": %s\n"),
1302  progname, logrotate_file, strerror(errno));
1303  exit(1);
1304  }
1305 
1306  print_msg(_("server signaled to rotate log file\n"));
1307 }
1308 
1309 
1310 /*
1311  * utility routines
1312  */
1313 
1314 static bool
1316 {
1317  /*
1318  * Test to see if the process is still there. Note that we do not
1319  * consider an EPERM failure to mean that the process is still there;
1320  * EPERM must mean that the given PID belongs to some other userid, and
1321  * considering the permissions on $PGDATA, that means it's not the
1322  * postmaster we are after.
1323  *
1324  * Don't believe that our own PID or parent shell's PID is the postmaster,
1325  * either. (Windows hasn't got getppid(), though.)
1326  */
1327  if (pid == getpid())
1328  return false;
1329 #ifndef WIN32
1330  if (pid == getppid())
1331  return false;
1332 #endif
1333  if (kill(pid, 0) == 0)
1334  return true;
1335  return false;
1336 }
1337 
1338 static void
1340 {
1341  pid_t pid;
1342 
1343  pid = get_pgpid(true);
1344  /* Is there a pid file? */
1345  if (pid != 0)
1346  {
1347  /* standalone backend? */
1348  if (pid < 0)
1349  {
1350  pid = -pid;
1351  if (postmaster_is_alive(pid))
1352  {
1353  printf(_("%s: single-user server is running (PID: %d)\n"),
1354  progname, (int) pid);
1355  return;
1356  }
1357  }
1358  else
1359  /* must be a postmaster */
1360  {
1361  if (postmaster_is_alive(pid))
1362  {
1363  char **optlines;
1364  char **curr_line;
1365  int numlines;
1366 
1367  printf(_("%s: server is running (PID: %d)\n"),
1368  progname, (int) pid);
1369 
1370  optlines = readfile(postopts_file, &numlines);
1371  if (optlines != NULL)
1372  {
1373  for (curr_line = optlines; *curr_line != NULL; curr_line++)
1374  puts(*curr_line);
1375 
1376  /* Free the results of readfile */
1377  free_readfile(optlines);
1378  }
1379  return;
1380  }
1381  }
1382  }
1383  printf(_("%s: no server running\n"), progname);
1384 
1385  /*
1386  * The Linux Standard Base Core Specification 3.1 says this should return
1387  * '3, program is not running'
1388  * https://refspecs.linuxbase.org/LSB_3.1.0/LSB-Core-generic/LSB-Core-generic/iniscrptact.html
1389  */
1390  exit(3);
1391 }
1392 
1393 
1394 
1395 static void
1396 do_kill(pid_t pid)
1397 {
1398  if (kill(pid, sig) != 0)
1399  {
1400  write_stderr(_("%s: could not send signal %d (PID: %d): %s\n"),
1401  progname, sig, (int) pid, strerror(errno));
1402  exit(1);
1403  }
1404 }
1405 
1406 #ifdef WIN32
1407 
1408 static bool
1409 pgwin32_IsInstalled(SC_HANDLE hSCM)
1410 {
1411  SC_HANDLE hService = OpenService(hSCM, register_servicename, SERVICE_QUERY_CONFIG);
1412  bool bResult = (hService != NULL);
1413 
1414  if (bResult)
1415  CloseServiceHandle(hService);
1416  return bResult;
1417 }
1418 
1419 static char *
1420 pgwin32_CommandLine(bool registration)
1421 {
1422  PQExpBuffer cmdLine = createPQExpBuffer();
1423  char cmdPath[MAXPGPATH];
1424  int ret;
1425 
1426  if (registration)
1427  {
1428  ret = find_my_exec(argv0, cmdPath);
1429  if (ret != 0)
1430  {
1431  write_stderr(_("%s: could not find own program executable\n"), progname);
1432  exit(1);
1433  }
1434  }
1435  else
1436  {
1437  ret = find_other_exec(argv0, "postgres", PG_BACKEND_VERSIONSTR,
1438  cmdPath);
1439  if (ret != 0)
1440  {
1441  write_stderr(_("%s: could not find postgres program executable\n"), progname);
1442  exit(1);
1443  }
1444  }
1445 
1446  /* if path does not end in .exe, append it */
1447  if (strlen(cmdPath) < 4 ||
1448  pg_strcasecmp(cmdPath + strlen(cmdPath) - 4, ".exe") != 0)
1449  snprintf(cmdPath + strlen(cmdPath), sizeof(cmdPath) - strlen(cmdPath),
1450  ".exe");
1451 
1452  /* use backslashes in path to avoid problems with some third-party tools */
1453  make_native_path(cmdPath);
1454 
1455  /* be sure to double-quote the executable's name in the command */
1456  appendPQExpBuffer(cmdLine, "\"%s\"", cmdPath);
1457 
1458  /* append assorted switches to the command line, as needed */
1459 
1460  if (registration)
1461  appendPQExpBuffer(cmdLine, " runservice -N \"%s\"",
1463 
1464  if (pg_config)
1465  {
1466  /* We need the -D path to be absolute */
1467  char *dataDir;
1468 
1469  if ((dataDir = make_absolute_path(pg_config)) == NULL)
1470  {
1471  /* make_absolute_path already reported the error */
1472  exit(1);
1473  }
1474  make_native_path(dataDir);
1475  appendPQExpBuffer(cmdLine, " -D \"%s\"", dataDir);
1476  free(dataDir);
1477  }
1478 
1479  if (registration && event_source != NULL)
1480  appendPQExpBuffer(cmdLine, " -e \"%s\"", event_source);
1481 
1482  if (registration && do_wait)
1483  appendPQExpBufferStr(cmdLine, " -w");
1484 
1485  /* Don't propagate a value from an environment variable. */
1486  if (registration && wait_seconds_arg && wait_seconds != DEFAULT_WAIT)
1487  appendPQExpBuffer(cmdLine, " -t %d", wait_seconds);
1488 
1489  if (registration && silent_mode)
1490  appendPQExpBufferStr(cmdLine, " -s");
1491 
1492  if (post_opts)
1493  {
1494  if (registration)
1495  appendPQExpBuffer(cmdLine, " -o \"%s\"", post_opts);
1496  else
1497  appendPQExpBuffer(cmdLine, " %s", post_opts);
1498  }
1499 
1500  return cmdLine->data;
1501 }
1502 
1503 static void
1504 pgwin32_doRegister(void)
1505 {
1506  SC_HANDLE hService;
1507  SC_HANDLE hSCM = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS);
1508 
1509  if (hSCM == NULL)
1510  {
1511  write_stderr(_("%s: could not open service manager\n"), progname);
1512  exit(1);
1513  }
1514  if (pgwin32_IsInstalled(hSCM))
1515  {
1516  CloseServiceHandle(hSCM);
1517  write_stderr(_("%s: service \"%s\" already registered\n"), progname, register_servicename);
1518  exit(1);
1519  }
1520 
1521  if ((hService = CreateService(hSCM, register_servicename, register_servicename,
1522  SERVICE_ALL_ACCESS, SERVICE_WIN32_OWN_PROCESS,
1523  pgctl_start_type, SERVICE_ERROR_NORMAL,
1524  pgwin32_CommandLine(true),
1525  NULL, NULL, "RPCSS\0", register_username, register_password)) == NULL)
1526  {
1527  CloseServiceHandle(hSCM);
1528  write_stderr(_("%s: could not register service \"%s\": error code %lu\n"),
1530  (unsigned long) GetLastError());
1531  exit(1);
1532  }
1533  CloseServiceHandle(hService);
1534  CloseServiceHandle(hSCM);
1535 }
1536 
1537 static void
1538 pgwin32_doUnregister(void)
1539 {
1540  SC_HANDLE hService;
1541  SC_HANDLE hSCM = OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS);
1542 
1543  if (hSCM == NULL)
1544  {
1545  write_stderr(_("%s: could not open service manager\n"), progname);
1546  exit(1);
1547  }
1548  if (!pgwin32_IsInstalled(hSCM))
1549  {
1550  CloseServiceHandle(hSCM);
1551  write_stderr(_("%s: service \"%s\" not registered\n"), progname, register_servicename);
1552  exit(1);
1553  }
1554 
1555  if ((hService = OpenService(hSCM, register_servicename, DELETE)) == NULL)
1556  {
1557  CloseServiceHandle(hSCM);
1558  write_stderr(_("%s: could not open service \"%s\": error code %lu\n"),
1560  (unsigned long) GetLastError());
1561  exit(1);
1562  }
1563  if (!DeleteService(hService))
1564  {
1565  CloseServiceHandle(hService);
1566  CloseServiceHandle(hSCM);
1567  write_stderr(_("%s: could not unregister service \"%s\": error code %lu\n"),
1569  (unsigned long) GetLastError());
1570  exit(1);
1571  }
1572  CloseServiceHandle(hService);
1573  CloseServiceHandle(hSCM);
1574 }
1575 
1576 static void
1577 pgwin32_SetServiceStatus(DWORD currentState)
1578 {
1579  status.dwCurrentState = currentState;
1580  SetServiceStatus(hStatus, (LPSERVICE_STATUS) &status);
1581 }
1582 
1583 static void WINAPI
1584 pgwin32_ServiceHandler(DWORD request)
1585 {
1586  switch (request)
1587  {
1588  case SERVICE_CONTROL_STOP:
1589  case SERVICE_CONTROL_SHUTDOWN:
1590 
1591  /*
1592  * We only need a short wait hint here as it just needs to wait
1593  * for the next checkpoint. They occur every 5 seconds during
1594  * shutdown
1595  */
1596  status.dwWaitHint = 10000;
1597  pgwin32_SetServiceStatus(SERVICE_STOP_PENDING);
1598  SetEvent(shutdownEvent);
1599  return;
1600 
1601  case SERVICE_CONTROL_PAUSE:
1602  /* Win32 config reloading */
1603  status.dwWaitHint = 5000;
1605  return;
1606 
1607  /* FIXME: These could be used to replace other signals etc */
1608  case SERVICE_CONTROL_CONTINUE:
1609  case SERVICE_CONTROL_INTERROGATE:
1610  default:
1611  break;
1612  }
1613 }
1614 
1615 static void WINAPI
1616 pgwin32_ServiceMain(DWORD argc, LPTSTR *argv)
1617 {
1618  PROCESS_INFORMATION pi;
1619  DWORD ret;
1620 
1621  /* Initialize variables */
1622  status.dwWin32ExitCode = S_OK;
1623  status.dwCheckPoint = 0;
1624  status.dwWaitHint = 60000;
1625  status.dwServiceType = SERVICE_WIN32_OWN_PROCESS;
1626  status.dwControlsAccepted = SERVICE_ACCEPT_STOP | SERVICE_ACCEPT_SHUTDOWN | SERVICE_ACCEPT_PAUSE_CONTINUE;
1627  status.dwServiceSpecificExitCode = 0;
1628  status.dwCurrentState = SERVICE_START_PENDING;
1629 
1630  memset(&pi, 0, sizeof(pi));
1631 
1632  read_post_opts();
1633 
1634  /* Register the control request handler */
1635  if ((hStatus = RegisterServiceCtrlHandler(register_servicename, pgwin32_ServiceHandler)) == (SERVICE_STATUS_HANDLE) 0)
1636  return;
1637 
1638  if ((shutdownEvent = CreateEvent(NULL, true, false, NULL)) == NULL)
1639  return;
1640 
1641  /* Start the postmaster */
1642  pgwin32_SetServiceStatus(SERVICE_START_PENDING);
1643  if (!CreateRestrictedProcess(pgwin32_CommandLine(false), &pi, true))
1644  {
1645  pgwin32_SetServiceStatus(SERVICE_STOPPED);
1646  return;
1647  }
1648  postmasterPID = pi.dwProcessId;
1649  postmasterProcess = pi.hProcess;
1650  CloseHandle(pi.hThread);
1651 
1652  if (do_wait)
1653  {
1654  write_eventlog(EVENTLOG_INFORMATION_TYPE, _("Waiting for server startup...\n"));
1656  {
1657  write_eventlog(EVENTLOG_ERROR_TYPE, _("Timed out waiting for server startup\n"));
1658  pgwin32_SetServiceStatus(SERVICE_STOPPED);
1659  return;
1660  }
1661  write_eventlog(EVENTLOG_INFORMATION_TYPE, _("Server started and accepting connections\n"));
1662  }
1663 
1664  pgwin32_SetServiceStatus(SERVICE_RUNNING);
1665 
1666  /* Wait for quit... */
1667  ret = WaitForMultipleObjects(2, shutdownHandles, FALSE, INFINITE);
1668 
1669  pgwin32_SetServiceStatus(SERVICE_STOP_PENDING);
1670  switch (ret)
1671  {
1672  case WAIT_OBJECT_0: /* shutdown event */
1673  {
1674  /*
1675  * status.dwCheckPoint can be incremented by
1676  * wait_for_postmaster_start(), so it might not start from 0.
1677  */
1678  int maxShutdownCheckPoint = status.dwCheckPoint + 12;
1679 
1680  kill(postmasterPID, SIGINT);
1681 
1682  /*
1683  * Increment the checkpoint and try again. Abort after 12
1684  * checkpoints as the postmaster has probably hung.
1685  */
1686  while (WaitForSingleObject(postmasterProcess, 5000) == WAIT_TIMEOUT && status.dwCheckPoint < maxShutdownCheckPoint)
1687  {
1688  status.dwCheckPoint++;
1689  SetServiceStatus(hStatus, (LPSERVICE_STATUS) &status);
1690  }
1691  break;
1692  }
1693 
1694  case (WAIT_OBJECT_0 + 1): /* postmaster went down */
1695  break;
1696 
1697  default:
1698  /* shouldn't get here? */
1699  break;
1700  }
1701 
1702  CloseHandle(shutdownEvent);
1703  CloseHandle(postmasterProcess);
1704 
1705  pgwin32_SetServiceStatus(SERVICE_STOPPED);
1706 }
1707 
1708 static void
1709 pgwin32_doRunAsService(void)
1710 {
1711  SERVICE_TABLE_ENTRY st[] = {{register_servicename, pgwin32_ServiceMain},
1712  {NULL, NULL}};
1713 
1714  if (StartServiceCtrlDispatcher(st) == 0)
1715  {
1716  write_stderr(_("%s: could not start service \"%s\": error code %lu\n"),
1718  (unsigned long) GetLastError());
1719  exit(1);
1720  }
1721 }
1722 
1723 
1724 /*
1725  * Set up STARTUPINFO for the new process to inherit this process' handles.
1726  *
1727  * Process started as services appear to have "empty" handles (GetStdHandle()
1728  * returns NULL) rather than invalid ones. But passing down NULL ourselves
1729  * doesn't work, it's interpreted as STARTUPINFO->hStd* not being set. But we
1730  * can pass down INVALID_HANDLE_VALUE - which makes GetStdHandle() in the new
1731  * process (and its child processes!) return INVALID_HANDLE_VALUE. Which
1732  * achieves the goal of postmaster running in a similar environment as pg_ctl.
1733  */
1734 static void
1735 InheritStdHandles(STARTUPINFO *si)
1736 {
1737  si->dwFlags |= STARTF_USESTDHANDLES;
1738  si->hStdInput = GetStdHandle(STD_INPUT_HANDLE);
1739  if (si->hStdInput == NULL)
1740  si->hStdInput = INVALID_HANDLE_VALUE;
1741  si->hStdOutput = GetStdHandle(STD_OUTPUT_HANDLE);
1742  if (si->hStdOutput == NULL)
1743  si->hStdOutput = INVALID_HANDLE_VALUE;
1744  si->hStdError = GetStdHandle(STD_ERROR_HANDLE);
1745  if (si->hStdError == NULL)
1746  si->hStdError = INVALID_HANDLE_VALUE;
1747 }
1748 
1749 /*
1750  * Create a restricted token, a job object sandbox, and execute the specified
1751  * process with it.
1752  *
1753  * Returns 0 on success, non-zero on failure, same as CreateProcess().
1754  *
1755  * NOTE! Job object will only work when running as a service, because it's
1756  * automatically destroyed when pg_ctl exits.
1757  */
1758 static int
1759 CreateRestrictedProcess(char *cmd, PROCESS_INFORMATION *processInfo, bool as_service)
1760 {
1761  int r;
1762  BOOL b;
1763  STARTUPINFO si;
1764  HANDLE origToken;
1765  HANDLE restrictedToken;
1766  BOOL inJob;
1767  SID_IDENTIFIER_AUTHORITY NtAuthority = {SECURITY_NT_AUTHORITY};
1768  SID_AND_ATTRIBUTES dropSids[2];
1769  PTOKEN_PRIVILEGES delPrivs;
1770 
1771  ZeroMemory(&si, sizeof(si));
1772  si.cb = sizeof(si);
1773 
1774  /*
1775  * Set stdin/stdout/stderr handles to be inherited in the child process.
1776  * That allows postmaster and the processes it starts to perform
1777  * additional checks to see if running in a service (otherwise they get
1778  * the default console handles - which point to "somewhere").
1779  */
1780  InheritStdHandles(&si);
1781 
1782  /* Open the current token to use as a base for the restricted one */
1783  if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ALL_ACCESS, &origToken))
1784  {
1785  /*
1786  * Most Windows targets make DWORD a 32-bit unsigned long, but in case
1787  * it doesn't cast DWORD before printing.
1788  */
1789  write_stderr(_("%s: could not open process token: error code %lu\n"),
1790  progname, (unsigned long) GetLastError());
1791  return 0;
1792  }
1793 
1794  /* Allocate list of SIDs to remove */
1795  ZeroMemory(&dropSids, sizeof(dropSids));
1796  if (!AllocateAndInitializeSid(&NtAuthority, 2,
1797  SECURITY_BUILTIN_DOMAIN_RID, DOMAIN_ALIAS_RID_ADMINS, 0, 0, 0, 0, 0,
1798  0, &dropSids[0].Sid) ||
1799  !AllocateAndInitializeSid(&NtAuthority, 2,
1800  SECURITY_BUILTIN_DOMAIN_RID, DOMAIN_ALIAS_RID_POWER_USERS, 0, 0, 0, 0, 0,
1801  0, &dropSids[1].Sid))
1802  {
1803  write_stderr(_("%s: could not allocate SIDs: error code %lu\n"),
1804  progname, (unsigned long) GetLastError());
1805  return 0;
1806  }
1807 
1808  /* Get list of privileges to remove */
1809  delPrivs = GetPrivilegesToDelete(origToken);
1810  if (delPrivs == NULL)
1811  /* Error message already printed */
1812  return 0;
1813 
1814  b = CreateRestrictedToken(origToken,
1815  0,
1816  sizeof(dropSids) / sizeof(dropSids[0]),
1817  dropSids,
1818  delPrivs->PrivilegeCount, delPrivs->Privileges,
1819  0, NULL,
1820  &restrictedToken);
1821 
1822  free(delPrivs);
1823  FreeSid(dropSids[1].Sid);
1824  FreeSid(dropSids[0].Sid);
1825  CloseHandle(origToken);
1826 
1827  if (!b)
1828  {
1829  write_stderr(_("%s: could not create restricted token: error code %lu\n"),
1830  progname, (unsigned long) GetLastError());
1831  return 0;
1832  }
1833 
1834  AddUserToTokenDacl(restrictedToken);
1835  r = CreateProcessAsUser(restrictedToken, NULL, cmd, NULL, NULL, TRUE, CREATE_SUSPENDED, NULL, NULL, &si, processInfo);
1836 
1837  if (IsProcessInJob(processInfo->hProcess, NULL, &inJob))
1838  {
1839  if (!inJob)
1840  {
1841  /*
1842  * Job objects are working, and the new process isn't in one, so
1843  * we can create one safely. If any problems show up when setting
1844  * it, we're going to ignore them.
1845  */
1846  HANDLE job;
1847  char jobname[128];
1848 
1849  sprintf(jobname, "PostgreSQL_%lu",
1850  (unsigned long) processInfo->dwProcessId);
1851 
1852  job = CreateJobObject(NULL, jobname);
1853  if (job)
1854  {
1855  JOBOBJECT_BASIC_LIMIT_INFORMATION basicLimit;
1856  JOBOBJECT_BASIC_UI_RESTRICTIONS uiRestrictions;
1857  JOBOBJECT_SECURITY_LIMIT_INFORMATION securityLimit;
1858 
1859  ZeroMemory(&basicLimit, sizeof(basicLimit));
1860  ZeroMemory(&uiRestrictions, sizeof(uiRestrictions));
1861  ZeroMemory(&securityLimit, sizeof(securityLimit));
1862 
1863  basicLimit.LimitFlags = JOB_OBJECT_LIMIT_DIE_ON_UNHANDLED_EXCEPTION | JOB_OBJECT_LIMIT_PRIORITY_CLASS;
1864  basicLimit.PriorityClass = NORMAL_PRIORITY_CLASS;
1865  SetInformationJobObject(job, JobObjectBasicLimitInformation, &basicLimit, sizeof(basicLimit));
1866 
1867  uiRestrictions.UIRestrictionsClass = JOB_OBJECT_UILIMIT_DESKTOP | JOB_OBJECT_UILIMIT_DISPLAYSETTINGS |
1868  JOB_OBJECT_UILIMIT_EXITWINDOWS | JOB_OBJECT_UILIMIT_READCLIPBOARD |
1869  JOB_OBJECT_UILIMIT_SYSTEMPARAMETERS | JOB_OBJECT_UILIMIT_WRITECLIPBOARD;
1870 
1871  SetInformationJobObject(job, JobObjectBasicUIRestrictions, &uiRestrictions, sizeof(uiRestrictions));
1872 
1873  securityLimit.SecurityLimitFlags = JOB_OBJECT_SECURITY_NO_ADMIN | JOB_OBJECT_SECURITY_ONLY_TOKEN;
1874  securityLimit.JobToken = restrictedToken;
1875  SetInformationJobObject(job, JobObjectSecurityLimitInformation, &securityLimit, sizeof(securityLimit));
1876 
1877  AssignProcessToJobObject(job, processInfo->hProcess);
1878  }
1879  }
1880  }
1881 
1882  CloseHandle(restrictedToken);
1883 
1884  ResumeThread(processInfo->hThread);
1885 
1886  /*
1887  * We intentionally don't close the job object handle, because we want the
1888  * object to live on until pg_ctl shuts down.
1889  */
1890  return r;
1891 }
1892 
1893 /*
1894  * Get a list of privileges to delete from the access token. We delete all privileges
1895  * except SeLockMemoryPrivilege which is needed to use large pages, and
1896  * SeChangeNotifyPrivilege which is enabled by default in DISABLE_MAX_PRIVILEGE.
1897  */
1898 static PTOKEN_PRIVILEGES
1899 GetPrivilegesToDelete(HANDLE hToken)
1900 {
1901  int i,
1902  j;
1903  DWORD length;
1904  PTOKEN_PRIVILEGES tokenPrivs;
1905  LUID luidLockPages;
1906  LUID luidChangeNotify;
1907 
1908  if (!LookupPrivilegeValue(NULL, SE_LOCK_MEMORY_NAME, &luidLockPages) ||
1909  !LookupPrivilegeValue(NULL, SE_CHANGE_NOTIFY_NAME, &luidChangeNotify))
1910  {
1911  write_stderr(_("%s: could not get LUIDs for privileges: error code %lu\n"),
1912  progname, (unsigned long) GetLastError());
1913  return NULL;
1914  }
1915 
1916  if (!GetTokenInformation(hToken, TokenPrivileges, NULL, 0, &length) &&
1917  GetLastError() != ERROR_INSUFFICIENT_BUFFER)
1918  {
1919  write_stderr(_("%s: could not get token information: error code %lu\n"),
1920  progname, (unsigned long) GetLastError());
1921  return NULL;
1922  }
1923 
1924  tokenPrivs = (PTOKEN_PRIVILEGES) pg_malloc_extended(length,
1926  if (tokenPrivs == NULL)
1927  {
1928  write_stderr(_("%s: out of memory\n"), progname);
1929  return NULL;
1930  }
1931 
1932  if (!GetTokenInformation(hToken, TokenPrivileges, tokenPrivs, length, &length))
1933  {
1934  write_stderr(_("%s: could not get token information: error code %lu\n"),
1935  progname, (unsigned long) GetLastError());
1936  free(tokenPrivs);
1937  return NULL;
1938  }
1939 
1940  for (i = 0; i < tokenPrivs->PrivilegeCount; i++)
1941  {
1942  if (memcmp(&tokenPrivs->Privileges[i].Luid, &luidLockPages, sizeof(LUID)) == 0 ||
1943  memcmp(&tokenPrivs->Privileges[i].Luid, &luidChangeNotify, sizeof(LUID)) == 0)
1944  {
1945  for (j = i; j < tokenPrivs->PrivilegeCount - 1; j++)
1946  tokenPrivs->Privileges[j] = tokenPrivs->Privileges[j + 1];
1947  tokenPrivs->PrivilegeCount--;
1948  }
1949  }
1950 
1951  return tokenPrivs;
1952 }
1953 #endif /* WIN32 */
1954 
1955 static void
1957 {
1958  write_stderr(_("Try \"%s --help\" for more information.\n"), progname);
1959 }
1960 
1961 
1962 
1963 static void
1964 do_help(void)
1965 {
1966  printf(_("%s is a utility to initialize, start, stop, or control a PostgreSQL server.\n\n"), progname);
1967  printf(_("Usage:\n"));
1968  printf(_(" %s init[db] [-D DATADIR] [-s] [-o OPTIONS]\n"), progname);
1969  printf(_(" %s start [-D DATADIR] [-l FILENAME] [-W] [-t SECS] [-s]\n"
1970  " [-o OPTIONS] [-p PATH] [-c]\n"), progname);
1971  printf(_(" %s stop [-D DATADIR] [-m SHUTDOWN-MODE] [-W] [-t SECS] [-s]\n"), progname);
1972  printf(_(" %s restart [-D DATADIR] [-m SHUTDOWN-MODE] [-W] [-t SECS] [-s]\n"
1973  " [-o OPTIONS] [-c]\n"), progname);
1974  printf(_(" %s reload [-D DATADIR] [-s]\n"), progname);
1975  printf(_(" %s status [-D DATADIR]\n"), progname);
1976  printf(_(" %s promote [-D DATADIR] [-W] [-t SECS] [-s]\n"), progname);
1977  printf(_(" %s logrotate [-D DATADIR] [-s]\n"), progname);
1978  printf(_(" %s kill SIGNALNAME PID\n"), progname);
1979 #ifdef WIN32
1980  printf(_(" %s register [-D DATADIR] [-N SERVICENAME] [-U USERNAME] [-P PASSWORD]\n"
1981  " [-S START-TYPE] [-e SOURCE] [-W] [-t SECS] [-s] [-o OPTIONS]\n"), progname);
1982  printf(_(" %s unregister [-N SERVICENAME]\n"), progname);
1983 #endif
1984 
1985  printf(_("\nCommon options:\n"));
1986  printf(_(" -D, --pgdata=DATADIR location of the database storage area\n"));
1987 #ifdef WIN32
1988  printf(_(" -e SOURCE event source for logging when running as a service\n"));
1989 #endif
1990  printf(_(" -s, --silent only print errors, no informational messages\n"));
1991  printf(_(" -t, --timeout=SECS seconds to wait when using -w option\n"));
1992  printf(_(" -V, --version output version information, then exit\n"));
1993  printf(_(" -w, --wait wait until operation completes (default)\n"));
1994  printf(_(" -W, --no-wait do not wait until operation completes\n"));
1995  printf(_(" -?, --help show this help, then exit\n"));
1996  printf(_("If the -D option is omitted, the environment variable PGDATA is used.\n"));
1997 
1998  printf(_("\nOptions for start or restart:\n"));
1999 #if defined(HAVE_GETRLIMIT)
2000  printf(_(" -c, --core-files allow postgres to produce core files\n"));
2001 #else
2002  printf(_(" -c, --core-files not applicable on this platform\n"));
2003 #endif
2004  printf(_(" -l, --log=FILENAME write (or append) server log to FILENAME\n"));
2005  printf(_(" -o, --options=OPTIONS command line options to pass to postgres\n"
2006  " (PostgreSQL server executable) or initdb\n"));
2007  printf(_(" -p PATH-TO-POSTGRES normally not necessary\n"));
2008  printf(_("\nOptions for stop or restart:\n"));
2009  printf(_(" -m, --mode=MODE MODE can be \"smart\", \"fast\", or \"immediate\"\n"));
2010 
2011  printf(_("\nShutdown modes are:\n"));
2012  printf(_(" smart quit after all clients have disconnected\n"));
2013  printf(_(" fast quit directly, with proper shutdown (default)\n"));
2014  printf(_(" immediate quit without complete shutdown; will lead to recovery on restart\n"));
2015 
2016  printf(_("\nAllowed signal names for kill:\n"));
2017  printf(" ABRT HUP INT KILL QUIT TERM USR1 USR2\n");
2018 
2019 #ifdef WIN32
2020  printf(_("\nOptions for register and unregister:\n"));
2021  printf(_(" -N SERVICENAME service name with which to register PostgreSQL server\n"));
2022  printf(_(" -P PASSWORD password of account to register PostgreSQL server\n"));
2023  printf(_(" -U USERNAME user name of account to register PostgreSQL server\n"));
2024  printf(_(" -S START-TYPE service start type to register PostgreSQL server\n"));
2025 
2026  printf(_("\nStart types are:\n"));
2027  printf(_(" auto start service automatically during system startup (default)\n"));
2028  printf(_(" demand start service on demand\n"));
2029 #endif
2030 
2031  printf(_("\nReport bugs to <%s>.\n"), PACKAGE_BUGREPORT);
2032  printf(_("%s home page: <%s>\n"), PACKAGE_NAME, PACKAGE_URL);
2033 }
2034 
2035 
2036 
2037 static void
2038 set_mode(char *modeopt)
2039 {
2040  if (strcmp(modeopt, "s") == 0 || strcmp(modeopt, "smart") == 0)
2041  {
2043  sig = SIGTERM;
2044  }
2045  else if (strcmp(modeopt, "f") == 0 || strcmp(modeopt, "fast") == 0)
2046  {
2048  sig = SIGINT;
2049  }
2050  else if (strcmp(modeopt, "i") == 0 || strcmp(modeopt, "immediate") == 0)
2051  {
2053  sig = SIGQUIT;
2054  }
2055  else
2056  {
2057  write_stderr(_("%s: unrecognized shutdown mode \"%s\"\n"), progname, modeopt);
2058  do_advice();
2059  exit(1);
2060  }
2061 }
2062 
2063 
2064 
2065 static void
2066 set_sig(char *signame)
2067 {
2068  if (strcmp(signame, "HUP") == 0)
2069  sig = SIGHUP;
2070  else if (strcmp(signame, "INT") == 0)
2071  sig = SIGINT;
2072  else if (strcmp(signame, "QUIT") == 0)
2073  sig = SIGQUIT;
2074  else if (strcmp(signame, "ABRT") == 0)
2075  sig = SIGABRT;
2076  else if (strcmp(signame, "KILL") == 0)
2077  sig = SIGKILL;
2078  else if (strcmp(signame, "TERM") == 0)
2079  sig = SIGTERM;
2080  else if (strcmp(signame, "USR1") == 0)
2081  sig = SIGUSR1;
2082  else if (strcmp(signame, "USR2") == 0)
2083  sig = SIGUSR2;
2084  else
2085  {
2086  write_stderr(_("%s: unrecognized signal name \"%s\"\n"), progname, signame);
2087  do_advice();
2088  exit(1);
2089  }
2090 }
2091 
2092 
2093 #ifdef WIN32
2094 static void
2095 set_starttype(char *starttypeopt)
2096 {
2097  if (strcmp(starttypeopt, "a") == 0 || strcmp(starttypeopt, "auto") == 0)
2098  pgctl_start_type = SERVICE_AUTO_START;
2099  else if (strcmp(starttypeopt, "d") == 0 || strcmp(starttypeopt, "demand") == 0)
2100  pgctl_start_type = SERVICE_DEMAND_START;
2101  else
2102  {
2103  write_stderr(_("%s: unrecognized start type \"%s\"\n"), progname, starttypeopt);
2104  do_advice();
2105  exit(1);
2106  }
2107 }
2108 #endif
2109 
2110 /*
2111  * adjust_data_dir
2112  *
2113  * If a configuration-only directory was specified, find the real data dir.
2114  */
2115 static void
2117 {
2118  char filename[MAXPGPATH];
2119  char *my_exec_path,
2120  *cmd;
2121  FILE *fd;
2122 
2123  /* do nothing if we're working without knowledge of data dir */
2124  if (pg_config == NULL)
2125  return;
2126 
2127  /* If there is no postgresql.conf, it can't be a config-only dir */
2128  snprintf(filename, sizeof(filename), "%s/postgresql.conf", pg_config);
2129  if ((fd = fopen(filename, "r")) == NULL)
2130  return;
2131  fclose(fd);
2132 
2133  /* If PG_VERSION exists, it can't be a config-only dir */
2134  snprintf(filename, sizeof(filename), "%s/PG_VERSION", pg_config);
2135  if ((fd = fopen(filename, "r")) != NULL)
2136  {
2137  fclose(fd);
2138  return;
2139  }
2140 
2141  /* Must be a configuration directory, so find the data directory */
2142 
2143  /* we use a private my_exec_path to avoid interfering with later uses */
2144  if (exec_path == NULL)
2146  else
2148 
2149  /* it's important for -C to be the first option, see main.c */
2150  cmd = psprintf("\"%s\" -C data_directory %s%s",
2151  my_exec_path,
2152  pgdata_opt ? pgdata_opt : "",
2153  post_opts ? post_opts : "");
2154  fflush(NULL);
2155 
2156  fd = popen(cmd, "r");
2157  if (fd == NULL || fgets(filename, sizeof(filename), fd) == NULL || pclose(fd) != 0)
2158  {
2159  write_stderr(_("%s: could not determine the data directory using command \"%s\"\n"), progname, cmd);
2160  exit(1);
2161  }
2162  free(my_exec_path);
2163 
2164  /* strip trailing newline and carriage return */
2165  (void) pg_strip_crlf(filename);
2166 
2167  free(pg_data);
2170 }
2171 
2172 
2173 static DBState
2175 {
2176  DBState ret;
2177  bool crc_ok;
2178  ControlFileData *control_file_data = get_controlfile(pg_data, &crc_ok);
2179 
2180  if (!crc_ok)
2181  {
2182  write_stderr(_("%s: control file appears to be corrupt\n"), progname);
2183  exit(1);
2184  }
2185 
2186  ret = control_file_data->state;
2187  pfree(control_file_data);
2188  return ret;
2189 }
2190 
2191 
2192 int
2193 main(int argc, char **argv)
2194 {
2195  static struct option long_options[] = {
2196  {"help", no_argument, NULL, '?'},
2197  {"version", no_argument, NULL, 'V'},
2198  {"log", required_argument, NULL, 'l'},
2199  {"mode", required_argument, NULL, 'm'},
2200  {"pgdata", required_argument, NULL, 'D'},
2201  {"options", required_argument, NULL, 'o'},
2202  {"silent", no_argument, NULL, 's'},
2203  {"timeout", required_argument, NULL, 't'},
2204  {"core-files", no_argument, NULL, 'c'},
2205  {"wait", no_argument, NULL, 'w'},
2206  {"no-wait", no_argument, NULL, 'W'},
2207  {NULL, 0, NULL, 0}
2208  };
2209 
2210  char *env_wait;
2211  int option_index;
2212  int c;
2213  pid_t killproc = 0;
2214 
2215  pg_logging_init(argv[0]);
2216  progname = get_progname(argv[0]);
2217  set_pglocale_pgservice(argv[0], PG_TEXTDOMAIN("pg_ctl"));
2218  start_time = time(NULL);
2219 
2220  /*
2221  * save argv[0] so do_start() can look for the postmaster if necessary. we
2222  * don't look for postmaster here because in many cases we won't need it.
2223  */
2224  argv0 = argv[0];
2225 
2226  /* Set restrictive mode mask until PGDATA permissions are checked */
2227  umask(PG_MODE_MASK_OWNER);
2228 
2229  /* support --help and --version even if invoked as root */
2230  if (argc > 1)
2231  {
2232  if (strcmp(argv[1], "--help") == 0 || strcmp(argv[1], "-?") == 0)
2233  {
2234  do_help();
2235  exit(0);
2236  }
2237  else if (strcmp(argv[1], "--version") == 0 || strcmp(argv[1], "-V") == 0)
2238  {
2239  puts("pg_ctl (PostgreSQL) " PG_VERSION);
2240  exit(0);
2241  }
2242  }
2243 
2244  /*
2245  * Disallow running as root, to forestall any possible security holes.
2246  */
2247 #ifndef WIN32
2248  if (geteuid() == 0)
2249  {
2250  write_stderr(_("%s: cannot be run as root\n"
2251  "Please log in (using, e.g., \"su\") as the "
2252  "(unprivileged) user that will\n"
2253  "own the server process.\n"),
2254  progname);
2255  exit(1);
2256  }
2257 #endif
2258 
2259  env_wait = getenv("PGCTLTIMEOUT");
2260  if (env_wait != NULL)
2261  wait_seconds = atoi(env_wait);
2262 
2263  /* process command-line options */
2264  while ((c = getopt_long(argc, argv, "cD:e:l:m:N:o:p:P:sS:t:U:wW",
2265  long_options, &option_index)) != -1)
2266  {
2267  switch (c)
2268  {
2269  case 'D':
2270  {
2271  char *pgdata_D;
2272 
2273  pgdata_D = pg_strdup(optarg);
2274  canonicalize_path(pgdata_D);
2275  setenv("PGDATA", pgdata_D, 1);
2276 
2277  /*
2278  * We could pass PGDATA just in an environment variable
2279  * but we do -D too for clearer postmaster 'ps' display
2280  */
2281  pgdata_opt = psprintf("-D \"%s\" ", pgdata_D);
2282  free(pgdata_D);
2283  break;
2284  }
2285  case 'e':
2287  break;
2288  case 'l':
2290  break;
2291  case 'm':
2292  set_mode(optarg);
2293  break;
2294  case 'N':
2296  break;
2297  case 'o':
2298  /* append option? */
2299  if (!post_opts)
2301  else
2302  {
2303  char *old_post_opts = post_opts;
2304 
2305  post_opts = psprintf("%s %s", old_post_opts, optarg);
2306  free(old_post_opts);
2307  }
2308  break;
2309  case 'p':
2311  break;
2312  case 'P':
2314  break;
2315  case 's':
2316  silent_mode = true;
2317  break;
2318  case 'S':
2319 #ifdef WIN32
2320  set_starttype(optarg);
2321 #else
2322  write_stderr(_("%s: -S option not supported on this platform\n"),
2323  progname);
2324  exit(1);
2325 #endif
2326  break;
2327  case 't':
2328  wait_seconds = atoi(optarg);
2329  wait_seconds_arg = true;
2330  break;
2331  case 'U':
2332  if (strchr(optarg, '\\'))
2334  else
2335  /* Prepend .\ for local accounts */
2336  register_username = psprintf(".\\%s", optarg);
2337  break;
2338  case 'w':
2339  do_wait = true;
2340  break;
2341  case 'W':
2342  do_wait = false;
2343  break;
2344  case 'c':
2345  allow_core_files = true;
2346  break;
2347  default:
2348  /* getopt_long already issued a suitable error message */
2349  do_advice();
2350  exit(1);
2351  }
2352  }
2353 
2354  /* Process an action */
2355  if (optind < argc)
2356  {
2357  if (strcmp(argv[optind], "init") == 0
2358  || strcmp(argv[optind], "initdb") == 0)
2360  else if (strcmp(argv[optind], "start") == 0)
2362  else if (strcmp(argv[optind], "stop") == 0)
2364  else if (strcmp(argv[optind], "restart") == 0)
2366  else if (strcmp(argv[optind], "reload") == 0)
2368  else if (strcmp(argv[optind], "status") == 0)
2370  else if (strcmp(argv[optind], "promote") == 0)
2372  else if (strcmp(argv[optind], "logrotate") == 0)
2374  else if (strcmp(argv[optind], "kill") == 0)
2375  {
2376  if (argc - optind < 3)
2377  {
2378  write_stderr(_("%s: missing arguments for kill mode\n"), progname);
2379  do_advice();
2380  exit(1);
2381  }
2383  set_sig(argv[++optind]);
2384  killproc = atol(argv[++optind]);
2385  }
2386 #ifdef WIN32
2387  else if (strcmp(argv[optind], "register") == 0)
2389  else if (strcmp(argv[optind], "unregister") == 0)
2391  else if (strcmp(argv[optind], "runservice") == 0)
2393 #endif
2394  else
2395  {
2396  write_stderr(_("%s: unrecognized operation mode \"%s\"\n"), progname, argv[optind]);
2397  do_advice();
2398  exit(1);
2399  }
2400  optind++;
2401  }
2402 
2403  if (optind < argc)
2404  {
2405  write_stderr(_("%s: too many command-line arguments (first is \"%s\")\n"), progname, argv[optind]);
2406  do_advice();
2407  exit(1);
2408  }
2409 
2410  if (ctl_command == NO_COMMAND)
2411  {
2412  write_stderr(_("%s: no operation specified\n"), progname);
2413  do_advice();
2414  exit(1);
2415  }
2416 
2417  /* Note we put any -D switch into the env var above */
2418  pg_config = getenv("PGDATA");
2419  if (pg_config)
2420  {
2424  }
2425 
2426  /* -D might point at config-only directory; if so find the real PGDATA */
2427  adjust_data_dir();
2428 
2429  /* Complain if -D needed and not provided */
2430  if (pg_config == NULL &&
2432  {
2433  write_stderr(_("%s: no database directory specified and environment variable PGDATA unset\n"),
2434  progname);
2435  do_advice();
2436  exit(1);
2437  }
2438 
2439  if (ctl_command == RELOAD_COMMAND)
2440  {
2441  sig = SIGHUP;
2442  do_wait = false;
2443  }
2444 
2445  if (pg_data)
2446  {
2447  snprintf(postopts_file, MAXPGPATH, "%s/postmaster.opts", pg_data);
2448  snprintf(version_file, MAXPGPATH, "%s/PG_VERSION", pg_data);
2449  snprintf(pid_file, MAXPGPATH, "%s/postmaster.pid", pg_data);
2450  snprintf(backup_file, MAXPGPATH, "%s/backup_label", pg_data);
2451 
2452  /*
2453  * Set mask based on PGDATA permissions,
2454  *
2455  * Don't error here if the data directory cannot be stat'd. This is
2456  * handled differently based on the command and we don't want to
2457  * interfere with that logic.
2458  */
2460  umask(pg_mode_mask);
2461  }
2462 
2463  switch (ctl_command)
2464  {
2465  case INIT_COMMAND:
2466  do_init();
2467  break;
2468  case STATUS_COMMAND:
2469  do_status();
2470  break;
2471  case START_COMMAND:
2472  do_start();
2473  break;
2474  case STOP_COMMAND:
2475  do_stop();
2476  break;
2477  case RESTART_COMMAND:
2478  do_restart();
2479  break;
2480  case RELOAD_COMMAND:
2481  do_reload();
2482  break;
2483  case PROMOTE_COMMAND:
2484  do_promote();
2485  break;
2486  case LOGROTATE_COMMAND:
2487  do_logrotate();
2488  break;
2489  case KILL_COMMAND:
2490  do_kill(killproc);
2491  break;
2492 #ifdef WIN32
2493  case REGISTER_COMMAND:
2494  pgwin32_doRegister();
2495  break;
2496  case UNREGISTER_COMMAND:
2497  pgwin32_doUnregister();
2498  break;
2500  pgwin32_doRunAsService();
2501  break;
2502 #endif
2503  default:
2504  break;
2505  }
2506 
2507  exit(0);
2508 }
#define SIGNAL_ARGS
Definition: c.h:1355
#define PG_TEXTDOMAIN(domain)
Definition: c.h:1227
#define PG_BINARY
Definition: c.h:1283
#define pg_attribute_printf(f, a)
Definition: c.h:180
int find_my_exec(const char *argv0, char *retpath)
Definition: exec.c:158
void set_pglocale_pgservice(const char *argv0, const char *app)
Definition: exec.c:436
int find_other_exec(const char *argv0, const char *target, const char *versionstr, char *retpath)
Definition: exec.c:327
ControlFileData * get_controlfile(const char *DataDir, bool *crc_ok_p)
#define _(x)
Definition: elog.c:91
void * pg_malloc_extended(size_t size, int flags)
Definition: fe_memutils.c:59
char * pg_strdup(const char *in)
Definition: fe_memutils.c:85
void * pg_malloc(size_t size)
Definition: fe_memutils.c:47
#define MCXT_ALLOC_NO_OOM
Definition: fe_memutils.h:17
int pg_mode_mask
Definition: file_perm.c:25
bool GetDataDirectoryCreatePerm(const char *dataDir)
#define PG_MODE_MASK_OWNER
Definition: file_perm.h:24
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:24
#define required_argument
Definition: getopt_long.h:25
char my_exec_path[MAXPGPATH]
Definition: globals.c:76
#define free(a)
Definition: header.h:65
#define close(a)
Definition: win32.h:12
#define read(a, b, c)
Definition: win32.h:13
int b
Definition: isn.c:70
int j
Definition: isn.c:74
int i
Definition: isn.c:73
static void const char * fmt
static void const char fflush(stdout)
va_end(args)
vfprintf(stderr, fmt, args)
exit(1)
va_start(args, fmt)
void pg_logging_init(const char *argv0)
Definition: logging.c:83
void pfree(void *pointer)
Definition: mcxt.c:1456
#define MAXPGPATH
#define DEFAULT_EVENT_SOURCE
DBState
Definition: pg_control.h:88
@ DB_IN_PRODUCTION
Definition: pg_control.h:95
@ DB_IN_ARCHIVE_RECOVERY
Definition: pg_control.h:94
const void size_t len
static char * post_opts
Definition: pg_ctl.c:84
static void read_post_opts(void)
Definition: pg_ctl.c:795
static void static void do_advice(void)
Definition: pg_ctl.c:1956
#define WAITS_PER_SEC
Definition: pg_ctl.c:72
static char * pgdata_opt
Definition: pg_ctl.c:83
static void do_reload(void)
Definition: pg_ctl.c:1140
static WaitPMResult wait_for_postmaster_start(pid_t pm_pid, bool do_checkpoint)
Definition: pg_ctl.c:593
static void do_help(void)
Definition: pg_ctl.c:1964
static void free_readfile(char **optlines)
Definition: pg_ctl.c:410
static char * register_username
Definition: pg_ctl.c:90
static char * find_other_exec_or_die(const char *argv0, const char *target, const char *versionstr)
Definition: pg_ctl.c:868
static char * event_source
Definition: pg_ctl.c:88
static void trap_sigint_during_startup(SIGNAL_ARGS)
Definition: pg_ctl.c:850
static volatile pid_t postmasterPID
Definition: pg_ctl.c:103
static void adjust_data_dir(void)
Definition: pg_ctl.c:2116
static char * register_servicename
Definition: pg_ctl.c:89
static char version_file[MAXPGPATH]
Definition: pg_ctl.c:97
static pid_t get_pgpid(bool is_status_request)
Definition: pg_ctl.c:246
static bool allow_core_files
Definition: pg_ctl.c:93
int main(int argc, char **argv)
Definition: pg_ctl.c:2193
static char ** readfile(const char *path, int *numlines)
Definition: pg_ctl.c:314
#define DEFAULT_WAIT
Definition: pg_ctl.c:68
static bool wait_for_postmaster_promote(void)
Definition: pg_ctl.c:747
static char postopts_file[MAXPGPATH]
Definition: pg_ctl.c:96
static void unlimit_core_size(void)
Definition: pg_ctl.c:775
WaitPMResult
Definition: pg_ctl.c:45
@ POSTMASTER_FAILED
Definition: pg_ctl.c:48
@ POSTMASTER_READY
Definition: pg_ctl.c:46
@ POSTMASTER_STILL_STARTING
Definition: pg_ctl.c:47
static int sig
Definition: pg_ctl.c:79
#define USEC_PER_SEC
Definition: pg_ctl.c:70
static void set_mode(char *modeopt)
Definition: pg_ctl.c:2038
static char promote_file[MAXPGPATH]
Definition: pg_ctl.c:100
static char * pg_config
Definition: pg_ctl.c:82
static void do_start(void)
Definition: pg_ctl.c:924
static DBState get_control_dbstate(void)
Definition: pg_ctl.c:2174
static char backup_file[MAXPGPATH]
Definition: pg_ctl.c:99
static void do_logrotate(void)
Definition: pg_ctl.c:1258
static void do_stop(void)
Definition: pg_ctl.c:1016
static char pid_file[MAXPGPATH]
Definition: pg_ctl.c:98
static char * pg_data
Definition: pg_ctl.c:81
static char * register_password
Definition: pg_ctl.c:91
static CtlCommand ctl_command
Definition: pg_ctl.c:80
static bool silent_mode
Definition: pg_ctl.c:77
ShutdownMode
Definition: pg_ctl.c:38
@ FAST_MODE
Definition: pg_ctl.c:40
@ IMMEDIATE_MODE
Definition: pg_ctl.c:41
@ SMART_MODE
Definition: pg_ctl.c:39
static void do_init(void)
Definition: pg_ctl.c:895
static char * argv0
Definition: pg_ctl.c:92
static void print_msg(const char *msg)
Definition: pg_ctl.c:236
static int wait_seconds
Definition: pg_ctl.c:75
CtlCommand
Definition: pg_ctl.c:52
@ REGISTER_COMMAND
Definition: pg_ctl.c:63
@ RUN_AS_SERVICE_COMMAND
Definition: pg_ctl.c:65
@ LOGROTATE_COMMAND
Definition: pg_ctl.c:61
@ RESTART_COMMAND
Definition: pg_ctl.c:57
@ UNREGISTER_COMMAND
Definition: pg_ctl.c:64
@ START_COMMAND
Definition: pg_ctl.c:55
@ KILL_COMMAND
Definition: pg_ctl.c:62
@ INIT_COMMAND
Definition: pg_ctl.c:54
@ STOP_COMMAND
Definition: pg_ctl.c:56
@ STATUS_COMMAND
Definition: pg_ctl.c:59
@ NO_COMMAND
Definition: pg_ctl.c:53
@ PROMOTE_COMMAND
Definition: pg_ctl.c:60
@ RELOAD_COMMAND
Definition: pg_ctl.c:58
static bool postmaster_is_alive(pid_t pid)
Definition: pg_ctl.c:1315
static pid_t start_postmaster(void)
Definition: pg_ctl.c:440
static void do_restart(void)
Definition: pg_ctl.c:1075
static bool wait_seconds_arg
Definition: pg_ctl.c:76
static char * log_file
Definition: pg_ctl.c:86
static bool wait_for_postmaster_stop(void)
Definition: pg_ctl.c:710
static void write_stderr(const char *fmt,...) pg_attribute_printf(1
Definition: pg_ctl.c:202
static void do_promote(void)
Definition: pg_ctl.c:1177
static time_t start_time
Definition: pg_ctl.c:94
static void set_sig(char *signame)
Definition: pg_ctl.c:2066
static const char * progname
Definition: pg_ctl.c:85
static void do_status(void)
Definition: pg_ctl.c:1339
static char logrotate_file[MAXPGPATH]
Definition: pg_ctl.c:101
static char * exec_path
Definition: pg_ctl.c:87
static void do_kill(pid_t pid)
Definition: pg_ctl.c:1396
static ShutdownMode shutdown_mode
Definition: pg_ctl.c:78
static bool do_wait
Definition: pg_ctl.c:74
static char * filename
Definition: pg_dumpall.c:119
PGDLLIMPORT int optind
Definition: getopt.c:50
PGDLLIMPORT char * optarg
Definition: getopt.c:52
#define PM_STATUS_READY
Definition: pidfile.h:53
#define PM_STATUS_STANDBY
Definition: pidfile.h:54
#define LOCK_FILE_LINE_START_TIME
Definition: pidfile.h:39
#define LOCK_FILE_LINE_PM_STATUS
Definition: pidfile.h:44
#define LOCK_FILE_LINE_PID
Definition: pidfile.h:37
#define vsnprintf
Definition: port.h:237
char * make_absolute_path(const char *path)
Definition: path.c:729
int pg_strcasecmp(const char *s1, const char *s2)
Definition: pgstrcasecmp.c:36
#define sprintf
Definition: port.h:240
void canonicalize_path(char *path)
Definition: path.c:264
const char * get_progname(const char *argv0)
Definition: path.c:574
pqsigfunc pqsignal(int signo, pqsigfunc func)
#define strerror
Definition: port.h:251
void make_native_path(char *filename)
Definition: path.c:167
#define snprintf
Definition: port.h:238
#define DEVNULL
Definition: port.h:160
#define PG_BACKEND_VERSIONSTR
Definition: port.h:143
#define printf(...)
Definition: port.h:244
size_t strlcpy(char *dst, const char *src, size_t siz)
Definition: strlcpy.c:45
PQExpBuffer createPQExpBuffer(void)
Definition: pqexpbuffer.c:72
void appendPQExpBuffer(PQExpBuffer str, const char *fmt,...)
Definition: pqexpbuffer.c:265
void appendPQExpBufferStr(PQExpBuffer str, const char *data)
Definition: pqexpbuffer.c:367
char * c
static int fd(const char *x, int i)
Definition: preproc-init.c:105
char * psprintf(const char *fmt,...)
Definition: psprintf.c:46
void pg_usleep(long microsec)
Definition: signal.c:53
int pg_strip_crlf(char *str)
Definition: string.c:155
__int64 st_size
Definition: win32_port.h:273
Definition: regguts.h:323
#define SIGHUP
Definition: win32_port.h:168
#define stat
Definition: win32_port.h:284
#define SIG_DFL
Definition: win32_port.h:163
#define SIGQUIT
Definition: win32_port.h:169
BOOL AddUserToTokenDacl(HANDLE hToken)
#define kill(pid, sig)
Definition: win32_port.h:485
#define SIGUSR1
Definition: win32_port.h:180
#define fstat
Definition: win32_port.h:283
#define SIGABRT
Definition: win32_port.h:171
#define setenv(x, y, z)
Definition: win32_port.h:537
int pgwin32_is_service(void)
#define SIGUSR2
Definition: win32_port.h:181
#define SIGKILL
Definition: win32_port.h:172