Пример #1
0
static int
sysctl_integriforce_so(SYSCTL_HANDLER_ARGS)
{
    integriforce_so_check_t *integriforce_so;
    secadm_prison_entry_t *entry;
    secadm_rule_t r, *rule;
    struct nameidata nd;
    struct vattr vap;
    secadm_key_t key;
    int err;

    if (!(req->newptr) || req->newlen != sizeof(integriforce_so_check_t))
        return (EINVAL);

    if (!(req->oldptr) || req->oldlen != sizeof(integriforce_so_check_t))
        return (EINVAL);

    integriforce_so = malloc(sizeof(integriforce_so_check_t), M_SECADM, M_WAITOK);

    err = SYSCTL_IN(req, integriforce_so, sizeof(integriforce_so_check_t));
    if (err) {
        free(integriforce_so, M_SECADM);
        return (err);
    }

    NDINIT(&nd, LOOKUP, FOLLOW, UIO_SYSSPACE, integriforce_so->isc_path, req->td);
    err = namei(&nd);
    if (err) {
        free(integriforce_so, M_SECADM);
        NDFREE(&nd, 0);
        return (err);
    }

    if ((err = vn_lock(nd.ni_vp, LK_SHARED | LK_RETRY)) != 0) {
        free(integriforce_so, M_SECADM);
        NDFREE(&nd, 0);
        return (err);
    }

    err = VOP_GETATTR(nd.ni_vp, &vap, req->td->td_ucred);
    if (err) {
        free(integriforce_so, M_SECADM);
        NDFREE(&nd, 0);
        return (err);
    }

    VOP_UNLOCK(nd.ni_vp, 0);

    key.sk_jid = req->td->td_ucred->cr_prison->pr_id;
    key.sk_type = secadm_integriforce_rule;
    key.sk_fileid = vap.va_fileid;
    strncpy(key.sk_mntonname,
            nd.ni_vp->v_mount->mnt_stat.f_mntonname, MNAMELEN);
    r.sr_key = fnv_32_buf(&key, sizeof(secadm_key_t), FNV1_32_INIT);

    entry = get_prison_list_entry(
                req->td->td_ucred->cr_prison->pr_id);

    PE_RLOCK(entry);
    rule = RB_FIND(secadm_rules_tree, &(entry->sp_rules), &r);

    if (rule) {
        integriforce_so->isc_result =
            do_integriforce_check(rule, &vap, nd.ni_vp,
                                  req->td->td_ucred);
    }

    PE_RUNLOCK(entry);

    SYSCTL_OUT(req, integriforce_so, sizeof(integriforce_so_check_t));
    free(integriforce_so, M_SECADM);

    NDFREE(&nd, 0);

    return (0);
}
Пример #2
0
int
secadm_vnode_check_exec(struct ucred *ucred, struct vnode *vp,
    struct label *vplabel, struct image_params *imgp,
    struct label *execlabel)
{
	struct rm_priotracker tracker;
	struct secadm_prison_entry *entry;
	secadm_rule_t *rule;
	struct vattr vap;
	size_t i;
	int err=0, flags=0;

	entry = get_prison_list_entry(ucred->cr_prison->pr_name, 0);
	if (entry == NULL)
		return (0);

	err = VOP_GETATTR(imgp->vp, &vap, ucred);
	if (err)
		return (err);

	SPL_RLOCK(entry, tracker);
	for (rule = entry->spl_rules; rule != NULL; rule = rule->sr_next) {
		if (vap.va_fileid != rule->sr_inode)
			continue;

		if (strcmp(imgp->vp->v_mount->mnt_stat.f_mntonname,
		    rule->sr_mount))
			continue;

		for (i=0; i < rule->sr_nfeatures; i++) {
			switch(rule->sr_features[i].sf_type) {
			case pageexec_enabled:
				flags |= PAX_NOTE_PAGEEXEC;
				break;
			case pageexec_disabled:
				flags |= PAX_NOTE_NOPAGEEXEC;
				break;
			case mprotect_enabled:
				flags |= PAX_NOTE_MPROTECT;
				break;
			case mprotect_disabled:
				flags |= PAX_NOTE_NOMPROTECT;
				break;
			case segvguard_enabled:
				flags |= PAX_NOTE_SEGVGUARD;
				break;
			case segvguard_disabled:
				flags |= PAX_NOTE_NOSEGVGUARD;
				break;
			case aslr_enabled:
				flags |= PAX_NOTE_ASLR;
				break;
			case aslr_disabled:
				flags |= PAX_NOTE_NOASLR;
				break;
			case integriforce:
				err = do_integriforce_check(rule, &vap, imgp->vp, ucred);
				break;
#if __HardenedBSD_version > 21
			case shlibrandom_enabled:
				flags |= PAX_NOTE_SHLIBRANDOM;
				break;
			case shlibrandom_disabled:
				flags |= PAX_NOTE_NOSHLIBRANDOM;
				break;
#endif
			default:
				break;
			}
		}

		break;
	}

	SPL_RUNLOCK(entry, tracker);

	if (err == 0 && flags)
		err = pax_elf(imgp, flags);

	return (err);
}