summaryrefslogtreecommitdiff
path: root/ANDROID_3.4.5/security/integrity/ima
diff options
context:
space:
mode:
Diffstat (limited to 'ANDROID_3.4.5/security/integrity/ima')
-rw-r--r--ANDROID_3.4.5/security/integrity/ima/Kconfig56
-rw-r--r--ANDROID_3.4.5/security/integrity/ima/Makefile9
-rw-r--r--ANDROID_3.4.5/security/integrity/ima/ima.h146
-rw-r--r--ANDROID_3.4.5/security/integrity/ima/ima_api.c185
-rw-r--r--ANDROID_3.4.5/security/integrity/ima/ima_audit.c66
-rw-r--r--ANDROID_3.4.5/security/integrity/ima/ima_crypto.c143
-rw-r--r--ANDROID_3.4.5/security/integrity/ima/ima_fs.c386
-rw-r--r--ANDROID_3.4.5/security/integrity/ima/ima_init.c97
-rw-r--r--ANDROID_3.4.5/security/integrity/ima/ima_main.c241
-rw-r--r--ANDROID_3.4.5/security/integrity/ima/ima_policy.c493
-rw-r--r--ANDROID_3.4.5/security/integrity/ima/ima_queue.c149
11 files changed, 0 insertions, 1971 deletions
diff --git a/ANDROID_3.4.5/security/integrity/ima/Kconfig b/ANDROID_3.4.5/security/integrity/ima/Kconfig
deleted file mode 100644
index 35664fe6..00000000
--- a/ANDROID_3.4.5/security/integrity/ima/Kconfig
+++ /dev/null
@@ -1,56 +0,0 @@
-# IBM Integrity Measurement Architecture
-#
-config IMA
- bool "Integrity Measurement Architecture(IMA)"
- depends on SECURITY
- select INTEGRITY
- select SECURITYFS
- select CRYPTO
- select CRYPTO_HMAC
- select CRYPTO_MD5
- select CRYPTO_SHA1
- select TCG_TPM if HAS_IOMEM && !UML
- select TCG_TIS if TCG_TPM && X86
- help
- The Trusted Computing Group(TCG) runtime Integrity
- Measurement Architecture(IMA) maintains a list of hash
- values of executables and other sensitive system files,
- as they are read or executed. If an attacker manages
- to change the contents of an important system file
- being measured, we can tell.
-
- If your system has a TPM chip, then IMA also maintains
- an aggregate integrity value over this list inside the
- TPM hardware, so that the TPM can prove to a third party
- whether or not critical system files have been modified.
- Read <http://www.usenix.org/events/sec04/tech/sailer.html>
- to learn more about IMA.
- If unsure, say N.
-
-config IMA_MEASURE_PCR_IDX
- int
- depends on IMA
- range 8 14
- default 10
- help
- IMA_MEASURE_PCR_IDX determines the TPM PCR register index
- that IMA uses to maintain the integrity aggregate of the
- measurement list. If unsure, use the default 10.
-
-config IMA_AUDIT
- bool
- depends on IMA
- default y
- help
- This option adds a kernel parameter 'ima_audit', which
- allows informational auditing messages to be enabled
- at boot. If this option is selected, informational integrity
- auditing messages can be enabled with 'ima_audit=1' on
- the kernel command line.
-
-config IMA_LSM_RULES
- bool
- depends on IMA && AUDIT && (SECURITY_SELINUX || SECURITY_SMACK)
- default y
- help
- Disabling this option will disregard LSM based policy rules.
diff --git a/ANDROID_3.4.5/security/integrity/ima/Makefile b/ANDROID_3.4.5/security/integrity/ima/Makefile
deleted file mode 100644
index 5690c021..00000000
--- a/ANDROID_3.4.5/security/integrity/ima/Makefile
+++ /dev/null
@@ -1,9 +0,0 @@
-#
-# Makefile for building Trusted Computing Group's(TCG) runtime Integrity
-# Measurement Architecture(IMA).
-#
-
-obj-$(CONFIG_IMA) += ima.o
-
-ima-y := ima_fs.o ima_queue.o ima_init.o ima_main.o ima_crypto.o ima_api.o \
- ima_policy.o ima_audit.o
diff --git a/ANDROID_3.4.5/security/integrity/ima/ima.h b/ANDROID_3.4.5/security/integrity/ima/ima.h
deleted file mode 100644
index 3ccf7aca..00000000
--- a/ANDROID_3.4.5/security/integrity/ima/ima.h
+++ /dev/null
@@ -1,146 +0,0 @@
-/*
- * Copyright (C) 2005,2006,2007,2008 IBM Corporation
- *
- * Authors:
- * Reiner Sailer <sailer@watson.ibm.com>
- * Mimi Zohar <zohar@us.ibm.com>
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License as
- * published by the Free Software Foundation, version 2 of the
- * License.
- *
- * File: ima.h
- * internal Integrity Measurement Architecture (IMA) definitions
- */
-
-#ifndef __LINUX_IMA_H
-#define __LINUX_IMA_H
-
-#include <linux/types.h>
-#include <linux/crypto.h>
-#include <linux/security.h>
-#include <linux/hash.h>
-#include <linux/tpm.h>
-#include <linux/audit.h>
-
-#include "../integrity.h"
-
-enum ima_show_type { IMA_SHOW_BINARY, IMA_SHOW_ASCII };
-enum tpm_pcrs { TPM_PCR0 = 0, TPM_PCR8 = 8 };
-
-/* digest size for IMA, fits SHA1 or MD5 */
-#define IMA_DIGEST_SIZE SHA1_DIGEST_SIZE
-#define IMA_EVENT_NAME_LEN_MAX 255
-
-#define IMA_HASH_BITS 9
-#define IMA_MEASURE_HTABLE_SIZE (1 << IMA_HASH_BITS)
-
-/* set during initialization */
-extern int ima_initialized;
-extern int ima_used_chip;
-extern char *ima_hash;
-
-/* IMA inode template definition */
-struct ima_template_data {
- u8 digest[IMA_DIGEST_SIZE]; /* sha1/md5 measurement hash */
- char file_name[IMA_EVENT_NAME_LEN_MAX + 1]; /* name + \0 */
-};
-
-struct ima_template_entry {
- u8 digest[IMA_DIGEST_SIZE]; /* sha1 or md5 measurement hash */
- const char *template_name;
- int template_len;
- struct ima_template_data template;
-};
-
-struct ima_queue_entry {
- struct hlist_node hnext; /* place in hash collision list */
- struct list_head later; /* place in ima_measurements list */
- struct ima_template_entry *entry;
-};
-extern struct list_head ima_measurements; /* list of all measurements */
-
-/* declarations */
-void integrity_audit_msg(int audit_msgno, struct inode *inode,
- const unsigned char *fname, const char *op,
- const char *cause, int result, int info);
-
-/* Internal IMA function definitions */
-int ima_init(void);
-void ima_cleanup(void);
-int ima_fs_init(void);
-void ima_fs_cleanup(void);
-int ima_inode_alloc(struct inode *inode);
-int ima_add_template_entry(struct ima_template_entry *entry, int violation,
- const char *op, struct inode *inode);
-int ima_calc_hash(struct file *file, char *digest);
-int ima_calc_template_hash(int template_len, void *template, char *digest);
-int ima_calc_boot_aggregate(char *digest);
-void ima_add_violation(struct inode *inode, const unsigned char *filename,
- const char *op, const char *cause);
-
-/*
- * used to protect h_table and sha_table
- */
-extern spinlock_t ima_queue_lock;
-
-struct ima_h_table {
- atomic_long_t len; /* number of stored measurements in the list */
- atomic_long_t violations;
- struct hlist_head queue[IMA_MEASURE_HTABLE_SIZE];
-};
-extern struct ima_h_table ima_htable;
-
-static inline unsigned long ima_hash_key(u8 *digest)
-{
- return hash_long(*digest, IMA_HASH_BITS);
-}
-
-/* LIM API function definitions */
-int ima_must_measure(struct inode *inode, int mask, int function);
-int ima_collect_measurement(struct integrity_iint_cache *iint,
- struct file *file);
-void ima_store_measurement(struct integrity_iint_cache *iint, struct file *file,
- const unsigned char *filename);
-int ima_store_template(struct ima_template_entry *entry, int violation,
- struct inode *inode);
-void ima_template_show(struct seq_file *m, void *e, enum ima_show_type show);
-
-/* rbtree tree calls to lookup, insert, delete
- * integrity data associated with an inode.
- */
-struct integrity_iint_cache *integrity_iint_insert(struct inode *inode);
-struct integrity_iint_cache *integrity_iint_find(struct inode *inode);
-
-/* IMA policy related functions */
-enum ima_hooks { FILE_CHECK = 1, FILE_MMAP, BPRM_CHECK };
-
-int ima_match_policy(struct inode *inode, enum ima_hooks func, int mask);
-void ima_init_policy(void);
-void ima_update_policy(void);
-ssize_t ima_parse_add_rule(char *);
-void ima_delete_rules(void);
-
-/* LSM based policy rules require audit */
-#ifdef CONFIG_IMA_LSM_RULES
-
-#define security_filter_rule_init security_audit_rule_init
-#define security_filter_rule_match security_audit_rule_match
-
-#else
-
-static inline int security_filter_rule_init(u32 field, u32 op, char *rulestr,
- void **lsmrule)
-{
- return -EINVAL;
-}
-
-static inline int security_filter_rule_match(u32 secid, u32 field, u32 op,
- void *lsmrule,
- struct audit_context *actx)
-{
- return -EINVAL;
-}
-#endif /* CONFIG_IMA_LSM_RULES */
-#endif
diff --git a/ANDROID_3.4.5/security/integrity/ima/ima_api.c b/ANDROID_3.4.5/security/integrity/ima/ima_api.c
deleted file mode 100644
index 88a2788b..00000000
--- a/ANDROID_3.4.5/security/integrity/ima/ima_api.c
+++ /dev/null
@@ -1,185 +0,0 @@
-/*
- * Copyright (C) 2008 IBM Corporation
- *
- * Author: Mimi Zohar <zohar@us.ibm.com>
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License as
- * published by the Free Software Foundation, version 2 of the
- * License.
- *
- * File: ima_api.c
- * Implements must_measure, collect_measurement, store_measurement,
- * and store_template.
- */
-#include <linux/module.h>
-#include <linux/slab.h>
-
-#include "ima.h"
-static const char *IMA_TEMPLATE_NAME = "ima";
-
-/*
- * ima_store_template - store ima template measurements
- *
- * Calculate the hash of a template entry, add the template entry
- * to an ordered list of measurement entries maintained inside the kernel,
- * and also update the aggregate integrity value (maintained inside the
- * configured TPM PCR) over the hashes of the current list of measurement
- * entries.
- *
- * Applications retrieve the current kernel-held measurement list through
- * the securityfs entries in /sys/kernel/security/ima. The signed aggregate
- * TPM PCR (called quote) can be retrieved using a TPM user space library
- * and is used to validate the measurement list.
- *
- * Returns 0 on success, error code otherwise
- */
-int ima_store_template(struct ima_template_entry *entry,
- int violation, struct inode *inode)
-{
- const char *op = "add_template_measure";
- const char *audit_cause = "hashing_error";
- int result;
-
- memset(entry->digest, 0, sizeof(entry->digest));
- entry->template_name = IMA_TEMPLATE_NAME;
- entry->template_len = sizeof(entry->template);
-
- if (!violation) {
- result = ima_calc_template_hash(entry->template_len,
- &entry->template,
- entry->digest);
- if (result < 0) {
- integrity_audit_msg(AUDIT_INTEGRITY_PCR, inode,
- entry->template_name, op,
- audit_cause, result, 0);
- return result;
- }
- }
- result = ima_add_template_entry(entry, violation, op, inode);
- return result;
-}
-
-/*
- * ima_add_violation - add violation to measurement list.
- *
- * Violations are flagged in the measurement list with zero hash values.
- * By extending the PCR with 0xFF's instead of with zeroes, the PCR
- * value is invalidated.
- */
-void ima_add_violation(struct inode *inode, const unsigned char *filename,
- const char *op, const char *cause)
-{
- struct ima_template_entry *entry;
- int violation = 1;
- int result;
-
- /* can overflow, only indicator */
- atomic_long_inc(&ima_htable.violations);
-
- entry = kmalloc(sizeof(*entry), GFP_KERNEL);
- if (!entry) {
- result = -ENOMEM;
- goto err_out;
- }
- memset(&entry->template, 0, sizeof(entry->template));
- strncpy(entry->template.file_name, filename, IMA_EVENT_NAME_LEN_MAX);
- result = ima_store_template(entry, violation, inode);
- if (result < 0)
- kfree(entry);
-err_out:
- integrity_audit_msg(AUDIT_INTEGRITY_PCR, inode, filename,
- op, cause, result, 0);
-}
-
-/**
- * ima_must_measure - measure decision based on policy.
- * @inode: pointer to inode to measure
- * @mask: contains the permission mask (MAY_READ, MAY_WRITE, MAY_EXECUTE)
- * @function: calling function (FILE_CHECK, BPRM_CHECK, FILE_MMAP)
- *
- * The policy is defined in terms of keypairs:
- * subj=, obj=, type=, func=, mask=, fsmagic=
- * subj,obj, and type: are LSM specific.
- * func: FILE_CHECK | BPRM_CHECK | FILE_MMAP
- * mask: contains the permission mask
- * fsmagic: hex value
- *
- * Return 0 to measure. For matching a DONT_MEASURE policy, no policy,
- * or other error, return an error code.
-*/
-int ima_must_measure(struct inode *inode, int mask, int function)
-{
- int must_measure;
-
- must_measure = ima_match_policy(inode, function, mask);
- return must_measure ? 0 : -EACCES;
-}
-
-/*
- * ima_collect_measurement - collect file measurement
- *
- * Calculate the file hash, if it doesn't already exist,
- * storing the measurement and i_version in the iint.
- *
- * Must be called with iint->mutex held.
- *
- * Return 0 on success, error code otherwise
- */
-int ima_collect_measurement(struct integrity_iint_cache *iint,
- struct file *file)
-{
- int result = -EEXIST;
-
- if (!(iint->flags & IMA_MEASURED)) {
- u64 i_version = file->f_dentry->d_inode->i_version;
-
- memset(iint->digest, 0, IMA_DIGEST_SIZE);
- result = ima_calc_hash(file, iint->digest);
- if (!result)
- iint->version = i_version;
- }
- return result;
-}
-
-/*
- * ima_store_measurement - store file measurement
- *
- * Create an "ima" template and then store the template by calling
- * ima_store_template.
- *
- * We only get here if the inode has not already been measured,
- * but the measurement could already exist:
- * - multiple copies of the same file on either the same or
- * different filesystems.
- * - the inode was previously flushed as well as the iint info,
- * containing the hashing info.
- *
- * Must be called with iint->mutex held.
- */
-void ima_store_measurement(struct integrity_iint_cache *iint,
- struct file *file, const unsigned char *filename)
-{
- const char *op = "add_template_measure";
- const char *audit_cause = "ENOMEM";
- int result = -ENOMEM;
- struct inode *inode = file->f_dentry->d_inode;
- struct ima_template_entry *entry;
- int violation = 0;
-
- entry = kmalloc(sizeof(*entry), GFP_KERNEL);
- if (!entry) {
- integrity_audit_msg(AUDIT_INTEGRITY_PCR, inode, filename,
- op, audit_cause, result, 0);
- return;
- }
- memset(&entry->template, 0, sizeof(entry->template));
- memcpy(entry->template.digest, iint->digest, IMA_DIGEST_SIZE);
- strncpy(entry->template.file_name, filename, IMA_EVENT_NAME_LEN_MAX);
-
- result = ima_store_template(entry, violation, inode);
- if (!result || result == -EEXIST)
- iint->flags |= IMA_MEASURED;
- if (result < 0)
- kfree(entry);
-}
diff --git a/ANDROID_3.4.5/security/integrity/ima/ima_audit.c b/ANDROID_3.4.5/security/integrity/ima/ima_audit.c
deleted file mode 100644
index 21e96bf1..00000000
--- a/ANDROID_3.4.5/security/integrity/ima/ima_audit.c
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * Copyright (C) 2008 IBM Corporation
- * Author: Mimi Zohar <zohar@us.ibm.com>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, version 2 of the License.
- *
- * File: integrity_audit.c
- * Audit calls for the integrity subsystem
- */
-
-#include <linux/fs.h>
-#include <linux/gfp.h>
-#include <linux/audit.h>
-#include "ima.h"
-
-static int ima_audit;
-
-#ifdef CONFIG_IMA_AUDIT
-
-/* ima_audit_setup - enable informational auditing messages */
-static int __init ima_audit_setup(char *str)
-{
- unsigned long audit;
-
- if (!strict_strtoul(str, 0, &audit))
- ima_audit = audit ? 1 : 0;
- return 1;
-}
-__setup("ima_audit=", ima_audit_setup);
-#endif
-
-void integrity_audit_msg(int audit_msgno, struct inode *inode,
- const unsigned char *fname, const char *op,
- const char *cause, int result, int audit_info)
-{
- struct audit_buffer *ab;
-
- if (!ima_audit && audit_info == 1) /* Skip informational messages */
- return;
-
- ab = audit_log_start(current->audit_context, GFP_KERNEL, audit_msgno);
- audit_log_format(ab, "pid=%d uid=%u auid=%u ses=%u",
- current->pid, current_cred()->uid,
- audit_get_loginuid(current),
- audit_get_sessionid(current));
- audit_log_task_context(ab);
- audit_log_format(ab, " op=");
- audit_log_string(ab, op);
- audit_log_format(ab, " cause=");
- audit_log_string(ab, cause);
- audit_log_format(ab, " comm=");
- audit_log_untrustedstring(ab, current->comm);
- if (fname) {
- audit_log_format(ab, " name=");
- audit_log_untrustedstring(ab, fname);
- }
- if (inode) {
- audit_log_format(ab, " dev=");
- audit_log_untrustedstring(ab, inode->i_sb->s_id);
- audit_log_format(ab, " ino=%lu", inode->i_ino);
- }
- audit_log_format(ab, " res=%d", !result);
- audit_log_end(ab);
-}
diff --git a/ANDROID_3.4.5/security/integrity/ima/ima_crypto.c b/ANDROID_3.4.5/security/integrity/ima/ima_crypto.c
deleted file mode 100644
index 9b3ade74..00000000
--- a/ANDROID_3.4.5/security/integrity/ima/ima_crypto.c
+++ /dev/null
@@ -1,143 +0,0 @@
-/*
- * Copyright (C) 2005,2006,2007,2008 IBM Corporation
- *
- * Authors:
- * Mimi Zohar <zohar@us.ibm.com>
- * Kylene Hall <kjhall@us.ibm.com>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, version 2 of the License.
- *
- * File: ima_crypto.c
- * Calculates md5/sha1 file hash, template hash, boot-aggreate hash
- */
-
-#include <linux/kernel.h>
-#include <linux/file.h>
-#include <linux/crypto.h>
-#include <linux/scatterlist.h>
-#include <linux/err.h>
-#include <linux/slab.h>
-#include "ima.h"
-
-static int init_desc(struct hash_desc *desc)
-{
- int rc;
-
- desc->tfm = crypto_alloc_hash(ima_hash, 0, CRYPTO_ALG_ASYNC);
- if (IS_ERR(desc->tfm)) {
- pr_info("IMA: failed to load %s transform: %ld\n",
- ima_hash, PTR_ERR(desc->tfm));
- rc = PTR_ERR(desc->tfm);
- return rc;
- }
- desc->flags = 0;
- rc = crypto_hash_init(desc);
- if (rc)
- crypto_free_hash(desc->tfm);
- return rc;
-}
-
-/*
- * Calculate the MD5/SHA1 file digest
- */
-int ima_calc_hash(struct file *file, char *digest)
-{
- struct hash_desc desc;
- struct scatterlist sg[1];
- loff_t i_size, offset = 0;
- char *rbuf;
- int rc;
-
- rc = init_desc(&desc);
- if (rc != 0)
- return rc;
-
- rbuf = kzalloc(PAGE_SIZE, GFP_KERNEL);
- if (!rbuf) {
- rc = -ENOMEM;
- goto out;
- }
- i_size = i_size_read(file->f_dentry->d_inode);
- while (offset < i_size) {
- int rbuf_len;
-
- rbuf_len = kernel_read(file, offset, rbuf, PAGE_SIZE);
- if (rbuf_len < 0) {
- rc = rbuf_len;
- break;
- }
- if (rbuf_len == 0)
- break;
- offset += rbuf_len;
- sg_init_one(sg, rbuf, rbuf_len);
-
- rc = crypto_hash_update(&desc, sg, rbuf_len);
- if (rc)
- break;
- }
- kfree(rbuf);
- if (!rc)
- rc = crypto_hash_final(&desc, digest);
-out:
- crypto_free_hash(desc.tfm);
- return rc;
-}
-
-/*
- * Calculate the hash of a given template
- */
-int ima_calc_template_hash(int template_len, void *template, char *digest)
-{
- struct hash_desc desc;
- struct scatterlist sg[1];
- int rc;
-
- rc = init_desc(&desc);
- if (rc != 0)
- return rc;
-
- sg_init_one(sg, template, template_len);
- rc = crypto_hash_update(&desc, sg, template_len);
- if (!rc)
- rc = crypto_hash_final(&desc, digest);
- crypto_free_hash(desc.tfm);
- return rc;
-}
-
-static void __init ima_pcrread(int idx, u8 *pcr)
-{
- if (!ima_used_chip)
- return;
-
- if (tpm_pcr_read(TPM_ANY_NUM, idx, pcr) != 0)
- pr_err("IMA: Error Communicating to TPM chip\n");
-}
-
-/*
- * Calculate the boot aggregate hash
- */
-int __init ima_calc_boot_aggregate(char *digest)
-{
- struct hash_desc desc;
- struct scatterlist sg;
- u8 pcr_i[IMA_DIGEST_SIZE];
- int rc, i;
-
- rc = init_desc(&desc);
- if (rc != 0)
- return rc;
-
- /* cumulative sha1 over tpm registers 0-7 */
- for (i = TPM_PCR0; i < TPM_PCR8; i++) {
- ima_pcrread(i, pcr_i);
- /* now accumulate with current aggregate */
- sg_init_one(&sg, pcr_i, IMA_DIGEST_SIZE);
- rc = crypto_hash_update(&desc, &sg, IMA_DIGEST_SIZE);
- }
- if (!rc)
- crypto_hash_final(&desc, digest);
- crypto_free_hash(desc.tfm);
- return rc;
-}
diff --git a/ANDROID_3.4.5/security/integrity/ima/ima_fs.c b/ANDROID_3.4.5/security/integrity/ima/ima_fs.c
deleted file mode 100644
index e1aa2b48..00000000
--- a/ANDROID_3.4.5/security/integrity/ima/ima_fs.c
+++ /dev/null
@@ -1,386 +0,0 @@
-/*
- * Copyright (C) 2005,2006,2007,2008 IBM Corporation
- *
- * Authors:
- * Kylene Hall <kjhall@us.ibm.com>
- * Reiner Sailer <sailer@us.ibm.com>
- * Mimi Zohar <zohar@us.ibm.com>
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License as
- * published by the Free Software Foundation, version 2 of the
- * License.
- *
- * File: ima_fs.c
- * implemenents security file system for reporting
- * current measurement list and IMA statistics
- */
-#include <linux/fcntl.h>
-#include <linux/slab.h>
-#include <linux/module.h>
-#include <linux/seq_file.h>
-#include <linux/rculist.h>
-#include <linux/rcupdate.h>
-#include <linux/parser.h>
-
-#include "ima.h"
-
-static int valid_policy = 1;
-#define TMPBUFLEN 12
-static ssize_t ima_show_htable_value(char __user *buf, size_t count,
- loff_t *ppos, atomic_long_t *val)
-{
- char tmpbuf[TMPBUFLEN];
- ssize_t len;
-
- len = scnprintf(tmpbuf, TMPBUFLEN, "%li\n", atomic_long_read(val));
- return simple_read_from_buffer(buf, count, ppos, tmpbuf, len);
-}
-
-static ssize_t ima_show_htable_violations(struct file *filp,
- char __user *buf,
- size_t count, loff_t *ppos)
-{
- return ima_show_htable_value(buf, count, ppos, &ima_htable.violations);
-}
-
-static const struct file_operations ima_htable_violations_ops = {
- .read = ima_show_htable_violations,
- .llseek = generic_file_llseek,
-};
-
-static ssize_t ima_show_measurements_count(struct file *filp,
- char __user *buf,
- size_t count, loff_t *ppos)
-{
- return ima_show_htable_value(buf, count, ppos, &ima_htable.len);
-
-}
-
-static const struct file_operations ima_measurements_count_ops = {
- .read = ima_show_measurements_count,
- .llseek = generic_file_llseek,
-};
-
-/* returns pointer to hlist_node */
-static void *ima_measurements_start(struct seq_file *m, loff_t *pos)
-{
- loff_t l = *pos;
- struct ima_queue_entry *qe;
-
- /* we need a lock since pos could point beyond last element */
- rcu_read_lock();
- list_for_each_entry_rcu(qe, &ima_measurements, later) {
- if (!l--) {
- rcu_read_unlock();
- return qe;
- }
- }
- rcu_read_unlock();
- return NULL;
-}
-
-static void *ima_measurements_next(struct seq_file *m, void *v, loff_t *pos)
-{
- struct ima_queue_entry *qe = v;
-
- /* lock protects when reading beyond last element
- * against concurrent list-extension
- */
- rcu_read_lock();
- qe = list_entry_rcu(qe->later.next,
- struct ima_queue_entry, later);
- rcu_read_unlock();
- (*pos)++;
-
- return (&qe->later == &ima_measurements) ? NULL : qe;
-}
-
-static void ima_measurements_stop(struct seq_file *m, void *v)
-{
-}
-
-static void ima_putc(struct seq_file *m, void *data, int datalen)
-{
- while (datalen--)
- seq_putc(m, *(char *)data++);
-}
-
-/* print format:
- * 32bit-le=pcr#
- * char[20]=template digest
- * 32bit-le=template name size
- * char[n]=template name
- * eventdata[n]=template specific data
- */
-static int ima_measurements_show(struct seq_file *m, void *v)
-{
- /* the list never shrinks, so we don't need a lock here */
- struct ima_queue_entry *qe = v;
- struct ima_template_entry *e;
- int namelen;
- u32 pcr = CONFIG_IMA_MEASURE_PCR_IDX;
-
- /* get entry */
- e = qe->entry;
- if (e == NULL)
- return -1;
-
- /*
- * 1st: PCRIndex
- * PCR used is always the same (config option) in
- * little-endian format
- */
- ima_putc(m, &pcr, sizeof pcr);
-
- /* 2nd: template digest */
- ima_putc(m, e->digest, IMA_DIGEST_SIZE);
-
- /* 3rd: template name size */
- namelen = strlen(e->template_name);
- ima_putc(m, &namelen, sizeof namelen);
-
- /* 4th: template name */
- ima_putc(m, (void *)e->template_name, namelen);
-
- /* 5th: template specific data */
- ima_template_show(m, (struct ima_template_data *)&e->template,
- IMA_SHOW_BINARY);
- return 0;
-}
-
-static const struct seq_operations ima_measurments_seqops = {
- .start = ima_measurements_start,
- .next = ima_measurements_next,
- .stop = ima_measurements_stop,
- .show = ima_measurements_show
-};
-
-static int ima_measurements_open(struct inode *inode, struct file *file)
-{
- return seq_open(file, &ima_measurments_seqops);
-}
-
-static const struct file_operations ima_measurements_ops = {
- .open = ima_measurements_open,
- .read = seq_read,
- .llseek = seq_lseek,
- .release = seq_release,
-};
-
-static void ima_print_digest(struct seq_file *m, u8 *digest)
-{
- int i;
-
- for (i = 0; i < IMA_DIGEST_SIZE; i++)
- seq_printf(m, "%02x", *(digest + i));
-}
-
-void ima_template_show(struct seq_file *m, void *e, enum ima_show_type show)
-{
- struct ima_template_data *entry = e;
- int namelen;
-
- switch (show) {
- case IMA_SHOW_ASCII:
- ima_print_digest(m, entry->digest);
- seq_printf(m, " %s\n", entry->file_name);
- break;
- case IMA_SHOW_BINARY:
- ima_putc(m, entry->digest, IMA_DIGEST_SIZE);
-
- namelen = strlen(entry->file_name);
- ima_putc(m, &namelen, sizeof namelen);
- ima_putc(m, entry->file_name, namelen);
- default:
- break;
- }
-}
-
-/* print in ascii */
-static int ima_ascii_measurements_show(struct seq_file *m, void *v)
-{
- /* the list never shrinks, so we don't need a lock here */
- struct ima_queue_entry *qe = v;
- struct ima_template_entry *e;
-
- /* get entry */
- e = qe->entry;
- if (e == NULL)
- return -1;
-
- /* 1st: PCR used (config option) */
- seq_printf(m, "%2d ", CONFIG_IMA_MEASURE_PCR_IDX);
-
- /* 2nd: SHA1 template hash */
- ima_print_digest(m, e->digest);
-
- /* 3th: template name */
- seq_printf(m, " %s ", e->template_name);
-
- /* 4th: template specific data */
- ima_template_show(m, (struct ima_template_data *)&e->template,
- IMA_SHOW_ASCII);
- return 0;
-}
-
-static const struct seq_operations ima_ascii_measurements_seqops = {
- .start = ima_measurements_start,
- .next = ima_measurements_next,
- .stop = ima_measurements_stop,
- .show = ima_ascii_measurements_show
-};
-
-static int ima_ascii_measurements_open(struct inode *inode, struct file *file)
-{
- return seq_open(file, &ima_ascii_measurements_seqops);
-}
-
-static const struct file_operations ima_ascii_measurements_ops = {
- .open = ima_ascii_measurements_open,
- .read = seq_read,
- .llseek = seq_lseek,
- .release = seq_release,
-};
-
-static ssize_t ima_write_policy(struct file *file, const char __user *buf,
- size_t datalen, loff_t *ppos)
-{
- char *data = NULL;
- ssize_t result;
-
- if (datalen >= PAGE_SIZE)
- datalen = PAGE_SIZE - 1;
-
- /* No partial writes. */
- result = -EINVAL;
- if (*ppos != 0)
- goto out;
-
- result = -ENOMEM;
- data = kmalloc(datalen + 1, GFP_KERNEL);
- if (!data)
- goto out;
-
- *(data + datalen) = '\0';
-
- result = -EFAULT;
- if (copy_from_user(data, buf, datalen))
- goto out;
-
- result = ima_parse_add_rule(data);
-out:
- if (result < 0)
- valid_policy = 0;
- kfree(data);
- return result;
-}
-
-static struct dentry *ima_dir;
-static struct dentry *binary_runtime_measurements;
-static struct dentry *ascii_runtime_measurements;
-static struct dentry *runtime_measurements_count;
-static struct dentry *violations;
-static struct dentry *ima_policy;
-
-static atomic_t policy_opencount = ATOMIC_INIT(1);
-/*
- * ima_open_policy: sequentialize access to the policy file
- */
-static int ima_open_policy(struct inode * inode, struct file * filp)
-{
- /* No point in being allowed to open it if you aren't going to write */
- if (!(filp->f_flags & O_WRONLY))
- return -EACCES;
- if (atomic_dec_and_test(&policy_opencount))
- return 0;
- return -EBUSY;
-}
-
-/*
- * ima_release_policy - start using the new measure policy rules.
- *
- * Initially, ima_measure points to the default policy rules, now
- * point to the new policy rules, and remove the securityfs policy file,
- * assuming a valid policy.
- */
-static int ima_release_policy(struct inode *inode, struct file *file)
-{
- if (!valid_policy) {
- ima_delete_rules();
- valid_policy = 1;
- atomic_set(&policy_opencount, 1);
- return 0;
- }
- ima_update_policy();
- securityfs_remove(ima_policy);
- ima_policy = NULL;
- return 0;
-}
-
-static const struct file_operations ima_measure_policy_ops = {
- .open = ima_open_policy,
- .write = ima_write_policy,
- .release = ima_release_policy,
- .llseek = generic_file_llseek,
-};
-
-int __init ima_fs_init(void)
-{
- ima_dir = securityfs_create_dir("ima", NULL);
- if (IS_ERR(ima_dir))
- return -1;
-
- binary_runtime_measurements =
- securityfs_create_file("binary_runtime_measurements",
- S_IRUSR | S_IRGRP, ima_dir, NULL,
- &ima_measurements_ops);
- if (IS_ERR(binary_runtime_measurements))
- goto out;
-
- ascii_runtime_measurements =
- securityfs_create_file("ascii_runtime_measurements",
- S_IRUSR | S_IRGRP, ima_dir, NULL,
- &ima_ascii_measurements_ops);
- if (IS_ERR(ascii_runtime_measurements))
- goto out;
-
- runtime_measurements_count =
- securityfs_create_file("runtime_measurements_count",
- S_IRUSR | S_IRGRP, ima_dir, NULL,
- &ima_measurements_count_ops);
- if (IS_ERR(runtime_measurements_count))
- goto out;
-
- violations =
- securityfs_create_file("violations", S_IRUSR | S_IRGRP,
- ima_dir, NULL, &ima_htable_violations_ops);
- if (IS_ERR(violations))
- goto out;
-
- ima_policy = securityfs_create_file("policy",
- S_IWUSR,
- ima_dir, NULL,
- &ima_measure_policy_ops);
- if (IS_ERR(ima_policy))
- goto out;
-
- return 0;
-out:
- securityfs_remove(runtime_measurements_count);
- securityfs_remove(ascii_runtime_measurements);
- securityfs_remove(binary_runtime_measurements);
- securityfs_remove(ima_dir);
- securityfs_remove(ima_policy);
- return -1;
-}
-
-void __exit ima_fs_cleanup(void)
-{
- securityfs_remove(violations);
- securityfs_remove(runtime_measurements_count);
- securityfs_remove(ascii_runtime_measurements);
- securityfs_remove(binary_runtime_measurements);
- securityfs_remove(ima_dir);
- securityfs_remove(ima_policy);
-}
diff --git a/ANDROID_3.4.5/security/integrity/ima/ima_init.c b/ANDROID_3.4.5/security/integrity/ima/ima_init.c
deleted file mode 100644
index 17f1f060..00000000
--- a/ANDROID_3.4.5/security/integrity/ima/ima_init.c
+++ /dev/null
@@ -1,97 +0,0 @@
-/*
- * Copyright (C) 2005,2006,2007,2008 IBM Corporation
- *
- * Authors:
- * Reiner Sailer <sailer@watson.ibm.com>
- * Leendert van Doorn <leendert@watson.ibm.com>
- * Mimi Zohar <zohar@us.ibm.com>
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License as
- * published by the Free Software Foundation, version 2 of the
- * License.
- *
- * File: ima_init.c
- * initialization and cleanup functions
- */
-#include <linux/module.h>
-#include <linux/scatterlist.h>
-#include <linux/slab.h>
-#include <linux/err.h>
-#include "ima.h"
-
-/* name for boot aggregate entry */
-static const char *boot_aggregate_name = "boot_aggregate";
-int ima_used_chip;
-
-/* Add the boot aggregate to the IMA measurement list and extend
- * the PCR register.
- *
- * Calculate the boot aggregate, a SHA1 over tpm registers 0-7,
- * assuming a TPM chip exists, and zeroes if the TPM chip does not
- * exist. Add the boot aggregate measurement to the measurement
- * list and extend the PCR register.
- *
- * If a tpm chip does not exist, indicate the core root of trust is
- * not hardware based by invalidating the aggregate PCR value.
- * (The aggregate PCR value is invalidated by adding one value to
- * the measurement list and extending the aggregate PCR value with
- * a different value.) Violations add a zero entry to the measurement
- * list and extend the aggregate PCR value with ff...ff's.
- */
-static void __init ima_add_boot_aggregate(void)
-{
- struct ima_template_entry *entry;
- const char *op = "add_boot_aggregate";
- const char *audit_cause = "ENOMEM";
- int result = -ENOMEM;
- int violation = 1;
-
- entry = kmalloc(sizeof(*entry), GFP_KERNEL);
- if (!entry)
- goto err_out;
-
- memset(&entry->template, 0, sizeof(entry->template));
- strncpy(entry->template.file_name, boot_aggregate_name,
- IMA_EVENT_NAME_LEN_MAX);
- if (ima_used_chip) {
- violation = 0;
- result = ima_calc_boot_aggregate(entry->template.digest);
- if (result < 0) {
- audit_cause = "hashing_error";
- kfree(entry);
- goto err_out;
- }
- }
- result = ima_store_template(entry, violation, NULL);
- if (result < 0)
- kfree(entry);
- return;
-err_out:
- integrity_audit_msg(AUDIT_INTEGRITY_PCR, NULL, boot_aggregate_name, op,
- audit_cause, result, 0);
-}
-
-int __init ima_init(void)
-{
- u8 pcr_i[IMA_DIGEST_SIZE];
- int rc;
-
- ima_used_chip = 0;
- rc = tpm_pcr_read(TPM_ANY_NUM, 0, pcr_i);
- if (rc == 0)
- ima_used_chip = 1;
-
- if (!ima_used_chip)
- pr_info("IMA: No TPM chip found, activating TPM-bypass!\n");
-
- ima_add_boot_aggregate(); /* boot aggregate must be first entry */
- ima_init_policy();
-
- return ima_fs_init();
-}
-
-void __exit ima_cleanup(void)
-{
- ima_fs_cleanup();
-}
diff --git a/ANDROID_3.4.5/security/integrity/ima/ima_main.c b/ANDROID_3.4.5/security/integrity/ima/ima_main.c
deleted file mode 100644
index 1eff5cb0..00000000
--- a/ANDROID_3.4.5/security/integrity/ima/ima_main.c
+++ /dev/null
@@ -1,241 +0,0 @@
-/*
- * Copyright (C) 2005,2006,2007,2008 IBM Corporation
- *
- * Authors:
- * Reiner Sailer <sailer@watson.ibm.com>
- * Serge Hallyn <serue@us.ibm.com>
- * Kylene Hall <kylene@us.ibm.com>
- * Mimi Zohar <zohar@us.ibm.com>
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License as
- * published by the Free Software Foundation, version 2 of the
- * License.
- *
- * File: ima_main.c
- * implements the IMA hooks: ima_bprm_check, ima_file_mmap,
- * and ima_file_check.
- */
-#include <linux/module.h>
-#include <linux/file.h>
-#include <linux/binfmts.h>
-#include <linux/mount.h>
-#include <linux/mman.h>
-#include <linux/slab.h>
-#include <linux/ima.h>
-
-#include "ima.h"
-
-int ima_initialized;
-
-char *ima_hash = "sha1";
-static int __init hash_setup(char *str)
-{
- if (strncmp(str, "md5", 3) == 0)
- ima_hash = "md5";
- return 1;
-}
-__setup("ima_hash=", hash_setup);
-
-/*
- * ima_rdwr_violation_check
- *
- * Only invalidate the PCR for measured files:
- * - Opening a file for write when already open for read,
- * results in a time of measure, time of use (ToMToU) error.
- * - Opening a file for read when already open for write,
- * could result in a file measurement error.
- *
- */
-static void ima_rdwr_violation_check(struct file *file)
-{
- struct dentry *dentry = file->f_path.dentry;
- struct inode *inode = dentry->d_inode;
- fmode_t mode = file->f_mode;
- int rc;
- bool send_tomtou = false, send_writers = false;
-
- if (!S_ISREG(inode->i_mode) || !ima_initialized)
- return;
-
- mutex_lock(&inode->i_mutex); /* file metadata: permissions, xattr */
-
- if (mode & FMODE_WRITE) {
- if (atomic_read(&inode->i_readcount) && IS_IMA(inode))
- send_tomtou = true;
- goto out;
- }
-
- rc = ima_must_measure(inode, MAY_READ, FILE_CHECK);
- if (rc < 0)
- goto out;
-
- if (atomic_read(&inode->i_writecount) > 0)
- send_writers = true;
-out:
- mutex_unlock(&inode->i_mutex);
-
- if (send_tomtou)
- ima_add_violation(inode, dentry->d_name.name, "invalid_pcr",
- "ToMToU");
- if (send_writers)
- ima_add_violation(inode, dentry->d_name.name, "invalid_pcr",
- "open_writers");
-}
-
-static void ima_check_last_writer(struct integrity_iint_cache *iint,
- struct inode *inode,
- struct file *file)
-{
- fmode_t mode = file->f_mode;
-
- mutex_lock(&iint->mutex);
- if (mode & FMODE_WRITE &&
- atomic_read(&inode->i_writecount) == 1 &&
- iint->version != inode->i_version)
- iint->flags &= ~IMA_MEASURED;
- mutex_unlock(&iint->mutex);
-}
-
-/**
- * ima_file_free - called on __fput()
- * @file: pointer to file structure being freed
- *
- * Flag files that changed, based on i_version
- */
-void ima_file_free(struct file *file)
-{
- struct inode *inode = file->f_dentry->d_inode;
- struct integrity_iint_cache *iint;
-
- if (!iint_initialized || !S_ISREG(inode->i_mode))
- return;
-
- iint = integrity_iint_find(inode);
- if (!iint)
- return;
-
- ima_check_last_writer(iint, inode, file);
-}
-
-static int process_measurement(struct file *file, const unsigned char *filename,
- int mask, int function)
-{
- struct inode *inode = file->f_dentry->d_inode;
- struct integrity_iint_cache *iint;
- int rc = 0;
-
- if (!ima_initialized || !S_ISREG(inode->i_mode))
- return 0;
-
- rc = ima_must_measure(inode, mask, function);
- if (rc != 0)
- return rc;
-retry:
- iint = integrity_iint_find(inode);
- if (!iint) {
- rc = integrity_inode_alloc(inode);
- if (!rc || rc == -EEXIST)
- goto retry;
- return rc;
- }
-
- mutex_lock(&iint->mutex);
-
- rc = iint->flags & IMA_MEASURED ? 1 : 0;
- if (rc != 0)
- goto out;
-
- rc = ima_collect_measurement(iint, file);
- if (!rc)
- ima_store_measurement(iint, file, filename);
-out:
- mutex_unlock(&iint->mutex);
- return rc;
-}
-
-/**
- * ima_file_mmap - based on policy, collect/store measurement.
- * @file: pointer to the file to be measured (May be NULL)
- * @prot: contains the protection that will be applied by the kernel.
- *
- * Measure files being mmapped executable based on the ima_must_measure()
- * policy decision.
- *
- * Return 0 on success, an error code on failure.
- * (Based on the results of appraise_measurement().)
- */
-int ima_file_mmap(struct file *file, unsigned long prot)
-{
- int rc;
-
- if (!file)
- return 0;
- if (prot & PROT_EXEC)
- rc = process_measurement(file, file->f_dentry->d_name.name,
- MAY_EXEC, FILE_MMAP);
- return 0;
-}
-
-/**
- * ima_bprm_check - based on policy, collect/store measurement.
- * @bprm: contains the linux_binprm structure
- *
- * The OS protects against an executable file, already open for write,
- * from being executed in deny_write_access() and an executable file,
- * already open for execute, from being modified in get_write_access().
- * So we can be certain that what we verify and measure here is actually
- * what is being executed.
- *
- * Return 0 on success, an error code on failure.
- * (Based on the results of appraise_measurement().)
- */
-int ima_bprm_check(struct linux_binprm *bprm)
-{
- int rc;
-
- rc = process_measurement(bprm->file, bprm->filename,
- MAY_EXEC, BPRM_CHECK);
- return 0;
-}
-
-/**
- * ima_path_check - based on policy, collect/store measurement.
- * @file: pointer to the file to be measured
- * @mask: contains MAY_READ, MAY_WRITE or MAY_EXECUTE
- *
- * Measure files based on the ima_must_measure() policy decision.
- *
- * Always return 0 and audit dentry_open failures.
- * (Return code will be based upon measurement appraisal.)
- */
-int ima_file_check(struct file *file, int mask)
-{
- int rc;
-
- ima_rdwr_violation_check(file);
- rc = process_measurement(file, file->f_dentry->d_name.name,
- mask & (MAY_READ | MAY_WRITE | MAY_EXEC),
- FILE_CHECK);
- return 0;
-}
-EXPORT_SYMBOL_GPL(ima_file_check);
-
-static int __init init_ima(void)
-{
- int error;
-
- error = ima_init();
- ima_initialized = 1;
- return error;
-}
-
-static void __exit cleanup_ima(void)
-{
- ima_cleanup();
-}
-
-late_initcall(init_ima); /* Start IMA after the TPM is available */
-
-MODULE_DESCRIPTION("Integrity Measurement Architecture");
-MODULE_LICENSE("GPL");
diff --git a/ANDROID_3.4.5/security/integrity/ima/ima_policy.c b/ANDROID_3.4.5/security/integrity/ima/ima_policy.c
deleted file mode 100644
index d8edff20..00000000
--- a/ANDROID_3.4.5/security/integrity/ima/ima_policy.c
+++ /dev/null
@@ -1,493 +0,0 @@
-/*
- * Copyright (C) 2008 IBM Corporation
- * Author: Mimi Zohar <zohar@us.ibm.com>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, version 2 of the License.
- *
- * ima_policy.c
- * - initialize default measure policy rules
- *
- */
-#include <linux/module.h>
-#include <linux/list.h>
-#include <linux/security.h>
-#include <linux/magic.h>
-#include <linux/parser.h>
-#include <linux/slab.h>
-
-#include "ima.h"
-
-/* flags definitions */
-#define IMA_FUNC 0x0001
-#define IMA_MASK 0x0002
-#define IMA_FSMAGIC 0x0004
-#define IMA_UID 0x0008
-
-enum ima_action { UNKNOWN = -1, DONT_MEASURE = 0, MEASURE };
-
-#define MAX_LSM_RULES 6
-enum lsm_rule_types { LSM_OBJ_USER, LSM_OBJ_ROLE, LSM_OBJ_TYPE,
- LSM_SUBJ_USER, LSM_SUBJ_ROLE, LSM_SUBJ_TYPE
-};
-
-struct ima_measure_rule_entry {
- struct list_head list;
- enum ima_action action;
- unsigned int flags;
- enum ima_hooks func;
- int mask;
- unsigned long fsmagic;
- uid_t uid;
- struct {
- void *rule; /* LSM file metadata specific */
- int type; /* audit type */
- } lsm[MAX_LSM_RULES];
-};
-
-/*
- * Without LSM specific knowledge, the default policy can only be
- * written in terms of .action, .func, .mask, .fsmagic, and .uid
- */
-
-/*
- * The minimum rule set to allow for full TCB coverage. Measures all files
- * opened or mmap for exec and everything read by root. Dangerous because
- * normal users can easily run the machine out of memory simply building
- * and running executables.
- */
-static struct ima_measure_rule_entry default_rules[] = {
- {.action = DONT_MEASURE,.fsmagic = PROC_SUPER_MAGIC,.flags = IMA_FSMAGIC},
- {.action = DONT_MEASURE,.fsmagic = SYSFS_MAGIC,.flags = IMA_FSMAGIC},
- {.action = DONT_MEASURE,.fsmagic = DEBUGFS_MAGIC,.flags = IMA_FSMAGIC},
- {.action = DONT_MEASURE,.fsmagic = TMPFS_MAGIC,.flags = IMA_FSMAGIC},
- {.action = DONT_MEASURE,.fsmagic = RAMFS_MAGIC,.flags = IMA_FSMAGIC},
- {.action = DONT_MEASURE,.fsmagic = SECURITYFS_MAGIC,.flags = IMA_FSMAGIC},
- {.action = DONT_MEASURE,.fsmagic = SELINUX_MAGIC,.flags = IMA_FSMAGIC},
- {.action = MEASURE,.func = FILE_MMAP,.mask = MAY_EXEC,
- .flags = IMA_FUNC | IMA_MASK},
- {.action = MEASURE,.func = BPRM_CHECK,.mask = MAY_EXEC,
- .flags = IMA_FUNC | IMA_MASK},
- {.action = MEASURE,.func = FILE_CHECK,.mask = MAY_READ,.uid = 0,
- .flags = IMA_FUNC | IMA_MASK | IMA_UID},
-};
-
-static LIST_HEAD(measure_default_rules);
-static LIST_HEAD(measure_policy_rules);
-static struct list_head *ima_measure;
-
-static DEFINE_MUTEX(ima_measure_mutex);
-
-static bool ima_use_tcb __initdata;
-static int __init default_policy_setup(char *str)
-{
- ima_use_tcb = 1;
- return 1;
-}
-__setup("ima_tcb", default_policy_setup);
-
-/**
- * ima_match_rules - determine whether an inode matches the measure rule.
- * @rule: a pointer to a rule
- * @inode: a pointer to an inode
- * @func: LIM hook identifier
- * @mask: requested action (MAY_READ | MAY_WRITE | MAY_APPEND | MAY_EXEC)
- *
- * Returns true on rule match, false on failure.
- */
-static bool ima_match_rules(struct ima_measure_rule_entry *rule,
- struct inode *inode, enum ima_hooks func, int mask)
-{
- struct task_struct *tsk = current;
- const struct cred *cred = current_cred();
- int i;
-
- if ((rule->flags & IMA_FUNC) && rule->func != func)
- return false;
- if ((rule->flags & IMA_MASK) && rule->mask != mask)
- return false;
- if ((rule->flags & IMA_FSMAGIC)
- && rule->fsmagic != inode->i_sb->s_magic)
- return false;
- if ((rule->flags & IMA_UID) && rule->uid != cred->uid)
- return false;
- for (i = 0; i < MAX_LSM_RULES; i++) {
- int rc = 0;
- u32 osid, sid;
-
- if (!rule->lsm[i].rule)
- continue;
-
- switch (i) {
- case LSM_OBJ_USER:
- case LSM_OBJ_ROLE:
- case LSM_OBJ_TYPE:
- security_inode_getsecid(inode, &osid);
- rc = security_filter_rule_match(osid,
- rule->lsm[i].type,
- Audit_equal,
- rule->lsm[i].rule,
- NULL);
- break;
- case LSM_SUBJ_USER:
- case LSM_SUBJ_ROLE:
- case LSM_SUBJ_TYPE:
- security_task_getsecid(tsk, &sid);
- rc = security_filter_rule_match(sid,
- rule->lsm[i].type,
- Audit_equal,
- rule->lsm[i].rule,
- NULL);
- default:
- break;
- }
- if (!rc)
- return false;
- }
- return true;
-}
-
-/**
- * ima_match_policy - decision based on LSM and other conditions
- * @inode: pointer to an inode for which the policy decision is being made
- * @func: IMA hook identifier
- * @mask: requested action (MAY_READ | MAY_WRITE | MAY_APPEND | MAY_EXEC)
- *
- * Measure decision based on func/mask/fsmagic and LSM(subj/obj/type)
- * conditions.
- *
- * (There is no need for locking when walking the policy list,
- * as elements in the list are never deleted, nor does the list
- * change.)
- */
-int ima_match_policy(struct inode *inode, enum ima_hooks func, int mask)
-{
- struct ima_measure_rule_entry *entry;
-
- list_for_each_entry(entry, ima_measure, list) {
- bool rc;
-
- rc = ima_match_rules(entry, inode, func, mask);
- if (rc)
- return entry->action;
- }
- return 0;
-}
-
-/**
- * ima_init_policy - initialize the default measure rules.
- *
- * ima_measure points to either the measure_default_rules or the
- * the new measure_policy_rules.
- */
-void __init ima_init_policy(void)
-{
- int i, entries;
-
- /* if !ima_use_tcb set entries = 0 so we load NO default rules */
- if (ima_use_tcb)
- entries = ARRAY_SIZE(default_rules);
- else
- entries = 0;
-
- for (i = 0; i < entries; i++)
- list_add_tail(&default_rules[i].list, &measure_default_rules);
- ima_measure = &measure_default_rules;
-}
-
-/**
- * ima_update_policy - update default_rules with new measure rules
- *
- * Called on file .release to update the default rules with a complete new
- * policy. Once updated, the policy is locked, no additional rules can be
- * added to the policy.
- */
-void ima_update_policy(void)
-{
- const char *op = "policy_update";
- const char *cause = "already exists";
- int result = 1;
- int audit_info = 0;
-
- if (ima_measure == &measure_default_rules) {
- ima_measure = &measure_policy_rules;
- cause = "complete";
- result = 0;
- }
- integrity_audit_msg(AUDIT_INTEGRITY_STATUS, NULL,
- NULL, op, cause, result, audit_info);
-}
-
-enum {
- Opt_err = -1,
- Opt_measure = 1, Opt_dont_measure,
- Opt_obj_user, Opt_obj_role, Opt_obj_type,
- Opt_subj_user, Opt_subj_role, Opt_subj_type,
- Opt_func, Opt_mask, Opt_fsmagic, Opt_uid
-};
-
-static match_table_t policy_tokens = {
- {Opt_measure, "measure"},
- {Opt_dont_measure, "dont_measure"},
- {Opt_obj_user, "obj_user=%s"},
- {Opt_obj_role, "obj_role=%s"},
- {Opt_obj_type, "obj_type=%s"},
- {Opt_subj_user, "subj_user=%s"},
- {Opt_subj_role, "subj_role=%s"},
- {Opt_subj_type, "subj_type=%s"},
- {Opt_func, "func=%s"},
- {Opt_mask, "mask=%s"},
- {Opt_fsmagic, "fsmagic=%s"},
- {Opt_uid, "uid=%s"},
- {Opt_err, NULL}
-};
-
-static int ima_lsm_rule_init(struct ima_measure_rule_entry *entry,
- char *args, int lsm_rule, int audit_type)
-{
- int result;
-
- if (entry->lsm[lsm_rule].rule)
- return -EINVAL;
-
- entry->lsm[lsm_rule].type = audit_type;
- result = security_filter_rule_init(entry->lsm[lsm_rule].type,
- Audit_equal, args,
- &entry->lsm[lsm_rule].rule);
- if (!entry->lsm[lsm_rule].rule)
- return -EINVAL;
- return result;
-}
-
-static void ima_log_string(struct audit_buffer *ab, char *key, char *value)
-{
- audit_log_format(ab, "%s=", key);
- audit_log_untrustedstring(ab, value);
- audit_log_format(ab, " ");
-}
-
-static int ima_parse_rule(char *rule, struct ima_measure_rule_entry *entry)
-{
- struct audit_buffer *ab;
- char *p;
- int result = 0;
-
- ab = audit_log_start(NULL, GFP_KERNEL, AUDIT_INTEGRITY_RULE);
-
- entry->uid = -1;
- entry->action = UNKNOWN;
- while ((p = strsep(&rule, " \t")) != NULL) {
- substring_t args[MAX_OPT_ARGS];
- int token;
- unsigned long lnum;
-
- if (result < 0)
- break;
- if ((*p == '\0') || (*p == ' ') || (*p == '\t'))
- continue;
- token = match_token(p, policy_tokens, args);
- switch (token) {
- case Opt_measure:
- ima_log_string(ab, "action", "measure");
-
- if (entry->action != UNKNOWN)
- result = -EINVAL;
-
- entry->action = MEASURE;
- break;
- case Opt_dont_measure:
- ima_log_string(ab, "action", "dont_measure");
-
- if (entry->action != UNKNOWN)
- result = -EINVAL;
-
- entry->action = DONT_MEASURE;
- break;
- case Opt_func:
- ima_log_string(ab, "func", args[0].from);
-
- if (entry->func)
- result = -EINVAL;
-
- if (strcmp(args[0].from, "FILE_CHECK") == 0)
- entry->func = FILE_CHECK;
- /* PATH_CHECK is for backwards compat */
- else if (strcmp(args[0].from, "PATH_CHECK") == 0)
- entry->func = FILE_CHECK;
- else if (strcmp(args[0].from, "FILE_MMAP") == 0)
- entry->func = FILE_MMAP;
- else if (strcmp(args[0].from, "BPRM_CHECK") == 0)
- entry->func = BPRM_CHECK;
- else
- result = -EINVAL;
- if (!result)
- entry->flags |= IMA_FUNC;
- break;
- case Opt_mask:
- ima_log_string(ab, "mask", args[0].from);
-
- if (entry->mask)
- result = -EINVAL;
-
- if ((strcmp(args[0].from, "MAY_EXEC")) == 0)
- entry->mask = MAY_EXEC;
- else if (strcmp(args[0].from, "MAY_WRITE") == 0)
- entry->mask = MAY_WRITE;
- else if (strcmp(args[0].from, "MAY_READ") == 0)
- entry->mask = MAY_READ;
- else if (strcmp(args[0].from, "MAY_APPEND") == 0)
- entry->mask = MAY_APPEND;
- else
- result = -EINVAL;
- if (!result)
- entry->flags |= IMA_MASK;
- break;
- case Opt_fsmagic:
- ima_log_string(ab, "fsmagic", args[0].from);
-
- if (entry->fsmagic) {
- result = -EINVAL;
- break;
- }
-
- result = strict_strtoul(args[0].from, 16,
- &entry->fsmagic);
- if (!result)
- entry->flags |= IMA_FSMAGIC;
- break;
- case Opt_uid:
- ima_log_string(ab, "uid", args[0].from);
-
- if (entry->uid != -1) {
- result = -EINVAL;
- break;
- }
-
- result = strict_strtoul(args[0].from, 10, &lnum);
- if (!result) {
- entry->uid = (uid_t) lnum;
- if (entry->uid != lnum)
- result = -EINVAL;
- else
- entry->flags |= IMA_UID;
- }
- break;
- case Opt_obj_user:
- ima_log_string(ab, "obj_user", args[0].from);
- result = ima_lsm_rule_init(entry, args[0].from,
- LSM_OBJ_USER,
- AUDIT_OBJ_USER);
- break;
- case Opt_obj_role:
- ima_log_string(ab, "obj_role", args[0].from);
- result = ima_lsm_rule_init(entry, args[0].from,
- LSM_OBJ_ROLE,
- AUDIT_OBJ_ROLE);
- break;
- case Opt_obj_type:
- ima_log_string(ab, "obj_type", args[0].from);
- result = ima_lsm_rule_init(entry, args[0].from,
- LSM_OBJ_TYPE,
- AUDIT_OBJ_TYPE);
- break;
- case Opt_subj_user:
- ima_log_string(ab, "subj_user", args[0].from);
- result = ima_lsm_rule_init(entry, args[0].from,
- LSM_SUBJ_USER,
- AUDIT_SUBJ_USER);
- break;
- case Opt_subj_role:
- ima_log_string(ab, "subj_role", args[0].from);
- result = ima_lsm_rule_init(entry, args[0].from,
- LSM_SUBJ_ROLE,
- AUDIT_SUBJ_ROLE);
- break;
- case Opt_subj_type:
- ima_log_string(ab, "subj_type", args[0].from);
- result = ima_lsm_rule_init(entry, args[0].from,
- LSM_SUBJ_TYPE,
- AUDIT_SUBJ_TYPE);
- break;
- case Opt_err:
- ima_log_string(ab, "UNKNOWN", p);
- result = -EINVAL;
- break;
- }
- }
- if (!result && (entry->action == UNKNOWN))
- result = -EINVAL;
-
- audit_log_format(ab, "res=%d", !result);
- audit_log_end(ab);
- return result;
-}
-
-/**
- * ima_parse_add_rule - add a rule to measure_policy_rules
- * @rule - ima measurement policy rule
- *
- * Uses a mutex to protect the policy list from multiple concurrent writers.
- * Returns the length of the rule parsed, an error code on failure
- */
-ssize_t ima_parse_add_rule(char *rule)
-{
- const char *op = "update_policy";
- char *p;
- struct ima_measure_rule_entry *entry;
- ssize_t result, len;
- int audit_info = 0;
-
- /* Prevent installed policy from changing */
- if (ima_measure != &measure_default_rules) {
- integrity_audit_msg(AUDIT_INTEGRITY_STATUS, NULL,
- NULL, op, "already exists",
- -EACCES, audit_info);
- return -EACCES;
- }
-
- entry = kzalloc(sizeof(*entry), GFP_KERNEL);
- if (!entry) {
- integrity_audit_msg(AUDIT_INTEGRITY_STATUS, NULL,
- NULL, op, "-ENOMEM", -ENOMEM, audit_info);
- return -ENOMEM;
- }
-
- INIT_LIST_HEAD(&entry->list);
-
- p = strsep(&rule, "\n");
- len = strlen(p) + 1;
-
- if (*p == '#') {
- kfree(entry);
- return len;
- }
-
- result = ima_parse_rule(p, entry);
- if (result) {
- kfree(entry);
- integrity_audit_msg(AUDIT_INTEGRITY_STATUS, NULL,
- NULL, op, "invalid policy", result,
- audit_info);
- return result;
- }
-
- mutex_lock(&ima_measure_mutex);
- list_add_tail(&entry->list, &measure_policy_rules);
- mutex_unlock(&ima_measure_mutex);
-
- return len;
-}
-
-/* ima_delete_rules called to cleanup invalid policy */
-void ima_delete_rules(void)
-{
- struct ima_measure_rule_entry *entry, *tmp;
-
- mutex_lock(&ima_measure_mutex);
- list_for_each_entry_safe(entry, tmp, &measure_policy_rules, list) {
- list_del(&entry->list);
- kfree(entry);
- }
- mutex_unlock(&ima_measure_mutex);
-}
diff --git a/ANDROID_3.4.5/security/integrity/ima/ima_queue.c b/ANDROID_3.4.5/security/integrity/ima/ima_queue.c
deleted file mode 100644
index 55a6271b..00000000
--- a/ANDROID_3.4.5/security/integrity/ima/ima_queue.c
+++ /dev/null
@@ -1,149 +0,0 @@
-/*
- * Copyright (C) 2005,2006,2007,2008 IBM Corporation
- *
- * Authors:
- * Serge Hallyn <serue@us.ibm.com>
- * Reiner Sailer <sailer@watson.ibm.com>
- * Mimi Zohar <zohar@us.ibm.com>
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License as
- * published by the Free Software Foundation, version 2 of the
- * License.
- *
- * File: ima_queue.c
- * Implements queues that store template measurements and
- * maintains aggregate over the stored measurements
- * in the pre-configured TPM PCR (if available).
- * The measurement list is append-only. No entry is
- * ever removed or changed during the boot-cycle.
- */
-#include <linux/module.h>
-#include <linux/rculist.h>
-#include <linux/slab.h>
-#include "ima.h"
-
-#define AUDIT_CAUSE_LEN_MAX 32
-
-LIST_HEAD(ima_measurements); /* list of all measurements */
-
-/* key: inode (before secure-hashing a file) */
-struct ima_h_table ima_htable = {
- .len = ATOMIC_LONG_INIT(0),
- .violations = ATOMIC_LONG_INIT(0),
- .queue[0 ... IMA_MEASURE_HTABLE_SIZE - 1] = HLIST_HEAD_INIT
-};
-
-/* mutex protects atomicity of extending measurement list
- * and extending the TPM PCR aggregate. Since tpm_extend can take
- * long (and the tpm driver uses a mutex), we can't use the spinlock.
- */
-static DEFINE_MUTEX(ima_extend_list_mutex);
-
-/* lookup up the digest value in the hash table, and return the entry */
-static struct ima_queue_entry *ima_lookup_digest_entry(u8 *digest_value)
-{
- struct ima_queue_entry *qe, *ret = NULL;
- unsigned int key;
- struct hlist_node *pos;
- int rc;
-
- key = ima_hash_key(digest_value);
- rcu_read_lock();
- hlist_for_each_entry_rcu(qe, pos, &ima_htable.queue[key], hnext) {
- rc = memcmp(qe->entry->digest, digest_value, IMA_DIGEST_SIZE);
- if (rc == 0) {
- ret = qe;
- break;
- }
- }
- rcu_read_unlock();
- return ret;
-}
-
-/* ima_add_template_entry helper function:
- * - Add template entry to measurement list and hash table.
- *
- * (Called with ima_extend_list_mutex held.)
- */
-static int ima_add_digest_entry(struct ima_template_entry *entry)
-{
- struct ima_queue_entry *qe;
- unsigned int key;
-
- qe = kmalloc(sizeof(*qe), GFP_KERNEL);
- if (qe == NULL) {
- pr_err("IMA: OUT OF MEMORY ERROR creating queue entry.\n");
- return -ENOMEM;
- }
- qe->entry = entry;
-
- INIT_LIST_HEAD(&qe->later);
- list_add_tail_rcu(&qe->later, &ima_measurements);
-
- atomic_long_inc(&ima_htable.len);
- key = ima_hash_key(entry->digest);
- hlist_add_head_rcu(&qe->hnext, &ima_htable.queue[key]);
- return 0;
-}
-
-static int ima_pcr_extend(const u8 *hash)
-{
- int result = 0;
-
- if (!ima_used_chip)
- return result;
-
- result = tpm_pcr_extend(TPM_ANY_NUM, CONFIG_IMA_MEASURE_PCR_IDX, hash);
- if (result != 0)
- pr_err("IMA: Error Communicating to TPM chip, result: %d\n",
- result);
- return result;
-}
-
-/* Add template entry to the measurement list and hash table,
- * and extend the pcr.
- */
-int ima_add_template_entry(struct ima_template_entry *entry, int violation,
- const char *op, struct inode *inode)
-{
- u8 digest[IMA_DIGEST_SIZE];
- const char *audit_cause = "hash_added";
- char tpm_audit_cause[AUDIT_CAUSE_LEN_MAX];
- int audit_info = 1;
- int result = 0, tpmresult = 0;
-
- mutex_lock(&ima_extend_list_mutex);
- if (!violation) {
- memcpy(digest, entry->digest, sizeof digest);
- if (ima_lookup_digest_entry(digest)) {
- audit_cause = "hash_exists";
- result = -EEXIST;
- goto out;
- }
- }
-
- result = ima_add_digest_entry(entry);
- if (result < 0) {
- audit_cause = "ENOMEM";
- audit_info = 0;
- goto out;
- }
-
- if (violation) /* invalidate pcr */
- memset(digest, 0xff, sizeof digest);
-
- tpmresult = ima_pcr_extend(digest);
- if (tpmresult != 0) {
- snprintf(tpm_audit_cause, AUDIT_CAUSE_LEN_MAX, "TPM_error(%d)",
- tpmresult);
- audit_cause = tpm_audit_cause;
- audit_info = 0;
- }
-out:
- mutex_unlock(&ima_extend_list_mutex);
- integrity_audit_msg(AUDIT_INTEGRITY_PCR, inode,
- entry->template.file_name,
- op, audit_cause, result, audit_info);
- return result;
-}