mirror of
https://gitlab.com/apparmor/apparmor
synced 2025-08-31 22:35:35 +00:00
Fix aa-mergeprof crash caused by accidentially initialzed hat
Hasher causes some fun in aa-mergeprof: If the profile in /etc/apparmor.d/ has a hat or subprofile that doesn't exist in the to-be-merged profile, aa-mergeprof crashes. This is caused by reading self.other.aa[program][hat]['include'] which accidently "creates" that profile inside the aa hasher as empty hasher (instead of ProfileStorage). Later, the code loops over self.other.aa[profile].keys(), expects everything to be ProfileStorage, and explodes [1] when for example trying to run .delete_duplicates on the hasher (which obviously doesn't provide this method). This patch adds checks to all self.other.aa accesses in CleanProf.remove_duplicate_rules() to avoid accidently creating new keys in the hasher. Interestingly this bug survived unnoticed for years (at least since 2.11). [1] last lines of the backtrace: File ".../utils/apparmor/cleanprofile.py", line 42, in compare_profiles deleted += self.remove_duplicate_rules(profile) File ".../utils/apparmor/cleanprofile.py", line 65, in remove_duplicate_rules deleted += apparmor.delete_duplicates(self.other.aa[program][hat], inc) File ".../utils/apparmor/aa.py", line 1680, in delete_duplicates deleted += profile[rule_type].delete_duplicates(include[incname][incname][rule_type]) AttributeError: 'collections.defaultdict' object has no attribute 'delete_duplicates'
This commit is contained in:
@@ -54,20 +54,24 @@ class CleanProf(object):
|
|||||||
|
|
||||||
#If different files remove duplicate includes in the other profile
|
#If different files remove duplicate includes in the other profile
|
||||||
if not self.same_file:
|
if not self.same_file:
|
||||||
for inc in includes:
|
if self.other.aa[program].get(hat): # carefully avoid to accidently initialize self.other.aa[program][hat]
|
||||||
if self.other.aa[program][hat]['include'].get(inc, False):
|
for inc in includes:
|
||||||
self.other.aa[program][hat]['include'].pop(inc)
|
if self.other.aa[program][hat]['include'].get(inc, False):
|
||||||
deleted += 1
|
self.other.aa[program][hat]['include'].pop(inc)
|
||||||
|
deleted += 1
|
||||||
|
|
||||||
#Clean up superfluous rules from includes in the other profile
|
#Clean up superfluous rules from includes in the other profile
|
||||||
for inc in includes:
|
for inc in includes:
|
||||||
if not self.profile.include.get(inc, {}).get(inc, False):
|
if not self.profile.include.get(inc, {}).get(inc, False):
|
||||||
apparmor.load_include(inc)
|
apparmor.load_include(inc)
|
||||||
deleted += apparmor.delete_duplicates(self.other.aa[program][hat], inc)
|
if self.other.aa[program].get(hat): # carefully avoid to accidently initialize self.other.aa[program][hat]
|
||||||
|
deleted += apparmor.delete_duplicates(self.other.aa[program][hat], inc)
|
||||||
|
|
||||||
#Clean duplicate rules in other profile
|
#Clean duplicate rules in other profile
|
||||||
for ruletype in apparmor.ruletypes:
|
for ruletype in apparmor.ruletypes:
|
||||||
if not self.same_file:
|
if not self.same_file:
|
||||||
deleted += self.other.aa[program][hat][ruletype].delete_duplicates(self.profile.aa[program][hat][ruletype])
|
if self.other.aa[program].get(hat): # carefully avoid to accidently initialize self.other.aa[program][hat]
|
||||||
|
deleted += self.other.aa[program][hat][ruletype].delete_duplicates(self.profile.aa[program][hat][ruletype])
|
||||||
else:
|
else:
|
||||||
deleted += self.other.aa[program][hat][ruletype].delete_duplicates(None)
|
deleted += self.other.aa[program][hat][ruletype].delete_duplicates(None)
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user