1edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep# Copyright 2016, Tresys Technology, LLC
2edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep#
3edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep# This file is part of SETools.
4edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep#
5edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep# SETools is free software: you can redistribute it and/or modify
6edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep# it under the terms of the GNU Lesser General Public License as
7edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep# published by the Free Software Foundation, either version 2.1 of
8edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep# the License, or (at your option) any later version.
9edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep#
10edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep# SETools is distributed in the hope that it will be useful,
11edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep# but WITHOUT ANY WARRANTY; without even the implied warranty of
12edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep# GNU Lesser General Public License for more details.
14edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep#
15edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep# You should have received a copy of the GNU Lesser General Public
16edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep# License along with SETools.  If not, see
17edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep# <http://www.gnu.org/licenses/>.
18edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep#
19edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoepfrom collections import namedtuple
20edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
21edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoepfrom .context import ContextWrapper
22edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoepfrom .descriptors import DiffResultDescriptor
23edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoepfrom .difference import Difference, Wrapper
24edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
25edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
26edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoepmodified_fsuse_record = namedtuple("modified_fsuse", ["rule",
27edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep                                                      "added_context",
28edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep                                                      "removed_context"])
29edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
30edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
31edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoepclass FSUsesDifference(Difference):
32edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
33edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep    """Determine the difference in fs_use_* rules between two policies."""
34edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
35edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep    added_fs_uses = DiffResultDescriptor("diff_fs_uses")
36edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep    removed_fs_uses = DiffResultDescriptor("diff_fs_uses")
37edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep    modified_fs_uses = DiffResultDescriptor("diff_fs_uses")
38edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
39edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep    def diff_fs_uses(self):
40edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        """Generate the difference in fs_use rules between the policies."""
41edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
42edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        self.log.info(
43edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep            "Generating fs_use_* differences from {0.left_policy} to {0.right_policy}".
44edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep            format(self))
45edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
46edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        self.added_fs_uses, self.removed_fs_uses, matched = self._set_diff(
47edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep            (FSUseWrapper(fs) for fs in self.left_policy.fs_uses()),
48edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep            (FSUseWrapper(fs) for fs in self.right_policy.fs_uses()))
49edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
50edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        self.modified_fs_uses = []
51edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
52edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        for left_rule, right_rule in matched:
53edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep            # Criteria for modified rules
54edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep            # 1. change to context
55edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep            if ContextWrapper(left_rule.context) != ContextWrapper(right_rule.context):
56edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep                self.modified_fs_uses.append(modified_fsuse_record(left_rule,
57edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep                                                                   right_rule.context,
58edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep                                                                   left_rule.context))
59edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
60edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep    #
61edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep    # Internal functions
62edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep    #
63edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep    def _reset_diff(self):
64edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        """Reset diff results on policy changes."""
65edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        self.log.debug("Resetting fs_use_* rule differences")
66edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        self.added_fs_uses = None
67edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        self.removed_fs_uses = None
68edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        self.modified_fs_uses = None
69edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
70edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
71edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoepclass FSUseWrapper(Wrapper):
72edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
73edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep    """Wrap fs_use_* rules to allow set operations."""
74edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
75edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep    def __init__(self, rule):
76edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        self.origin = rule
77edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        self.ruletype = rule.ruletype
78edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        self.fs = rule.fs
79edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        self.context = ContextWrapper(rule.context)
80edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        self.key = hash(rule)
81edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
82edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep    def __hash__(self):
83edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        return self.key
84edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
85edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep    def __lt__(self, other):
86edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        return self.key < other.key
87edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep
88edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep    def __eq__(self, other):
89edbb763a2b63074cd468a5d33a17908b2cc0654Jeff Vander Stoep        return self.ruletype == other.ruletype and self.fs == other.fs
90