コード例 #1
0
ファイル: adm_kef.c プロジェクト: CoryXie/opensolaris
/*
 * Display the policy information for a kernel software provider.
 * This implements part of the "cryptoadm list -p" command.
 *
 * Parameters phardlist and psoftlist are supplied by
 * getent_kef().
 * If NULL, this function obtains it by calling get_kcfconf_info()
 * via getent_kef() internally.
 */
int
list_policy_for_soft(char *provname,
    entrylist_t *phardlist, entrylist_t *psoftlist)
{
	int		rc;
	entry_t		*pent = NULL;
	mechlist_t	*pmechlist = NULL;
	boolean_t	has_random = B_FALSE;
	boolean_t	has_mechs = B_FALSE;
	boolean_t	in_kernel = B_FALSE;

	if (provname == NULL) {
		return (FAILURE);
	}

	if (check_kernel_for_soft(provname, NULL, &in_kernel) == FAILURE) {
		return (FAILURE);
	} else if (in_kernel == B_FALSE) {
		cryptoerror(LOG_STDERR, gettext("%s does not exist."),
		    provname);
		return (FAILURE);
	}
	pent = getent_kef(provname, phardlist, psoftlist);

	rc = get_soft_info(provname, &pmechlist, phardlist, psoftlist);
	if (rc == SUCCESS) {
		has_random = filter_mechlist(&pmechlist, RANDOM);
		if (pmechlist != NULL) {
			has_mechs = B_TRUE;
			free_mechlist(pmechlist);
		}
	} else {
		cryptoerror(LOG_STDERR, gettext(
		    "failed to retrieve the mechanism list for %s."),
		    provname);
		return (rc);
	}

	print_kef_policy(provname, pent, has_random, has_mechs);
	free_entry(pent);
	return (SUCCESS);
}
コード例 #2
0
ファイル: adm_kef.c プロジェクト: CoryXie/opensolaris
/*
 * Display the mechanism list for a kernel software provider.
 * This implements part of the "cryptoadm list -m" command.
 *
 * Parameters phardlist and psoftlist are supplied by
 * get_soft_info().
 * If NULL, this function obtains it by calling getent_kef() and
 * then get_kcfconf_info() via get_soft_info() internally.
 */
int
list_mechlist_for_soft(char *provname,
    entrylist_t *phardlist, entrylist_t *psoftlist)
{
	mechlist_t	*pmechlist = NULL;
	int		rc;

	if (provname == NULL) {
		return (FAILURE);
	}

	rc = get_soft_info(provname, &pmechlist, phardlist, psoftlist);
	if (rc == SUCCESS) {
		(void) filter_mechlist(&pmechlist, RANDOM);
		print_mechlist(provname, pmechlist);
		free_mechlist(pmechlist);
	} else {
		cryptoerror(LOG_STDERR, gettext(
		    "failed to retrieve the mechanism list for %s."),
		    provname);
	}

	return (rc);
}
コード例 #3
0
static int
cryptoadm_ioctl(dev_t dev, int cmd, intptr_t arg, int mode, cred_t *c,
    int *rval)
{
	int error;
#define	ARG	((caddr_t)arg)

	switch (cmd) {
	case CRYPTO_LOAD_DEV_DISABLED:
	case CRYPTO_LOAD_SOFT_DISABLED:
	case CRYPTO_LOAD_SOFT_CONFIG:
	case CRYPTO_UNLOAD_SOFT_MODULE:
	case CRYPTO_POOL_CREATE:
	case CRYPTO_POOL_WAIT:
	case CRYPTO_POOL_RUN:
	case CRYPTO_LOAD_DOOR:
	case CRYPTO_FIPS140_SET:
		if ((error = drv_priv(c)) != 0)
			return (error);
	default:
		break;
	}

	switch (cmd) {
	case CRYPTO_GET_DEV_LIST:
		return (get_dev_list(dev, ARG, mode, rval));

	case CRYPTO_GET_DEV_INFO:
		return (get_dev_info(dev, ARG, mode, rval));

	case CRYPTO_GET_SOFT_LIST:
		return (get_soft_list(dev, ARG, mode, rval));

	case CRYPTO_GET_SOFT_INFO:
		return (get_soft_info(dev, ARG, mode, rval));

	case CRYPTO_LOAD_DEV_DISABLED:
		return (load_dev_disabled(dev, ARG, mode, rval));

	case CRYPTO_LOAD_SOFT_DISABLED:
		return (load_soft_disabled(dev, ARG, mode, rval));

	case CRYPTO_LOAD_SOFT_CONFIG:
		return (load_soft_config(dev, ARG, mode, rval));

	case CRYPTO_UNLOAD_SOFT_MODULE:
		return (unload_soft_module(dev, ARG, mode, rval));

	case CRYPTO_POOL_CREATE:
		/*
		 * The framework allocates and initializes the pool.
		 * So, this is a no op. We are keeping this ioctl around
		 * to be used for any future threadpool related work.
		 */
		if (audit_active)
			audit_cryptoadm(CRYPTO_POOL_CREATE, NULL, NULL,
			    0, 0, 0, 0);
		return (0);

	case CRYPTO_POOL_WAIT: {
		int nthrs = 0, err;

		if ((err = kcf_svc_wait(&nthrs)) == 0) {
			if (copyout((caddr_t)&nthrs, ARG, sizeof (int))
			    == -1)
				err = EFAULT;
		}
		if (audit_active)
			audit_cryptoadm(CRYPTO_POOL_WAIT, NULL, NULL,
			    0, 0, 0, err);
		return (err);
	}

	case CRYPTO_POOL_RUN: {
		int err;

		err = kcf_svc_do_run();
		if (audit_active)
			audit_cryptoadm(CRYPTO_POOL_RUN, NULL, NULL,
			    0, 0, 0, err);
		return (err);
	}

	case CRYPTO_LOAD_DOOR:
		return (load_door(dev, ARG, mode, rval));
	case CRYPTO_FIPS140_STATUS:
		return (fips140_actions(dev, ARG, mode, rval, cmd));
	case CRYPTO_FIPS140_SET: {
		int err;

		err = fips140_actions(dev, ARG, mode, rval, cmd);
		if (audit_active)
			audit_cryptoadm(CRYPTO_FIPS140_SET, NULL, NULL,
			    0, 0, 0, err);
		return (err);
	}
	}

	return (EINVAL);
}
コード例 #4
0
ファイル: adm_kef.c プロジェクト: CoryXie/opensolaris
/*
 * Disable a kernel software provider.
 * This implements the "cryptoadm disable" command for
 * kernel software providers.
 */
int
disable_kef_software(char *provname, boolean_t rndflag, boolean_t allflag,
    mechlist_t *dislist)
{
	crypto_load_soft_disabled_t	*pload_soft_dis = NULL;
	mechlist_t			*infolist = NULL;
	entry_t				*pent = NULL;
	entrylist_t			*phardlist = NULL;
	entrylist_t			*psoftlist = NULL;
	boolean_t			in_kernel = B_FALSE;
	int				fd = -1;
	int				rc = SUCCESS;

	if (provname == NULL) {
		return (FAILURE);
	}

	/*
	 * Check if the kernel software provider is currently unloaded.
	 * If it is unloaded, return FAILURE, because the disable subcommand
	 * can not perform on inactive (unloaded) providers.
	 */
	if (check_kernel_for_soft(provname, NULL, &in_kernel) == FAILURE) {
		return (FAILURE);
	} else if (in_kernel == B_FALSE) {
		cryptoerror(LOG_STDERR,
		    gettext("%s is not loaded or does not exist."),
		    provname);
		return (FAILURE);
	}

	if (get_kcfconf_info(&phardlist, &psoftlist) == FAILURE) {
		cryptoerror(LOG_ERR,
		    "failed to retrieve the providers' "
		    "information from the configuration file - %s.",
		    _PATH_KCF_CONF);
		return (FAILURE);
	}

	/*
	 * Get the entry of this provider from the kcf.conf file, if any.
	 * Otherwise, create a new kcf.conf entry for writing back to the file.
	 */
	pent = getent_kef(provname, phardlist, psoftlist);
	if (pent == NULL) { /* create a new entry */
		pent = create_entry(provname);
		if (pent == NULL) {
			cryptodebug("out of memory.");
			rc = FAILURE;
			goto out;
		}
	}

	/* Get the mechanism list for the software provider from the kernel */
	if (get_soft_info(provname, &infolist, phardlist, psoftlist) ==
	    FAILURE) {
		rc = FAILURE;
		goto out;
	}

	if ((infolist != NULL) && (infolist->name[0] != '\0')) {
		/*
		 * Replace the supportedlist from kcf.conf with possibly
		 * more-up-to-date list from the kernel.  This is the case
		 * for default software providers that had more mechanisms
		 * added in the current version of the kernel.
		 */
		free_mechlist(pent->suplist);
		pent->suplist = infolist;
	}

	/*
	 * kCF treats random as an internal mechanism. So, we need to
	 * filter it from the mechanism list here, if we are NOT disabling
	 * or enabling the random feature. Note that we map random feature at
	 * cryptoadm(1M) level to the "random" mechanism in kCF.
	 */
	if (!rndflag) {
		(void) filter_mechlist(&infolist, RANDOM);
	}

	/* Calculate the new disabled list */
	if (disable_mechs(&pent, infolist, allflag, dislist) == FAILURE) {
		rc = FAILURE;
		goto out;
	}

	/* Update the kcf.conf file with the updated entry */
	if (update_kcfconf(pent, MODIFY_MODE) == FAILURE) {
		rc = FAILURE;
		goto out;
	}

	/* Setup argument to inform kernel about the new disabled list. */
	if ((pload_soft_dis = setup_soft_dis(pent)) == NULL) {
		rc = FAILURE;
		goto out;
	}

	if ((fd = open(ADMIN_IOCTL_DEVICE, O_RDWR)) == -1) {
		cryptoerror(LOG_STDERR,
		    gettext("failed to open %s for RW: %s"),
		    ADMIN_IOCTL_DEVICE, strerror(errno));
		rc = FAILURE;
		goto out;
	}

	/* Inform kernel about the new disabled list. */
	if (ioctl(fd, CRYPTO_LOAD_SOFT_DISABLED, pload_soft_dis) == -1) {
		cryptodebug("CRYPTO_LOAD_SOFT_DISABLED ioctl failed: %s",
		    strerror(errno));
		rc = FAILURE;
		goto out;
	}

	if (pload_soft_dis->sd_return_value != CRYPTO_SUCCESS) {
		cryptodebug("CRYPTO_LOAD_SOFT_DISABLED ioctl return_value = "
		    "%d", pload_soft_dis->sd_return_value);
		rc = FAILURE;
		goto out;
	}

out:
	free_entrylist(phardlist);
	free_entrylist(psoftlist);
	free_mechlist(infolist);
	free_entry(pent);
	free(pload_soft_dis);
	if (fd != -1)
		(void) close(fd);
	return (rc);
}