1 /* 2 * AppArmor security module 3 * 4 * This file contains AppArmor auditing functions 5 * 6 * Copyright (C) 1998-2008 Novell/SUSE 7 * Copyright 2009-2010 Canonical Ltd. 8 * 9 * This program is free software; you can redistribute it and/or 10 * modify it under the terms of the GNU General Public License as 11 * published by the Free Software Foundation, version 2 of the 12 * License. 13 */ 14 15 #include <linux/audit.h> 16 #include <linux/socket.h> 17 18 #include "include/apparmor.h" 19 #include "include/audit.h" 20 #include "include/policy.h" 21 22 const char *const op_table[] = { 23 "null", 24 25 "sysctl", 26 "capable", 27 28 "unlink", 29 "mkdir", 30 "rmdir", 31 "mknod", 32 "truncate", 33 "link", 34 "symlink", 35 "rename_src", 36 "rename_dest", 37 "chmod", 38 "chown", 39 "getattr", 40 "open", 41 42 "file_perm", 43 "file_lock", 44 "file_mmap", 45 "file_mprotect", 46 47 "create", 48 "post_create", 49 "bind", 50 "connect", 51 "listen", 52 "accept", 53 "sendmsg", 54 "recvmsg", 55 "getsockname", 56 "getpeername", 57 "getsockopt", 58 "setsockopt", 59 "socket_shutdown", 60 61 "ptrace", 62 63 "exec", 64 "change_hat", 65 "change_profile", 66 "change_onexec", 67 68 "setprocattr", 69 "setrlimit", 70 71 "profile_replace", 72 "profile_load", 73 "profile_remove" 74 }; 75 76 const char *const audit_mode_names[] = { 77 "normal", 78 "quiet_denied", 79 "quiet", 80 "noquiet", 81 "all" 82 }; 83 84 static const char *const aa_audit_type[] = { 85 "AUDIT", 86 "ALLOWED", 87 "DENIED", 88 "HINT", 89 "STATUS", 90 "ERROR", 91 "KILLED" 92 "AUTO" 93 }; 94 95 /* 96 * Currently AppArmor auditing is fed straight into the audit framework. 97 * 98 * TODO: 99 * netlink interface for complain mode 100 * user auditing, - send user auditing to netlink interface 101 * system control of whether user audit messages go to system log 102 */ 103 104 /** 105 * audit_base - core AppArmor function. 106 * @ab: audit buffer to fill (NOT NULL) 107 * @ca: audit structure containing data to audit (NOT NULL) 108 * 109 * Record common AppArmor audit data from @sa 110 */ 111 static void audit_pre(struct audit_buffer *ab, void *ca) 112 { 113 struct common_audit_data *sa = ca; 114 struct task_struct *tsk = sa->aad->tsk ? sa->aad->tsk : current; 115 116 if (aa_g_audit_header) { 117 audit_log_format(ab, "apparmor="); 118 audit_log_string(ab, aa_audit_type[sa->aad->type]); 119 } 120 121 if (sa->aad->op) { 122 audit_log_format(ab, " operation="); 123 audit_log_string(ab, op_table[sa->aad->op]); 124 } 125 126 if (sa->aad->info) { 127 audit_log_format(ab, " info="); 128 audit_log_string(ab, sa->aad->info); 129 if (sa->aad->error) 130 audit_log_format(ab, " error=%d", sa->aad->error); 131 } 132 133 if (sa->aad->profile) { 134 struct aa_profile *profile = sa->aad->profile; 135 pid_t pid; 136 rcu_read_lock(); 137 pid = rcu_dereference(tsk->real_parent)->pid; 138 rcu_read_unlock(); 139 audit_log_format(ab, " parent=%d", pid); 140 if (profile->ns != root_ns) { 141 audit_log_format(ab, " namespace="); 142 audit_log_untrustedstring(ab, profile->ns->base.hname); 143 } 144 audit_log_format(ab, " profile="); 145 audit_log_untrustedstring(ab, profile->base.hname); 146 } 147 148 if (sa->aad->name) { 149 audit_log_format(ab, " name="); 150 audit_log_untrustedstring(ab, sa->aad->name); 151 } 152 153 if (sa->aad->tsk) { 154 audit_log_format(ab, " pid=%d comm=", tsk->pid); 155 audit_log_untrustedstring(ab, tsk->comm); 156 } 157 158 } 159 160 /** 161 * aa_audit_msg - Log a message to the audit subsystem 162 * @sa: audit event structure (NOT NULL) 163 * @cb: optional callback fn for type specific fields (MAYBE NULL) 164 */ 165 void aa_audit_msg(int type, struct common_audit_data *sa, 166 void (*cb) (struct audit_buffer *, void *)) 167 { 168 sa->aad->type = type; 169 common_lsm_audit(sa, audit_pre, cb); 170 } 171 172 /** 173 * aa_audit - Log a profile based audit event to the audit subsystem 174 * @type: audit type for the message 175 * @profile: profile to check against (NOT NULL) 176 * @gfp: allocation flags to use 177 * @sa: audit event (NOT NULL) 178 * @cb: optional callback fn for type specific fields (MAYBE NULL) 179 * 180 * Handle default message switching based off of audit mode flags 181 * 182 * Returns: error on failure 183 */ 184 int aa_audit(int type, struct aa_profile *profile, gfp_t gfp, 185 struct common_audit_data *sa, 186 void (*cb) (struct audit_buffer *, void *)) 187 { 188 BUG_ON(!profile); 189 190 if (type == AUDIT_APPARMOR_AUTO) { 191 if (likely(!sa->aad->error)) { 192 if (AUDIT_MODE(profile) != AUDIT_ALL) 193 return 0; 194 type = AUDIT_APPARMOR_AUDIT; 195 } else if (COMPLAIN_MODE(profile)) 196 type = AUDIT_APPARMOR_ALLOWED; 197 else 198 type = AUDIT_APPARMOR_DENIED; 199 } 200 if (AUDIT_MODE(profile) == AUDIT_QUIET || 201 (type == AUDIT_APPARMOR_DENIED && 202 AUDIT_MODE(profile) == AUDIT_QUIET)) 203 return sa->aad->error; 204 205 if (KILL_MODE(profile) && type == AUDIT_APPARMOR_DENIED) 206 type = AUDIT_APPARMOR_KILL; 207 208 if (!unconfined(profile)) 209 sa->aad->profile = profile; 210 211 aa_audit_msg(type, sa, cb); 212 213 if (sa->aad->type == AUDIT_APPARMOR_KILL) 214 (void)send_sig_info(SIGKILL, NULL, 215 sa->aad->tsk ? sa->aad->tsk : current); 216 217 if (sa->aad->type == AUDIT_APPARMOR_ALLOWED) 218 return complain_error(sa->aad->error); 219 220 return sa->aad->error; 221 } 222