mirror of
https://gitlab.com/apparmor/apparmor
synced 2025-09-02 15:25:27 +00:00
[18/38] Re-add globbing support for file rules to aa-logprof
This change also needs some other changes in ask_the_questions(): - set q.options and q.selected inside the loop (because glob() and glob_ext() add another option) - set 'selection' outside the if block to avoid doing it in nearly every if branch - make sure to add the selected rule, not just rule_obj (which doesn't contain a modified, for example globbed, rule) - skip 'deny' if an #include is selected - re-add handling for CMD_GLOB and CMD_GLOB_EXT (was lost when switching to FileRule) - add selection_to_rule_obj() helper function - add glob and glob with ext buttons in available_buttons() if rule_obj.can_glob or rule_obj.can_glob_ext Also apply the changes in ask_the_questions() to aa-mergeprof to keep it in sync with aa.py, and disable the old path handling in aa-mergeprof. Note: in its current state, aa-mergeprof will ask for some "superfluous" file permissions, and doesn't check for 'x' conflicts. One of the following patches will fix that. Acked-by: Steve Beattie <steve@nxnw.org>
This commit is contained in:
@@ -24,8 +24,8 @@ import apparmor.severity
|
|||||||
import apparmor.cleanprofile as cleanprofile
|
import apparmor.cleanprofile as cleanprofile
|
||||||
import apparmor.ui as aaui
|
import apparmor.ui as aaui
|
||||||
|
|
||||||
from apparmor.aa import (available_buttons, combine_name, delete_duplicates,
|
from apparmor.aa import (add_to_options, available_buttons, combine_name, delete_duplicates,
|
||||||
get_profile_filename, is_known_rule, match_includes)
|
get_profile_filename, is_known_rule, match_includes, selection_to_rule_obj)
|
||||||
from apparmor.common import AppArmorException
|
from apparmor.common import AppArmorException
|
||||||
from apparmor.regex import re_match_include
|
from apparmor.regex import re_match_include
|
||||||
|
|
||||||
@@ -327,7 +327,9 @@ class Merge(object):
|
|||||||
|
|
||||||
# Process all the path entries.
|
# Process all the path entries.
|
||||||
for allow in ['allow', 'deny']:
|
for allow in ['allow', 'deny']:
|
||||||
for path in sorted(other.aa[profile][hat][allow]['path'].keys()):
|
if False: # XXX
|
||||||
|
#for path in sorted(other.aa[profile][hat][allow]['path'].keys()):
|
||||||
|
path = None # XXX needed to keep 'make check' happy
|
||||||
#print(path, other.aa[profile][hat][allow]['path'][path])
|
#print(path, other.aa[profile][hat][allow]['path'][path])
|
||||||
mode = other.aa[profile][hat][allow]['path'][path]['mode']
|
mode = other.aa[profile][hat][allow]['path'][path]['mode']
|
||||||
|
|
||||||
@@ -654,11 +656,11 @@ class Merge(object):
|
|||||||
options += list(map(lambda inc: '#include <%s>' % inc, sorted(set(newincludes))))
|
options += list(map(lambda inc: '#include <%s>' % inc, sorted(set(newincludes))))
|
||||||
|
|
||||||
options.append(rule_obj.get_clean())
|
options.append(rule_obj.get_clean())
|
||||||
q.options = options
|
|
||||||
q.selected = default_option - 1
|
|
||||||
|
|
||||||
done = False
|
done = False
|
||||||
while not done:
|
while not done:
|
||||||
|
q.options = options
|
||||||
|
q.selected = default_option - 1
|
||||||
q.headers = [_('Profile'), combine_name(profile, hat)]
|
q.headers = [_('Profile'), combine_name(profile, hat)]
|
||||||
q.headers += rule_obj.logprof_header()
|
q.headers += rule_obj.logprof_header()
|
||||||
|
|
||||||
@@ -671,6 +673,7 @@ class Merge(object):
|
|||||||
q.default = q.functions[0]
|
q.default = q.functions[0]
|
||||||
|
|
||||||
ans, selected = q.promptUser()
|
ans, selected = q.promptUser()
|
||||||
|
selection = options[selected]
|
||||||
if ans == 'CMD_IGNORE_ENTRY':
|
if ans == 'CMD_IGNORE_ENTRY':
|
||||||
done = True
|
done = True
|
||||||
break
|
break
|
||||||
@@ -693,8 +696,6 @@ class Merge(object):
|
|||||||
done = True
|
done = True
|
||||||
changed[profile] = True
|
changed[profile] = True
|
||||||
|
|
||||||
selection = options[selected]
|
|
||||||
|
|
||||||
inc = re_match_include(selection)
|
inc = re_match_include(selection)
|
||||||
if inc:
|
if inc:
|
||||||
deleted = delete_duplicates(aa[profile][hat], inc)
|
deleted = delete_duplicates(aa[profile][hat], inc)
|
||||||
@@ -706,19 +707,37 @@ class Merge(object):
|
|||||||
aaui.UI_Info(_('Deleted %s previous matching profile entries.') % deleted)
|
aaui.UI_Info(_('Deleted %s previous matching profile entries.') % deleted)
|
||||||
|
|
||||||
else:
|
else:
|
||||||
|
rule_obj = selection_to_rule_obj(rule_obj, selection)
|
||||||
aa[profile][hat][ruletype].add(rule_obj)
|
aa[profile][hat][ruletype].add(rule_obj)
|
||||||
|
|
||||||
aaui.UI_Info(_('Adding %s to profile.') % rule_obj.get_clean())
|
aaui.UI_Info(_('Adding %s to profile.') % rule_obj.get_clean())
|
||||||
|
|
||||||
elif ans == 'CMD_DENY':
|
elif ans == 'CMD_DENY':
|
||||||
|
if re_match_include(selection):
|
||||||
|
aaui.UI_Important("Denying via an include file isn't supported by the AppArmor tools")
|
||||||
|
|
||||||
|
else:
|
||||||
done = True
|
done = True
|
||||||
changed[profile] = True
|
changed[profile] = True
|
||||||
|
|
||||||
|
rule_obj = selection_to_rule_obj(rule_obj, selection)
|
||||||
rule_obj.deny = True
|
rule_obj.deny = True
|
||||||
rule_obj.raw_rule = None # reset raw rule after manually modifying rule_obj
|
rule_obj.raw_rule = None # reset raw rule after manually modifying rule_obj
|
||||||
aa[profile][hat][ruletype].add(rule_obj)
|
aa[profile][hat][ruletype].add(rule_obj)
|
||||||
aaui.UI_Info(_('Adding %s to profile.') % rule_obj.get_clean())
|
aaui.UI_Info(_('Adding %s to profile.') % rule_obj.get_clean())
|
||||||
|
|
||||||
|
elif ans == 'CMD_GLOB':
|
||||||
|
if not re_match_include(selection):
|
||||||
|
globbed_rule_obj = selection_to_rule_obj(rule_obj, selection)
|
||||||
|
globbed_rule_obj.glob()
|
||||||
|
options, default_option = add_to_options(options, globbed_rule_obj.get_raw())
|
||||||
|
|
||||||
|
elif ans == 'CMD_GLOBEXT':
|
||||||
|
if not re_match_include(selection):
|
||||||
|
globbed_rule_obj = selection_to_rule_obj(rule_obj, selection)
|
||||||
|
globbed_rule_obj.glob_ext()
|
||||||
|
options, default_option = add_to_options(options, globbed_rule_obj.get_raw())
|
||||||
|
|
||||||
else:
|
else:
|
||||||
done = False
|
done = False
|
||||||
|
|
||||||
|
@@ -1530,13 +1530,13 @@ def ask_the_questions():
|
|||||||
options += list(map(lambda inc: '#include <%s>' % inc, sorted(set(newincludes))))
|
options += list(map(lambda inc: '#include <%s>' % inc, sorted(set(newincludes))))
|
||||||
|
|
||||||
options.append(rule_obj.get_clean())
|
options.append(rule_obj.get_clean())
|
||||||
q.options = options
|
|
||||||
q.selected = default_option - 1
|
|
||||||
|
|
||||||
seen_events += 1
|
seen_events += 1
|
||||||
|
|
||||||
done = False
|
done = False
|
||||||
while not done:
|
while not done:
|
||||||
|
q.options = options
|
||||||
|
q.selected = default_option - 1
|
||||||
q.headers = [_('Profile'), combine_name(profile, hat)]
|
q.headers = [_('Profile'), combine_name(profile, hat)]
|
||||||
q.headers += rule_obj.logprof_header()
|
q.headers += rule_obj.logprof_header()
|
||||||
|
|
||||||
@@ -1555,6 +1555,8 @@ def ask_the_questions():
|
|||||||
q.default = 'CMD_ALLOW'
|
q.default = 'CMD_ALLOW'
|
||||||
|
|
||||||
ans, selected = q.promptUser()
|
ans, selected = q.promptUser()
|
||||||
|
selection = options[selected]
|
||||||
|
|
||||||
if ans == 'CMD_IGNORE_ENTRY':
|
if ans == 'CMD_IGNORE_ENTRY':
|
||||||
done = True
|
done = True
|
||||||
break
|
break
|
||||||
@@ -1577,8 +1579,6 @@ def ask_the_questions():
|
|||||||
done = True
|
done = True
|
||||||
changed[profile] = True
|
changed[profile] = True
|
||||||
|
|
||||||
selection = options[selected]
|
|
||||||
|
|
||||||
inc = re_match_include(selection)
|
inc = re_match_include(selection)
|
||||||
if inc:
|
if inc:
|
||||||
deleted = delete_duplicates(aa[profile][hat], inc)
|
deleted = delete_duplicates(aa[profile][hat], inc)
|
||||||
@@ -1590,23 +1590,45 @@ def ask_the_questions():
|
|||||||
aaui.UI_Info(_('Deleted %s previous matching profile entries.') % deleted)
|
aaui.UI_Info(_('Deleted %s previous matching profile entries.') % deleted)
|
||||||
|
|
||||||
else:
|
else:
|
||||||
|
rule_obj = selection_to_rule_obj(rule_obj, selection)
|
||||||
aa[profile][hat][ruletype].add(rule_obj)
|
aa[profile][hat][ruletype].add(rule_obj)
|
||||||
|
|
||||||
aaui.UI_Info(_('Adding %s to profile.') % rule_obj.get_clean())
|
aaui.UI_Info(_('Adding %s to profile.') % rule_obj.get_clean())
|
||||||
|
|
||||||
elif ans == 'CMD_DENY':
|
elif ans == 'CMD_DENY':
|
||||||
|
if re_match_include(selection):
|
||||||
|
aaui.UI_Important("Denying via an include file isn't supported by the AppArmor tools")
|
||||||
|
|
||||||
|
else:
|
||||||
done = True
|
done = True
|
||||||
changed[profile] = True
|
changed[profile] = True
|
||||||
|
|
||||||
|
rule_obj = selection_to_rule_obj(rule_obj, selection)
|
||||||
rule_obj.deny = True
|
rule_obj.deny = True
|
||||||
rule_obj.raw_rule = None # reset raw rule after manually modifying rule_obj
|
rule_obj.raw_rule = None # reset raw rule after manually modifying rule_obj
|
||||||
aa[profile][hat][ruletype].add(rule_obj)
|
aa[profile][hat][ruletype].add(rule_obj)
|
||||||
aaui.UI_Info(_('Adding %s to profile.') % rule_obj.get_clean())
|
aaui.UI_Info(_('Adding %s to profile.') % rule_obj.get_clean())
|
||||||
|
|
||||||
|
elif ans == 'CMD_GLOB':
|
||||||
|
if not re_match_include(selection):
|
||||||
|
globbed_rule_obj = selection_to_rule_obj(rule_obj, selection)
|
||||||
|
globbed_rule_obj.glob()
|
||||||
|
options, default_option = add_to_options(options, globbed_rule_obj.get_raw())
|
||||||
|
|
||||||
|
elif ans == 'CMD_GLOBEXT':
|
||||||
|
if not re_match_include(selection):
|
||||||
|
globbed_rule_obj = selection_to_rule_obj(rule_obj, selection)
|
||||||
|
globbed_rule_obj.glob_ext()
|
||||||
|
options, default_option = add_to_options(options, globbed_rule_obj.get_raw())
|
||||||
|
|
||||||
else:
|
else:
|
||||||
done = False
|
done = False
|
||||||
# END of code (mostly) shared with aa-mergeprof
|
# END of code (mostly) shared with aa-mergeprof
|
||||||
|
|
||||||
|
def selection_to_rule_obj(rule_obj, selection):
|
||||||
|
rule_type = type(rule_obj)
|
||||||
|
return rule_type.parse(selection)
|
||||||
|
|
||||||
def ask_the_questions_OLD_FILE_CODE(): # XXX unused
|
def ask_the_questions_OLD_FILE_CODE(): # XXX unused
|
||||||
global seen_events
|
global seen_events
|
||||||
# Process all the path entries.
|
# Process all the path entries.
|
||||||
@@ -1912,6 +1934,12 @@ def available_buttons(rule_obj):
|
|||||||
|
|
||||||
buttons += ['CMD_DENY', 'CMD_IGNORE_ENTRY']
|
buttons += ['CMD_DENY', 'CMD_IGNORE_ENTRY']
|
||||||
|
|
||||||
|
if rule_obj.can_glob:
|
||||||
|
buttons += ['CMD_GLOB']
|
||||||
|
|
||||||
|
if rule_obj.can_glob_ext:
|
||||||
|
buttons += ['CMD_GLOBEXT']
|
||||||
|
|
||||||
if rule_obj.audit:
|
if rule_obj.audit:
|
||||||
buttons += ['CMD_AUDIT_OFF']
|
buttons += ['CMD_AUDIT_OFF']
|
||||||
else:
|
else:
|
||||||
|
Reference in New Issue
Block a user