Пример #1
0
int avtab_read_item(struct avtab *a, void *fp, struct policydb *pol,
		    int (*insertf)(struct avtab *a, struct avtab_key *k,
				   struct avtab_datum *d, void *p),
		    void *p)
{
	__le16 buf16[4];
	u16 enabled;
	__le32 buf32[7];
	u32 items, items2, val, vers = pol->policyvers;
	struct avtab_key key;
	struct avtab_datum datum;
	int i, rc;
	unsigned set;

	memset(&key, 0, sizeof(struct avtab_key));
	memset(&datum, 0, sizeof(struct avtab_datum));

	if (vers < POLICYDB_VERSION_AVTAB) {
		rc = next_entry(buf32, fp, sizeof(u32));
		if (rc) {
			printk(KERN_ERR "SELinux: avtab: truncated entry\n");
			return rc;
		}
		items2 = le32_to_cpu(buf32[0]);
		if (items2 > ARRAY_SIZE(buf32)) {
			printk(KERN_ERR "SELinux: avtab: entry overflow\n");
			return -EINVAL;

		}
		rc = next_entry(buf32, fp, sizeof(u32)*items2);
		if (rc) {
			printk(KERN_ERR "SELinux: avtab: truncated entry\n");
			return rc;
		}
		items = 0;

		val = le32_to_cpu(buf32[items++]);
		key.source_type = (u16)val;
		if (key.source_type != val) {
			printk(KERN_ERR "SELinux: avtab: truncated source type\n");
			return -EINVAL;
		}
		val = le32_to_cpu(buf32[items++]);
		key.target_type = (u16)val;
		if (key.target_type != val) {
			printk(KERN_ERR "SELinux: avtab: truncated target type\n");
			return -EINVAL;
		}
		val = le32_to_cpu(buf32[items++]);
		key.target_class = (u16)val;
		if (key.target_class != val) {
			printk(KERN_ERR "SELinux: avtab: truncated target class\n");
			return -EINVAL;
		}

		val = le32_to_cpu(buf32[items++]);
		enabled = (val & AVTAB_ENABLED_OLD) ? AVTAB_ENABLED : 0;

		if (!(val & (AVTAB_AV | AVTAB_TYPE))) {
			printk(KERN_ERR "SELinux: avtab: null entry\n");
			return -EINVAL;
		}
		if ((val & AVTAB_AV) &&
		    (val & AVTAB_TYPE)) {
			printk(KERN_ERR "SELinux: avtab: entry has both access vectors and types\n");
			return -EINVAL;
		}

		for (i = 0; i < ARRAY_SIZE(spec_order); i++) {
			if (val & spec_order[i]) {
				key.specified = spec_order[i] | enabled;
				datum.data = le32_to_cpu(buf32[items++]);
				rc = insertf(a, &key, &datum, p);
				if (rc)
					return rc;
			}
		}

		if (items != items2) {
			printk(KERN_ERR "SELinux: avtab: entry only had %d items, expected %d\n", items2, items);
			return -EINVAL;
		}
		return 0;
	}

	rc = next_entry(buf16, fp, sizeof(u16)*4);
	if (rc) {
		printk(KERN_ERR "SELinux: avtab: truncated entry\n");
		return rc;
	}

	items = 0;
	key.source_type = le16_to_cpu(buf16[items++]);
	key.target_type = le16_to_cpu(buf16[items++]);
	key.target_class = le16_to_cpu(buf16[items++]);
	key.specified = le16_to_cpu(buf16[items++]);

	if (!policydb_type_isvalid(pol, key.source_type) ||
	    !policydb_type_isvalid(pol, key.target_type) ||
	    !policydb_class_isvalid(pol, key.target_class)) {
		printk(KERN_ERR "SELinux: avtab: invalid type or class\n");
		return -EINVAL;
	}

	set = 0;
	for (i = 0; i < ARRAY_SIZE(spec_order); i++) {
		if (key.specified & spec_order[i])
			set++;
	}
	if (!set || set > 1) {
		printk(KERN_ERR "SELinux:  avtab:  more than one specifier\n");
		return -EINVAL;
	}

	rc = next_entry(buf32, fp, sizeof(u32));
	if (rc) {
		printk(KERN_ERR "SELinux: avtab: truncated entry\n");
		return rc;
	}
	datum.data = le32_to_cpu(*buf32);
	if ((key.specified & AVTAB_TYPE) &&
	    !policydb_type_isvalid(pol, datum.data)) {
		printk(KERN_ERR "SELinux: avtab: invalid type\n");
		return -EINVAL;
	}
	return insertf(a, &key, &datum, p);
}
Пример #2
0
int avtab_read_item(void *fp, u32 vers, struct avtab *a,
                            int (*insertf)(struct avtab *a, struct avtab_key *k,
                                    struct avtab_datum *d, void *p), void *p)
{
    __le16 buf16[4];
    u16 enabled;
    __le32 buf32[7];
    u32 items, items2, val;
    struct avtab_key key;
    struct avtab_datum datum;
    int i, rc;

    memset(&key, 0, sizeof(struct avtab_key));
    memset(&datum, 0, sizeof(struct avtab_datum));

    if ( vers < POLICYDB_VERSION_AVTAB )
    {
        rc = next_entry(buf32, fp, sizeof(u32));
        if ( rc < 0 )
        {
            printk(KERN_ERR "security: avtab: truncated entry\n");
            return -1;
        }
        items2 = le32_to_cpu(buf32[0]);
        if ( items2 > ARRAY_SIZE(buf32) )
        {
            printk(KERN_ERR "security: avtab: entry overflow\n");
            return -1;

        }
        rc = next_entry(buf32, fp, sizeof(u32)*items2);
        if ( rc < 0 )
        {
            printk(KERN_ERR "security: avtab: truncated entry\n");
            return -1;
        }
        items = 0;

        val = le32_to_cpu(buf32[items++]);
        key.source_type = (u16)val;
        if ( key.source_type != val )
        {
            printk("security: avtab: truncated source type\n");
            return -1;
        }
        val = le32_to_cpu(buf32[items++]);
        key.target_type = (u16)val;
        if ( key.target_type != val )
        {
            printk("security: avtab: truncated target type\n");
            return -1;
        }
        val = le32_to_cpu(buf32[items++]);
        key.target_class = (u16)val;
        if ( key.target_class != val )
        {
            printk("security: avtab: truncated target class\n");
            return -1;
        }

        val = le32_to_cpu(buf32[items++]);
        enabled = (val & AVTAB_ENABLED_OLD) ? AVTAB_ENABLED : 0;

        if ( !(val & (AVTAB_AV | AVTAB_TYPE)) )
        {
            printk("security: avtab: null entry\n");
            return -1;
        }
        if ( (val & AVTAB_AV) && (val & AVTAB_TYPE) )
        {
            printk("security: avtab: entry has both access vectors and types\n");
            return -1;
        }

        for ( i = 0; i < sizeof(spec_order)/sizeof(u16); i++ )
        {
            if ( val & spec_order[i] )
            {
                key.specified = spec_order[i] | enabled;
                datum.data = le32_to_cpu(buf32[items++]);
                rc = insertf(a, &key, &datum, p);
                if ( rc )
                    return rc;
            }
        }

        if ( items != items2 ) {
            printk("security: avtab: entry only had %d items, expected %d\n", 
                                                                items2, items);
            return -1;
        }
        return 0;
    }

    rc = next_entry(buf16, fp, sizeof(u16)*4);
    if ( rc < 0 )
    {
        printk("security: avtab: truncated entry\n");
        return -1;
    }

    items = 0;
    key.source_type = le16_to_cpu(buf16[items++]);
    key.target_type = le16_to_cpu(buf16[items++]);
    key.target_class = le16_to_cpu(buf16[items++]);
    key.specified = le16_to_cpu(buf16[items++]);

    rc = next_entry(buf32, fp, sizeof(u32));
    if ( rc < 0 )
    {
        printk("security: avtab: truncated entry\n");
        return -1;
    }
    datum.data = le32_to_cpu(*buf32);
    return insertf(a, &key, &datum, p);
}
Пример #3
0
int avtab_read_item(struct policy_file *fp, uint32_t vers, avtab_t * a,
		    int (*insertf) (avtab_t * a, avtab_key_t * k,
				    avtab_datum_t * d, void *p), void *p)
{
	uint8_t buf8;
	uint16_t buf16[4], enabled;
	uint32_t buf32[8], items, items2, val;
	avtab_key_t key;
	avtab_datum_t datum;
	avtab_extended_perms_t xperms;
	unsigned set;
	unsigned int i;
	int rc;

	memset(&key, 0, sizeof(avtab_key_t));
	memset(&datum, 0, sizeof(avtab_datum_t));
	memset(&xperms, 0, sizeof(avtab_extended_perms_t));

	if (vers < POLICYDB_VERSION_AVTAB) {
		rc = next_entry(buf32, fp, sizeof(uint32_t));
		if (rc < 0) {
			ERR(fp->handle, "truncated entry");
			return -1;
		}
		items2 = le32_to_cpu(buf32[0]);

		if (items2 < 5 || items2 > ARRAY_SIZE(buf32)) {
			ERR(fp->handle, "invalid item count");
			return -1;
		}

		rc = next_entry(buf32, fp, sizeof(uint32_t) * items2);
		if (rc < 0) {
			ERR(fp->handle, "truncated entry");
			return -1;
		}

		items = 0;
		val = le32_to_cpu(buf32[items++]);
		key.source_type = (uint16_t) val;
		if (key.source_type != val) {
			ERR(fp->handle, "truncated source type");
			return -1;
		}
		val = le32_to_cpu(buf32[items++]);
		key.target_type = (uint16_t) val;
		if (key.target_type != val) {
			ERR(fp->handle, "truncated target type");
			return -1;
		}
		val = le32_to_cpu(buf32[items++]);
		key.target_class = (uint16_t) val;
		if (key.target_class != val) {
			ERR(fp->handle, "truncated target class");
			return -1;
		}

		val = le32_to_cpu(buf32[items++]);
		enabled = (val & AVTAB_ENABLED_OLD) ? AVTAB_ENABLED : 0;

		if (!(val & (AVTAB_AV | AVTAB_TYPE))) {
			ERR(fp->handle, "null entry");
			return -1;
		}
		if ((val & AVTAB_AV) && (val & AVTAB_TYPE)) {
			ERR(fp->handle, "entry has both access "
			    "vectors and types");
			return -1;
		}

		for (i = 0; i < ARRAY_SIZE(spec_order); i++) {
			if (val & spec_order[i]) {
				key.specified = spec_order[i] | enabled;
				datum.data = le32_to_cpu(buf32[items++]);
				rc = insertf(a, &key, &datum, p);
				if (rc)
					return rc;
			}
		}

		if (items != items2) {
			ERR(fp->handle, "entry only had %d items, "
			    "expected %d", items2, items);
			return -1;
		}
		return 0;
	}

	rc = next_entry(buf16, fp, sizeof(uint16_t) * 4);
	if (rc < 0) {
		ERR(fp->handle, "truncated entry");
		return -1;
	}
	items = 0;
	key.source_type = le16_to_cpu(buf16[items++]);
	key.target_type = le16_to_cpu(buf16[items++]);
	key.target_class = le16_to_cpu(buf16[items++]);
	key.specified = le16_to_cpu(buf16[items++]);

	set = 0;
	for (i = 0; i < ARRAY_SIZE(spec_order); i++) {
		if (key.specified & spec_order[i])
			set++;
	}
	if (!set || set > 1) {
		ERR(fp->handle, "more than one specifier");
		return -1;
	}

	if ((vers < POLICYDB_VERSION_XPERMS_IOCTL) &&
			(key.specified & AVTAB_XPERMS)) {
		ERR(fp->handle, "policy version %u does not support extended "
				"permissions rules and one was specified\n", vers);
		return -1;
	} else if (key.specified & AVTAB_XPERMS) {
		rc = next_entry(&buf8, fp, sizeof(uint8_t));
		if (rc < 0) {
			ERR(fp->handle, "truncated entry");
			return -1;
		}
		xperms.specified = buf8;
		rc = next_entry(&buf8, fp, sizeof(uint8_t));
		if (rc < 0) {
			ERR(fp->handle, "truncated entry");
			return -1;
		}
		xperms.driver = buf8;
		rc = next_entry(buf32, fp, sizeof(uint32_t)*8);
		if (rc < 0) {
			ERR(fp->handle, "truncated entry");
			return -1;
		}
		for (i = 0; i < ARRAY_SIZE(xperms.perms); i++)
			xperms.perms[i] = le32_to_cpu(buf32[i]);
		datum.xperms = &xperms;
	} else {
		rc = next_entry(buf32, fp, sizeof(uint32_t));
		if (rc < 0) {
			ERR(fp->handle, "truncated entry");
			return -1;
		}
		datum.data = le32_to_cpu(*buf32);
	}
	return insertf(a, &key, &datum, p);
}