diff --git a/documentation/Techdoc - eHFA.odt b/documentation/Techdoc - eHFA.odt index 545bc58af..45ec9d6a3 100644 Binary files a/documentation/Techdoc - eHFA.odt and b/documentation/Techdoc - eHFA.odt differ diff --git a/parser/libapparmor_re/aare_rules.cc b/parser/libapparmor_re/aare_rules.cc index 02aa80fa0..4bf38f71d 100644 --- a/parser/libapparmor_re/aare_rules.cc +++ b/parser/libapparmor_re/aare_rules.cc @@ -63,7 +63,7 @@ void aare_rules::add_to_rules(Node *tree, Node *perms) static Node *cat_with_null_seperator(Node *l, Node *r) { - return new CatNode(new CatNode(l, new CharNode(0)), r); + return new CatNode(new CatNode(l, new CharSetNode(0)), r); } bool aare_rules::add_rule_vec(int deny, uint32_t perms, uint32_t audit, diff --git a/parser/libapparmor_re/expr-tree.cc b/parser/libapparmor_re/expr-tree.cc index a80f9037f..c7e4b6e54 100644 --- a/parser/libapparmor_re/expr-tree.cc +++ b/parser/libapparmor_re/expr-tree.cc @@ -232,12 +232,6 @@ void AltNode::normalize(int dir) } else if (dynamic_cast(child[dir])) { // (a | b) | c -> a | (b | c) rotate_node(this, dir); - } else if (dynamic_cast(child[dir]) && - dynamic_cast(child[!dir])) { - // [a] | b -> b | [a] - Node *c = child[dir]; - child[dir] = child[!dir]; - child[!dir] = c; } else { break; } @@ -252,76 +246,77 @@ void AltNode::normalize(int dir) //charset conversion is disabled for now, //it hinders tree optimization in some cases, so it need to be either //done post optimization, or have extra factoring rules added -#if 0 static Node *merge_charset(Node *a, Node *b) { - if (dynamic_cast(a) && dynamic_cast(b)) { - Chars chars; - chars.insert(dynamic_cast(a)->c); - chars.insert(dynamic_cast(b)->c); - CharSetNode *n = new CharSetNode(chars); - return n; - } else if (dynamic_cast(a) && - dynamic_cast(b)) { - Chars *chars = &dynamic_cast(b)->chars; - chars->insert(dynamic_cast(a)->c); - return b; - } else if (dynamic_cast(a) && - dynamic_cast(b)) { - Chars *from = &dynamic_cast(a)->chars; - Chars *to = &dynamic_cast(b)->chars; - for (Chars::iterator i = from->begin(); i != from->end(); i++) - to->insert(*i); - return b; - } - //return ???; + Chars *from = &dynamic_cast(b)->chars; + Chars *to = &dynamic_cast(a)->chars; + for (Chars::iterator i = from->begin(); i != from->end(); i++) + to->insert(*i); + b->release(); + return a; } -static Node *alt_to_charsets(Node *t, int dir) -{ -/* - Node *first = NULL; - Node *p = t; - Node *i = t; - for (;dynamic_cast(i);) { - if (dynamic_cast(i->child[dir]) || - dynamic_cast(i->child[dir])) { - if (!first) { - first = i; - p = i; - i = i->child[!dir]; - } else { - first->child[dir] = merge_charset(first->child[dir], - i->child[dir]); - p->child[!dir] = i->child[!dir]; - Node *tmp = i; - i = tmp->child[!dir]; - tmp->child[!dir] = NULL; - tmp->release(); - } - } else { - p = i; - i = i->child[!dir]; +/* given a constructed alt vector do duplicate elimination and merging */ +eliminate_dups_and_merge(vector vec) { + std::sort(vec->begin(), vec->end(), ???); + + i = vec->begin(); + if (vec->begin()->is_charset()) { + for (j = i+1; *j->is_charset() && j != vec->end(); + j++) { + merge_charset(*i, *j); + *j = NULL; + merge_count++; } + if (j != vec->end()) + i = j; } - // last altnode of chain check other dir as well - if (first && (dynamic_cast(i) || - dynamic_cast(i))) { - - } -*/ -/* - if (dynamic_cast(t->child[dir]) || - dynamic_cast(t->child[dir])) - char_test = true; - (char_test && - (dynamic_cast(i->child[dir]) || - dynamic_cast(i->child[dir])))) { -*/ - return t; + /* merged charsets, now eliminate other dups */ + for (j = i + 1; ??; ???) { + + } +} + +flatten_altnode(Node *t) { + + /* flatten tree */ + elimintated_alt_nodes++; + + eliminate_dups_and_merge(); +} + +flatten_catnode(Node *t) { + + /* flatten tree */ + eliminated_cat_nodes++; + + /* only elimination to be done is accept nodes */ +} + +factor() { + + factor everything from right, then left + + factor longest/most - look at both left and right, which is most? + to determine which dir to factor first + + ab | abc | abcd | abcde + + a (b | bc | bcd | bcde) + + a ( b (E | c | cd | cde)) + + a ( b (E | c (E | d | de)) + + a ( b (E | c (E | d (E | e)))) + + so once flattened, work top to bottom + + may actually want to flatten charsets into single chars in altnode + to make it easier to factor them + } -#endif static Node *basic_alt_factor(Node *t, int dir) { @@ -335,6 +330,13 @@ static Node *basic_alt_factor(Node *t, int dir) t->release(); return tmp; } + if (dynamic_cast(t->child[dir]) && + dynamic_cast(t->child[!dir])) { + Node *res = merge_charset(t->child[dir], t->child[!dir]); + t->child[dir] = t->child[!dir] = NULL; + t->release(); + return res; + } // (ab) | (ac) -> a(b|c) if (dynamic_cast(t->child[dir]) && dynamic_cast(t->child[!dir]) && @@ -534,8 +536,6 @@ static void count_tree_nodes(Node *t, struct node_counts *counts) } else if (dynamic_cast(t)) { counts->star++; count_tree_nodes(t->child[0], counts); - } else if (dynamic_cast(t)) { - counts->charnode++; } else if (dynamic_cast(t)) { counts->any++; } else if (dynamic_cast(t)) { @@ -554,11 +554,11 @@ Node *simplify_tree(Node *t, dfaflags_t flags) bool update; if (flags & DFA_DUMP_TREE_STATS) { - struct node_counts counts = { 0, 0, 0, 0, 0, 0, 0, 0 }; + struct node_counts counts = { 0, 0, 0, 0, 0, 0, 0 }; count_tree_nodes(t, &counts); fprintf(stderr, - "expr tree: c %d, [] %d, [^] %d, | %d, + %d, * %d, . %d, cat %d\n", - counts.charnode, counts.charset, counts.notcharset, + "expr tree: [] %d, [^] %d, | %d, + %d, * %d, . %d, cat %d\n", + counts.charset, counts.notcharset, counts.alt, counts.plus, counts.star, counts.any, counts.cat); } @@ -590,11 +590,11 @@ Node *simplify_tree(Node *t, dfaflags_t flags) } } while (update); if (flags & DFA_DUMP_TREE_STATS) { - struct node_counts counts = { 0, 0, 0, 0, 0, 0, 0, 0 }; + struct node_counts counts = { 0, 0, 0, 0, 0, 0, 0 }; count_tree_nodes(t, &counts); fprintf(stderr, - "simplified expr tree: c %d, [] %d, [^] %d, | %d, + %d, * %d, . %d, cat %d\n", - counts.charnode, counts.charset, counts.notcharset, + "simplified expr tree: [] %d, [^] %d, | %d, + %d, * %d, . %d, cat %d\n", + counts.charset, counts.notcharset, counts.alt, counts.plus, counts.star, counts.any, counts.cat); } diff --git a/parser/libapparmor_re/expr-tree.h b/parser/libapparmor_re/expr-tree.h index afd426f51..80f29817d 100644 --- a/parser/libapparmor_re/expr-tree.h +++ b/parser/libapparmor_re/expr-tree.h @@ -229,41 +229,11 @@ public: int is_postprocess(void) { return false; } }; -/* Match one specific character (/c/). */ -class CharNode: public CNode { -public: - CharNode(uchar c): c(c) { } - void follow(Cases &cases) - { - NodeSet **x = &cases.cases[c]; - if (!*x) { - if (cases.otherwise) - *x = new NodeSet(*cases.otherwise); - else - *x = new NodeSet; - } - (*x)->insert(followpos.begin(), followpos.end()); - } - int eq(Node *other) - { - CharNode *o = dynamic_cast(other); - if (o) { - return c == o->c; - } - return 0; - } - ostream &dump(ostream &os) - { - return os << c; - } - - uchar c; -}; - /* Match a set of characters (/[abc]/). */ class CharSetNode: public CNode { public: CharSetNode(Chars &chars): chars(chars) { } + CharSetNode(uchar c): chars() { chars.insert(c); } void follow(Cases &cases) { for (Chars::iterator i = chars.begin(); i != chars.end(); i++) { @@ -591,7 +561,6 @@ public: }; struct node_counts { - int charnode; int charset; int notcharset; int alt; diff --git a/parser/libapparmor_re/parse.y b/parser/libapparmor_re/parse.y index 3ec07e12c..2a944c525 100644 --- a/parser/libapparmor_re/parse.y +++ b/parser/libapparmor_re/parse.y @@ -102,7 +102,7 @@ qterm : term ; term : '.' { $$ = new AnyCharNode; } - | regex_char { $$ = new CharNode($1); } + | regex_char { $$ = new CharSetNode($1); } | '[' charset ']' { $$ = new CharSetNode(*$2); delete $2; } | '[' '^' charset ']' diff --git a/presentations/LSS_apparmor-labeling-2013.odp b/presentations/LSS_apparmor-labeling-2013.odp new file mode 100644 index 000000000..82b801b75 Binary files /dev/null and b/presentations/LSS_apparmor-labeling-2013.odp differ diff --git a/presentations/LSS_apparmor-userspace-2013.odp b/presentations/LSS_apparmor-userspace-2013.odp new file mode 100644 index 000000000..87ae5f889 Binary files /dev/null and b/presentations/LSS_apparmor-userspace-2013.odp differ