Add signal rules and make sure the parser encodes support for them
if the supported feature set reports supporting them.

The current format of the signal rule is

  [audit] [deny] signal [<signal_perms>] [<signal_set>] <target_profile>,

  signal_perm  := 'send'|'receive'|'r'|'w'|'rw'
  signal_perms := <signal_perm> | '(' <signal_perm> ([,]<signal_perm>)* ')'
  signal := ("hup"|"int"|"quit"|"ill"|"trap"|"abrt"|"bus"|"fpe"|"kill"|
             "usr1"|"segv"|"usr2"|"pipe"|"alrm"|"term"|"tkflt"|"chld"|
             "cont"|"stop"|"stp"|"ttin"|"ttou"|"urg"|"xcpu"|"xfsz"|"vtalrm"|
             "prof"|"winch"|"io"|"pwr"|"sys"|"emt"|"exists")
  signal_set   := set=<signal> | '(' <signal> ([,]<signal>)* ')'


it does not currently follow the peer=() format, and there is some question
as to whether it should or not. Input welcome.


---
 parser/Makefile        |    8 +
 parser/parser.h        |    5 
 parser/parser_common.c |    1 
 parser/parser_lex.l    |   22 ++-
 parser/parser_main.c   |    2 
 parser/parser_misc.c   |    1 
 parser/parser_regex.c  |    7 -
 parser/parser_yacc.y   |   68 +++++++++++
 parser/policydb.h      |    1 
 parser/signal.c        |  290 +++++++++++++++++++++++++++++++++++++++++++++++++
 parser/signal.h        |   58 +++++++++
 11 files changed, 451 insertions(+), 12 deletions(-)

--- 2.9-test.orig/parser/Makefile
+++ 2.9-test/parser/Makefile
@@ -79,8 +79,9 @@
 SRCS = parser_common.c parser_include.c parser_interface.c parser_lex.c \
        parser_main.c parser_misc.c parser_merge.c parser_symtab.c \
        parser_yacc.c parser_regex.c parser_variable.c parser_policy.c \
-       parser_alias.c mount.c dbus.c lib.c profile.cc rule.c
-HDRS = parser.h parser_include.h immunix.h mount.h dbus.h lib.h profile.h 
rule.h
+       parser_alias.c mount.c dbus.c lib.c profile.cc rule.c signal.c
+HDRS = parser.h parser_include.h immunix.h mount.h dbus.h lib.h profile.h \
+       rule.h signal.h
 TOOLS = apparmor_parser
 
 OBJECTS = $(SRCS:.c=.o)
@@ -239,6 +240,9 @@
 dbus.o: dbus.c dbus.h parser.h immunix.h parser_yacc.h rule.h $(APPARMOR_H)
        $(CXX) $(EXTRA_CFLAGS) -c -o $@ $<
 
+signal.o: signal.c signal.h parser.h immunix.h parser_yacc.h rule.h 
$(APPARMOR_H)
+       $(CXX) $(EXTRA_CFLAGS) -c -o $@ $<
+
 profile.o: profile.cc profile.h parser.h
        $(CXX) $(EXTRA_CFLAGS) -c -o $@ $<
 
--- 2.9-test.orig/parser/parser.h
+++ 2.9-test/parser/parser.h
@@ -300,6 +300,7 @@
 extern int kernel_supports_policydb;
 extern int kernel_supports_mount;
 extern int kernel_supports_dbus;
+extern int kernel_supports_signal;
 extern int conf_verbose;
 extern int conf_quiet;
 extern int names_only;
@@ -331,7 +332,9 @@
 extern const char *basedir;
 
 /* parser_regex.c */
-extern const char *default_match_pattern;
+#define default_match_pattern "[^\\000]*"
+#define anyone_match_pattern "[^\\000]+"
+
 extern pattern_t convert_aaregex_to_pcre(const char *aare, int anchor,
                                         std::string& pcre, int *first_re_pos);
 extern int build_list_val_expr(std::string& buffer, struct value_list *list);
--- 2.9-test.orig/parser/parser_common.c
+++ 2.9-test/parser/parser_common.c
@@ -70,6 +70,7 @@
 int kernel_supports_policydb = 0;      /* kernel supports new policydb */
 int kernel_supports_mount = 0;         /* kernel supports mount rules */
 int kernel_supports_dbus = 0;          /* kernel supports dbus rules */
+int kernel_supports_signal = 0;                /* kernel supports signal rules 
*/
 int conf_verbose = 0;
 int conf_quiet = 0;
 int names_only = 0;
--- 2.9-test.orig/parser/parser_lex.l
+++ 2.9-test/parser/parser_lex.l
@@ -253,6 +253,7 @@
 %x RLIMIT_MODE
 %x MOUNT_MODE
 %x DBUS_MODE
+%x SIGNAL_MODE
 %x CHANGE_PROFILE_MODE
 %x INCLUDE
 
@@ -267,7 +268,7 @@
        }
 %}
 
-<INITIAL,INCLUDE,LIST_VAL_MODE,EXTCOND_MODE,LIST_COND_VAL,LIST_COND_PAREN_VAL,LIST_COND_MODE,EXTCONDLIST_MODE,ASSIGN_MODE,NETWORK_MODE,CHANGE_PROFILE_MODE,RLIMIT_MODE,MOUNT_MODE,DBUS_MODE>{
+<INITIAL,INCLUDE,LIST_VAL_MODE,EXTCOND_MODE,LIST_COND_VAL,LIST_COND_PAREN_VAL,LIST_COND_MODE,EXTCONDLIST_MODE,ASSIGN_MODE,NETWORK_MODE,CHANGE_PROFILE_MODE,RLIMIT_MODE,MOUNT_MODE,DBUS_MODE,SIGNAL_MODE>{
        {WS}+   {  DUMP_PREPROCESS; /* Ignoring whitespace */ }
 }
 
@@ -293,7 +294,7 @@
                yyterminate();
 }
 
-<INITIAL,MOUNT_MODE,DBUS_MODE>{
+<INITIAL,MOUNT_MODE,DBUS_MODE,SIGNAL_MODE>{
        {VARIABLE_NAME}/{WS}*=  {
                /* we match to the = in the lexer so that we can switch scanner
                 * state.  By the time the parser see the = it may be too late
@@ -462,12 +463,15 @@
 }
 
 <DBUS_MODE>{
+       bind            { RETURN_TOKEN(TOK_BIND); }
+       eavesdrop       { RETURN_TOKEN(TOK_EAVESDROP); }
+}
+
+<DBUS_MODE,SIGNAL_MODE>{
        send            { RETURN_TOKEN(TOK_SEND); }
        receive         { RETURN_TOKEN(TOK_RECEIVE); }
-       bind            { RETURN_TOKEN(TOK_BIND); }
        read            { RETURN_TOKEN(TOK_READ); }
        write           { RETURN_TOKEN(TOK_WRITE); }
-       eavesdrop       { RETURN_TOKEN(TOK_EAVESDROP); }
        {OPEN_PAREN}    {
                        yy_push_state(LIST_VAL_MODE);
                        RETURN_TOKEN(TOK_OPENPAREN);
@@ -478,7 +482,7 @@
                        }
 }
 
-<MOUNT_MODE,DBUS_MODE>{
+<MOUNT_MODE,DBUS_MODE,SIGNAL_MODE>{
        {ARROW}         { RETURN_TOKEN(TOK_ARROW); }
 
        ({IDS_NOEQ}|{PATHNAME}|{QUOTED_ID}) {
@@ -567,13 +571,16 @@
        case TOK_DBUS:
                state = DBUS_MODE;
                break;
+       case TOK_SIGNAL:
+               state = SIGNAL_MODE;
+               break;
        default: /* nothing */
                break;
        }
        PUSH_AND_RETURN(state, token);
 }
 
-<INITIAL,NETWORK_MODE,RLIMIT_MODE,MOUNT_MODE,DBUS_MODE>{
+<INITIAL,NETWORK_MODE,RLIMIT_MODE,MOUNT_MODE,DBUS_MODE,SIGNAL_MODE>{
        {END_OF_RULE}   {
                if (YY_START != INITIAL)
                        yy_pop_state();
@@ -586,7 +593,7 @@
        }
 }
 
-<INITIAL,SUB_ID,SUB_VALUE,LIST_VAL_MODE,EXTCOND_MODE,LIST_COND_VAL,LIST_COND_PAREN_VAL,LIST_COND_MODE,EXTCONDLIST_MODE,ASSIGN_MODE,NETWORK_MODE,CHANGE_PROFILE_MODE,MOUNT_MODE,DBUS_MODE>{
+<INITIAL,SUB_ID,SUB_VALUE,LIST_VAL_MODE,EXTCOND_MODE,LIST_COND_VAL,LIST_COND_PAREN_VAL,LIST_COND_MODE,EXTCONDLIST_MODE,ASSIGN_MODE,NETWORK_MODE,CHANGE_PROFILE_MODE,MOUNT_MODE,DBUS_MODE,SIGNAL_MODE>{
        [^\n]   {
                DUMP_PREPROCESS;
                /* Something we didn't expect */
@@ -613,6 +620,7 @@
        STATE_TABLE_ENT(RLIMIT_MODE),
        STATE_TABLE_ENT(MOUNT_MODE),
        STATE_TABLE_ENT(DBUS_MODE),
+       STATE_TABLE_ENT(SIGNAL_MODE),
        STATE_TABLE_ENT(CHANGE_PROFILE_MODE),
        STATE_TABLE_ENT(INCLUDE),
 };
--- 2.9-test.orig/parser/parser_main.c
+++ 2.9-test/parser/parser_main.c
@@ -847,6 +847,8 @@
                kernel_supports_mount = 1;
        if (strstr(features_string, "dbus"))
                kernel_supports_dbus = 1;
+       if (strstr(features_string, "signal"))
+               kernel_supports_signal = 1;
 }
 
 int process_binary(int option, const char *profilename)
--- 2.9-test.orig/parser/parser_misc.c
+++ 2.9-test/parser/parser_misc.c
@@ -142,6 +142,7 @@
        {"pivot_root",          TOK_PIVOTROOT},
        {"in",                  TOK_IN},
        {"dbus",                TOK_DBUS},
+       {"signal",              TOK_SIGNAL},
        {"send",                TOK_SEND},
        {"receive",             TOK_RECEIVE},
        {"bind",                TOK_BIND},
--- 2.9-test.orig/parser/parser_regex.c
+++ 2.9-test/parser/parser_regex.c
@@ -43,8 +43,6 @@
        e_parse_error,
 };
 
-/* match any char except \000 0 or more times */
-const char *default_match_pattern = "[^\\000]*";
 
 /* Filters out multiple slashes (except if the first two are slashes,
  * that's a distinct namespace in linux) and trailing slashes.
@@ -675,6 +673,7 @@
 static const char *mediates_file = CLASS_STR(AA_CLASS_FILE);
 static const char *mediates_mount = CLASS_STR(AA_CLASS_MOUNT);
 static const char *mediates_dbus =  CLASS_STR(AA_CLASS_DBUS);
+static const char *mediates_signal =  CLASS_STR(AA_CLASS_SIGNAL);
 
 int process_profile_policydb(Profile *prof)
 {
@@ -701,6 +700,10 @@
        if (kernel_supports_dbus &&
            !prof->policy.rules->add_rule(mediates_dbus, 0, AA_MAY_READ, 0, 
dfaflags))
                goto out;
+       if (kernel_supports_signal &&
+           !prof->policy.rules->add_rule(mediates_signal, 0, AA_MAY_READ, 0, 
dfaflags))
+               goto out;
+
        if (prof->policy.rules->rule_count > 0) {
                prof->policy.dfa = 
prof->policy.rules->create_dfa(&prof->policy.size, dfaflags);
                delete prof->policy.rules;
--- 2.9-test.orig/parser/parser_yacc.y
+++ 2.9-test/parser/parser_yacc.y
@@ -28,6 +28,8 @@
 #include <fcntl.h>
 #include <libintl.h>
 #include <sys/apparmor.h>
+
+#include <iostream>
 #define _(s) gettext(s)
 
 /* #define DEBUG */
@@ -128,6 +130,7 @@
 %token TOK_PIVOTROOT
 %token TOK_IN
 %token TOK_DBUS
+%token TOK_SIGNAL
 %token TOK_SEND
 %token TOK_RECEIVE
 %token TOK_BIND
@@ -166,6 +169,7 @@
        #include "profile.h"
        #include "mount.h"
        #include "dbus.h"
+       #include "signal.h"
 }
 
 %union {
@@ -179,6 +183,7 @@
 
        mnt_rule *mnt_entry;
        dbus_rule *dbus_entry;
+       signal_rule *signal_entry;
 
        flagvals flags;
        int fmode;
@@ -241,6 +246,10 @@
 %type <fmode>  dbus_perms
 %type <fmode>  opt_dbus_perm
 %type <dbus_entry>     dbus_rule
+%type <fmode>  signal_perm
+%type <fmode>  signal_perms
+%type <fmode>  opt_signal_perm
+%type <signal_entry>   signal_rule
 %type <transition> opt_named_transition
 %type <boolean> opt_unsafe
 %type <boolean> opt_file
@@ -698,6 +707,22 @@
                $$ = $1;
        }
 
+rules:  rules opt_prefix signal_rule
+       {
+               if ($2.owner)
+                       yyerror(_("owner prefix not allowed on signal rules"));
+               if ($2.deny && $2.audit) {
+                       $3->deny = 1;
+               } else if ($2.deny) {
+                       $3->deny = 1;
+                       $3->audit = $3->mode;
+               } else if ($2.audit) {
+                       $3->audit = $3->mode;
+               }
+               $1->rule_ents.push_back($3);
+               $$ = $1;
+       }
+
 rules: rules change_profile
        {
                PDEBUG("matched: rules change_profile\n");
@@ -1214,6 +1239,49 @@
                $$ = ent;
        }
 
+signal_perm: TOK_VALUE
+       {
+               if (strcmp($1, "send") == 0 || strcmp($1, "write") == 0)
+                       $$ = AA_MAY_SEND;
+               else if (strcmp($1, "receive") == 0 || strcmp($1, "read") == 0)
+                       $$ = AA_MAY_RECEIVE;
+               else if ($1) {
+                       parse_signal_mode($1, &$$, 1);
+               } else
+                       $$ = 0;
+
+               if ($1)
+                       free($1);
+       }
+       | TOK_SEND { $$ = AA_MAY_SEND; }
+       | TOK_RECEIVE { $$ = AA_MAY_RECEIVE; }
+       | TOK_READ { $$ = AA_MAY_RECEIVE; }
+       | TOK_WRITE { $$ = AA_MAY_SEND; }
+       | TOK_MODE
+       {
+               parse_signal_mode($1, &$$, 1);
+               free($1);
+       }
+
+signal_perms: { /* nothing */ $$ = 0; }
+       | signal_perms signal_perm { $$ = $1 | $2; }
+       | signal_perms TOK_COMMA signal_perm { $$ = $1 | $3; }
+
+opt_signal_perm: { /* nothing */ $$ = 0; }
+       | signal_perm { $$ = $1; }
+       | TOK_OPENPAREN signal_perms TOK_CLOSEPAREN { $$ = $2; }
+
+signal_rule: TOK_SIGNAL opt_signal_perm opt_conds TOK_END_OF_RULE
+       {
+               signal_rule *ent = new signal_rule($2, $3, NULL);
+               $$ = ent;
+       }
+       |  TOK_SIGNAL opt_signal_perm opt_conds TOK_ID TOK_END_OF_RULE
+       {
+               signal_rule *ent = new signal_rule($2, $3, $4);
+               $$ = ent;
+       }
+
 hat_start: TOK_CARET {}
        | TOK_HAT {}
 
--- 2.9-test.orig/parser/policydb.h
+++ 2.9-test/parser/policydb.h
@@ -31,6 +31,7 @@
 #define AA_CLASS_MOUNT         7
 #define AA_CLASS_NS_DOMAIN     8
 #define AA_CLASS_PTRACE                9
+#define AA_CLASS_SIGNAL                10
 
 #define AA_CLASS_ENV           16
 
--- /dev/null
+++ 2.9-test/parser/signal.c
@@ -0,0 +1,290 @@
+/*
+ *   Copyright (c) 2014
+ *   Canonical, Ltd. (All rights reserved)
+ *
+ *   This program is free software; you can redistribute it and/or
+ *   modify it under the terms of version 2 of the GNU General Public
+ *   License published by the Free Software Foundation.
+ *
+ *   This program is distributed in the hope that it will be useful,
+ *   but WITHOUT ANY WARRANTY; without even the implied warranty of
+ *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ *   GNU General Public License for more details.
+ *
+ *   You should have received a copy of the GNU General Public License
+ *   along with this program; if not, contact Novell, Inc. or Canonical
+ *   Ltd.
+ */
+
+#include <stdlib.h>
+#include <string.h>
+#include <sys/apparmor.h>
+
+#include <iomanip>
+#include <string>
+#include <sstream>
+#include <map>
+
+#include "parser.h"
+#include "profile.h"
+#include "parser_yacc.h"
+#include "signal.h"
+
+#define MAXMAPPED_SIG 35
+#define MINRT_SIG 128          /* base of RT sigs */
+#define MAXRT_SIG 32           /* Max RT above MINRT_SIG */
+
+/* Signal names mapped to and internal ordering */
+static struct signal_map { const char *name; int num; } signal_map[] = {
+       {"hup",         1},
+       {"int",         2},
+       {"quit",        3},
+       {"ill",         4},
+       {"trap",        5},
+       {"abrt",        6},
+       {"bus",         7},
+       {"fpe",         8},
+       {"kill",        9},
+       {"usr1",        10},
+       {"segv",        11},
+       {"usr2",        12},
+       {"pipe",        13},
+       {"alrm",        14},
+       {"term",        15},
+       {"tkflt",       16},
+       {"chld",        17},
+       {"cont",        18},
+       {"stop",        19},
+       {"stp",         20},
+       {"ttin",        21},
+       {"ttou",        22},
+       {"urg",         23},
+       {"xcpu",        24},
+       {"xfsz",        25},
+       {"vtalrm",      26},
+       {"prof",        27},
+       {"winch",       28},
+       {"io",          29},
+       {"pwr",         30},
+       {"sys",         31},
+       {"emt",         32},
+       {"exists",      35},
+
+       /* terminate */
+       {NULL,          0}
+};
+
+/* this table is ordered post sig_map[sig] mapping */
+static const char *const sig_names[MAXMAPPED_SIG + 1] = {
+       "unknown",
+       "hup",
+       "int",
+       "quit",
+       "ill",
+       "trap",
+       "abrt",
+       "bus",
+       "fpe",
+       "kill",
+       "usr1",
+       "segv",
+       "usr2",
+       "pipe",
+       "alrm",
+       "term",
+       "tkflt",
+       "chld",
+       "cont",
+       "stop",
+       "stp",
+       "ttin",
+       "ttou",
+       "urg",
+       "xcpu",
+       "xfsz",
+       "vtalrm",
+       "prof",
+       "winch",
+       "io",
+       "pwr",
+       "sys",
+       "emt",
+       "lost",
+       "unused",
+
+       "exists",       /* always last existance test mapped to MAXMAPPED_SIG */
+};
+
+
+int parse_signal_mode(const char *str_mode, int *mode, int fail)
+{
+       return parse_X_mode("signal", AA_VALID_SIGNAL_PERMS, str_mode, mode, 
fail);
+}
+
+static int find_signal_mapping(const char *sig)
+{
+       if (strncmp("rtmin+", sig, 6) == 0) {
+               char *end;
+               unsigned long n = strtoul(sig + 6, &end, 10);
+               if (end == sig || n > MAXRT_SIG)
+                       return -1;
+               return MINRT_SIG + n;
+       } else {
+               for (int i = 0; signal_map[i].name; i++) {
+                       if (strcmp(sig, signal_map[i].name) == 0)
+                               return signal_map[i].num;
+               }
+       }
+       return -1;
+}
+
+void signal_rule::extract_sigs(struct value_list **list)
+{
+       struct value_list *entry, *tmp, *prev = NULL;
+       list_for_each_safe(*list, entry, tmp) {
+               int i = find_signal_mapping(entry->value);
+               if (i != -1) {
+                       signals.insert(i);
+                       list_remove_at(*list, prev, entry);
+                       free_value_list(entry);
+               } else {
+                       yyerror("unknown signal \"%s\"\n", entry->value);
+                       prev = entry;
+               }
+       }
+}
+
+void signal_rule::move_conditionals(struct cond_entry *conds)
+{
+       struct cond_entry *cond_ent;
+
+       list_for_each(conds, cond_ent) {
+               /* for now disallow keyword 'in' (list) */
+               if (!cond_ent->eq)
+                       yyerror("keyword \"in\" is not allowed in signal 
rules\n");
+               /* use alternation instead????
+                * set=(kill,usr1) vs. set={kill,usr1}
+                */
+               if (strcmp(cond_ent->name, "set") == 0) {
+                       extract_sigs(&cond_ent->vals);
+               } else {
+                       yyerror("invalid signal rule conditional \"%s\"\n",
+                               cond_ent->name);
+               }
+       }
+}
+
+signal_rule::signal_rule(int mode_p, struct cond_entry *conds,
+                        char *peer):
+       signals(), peer_label(peer), audit(0), deny(0)
+{
+       if (mode_p) {
+               mode = mode_p;
+               if (mode & ~AA_VALID_SIGNAL_PERMS)
+                       yyerror("mode contains invalid permission for 
signals\n");
+       } else {
+               mode = AA_VALID_SIGNAL_PERMS;
+       }
+
+       move_conditionals(conds);
+
+       free_cond_list(conds);
+}
+
+ostream &signal_rule::dump(ostream &os)
+{
+       if (audit)
+               os << "audit ";
+       if (deny)
+               os << "deny ";
+
+       os << "signal";
+
+       if (mode != AA_VALID_SIGNAL_PERMS) {
+               os << " (";
+
+               if (mode & AA_MAY_SEND)
+                       os << "send ";
+               if (mode & AA_MAY_RECEIVE)
+                       os << "receive ";
+               os << ")";
+       }
+
+       if (!signals.empty()) {
+               os << " set=(";
+               for (Signals::iterator i = signals.begin(); i != signals.end();
+                    i++) {
+                       if (i != signals.begin())
+                               os << ", ";
+                       if (*i < MINRT_SIG)
+                               os << sig_names[*i];
+                       else
+                               os << "rtmin+" << (*i - MINRT_SIG);
+               }
+               os << ")";
+       }
+
+       if (peer_label)
+               os << " " << peer_label;
+
+       os << ",\n";
+
+       return os;
+}
+
+int signal_rule::expand_variables(void)
+{
+       return expand_entry_variables(&peer_label);
+}
+
+int signal_rule::gen_policy_re(Profile &prof)
+{
+       std::ostringstream buffer;
+       std::string buf;
+
+       pattern_t ptype;
+       int pos;
+
+       /* ?? do we want to generate the rules in the policy so that it
+        * the compile could be used on another kernel unchanged??
+        * Current caching doesn't support this but in the future maybe
+        */
+       if (!kernel_supports_signal) {
+               pwarn("profile %s signal rules not enforced\n", prof.name);
+               return RULE_NOT_SUPPORTED;
+       }
+
+       buffer << "\\x" << std::setfill('0') << std::setw(2) << std::hex << 
AA_CLASS_SIGNAL;
+
+       if (signals.size()) {
+               buffer << "[";
+               for (Signals::iterator i = signals.begin(); i != signals.end(); 
i++) {
+                       buffer << "\\x" << std::setfill('0') << std::setw(2) << 
std::hex << *i;
+               }
+               buffer << "]";
+       } else {
+               /* match any char */
+               buffer << ".";
+       }
+
+       if (peer_label) {
+               ptype = convert_aaregex_to_pcre(peer_label, 0, buf, &pos);
+               if (ptype == ePatternInvalid)
+                       goto fail;
+               buffer << buf;
+       } else {
+               buffer << anyone_match_pattern;
+       }
+
+       buf = buffer.str();
+       if (mode & (AA_MAY_SEND | AA_MAY_RECEIVE)) {
+               if (!prof.policy.rules->add_rule(buf.c_str(), deny, mode, audit,
+                                                dfaflags))
+                       goto fail;
+       }
+
+       return RULE_OK;
+
+fail:
+       return RULE_ERROR;
+}
--- /dev/null
+++ 2.9-test/parser/signal.h
@@ -0,0 +1,58 @@
+/*
+ *   Copyright (c) 2014
+ *   Canonical, Ltd. (All rights reserved)
+ *
+ *   This program is free software; you can redistribute it and/or
+ *   modify it under the terms of version 2 of the GNU General Public
+ *   License published by the Free Software Foundation.
+ *
+ *   This program is distributed in the hope that it will be useful,
+ *   but WITHOUT ANY WARRANTY; without even the implied warranty of
+ *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ *   GNU General Public License for more details.
+ *
+ *   You should have received a copy of the GNU General Public License
+ *   along with this program; if not, contact Novell, Inc. or Canonical
+ *   Ltd.
+ */
+
+#ifndef __AA_SIGNAL_H
+#define __AA_SIGNAL_H
+
+#include "parser.h"
+#include "rule.h"
+#include "profile.h"
+
+
+#define AA_MAY_SEND                    (1 << 1)
+#define AA_MAY_RECEIVE                 (1 << 2)
+#define AA_VALID_SIGNAL_PERMS          (AA_MAY_SEND | AA_MAY_RECEIVE)
+
+
+typedef set<int> Signals;
+
+int parse_signal_mode(const char *str_mode, int *mode, int fail);
+
+class signal_rule: public rule_t {
+       void extract_sigs(struct value_list **list);
+       void move_conditionals(struct cond_entry *conds);
+public:
+       Signals signals;
+       char *peer_label;
+       int mode;
+       int audit;
+       int deny;
+
+       signal_rule(int mode, struct cond_entry *conds, char *peer);
+       virtual ~signal_rule() {
+               signals.clear();
+               free(peer_label);
+       };
+
+       virtual ostream &dump(ostream &os);
+       virtual int expand_variables(void);
+       virtual int gen_policy_re(Profile &prof);
+       virtual void post_process(Profile &prof __unused) { };
+};
+
+#endif /* __AA_SIGNAL_H */


-- 
AppArmor mailing list
AppArmor@lists.ubuntu.com
Modify settings or unsubscribe at: 
https://lists.ubuntu.com/mailman/listinfo/apparmor

Reply via email to