示例#1
0
/*
 * Create the slm to picl plugin door
 */
static int
setup_door(void)
{
	struct stat	stbuf;

	/*
	 * Create the door
	 */
	door_id = door_create(event_handler, PICLEVENT_DOOR_COOKIE,
	    DOOR_REFUSE_DESC | DOOR_NO_CANCEL);

	if (door_id < 0)
		return (-1);

	if (stat(PICLEVENT_DOOR, &stbuf) < 0) {
		int newfd;
		if ((newfd = creat(PICLEVENT_DOOR, 0444)) < 0) {
			(void) door_revoke(door_id);
			door_id = -1;
			return (-1);
		}
		(void) close(newfd);
	}

	if (fattach(door_id, PICLEVENT_DOOR) < 0) {
		if ((errno != EBUSY) || (fdetach(PICLEVENT_DOOR) < 0) ||
		    (fattach(door_id, PICLEVENT_DOOR) < 0)) {
			(void) door_revoke(door_id);
			door_id = -1;
			return (-1);
		}
	}

	return (0);
}
示例#2
0
int
_nscd_setup_child_server(int did)
{

	int		errnum;
	int		fd;
	nscd_rc_t	rc;
	char		*me = "_nscd_setup_child_server";

	/* Re-establish our own server thread pool */
	(void) door_server_create(server_create);
	if (thr_keycreate(&server_key, server_destroy) != 0) {
		errnum = errno;
		_NSCD_LOG(NSCD_LOG_FRONT_END, NSCD_LOG_LEVEL_DEBUG)
		(me, "thr_keycreate failed: %s", strerror(errnum));
		return (-1);
	}

	/*
	 * Create a new door.
	 * Keep DOOR_REFUSE_DESC (self-cred nscds don't fork)
	 */
	(void) close(did);
	if ((fd = door_create(switcher, NAME_SERVICE_DOOR_COOKIE,
	    DOOR_REFUSE_DESC|DOOR_UNREF|DOOR_NO_CANCEL)) < 0) {
		errnum = errno;
		_NSCD_LOG(NSCD_LOG_FRONT_END, NSCD_LOG_LEVEL_DEBUG)
		(me, "door_create failed: %s", strerror(errnum));
		return (-1);
	}

	/*
	 * kick off routing socket monitor thread
	 */
	if (thr_create(NULL, NULL,
	    (void *(*)(void *))rts_mon, 0, 0, NULL) != 0) {
		errnum = errno;
		_NSCD_LOG(NSCD_LOG_FRONT_END, NSCD_LOG_LEVEL_ERROR)
		(me, "thr_create (routing socket monitor): %s\n",
		    strerror(errnum));
		(void) door_revoke(fd);
		return (-1);
	}

	/*
	 * start monitoring the states of the name service clients
	 */
	rc = _nscd_init_smf_monitor();
	if (rc != NSCD_SUCCESS) {
		_NSCD_LOG(NSCD_LOG_FRONT_END, NSCD_LOG_LEVEL_ERROR)
	(me, "unable to start the SMF monitor (rc = %d)\n", rc);

		(void) door_revoke(fd);
		return (-1);
	}

	return (fd);
}
示例#3
0
int
revoke_event_service(int fd)
{
	struct door_info info;
	door_cookie_t *cookie;

	if (door_info(fd, &info) == -1) {
		return (-1);
	}

	if (door_revoke(fd) != 0) {
		return (-1);
	}

	/* wait for existing door calls to finish */
	(void) sleep(1);

	if ((cookie = (door_cookie_t *)(uintptr_t)info.di_data) != NULL) {
		struct door_result *tmp = cookie->results;
		while (tmp) {
			cookie->results = tmp->next;
			free(tmp->data);
			free(tmp);
			tmp = cookie->results;
		}
		free(cookie);
	}
	return (0);
}
示例#4
0
int
ndmp_door_init(void)
{
	int fd;

	(void) mutex_lock(&ndmp_doorsrv_mutex);

	if (ndmp_door_fildes != -1) {
		syslog(LOG_ERR,
		    "ndmp_door_init: ndmpd service is already running.");
		(void) mutex_unlock(&ndmp_doorsrv_mutex);
		return (0);
	}

	if ((ndmp_door_fildes = door_create(ndmp_door_server,
	    NULL, DOOR_UNREF)) < 0) {
		syslog(LOG_ERR, "ndmp_door_init: Could not create door.");
		(void) mutex_unlock(&ndmp_doorsrv_mutex);
		return (-1);
	}

	(void) unlink(NDMP_DOOR_SVC);

	if ((fd = creat(NDMP_DOOR_SVC, 0444)) < 0) {
		syslog(LOG_ERR, "ndmp_door_init: Can't create %s: %m.",
		    NDMP_DOOR_SVC);
		(void) door_revoke(ndmp_door_fildes);
		ndmp_door_fildes = -1;
		(void) mutex_unlock(&ndmp_doorsrv_mutex);
		return (-1);
	}

	(void) close(fd);
	(void) fdetach(NDMP_DOOR_SVC);

	if (fattach(ndmp_door_fildes, NDMP_DOOR_SVC) < 0) {
		syslog(LOG_ERR, "ndmp_door_init: fattach failed %m");
		(void) door_revoke(ndmp_door_fildes);
		ndmp_door_fildes = -1;
		(void) mutex_unlock(&ndmp_doorsrv_mutex);
		return (-1);
	}

	syslog(LOG_DEBUG, "ndmp_door_init: Door server successfully started");
	(void) mutex_unlock(&ndmp_doorsrv_mutex);
	return (0);
}
示例#5
0
/*
 * This function is the fini entry point of the plugin
 */
static void
eventplugin_fini(void)
{
	if (door_id >= 0) {
		(void) door_revoke(door_id);
		door_id = -1;
	}
}
示例#6
0
/*
 * sysevent_evc_unbind - Unbind from previously bound/created channel
 */
int
sysevent_evc_unbind(evchan_t *scp)
{
	sev_unsubscribe_args_t uargs;
	evchan_subscr_t *subp;
	int errcp;

	if (scp == NULL || misaligned(scp))
		return (errno = EINVAL);

	if (will_deadlock(scp))
		return (errno = EDEADLK);

	(void) mutex_lock(EV_LOCK(scp));

	/*
	 * Unsubscribe, if we are in the process which did the bind.
	 */
	if (EV_PID(scp) == getpid()) {
		uargs.sid.name = NULL;
		uargs.sid.len = 0;
		/*
		 * The unsubscribe ioctl will block until all door upcalls have
		 * drained.
		 */
		if (ioctl(EV_FD(scp), SEV_UNSUBSCRIBE, (intptr_t)&uargs) != 0) {
			errcp = errno;
			(void) mutex_unlock(EV_LOCK(scp));
			return (errno = errcp);
		}
	}

	while ((subp =  EV_SUB_NEXT(scp)) != NULL) {
		EV_SUB_NEXT(scp) = subp->evsub_next;

		/* If door_xcreate was applied we can clean up */
		if (subp->evsub_attr)
			kill_door_servers(subp);

		if (door_revoke(subp->evsub_door_desc) != 0 && errno == EPERM)
			(void) close(subp->evsub_door_desc);

		free(subp->evsub_sid);
		free(subp);
	}

	(void) mutex_unlock(EV_LOCK(scp));

	/*
	 * The close of the driver will do the unsubscribe if a) it is the last
	 * close and b) we are in a child which inherited subscriptions.
	 */
	(void) close(EV_FD(scp));
	(void) mutex_destroy(EV_LOCK(scp));
	free(scp);

	return (0);
}
示例#7
0
/*
 * Create the driver to wpad door
 */
int
wpa_supplicant_door_setup(void *cookie, char *doorname)
{
	struct stat stbuf;
	int error = 0;

	wpa_printf(MSG_DEBUG, "wpa_supplicant_door_setup(%s)", doorname);
	/*
	 * Create the door
	 */
	door_id = door_create(event_handler, cookie,
	    DOOR_UNREF | DOOR_REFUSE_DESC | DOOR_NO_CANCEL);

	if (door_id < 0) {
		error = -1;
		goto out;
	}

	if (stat(doorname, &stbuf) < 0) {
		int newfd;
		if ((newfd = creat(doorname, 0666)) < 0) {
			(void) door_revoke(door_id);
			door_id = -1;
			error = -1;

			goto out;
		}
		(void) close(newfd);
	}

	if (fattach(door_id, doorname) < 0) {
		if ((errno != EBUSY) || (fdetach(doorname) < 0) ||
		    (fattach(door_id, doorname) < 0)) {
			(void) door_revoke(door_id);
			door_id = -1;
			error = -1;

			goto out;
		}
	}

out:
	return (error);
}
示例#8
0
/*
 * door_server_fini()
 *
 *	Terminate and cleanup the door server.
 */
void
door_server_fini(void)
{
    if (door_fd != -1) {
        (void) door_revoke(door_fd);
        (void) fdetach(HOTPLUGD_DOOR);
    }

    (void) unlink(HOTPLUGD_DOOR);
}
示例#9
0
static void
ipmgmt_door_fini()
{
	if (ipmgmt_door_fd == -1)
		return;

	(void) fdetach(IPMGMT_DOOR);
	if (door_revoke(ipmgmt_door_fd) == -1) {
		ipmgmt_log(LOG_ERR, "failed to revoke access to door %s: %s",
		    IPMGMT_DOOR, strerror(errno));
	}
}
示例#10
0
void
ndmp_door_fini(void)
{
	(void) mutex_lock(&ndmp_doorsrv_mutex);

	if (ndmp_door_fildes != -1) {
		(void) fdetach(NDMP_DOOR_SVC);
		(void) door_revoke(ndmp_door_fildes);
		ndmp_door_fildes = -1;
	}

	(void) mutex_unlock(&ndmp_doorsrv_mutex);
}
示例#11
0
int
setup_main_door(const char *doorpath)
{
	mode_t oldmask;
	int fd;

	int door_flags = DOOR_UNREF | DOOR_REFUSE_DESC;
#ifdef DOOR_NO_CANCEL
	door_flags |= DOOR_NO_CANCEL;
#endif
	if ((main_door_fd = door_create(main_switcher, REPOSITORY_DOOR_COOKIE,
	    door_flags)) < 0) {
		perror("door_create");
		return (0);
	}

#ifdef DOOR_PARAM_DATA_MIN
	if (door_setparam(main_door_fd, DOOR_PARAM_DATA_MIN,
	    offsetofend(repository_door_request_t, rdr_request)) == -1 ||
	    door_setparam(main_door_fd, DOOR_PARAM_DATA_MAX,
	    sizeof (repository_door_request_t)) == -1) {
		perror("door_setparam");
		return (0);
	}
#endif /* DOOR_PARAM_DATA_MIN */

	/*
	 * Create the file if it doesn't exist.  Ignore errors, since
	 * fattach(3C) will catch any real problems.
	 */
	oldmask = umask(000);		/* disable umask temporarily */
	fd = open(doorpath, O_RDWR | O_CREAT | O_EXCL, 0644);
	(void) umask(oldmask);

	if (fd >= 0)
		(void) close(fd);

	if (fattach(main_door_fd, doorpath) < 0) {
		if ((errno != EBUSY) ||
		    (fdetach(doorpath) < 0) ||
		    (fattach(main_door_fd, doorpath) < 0)) {
			perror("fattach");
			(void) door_revoke(main_door_fd);
			main_door_fd = -1;
			return (0);
		}
	}

	return (1);
}
/*
 * Stop the smbd opipe door service.
 */
void
smbd_opipe_stop(void)
{
	(void) pthread_mutex_lock(&smbd_opipe_mutex);

	smbd_door_fini(&smbd_opipe_sdh);

	if (smbd_opipe_fd != -1) {
		(void) door_revoke(smbd_opipe_fd);
		smbd_opipe_fd = -1;
	}

	(void) pthread_mutex_unlock(&smbd_opipe_mutex);
}
示例#13
0
static void
dlmgmt_door_fini()
{
	if (dlmgmt_door_fd == -1)
		return;

	if (door_revoke(dlmgmt_door_fd) == -1) {
		dlmgmt_log(LOG_WARNING, "door_revoke(%s) failed: %s",
		    DLMGMT_DOOR, strerror(errno));
	}

	(void) fdetach(DLMGMT_DOOR);
	(void) dlmgmt_set_doorfd(B_FALSE);
}
示例#14
0
/*
 * vs_stats_fini
 *
 * Invoked on daemon unload
 */
void
vs_stats_fini(void)
{
	(void) pthread_mutex_lock(&vs_stats_mutex);

	/* door termination */
	if (vs_stats_door_fd != -1)
		(void) door_revoke(vs_stats_door_fd);
	vs_stats_door_fd = -1;

	(void) fdetach(VS_STATS_DOOR_NAME);
	(void) unlink(VS_STATS_DOOR_NAME);

	(void) pthread_mutex_unlock(&vs_stats_mutex);
}
示例#15
0
/*
 * vscan_door_fini
 *
 * Stop the vscand door service.
 */
void
vs_door_fini(void)
{
	(void) pthread_mutex_lock(&vs_door_mutex);

	if (vs_door_fd >= 0) {
		if (door_revoke(vs_door_fd) < 0)
			syslog(LOG_ERR, "vscand: door revoke %s",
			    strerror(errno));
	}

	vs_door_fd = -1;

	(void) pthread_mutex_unlock(&vs_door_mutex);
}
示例#16
0
int main(void)
{
   int res = 1;
   int did = -1;
   struct sigaction sa;

   sa.sa_sigaction = signal_handler;
   sa.sa_flags = SA_RESTART;
   if (sigfillset(&sa.sa_mask)) {
      perror("sigfillset");
      return 1;
   }
   if (sigaction(SIGINT, &sa, NULL)) {
      perror("sigaction");
      return 1;
   }

   door_server_create(create_door_thread);

   if ((did = door_create(server_procedure, NULL, 0)) < 0) {
      perror("door_create");
      return 1;
   }

   /* Let the server thread to run. */
   sleep(2);

   /* Send a signal to the server thread that should be already created and
      blocked in door_return. */
   if (_lwp_kill(server_lwpid, SIGINT)) {
      perror("_lwp_kill");
      goto out;
   }

   /* Let the other thread to run. */
   sleep(2);

   res = 0;

out:
   if (did >= 0 && door_revoke(did))
      perror("door_revoke");

   return res;
}
示例#17
0
static int
dlmgmt_door_init()
{
	int fd;
	int err;

	/*
	 * Create the door file for dlmgmtd.
	 */
	if ((fd = open(DLMGMT_DOOR, O_CREAT|O_RDONLY, 0644)) == -1) {
		err = errno;
		dlmgmt_log(LOG_ERR, "open(%s) failed: %s",
		    DLMGMT_DOOR, strerror(err));
		return (err);
	}
	(void) close(fd);

	if ((dlmgmt_door_fd = door_create(dlmgmt_handler, NULL,
	    DOOR_REFUSE_DESC | DOOR_NO_CANCEL)) == -1) {
		err = errno;
		dlmgmt_log(LOG_ERR, "door_create() failed: %s",
		    strerror(err));
		return (err);
	}
	if (fattach(dlmgmt_door_fd, DLMGMT_DOOR) != 0) {
		err = errno;
		dlmgmt_log(LOG_ERR, "fattach(%s) failed: %s",
		    DLMGMT_DOOR, strerror(err));
		goto fail;
	}
	if ((err = dlmgmt_set_doorfd(B_TRUE)) != 0) {
		dlmgmt_log(LOG_ERR, "cannot set kernel doorfd: %s",
		    strerror(err));
		(void) fdetach(DLMGMT_DOOR);
		goto fail;
	}

	return (0);
fail:
	(void) door_revoke(dlmgmt_door_fd);
	dlmgmt_door_fd = -1;
	return (err);
}
示例#18
0
/*
 * Destroy the unlock descriptor `ud' -- `ud' must be unlocked on entry.
 * If there's room and `cacheable' is set, then, keep the unlock descriptor
 * on the reclaim list to lower future creation cost.
 */
static void
ud_destroy(dsvcd_unlock_desc_t *ud, boolean_t cacheable)
{
	assert(!MUTEX_HELD(&ud->ud_lock));

	ud->ud_cn = NULL;
	(void) mutex_lock(&ud_reclaim_lock);
	if (cacheable && ud_reclaim_count < UD_RECLAIM_MAX) {
		ud->ud_next = ud_reclaim_list;
		ud_reclaim_list = ud;
		ud_reclaim_count++;
		(void) mutex_unlock(&ud_reclaim_lock);
	} else {
		(void) mutex_unlock(&ud_reclaim_lock);
		(void) door_revoke(ud->ud_fd);
		(void) mutex_destroy(&ud->ud_lock);
		free(ud);
	}
}
示例#19
0
void
wpa_supplicant_door_destroy(char *doorname)
{
	wpa_printf(MSG_DEBUG, "wpa_supplicant_door_destroy(%s)\n", doorname);

	if (door_id == -1)
		return;

	if (door_revoke(door_id) == -1) {
		wpa_printf(MSG_ERROR, "failed to door_revoke(%d) %s, exiting.",
		    door_id, strerror(errno));
	}

	if (fdetach(doorname) == -1) {
		wpa_printf(MSG_ERROR, "failed to fdetach %s: %s, exiting.",
		    doorname, strerror(errno));
	}

	(void) close(door_id);
}
示例#20
0
static gboolean
afstreams_sd_deinit(LogPipe *s)
{
  AFStreamsSourceDriver *self = (AFStreamsSourceDriver *) s;

  if (self->reader)
    {
      log_pipe_deinit((LogPipe *) self->reader);
      log_pipe_unref((LogPipe *) self->reader);
      self->reader = NULL;
    }
  if (self->door_fd != -1)
    {
      door_revoke(self->door_fd);
      close(self->door_fd);
    }

  if (!log_src_driver_deinit_method(s))
    return FALSE;

  return TRUE;
}
示例#21
0
/*
 * door_server_init()
 *
 *	Create the door file, and initialize the door server.
 */
boolean_t
door_server_init(void)
{
    int	fd;

    /* Create the door file */
    if ((fd = open(HOTPLUGD_DOOR, O_CREAT|O_EXCL|O_RDONLY, 0644)) == -1) {
        if (errno == EEXIST) {
            log_err("Door service is already running.\n");
        } else {
            log_err("Cannot open door file '%s': %s\n",
                    HOTPLUGD_DOOR, strerror(errno));
        }
        return (B_FALSE);
    }
    (void) close(fd);

    /* Initialize the door service */
    if ((door_fd = door_create(door_server, NULL,
                               DOOR_REFUSE_DESC | DOOR_NO_CANCEL)) == -1) {
        log_err("Cannot create door service: %s\n", strerror(errno));
        return (B_FALSE);
    }

    /* Cleanup stale door associations */
    (void) fdetach(HOTPLUGD_DOOR);

    /* Associate door service with door file */
    if (fattach(door_fd, HOTPLUGD_DOOR) != 0) {
        log_err("Cannot attach to door file '%s': %s\n", HOTPLUGD_DOOR,
                strerror(errno));
        (void) door_revoke(door_fd);
        (void) fdetach(HOTPLUGD_DOOR);
        door_fd = -1;
        return (B_FALSE);
    }

    return (B_TRUE);
}
示例#22
0
static int
ipmgmt_door_init()
{
	int fd;
	int err;

	/* create the door file for ipmgmtd */
	if ((fd = open(IPMGMT_DOOR, O_CREAT|O_RDONLY, IPADM_FILE_MODE)) == -1) {
		err = errno;
		ipmgmt_log(LOG_ERR, "could not open %s: %s",
		    IPMGMT_DOOR, strerror(err));
		return (err);
	}
	(void) close(fd);

	if ((ipmgmt_door_fd = door_create(ipmgmt_handler, NULL,
	    DOOR_REFUSE_DESC | DOOR_NO_CANCEL)) == -1) {
		err = errno;
		ipmgmt_log(LOG_ERR, "failed to create door: %s", strerror(err));
		return (err);
	}
	/*
	 * fdetach first in case a previous daemon instance exited
	 * ungracefully.
	 */
	(void) fdetach(IPMGMT_DOOR);
	if (fattach(ipmgmt_door_fd, IPMGMT_DOOR) != 0) {
		err = errno;
		ipmgmt_log(LOG_ERR, "failed to attach door to %s: %s",
		    IPMGMT_DOOR, strerror(err));
		goto fail;
	}
	return (0);
fail:
	(void) door_revoke(ipmgmt_door_fd);
	ipmgmt_door_fd = -1;
	return (err);
}
示例#23
0
/*
 * vs_stats_init
 *
 * Invoked on daemon load and unload
 */
int
vs_stats_init(void)
{
	(void) pthread_mutex_lock(&vs_stats_mutex);

	(void) memset(&vscan_stats, 0, sizeof (vs_stats_t));

	/* door initialization */
	if ((vs_stats_door_fd = door_create(vs_stats_door_call,
	    &vs_stats_door_cookie, (DOOR_UNREF | DOOR_REFUSE_DESC))) < 0) {
		vs_stats_door_fd = -1;
	} else {
		(void) fdetach(VS_STATS_DOOR_NAME);
		if (fattach(vs_stats_door_fd, VS_STATS_DOOR_NAME) < 0) {
			(void) door_revoke(vs_stats_door_fd);
			vs_stats_door_fd = -1;
		}
	}

	(void) pthread_mutex_unlock(&vs_stats_mutex);

	return ((vs_stats_door_fd == -1) ? -1 : 0);
}
示例#24
0
int
_nscd_setup_server(char *execname, char **argv)
{

	int		fd;
	int		errnum;
	int		bind_failed = 0;
	mode_t		old_mask;
	struct stat	buf;
	sigset_t	myset;
	struct sigaction action;
	char		*me = "_nscd_setup_server";

	main_execname = execname;
	main_argv = argv;

	/* Any nscd process is to ignore SIGPIPE */
	if (signal(SIGPIPE, SIG_IGN) == SIG_ERR) {
		errnum = errno;
		_NSCD_LOG(NSCD_LOG_FRONT_END, NSCD_LOG_LEVEL_ERROR)
		(me, "signal (SIGPIPE): %s\n", strerror(errnum));
		return (-1);
	}

	keep_open_dns_socket();

	/*
	 * the max number of server threads should be fixed now, so
	 * set flag to indicate that no in-flight change is allowed
	 */
	max_servers_set = 1;

	(void) thr_keycreate(&lookup_state_key, NULL);
	(void) sema_init(&common_sema, frontend_cfg_g.common_worker_threads,
	    USYNC_THREAD, 0);

	/* Establish server thread pool */
	(void) door_server_create(server_create);
	if (thr_keycreate(&server_key, server_destroy) != 0) {
		errnum = errno;
		_NSCD_LOG(NSCD_LOG_FRONT_END, NSCD_LOG_LEVEL_ERROR)
		(me, "thr_keycreate (server thread): %s\n",
		    strerror(errnum));
		return (-1);
	}

	/* Create a door */
	if ((fd = door_create(switcher, NAME_SERVICE_DOOR_COOKIE,
	    DOOR_UNREF | DOOR_NO_CANCEL)) < 0) {
		errnum = errno;
		_NSCD_LOG(NSCD_LOG_FRONT_END, NSCD_LOG_LEVEL_ERROR)
		(me, "door_create: %s\n", strerror(errnum));
		return (-1);
	}

	/* if not main nscd, no more setup to do */
	if (_whoami != NSCD_MAIN)
		return (fd);

	/* bind to file system */
	if (is_system_labeled() && (getzoneid() == GLOBAL_ZONEID)) {
		if (stat(TSOL_NAME_SERVICE_DOOR, &buf) < 0) {
			int	newfd;

			/* make sure the door will be readable by all */
			old_mask = umask(0);
			if ((newfd = creat(TSOL_NAME_SERVICE_DOOR, 0444)) < 0) {
				errnum = errno;
				_NSCD_LOG(NSCD_LOG_FRONT_END,
				    NSCD_LOG_LEVEL_ERROR)
				(me, "Cannot create %s: %s\n",
				    TSOL_NAME_SERVICE_DOOR,
				    strerror(errnum));
				bind_failed = 1;
			}
			/* rstore the old file mode creation mask */
			(void) umask(old_mask);
			(void) close(newfd);
		}
		if (symlink(TSOL_NAME_SERVICE_DOOR, NAME_SERVICE_DOOR) != 0) {
			if (errno != EEXIST) {
				errnum = errno;
				_NSCD_LOG(NSCD_LOG_FRONT_END,
				    NSCD_LOG_LEVEL_ERROR)
				(me, "Cannot symlink %s: %s\n",
				    NAME_SERVICE_DOOR, strerror(errnum));
				bind_failed = 1;
			}
		}
	} else if (stat(NAME_SERVICE_DOOR, &buf) < 0) {
		int	newfd;

		/* make sure the door will be readable by all */
		old_mask = umask(0);
		if ((newfd = creat(NAME_SERVICE_DOOR, 0444)) < 0) {
			errnum = errno;
			_NSCD_LOG(NSCD_LOG_FRONT_END, NSCD_LOG_LEVEL_ERROR)
			(me, "Cannot create %s: %s\n", NAME_SERVICE_DOOR,
			    strerror(errnum));
			bind_failed = 1;
		}
		/* rstore the old file mode creation mask */
		(void) umask(old_mask);
		(void) close(newfd);
	}

	if (bind_failed == 1) {
		(void) door_revoke(fd);
		return (-1);
	}

	if (fattach(fd, NAME_SERVICE_DOOR) < 0) {
		if ((errno != EBUSY) ||
		    (fdetach(NAME_SERVICE_DOOR) <  0) ||
		    (fattach(fd, NAME_SERVICE_DOOR) < 0)) {
			errnum = errno;
			_NSCD_LOG(NSCD_LOG_FRONT_END, NSCD_LOG_LEVEL_ERROR)
			(me, "fattach: %s\n", strerror(errnum));
			(void) door_revoke(fd);
			return (-1);
		}
	}

	/*
	 * kick off routing socket monitor thread
	 */
	if (thr_create(NULL, NULL,
	    (void *(*)(void *))rts_mon, 0, 0, NULL) != 0) {
		errnum = errno;
		_NSCD_LOG(NSCD_LOG_FRONT_END, NSCD_LOG_LEVEL_ERROR)
		(me, "thr_create (routing socket monitor): %s\n",
		    strerror(errnum));

		(void) door_revoke(fd);
		return (-1);
	}

	/*
	 * set up signal handler for SIGHUP
	 */
	action.sa_handler = dozip;
	action.sa_flags = 0;
	(void) sigemptyset(&action.sa_mask);
	(void) sigemptyset(&myset);
	(void) sigaddset(&myset, SIGHUP);

	if (sigaction(SIGHUP, &action, NULL) < 0) {
		errnum = errno;
		_NSCD_LOG(NSCD_LOG_FRONT_END, NSCD_LOG_LEVEL_ERROR)
		(me, "sigaction (SIGHUP): %s\n", strerror(errnum));

		(void) door_revoke(fd);
		return (-1);
	}

	return (fd);
}
示例#25
0
int
main(int argc, char **argv)
{
	static const int door_attrs =
	    DOOR_REFUSE_DESC | DOOR_NO_CANCEL;
	sigset_t oldmask, tmpmask;
	char *env, *door_path = NULL;
	int door_fd = -1, tmp_fd = -1;
	int err, i, sig;
	int rc = EXIT_FAIL;

	/* Debugging support. */
	if ((env = getenv("SMBFS_DEBUG")) != NULL) {
		smb_debug = atoi(env);
		if (smb_debug < 1)
			smb_debug = 1;
	}

	/*
	 * Find out if an IOD is already running.
	 * If so, we lost a harmless startup race.
	 * An IOD did start, so exit success.
	 */
	err = smb_iod_open_door(&door_fd);
	if (err == 0) {
		close(door_fd);
		door_fd = -1;
		DPRINT("main: already running\n");
		exit(EXIT_OK);
	}

	/*
	 * Create a file for the door.
	 */
	door_path = smb_iod_door_path();
	unlink(door_path);
	tmp_fd = open(door_path, O_RDWR|O_CREAT|O_EXCL, 0600);
	if (tmp_fd < 0) {
		perror(door_path);
		exit(EXIT_FAIL);
	}
	close(tmp_fd);
	tmp_fd = -1;


	/*
	 * Close FDs 0,1,2 so we don't have a TTY, and
	 * re-open them on /dev/null so they won't be
	 * used for device handles (etc.) later, and
	 * we don't have to worry about printf calls
	 * or whatever going to these FDs.
	 */
	for (i = 0; i < 3; i++) {
		/* Exception: If smb_debug, keep stderr */
		if (smb_debug && i == 2)
			break;
		close(i);
		tmp_fd = open("/dev/null", O_RDWR);
		if (tmp_fd < 0)
			perror("/dev/null");
		if (tmp_fd != i)
			DPRINT("Open /dev/null - wrong fd?\n");
	}

	/*
	 * Become session leader.
	 */
	setsid();

	/*
	 * Create door service threads with signals blocked.
	 */
	sigfillset(&tmpmask);
	sigprocmask(SIG_BLOCK, &tmpmask, &oldmask);

	/* Setup the door service. */
	door_fd = door_create(iod_dispatch, NULL, door_attrs);
	if (door_fd < 0) {
		fprintf(stderr, "%s: door_create failed\n", argv[0]);
		rc = EXIT_FAIL;
		goto errout;
	}
	fdetach(door_path);
	if (fattach(door_fd, door_path) < 0) {
		fprintf(stderr, "%s: fattach failed\n", argv[0]);
		rc = EXIT_FAIL;
		goto errout;
	}

	/*
	 * Post the initial alarm, and then just
	 * wait for signals.
	 */
	alarm(ALARM_TIME);
again:
	sig = sigwait(&tmpmask);
	DPRINT("main: sig=%d\n", sig);

	/*
	 * If a door call races with the alarm, ignore the alarm.
	 * It will be rescheduled when the threads go away.
	 */
	mutex_lock(&iod_mutex);
	if (sig == SIGALRM && iod_thr_count > 0) {
		mutex_unlock(&iod_mutex);
		goto again;
	}
	iod_terminating = 1;
	mutex_unlock(&iod_mutex);
	rc = EXIT_OK;

errout:
	fdetach(door_path);
	door_revoke(door_fd);
	door_fd = -1;
	unlink(door_path);

	return (rc);
}