]> git.sur5r.net Git - bacula/bacula/blobdiff - bacula/src/lib/bsys.c
Work on state file. Add popup if Abort on Windows. Attempt cleaner shutdown
[bacula/bacula] / bacula / src / lib / bsys.c
index 57a7c02ab0536b88ea307da1997f8ecc01c5f8d7..13a5f8295b71fe8f586a28424344e48bff9c4ed2 100644 (file)
@@ -290,7 +290,7 @@ static int del_pid_file_ok = FALSE;
 /*
  * Create a standard "Unix" pid file.
  */
-void create_pid_file(char *dir, char *progname, int port)
+void create_pid_file(char *dir, const char *progname, int port)
 {
 #if !defined(HAVE_CYGWIN) && !defined(HAVE_WIN32)
    int pidfd, len;
@@ -329,10 +329,11 @@ void create_pid_file(char *dir, char *progname, int port)
 #endif
 }
 
+
 /*
  * Delete the pid file if we created it
  */
-int delete_pid_file(char *dir, char *progname, int port)
+int delete_pid_file(char *dir, const char *progname, int port)
 {
 #if !defined(HAVE_CYGWIN)  && !defined(HAVE_WIN32)
    POOLMEM *fname = get_pool_memory(PM_FNAME);
@@ -349,6 +350,84 @@ int delete_pid_file(char *dir, char *progname, int port)
    return 1;
 }
 
+struct s_state_hdr {
+   char id[14];
+   int32_t version;
+   uint64_t last_jobs_addr;
+   uint64_t reserved[20];
+};
+
+static struct s_state_hdr state_hdr = { 
+   "Bacula State\n",
+   3,
+   0
+};
+
+/*
+ * Open and read the state file for the daemon
+ */
+void read_state_file(char *dir, const char *progname, int port)
+{
+   int sfd;
+   POOLMEM *fname = get_pool_memory(PM_FNAME);
+   struct s_state_hdr hdr;
+
+   Mmsg(&fname, "%s/%s.%d.state", dir, progname, port);
+   /* If file exists, see what we have */
+   if ((sfd = open(mp_chr(fname), O_RDONLY, 0)) < 0 ||
+       read(sfd, &hdr, sizeof(hdr)) < 0 ||
+       hdr.version != state_hdr.version) {
+      Dmsg2(000, "Could not open or read state file. sfd=%d: ERR=%s\n", 
+                   sfd, strerror(errno));
+      goto bail_out;
+   }
+   hdr.id[13] = 0;
+   if (strcmp(hdr.id, state_hdr.id) != 0) {
+      Dmsg0(000, "State file header invalid.\n");
+      goto bail_out;
+   }
+   read_last_jobs_list(sfd, hdr.last_jobs_addr);
+bail_out:
+   if (sfd >= 0) {
+      close(sfd);
+   }
+   free_pool_memory(fname);
+}
+
+/*
+ * Write the state file
+ */
+void write_state_file(char *dir, const char *progname, int port)
+{
+   int sfd;
+   POOLMEM *fname = get_pool_memory(PM_FNAME);
+
+   Mmsg(&fname, "%s/%s.%d.state", dir, progname, port);
+   /* Create new state file */
+   if ((sfd = open(mp_chr(fname), O_CREAT | O_TRUNC | O_WRONLY, 0640)) < 0) {
+      Dmsg2(000, _("Could not create state file. %s ERR=%s\n"), fname, strerror(errno));
+      Emsg2(M_ERROR, 0, _("Could not create state file. %s ERR=%s\n"), fname, strerror(errno));
+      goto bail_out;
+   }
+   if (write(sfd, &state_hdr, sizeof(state_hdr)) < 0) {
+      Dmsg1(000, "Write error: ERR=%s\n", strerror(errno));
+      goto bail_out;
+   }
+   state_hdr.last_jobs_addr = sizeof(state_hdr);
+   state_hdr.reserved[0] = write_last_jobs_list(sfd, state_hdr.last_jobs_addr);   
+   if (lseek(sfd, 0, SEEK_SET) < 0) {
+      Dmsg1(000, "lseek error: ERR=%s\n", strerror(errno));
+      goto bail_out;
+   }  
+   write(sfd, &state_hdr, sizeof(state_hdr));
+bail_out:
+   if (sfd >= 0) {
+      close(sfd);
+   }
+   free_pool_memory(fname);
+}
+
+
 /*
  * Drop to privilege new userid and new gid if non-NULL
  */