Logo Search packages:      
Sourcecode: hal version File versions

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

Entry point for HAL daemon

Parameters:
argc Number of arguments
argv Array of arguments
Returns:
Exit code

Definition at line 321 of file hald.c.

References DIE, drop_privileges(), HAL_ERROR, HAL_INFO, logger_disable(), logger_enable(), logger_init(), and usage().

{
      GMainLoop *loop;
      guint sigterm_iochn_listener_source_id;

      openlog ("hald", LOG_PID, LOG_DAEMON);

      g_type_init ();

      logger_init ();
      if (getenv ("HALD_VERBOSE"))
            hald_is_verbose = TRUE;
      else
            hald_is_verbose = FALSE;

      while (1) {
            int c;
            int option_index = 0;
            const char *opt;
            static struct option long_options[] = {
                  {"daemon", 1, NULL, 0},
                  {"verbose", 1, NULL, 0},
                  {"help", 0, NULL, 0},
                  {"drop-privileges", 0, NULL, 0},
                  {NULL, 0, NULL, 0}
            };

            c = getopt_long (argc, argv, "",
                         long_options, &option_index);
            if (c == -1)
                  break;

            switch (c) {
            case 0:
                  opt = long_options[option_index].name;

                  if (strcmp (opt, "help") == 0) {
                        usage ();
                        return 0;
                  } else if (strcmp (opt, "daemon") == 0) {
                        if (strcmp ("yes", optarg) == 0) {
                              opt_become_daemon = TRUE;
                        } else if (strcmp ("no", optarg) == 0) {
                              opt_become_daemon = FALSE;
                        } else {
                              usage ();
                              return 1;
                        }
                  } else if (strcmp (opt, "verbose") == 0) {
                        if (strcmp ("yes", optarg) == 0) {
                              hald_is_verbose = TRUE;
                        } else if (strcmp ("no", optarg) == 0) {
                              hald_is_verbose = FALSE;
                        } else {
                              usage ();
                              return 1;
                        }
                  } else if (strcmp (opt, "drop-privileges") == 0)
                        drop_privileges ();
                  break;

            default:
                  usage ();
                  return 1;
                  break;
            }
      }

      if (hald_is_verbose)
            logger_enable ();
      else
            logger_disable ();

      HAL_INFO ((PACKAGE_STRING));
      if (opt_become_daemon)
            HAL_INFO (("Will daemonize"));
      else
            HAL_INFO (("Will not daemonize"));

      if (opt_become_daemon) {
            int child_pid;
            int dev_null_fd;
            int pf;
            char pid[9];

            HAL_INFO (("Becoming a daemon"));

            if (pipe (startup_daemonize_pipe) != 0) {
                  fprintf (stderr, "Could not setup pipe: %s\n", strerror(errno));
                  exit (1);
            }


            if (chdir ("/") < 0) {
                  fprintf (stderr, "Could not chdir to /: %s\n", strerror(errno));
                  exit (1);
            }

            child_pid = fork ();
            switch (child_pid) {
            case -1:
                  fprintf (stderr, "Cannot fork(): %s\n", strerror(errno));
                  break;

            case 0:
                  /* child */

                  dev_null_fd = open ("/dev/null", O_RDWR);
                  /* ignore if we can't open /dev/null */
                  if (dev_null_fd >= 0) {
                        /* attach /dev/null to stdout, stdin, stderr */
                        dup2 (dev_null_fd, 0);
                        dup2 (dev_null_fd, 1);
                        dup2 (dev_null_fd, 2);
                  }

                  umask (022);
                  break;

            default:
                    {
                        /* parent, block until child writes */
                        /* char buf[1];
                        read (startup_daemonize_pipe[0], &buf, sizeof (buf));*/
                        exit (0);
                        break;
                  }
            }

            /* Create session */
            setsid ();

            /* remove old pid file */
            unlink(HALD_PID_FILE);

            /* Make a new one */
            if ((pf=open(HALD_PID_FILE, O_WRONLY|O_CREAT|O_TRUNC|O_EXCL,
                  0644)) == -1) {
                  HAL_ERROR (("Cannot create pid file"));
                  exit(1);
            }
            sprintf(pid, "%lu\n", (long unsigned)getpid());
            write(pf, pid, strlen(pid));
            close(pf);
            atexit(delete_pid);
      }


      /* we need to do stuff when we are expected to terminate, thus
       * this involves looking for SIGTERM; UNIX signal handlers are
       * evil though, so set up a pipe to transmit the signal.
       */

      /* create pipe */
      if (pipe (sigterm_unix_signal_pipe_fds) != 0) {
            DIE (("Could not setup pipe, errno=%d", errno));
      }
      
      /* setup glib handler - 0 is for reading, 1 is for writing */
      sigterm_iochn = g_io_channel_unix_new (sigterm_unix_signal_pipe_fds[0]);
      if (sigterm_iochn == NULL)
            DIE (("Could not create GIOChannel"));
      
      /* get callback when there is data to read */
      sigterm_iochn_listener_source_id = g_io_add_watch (
            sigterm_iochn, G_IO_IN, sigterm_iochn_data, NULL);
      
      /* Finally, setup unix signal handler for TERM */
      signal (SIGTERM, handle_sigterm);


      hald_read_conf_file ();

      /* set up the dbus services */
      if (!hald_dbus_init ())
            return 1;

      loop = g_main_loop_new (NULL, FALSE);

      /* initialize persitent property store, read uuid from path */
      if (hald_get_conf ()->persistent_device_list)
            hal_pstore_init (PACKAGE_LOCALSTATEDIR "/lib/hal/uuid");

      /* initialize operating system specific parts */
      osspec_init ();

      hald_is_initialising = TRUE;

      /* detect devices */
      osspec_probe ();

      /* run the main loop and serve clients */
      g_main_loop_run (loop);

      return 0;
}


Generated by  Doxygen 1.6.0   Back to index