mirror of
https://gitlab.com/apparmor/apparmor.git
synced 2025-03-04 08:24:42 +01:00
Remove Python 2 support.
This commit is contained in:
parent
43f419458e
commit
df97cf89bd
37 changed files with 146 additions and 319 deletions
|
@ -1,6 +1 @@
|
|||
import sys
|
||||
|
||||
if sys.version_info[0] >= 3:
|
||||
from LibAppArmor.LibAppArmor import *
|
||||
else:
|
||||
from .LibAppArmor import *
|
||||
from LibAppArmor.LibAppArmor import *
|
||||
|
|
|
@ -17,7 +17,6 @@
|
|||
|
||||
from argparse import ArgumentParser
|
||||
import os
|
||||
import platform
|
||||
import shutil
|
||||
import time
|
||||
import tempfile
|
||||
|
@ -147,9 +146,6 @@ class AAParserCachingCommon(testlib.AATestTemplate):
|
|||
|
||||
class AAParserBasicCachingTests(AAParserCachingCommon):
|
||||
|
||||
def setUp(self):
|
||||
super(AAParserBasicCachingTests, self).setUp()
|
||||
|
||||
def test_no_cache_by_default(self):
|
||||
'''test profiles are not cached by default'''
|
||||
|
||||
|
@ -201,7 +197,7 @@ class AAParserAltCacheBasicTests(AAParserBasicCachingTests):
|
|||
'''Same tests as above, but with an alternate cache location specified on the command line'''
|
||||
|
||||
def setUp(self):
|
||||
super(AAParserAltCacheBasicTests, self).setUp()
|
||||
super().setUp()
|
||||
|
||||
alt_cache_loc = tempfile.mkdtemp(prefix='aa-alt-cache', dir=self.tmp_dir)
|
||||
os.chmod(alt_cache_loc, 0o755)
|
||||
|
@ -213,14 +209,14 @@ class AAParserAltCacheBasicTests(AAParserBasicCachingTests):
|
|||
def tearDown(self):
|
||||
if len(os.listdir(self.unused_cache_loc)) > 0:
|
||||
self.fail('original cache dir \'%s\' not empty' % self.unused_cache_loc)
|
||||
super(AAParserAltCacheBasicTests, self).tearDown()
|
||||
super().tearDown()
|
||||
|
||||
|
||||
class AAParserCreateCacheBasicTestsCacheExists(AAParserBasicCachingTests):
|
||||
'''Same tests as above, but with create cache option on the command line and the cache already exists'''
|
||||
|
||||
def setUp(self):
|
||||
super(AAParserCreateCacheBasicTestsCacheExists, self).setUp()
|
||||
super().setUp()
|
||||
self.cmd_prefix.append('--create-cache-dir')
|
||||
|
||||
|
||||
|
@ -228,7 +224,7 @@ class AAParserCreateCacheBasicTestsCacheNotExist(AAParserBasicCachingTests):
|
|||
'''Same tests as above, but with create cache option on the command line and cache dir removed'''
|
||||
|
||||
def setUp(self):
|
||||
super(AAParserCreateCacheBasicTestsCacheNotExist, self).setUp()
|
||||
super().setUp()
|
||||
shutil.rmtree(self.cache_dir)
|
||||
self.cmd_prefix.append('--create-cache-dir')
|
||||
|
||||
|
@ -238,7 +234,7 @@ class AAParserCreateCacheAltCacheTestsCacheNotExist(AAParserBasicCachingTests):
|
|||
alt cache specified, and cache dir removed'''
|
||||
|
||||
def setUp(self):
|
||||
super(AAParserCreateCacheAltCacheTestsCacheNotExist, self).setUp()
|
||||
super().setUp()
|
||||
shutil.rmtree(self.cache_dir)
|
||||
self.cmd_prefix.append('--create-cache-dir')
|
||||
|
||||
|
@ -246,7 +242,7 @@ class AAParserCreateCacheAltCacheTestsCacheNotExist(AAParserBasicCachingTests):
|
|||
class AAParserCachingTests(AAParserCachingCommon):
|
||||
|
||||
def setUp(self):
|
||||
super(AAParserCachingTests, self).setUp()
|
||||
super().setUp()
|
||||
|
||||
r = testlib.filesystem_time_resolution()
|
||||
self.mtime_res = r[1]
|
||||
|
@ -258,24 +254,10 @@ class AAParserCachingTests(AAParserCachingCommon):
|
|||
self.run_cmd_check(cmd)
|
||||
self.assert_path_exists(self.cache_file)
|
||||
|
||||
def _assertTimeStampEquals(self, time1, time2):
|
||||
'''Compare two timestamps to ensure equality'''
|
||||
|
||||
# python 3.2 and earlier don't support writing timestamps with
|
||||
# nanosecond resolution, only microsecond. When comparing
|
||||
# timestamps in such an environment, loosen the equality bounds
|
||||
# to compensate
|
||||
# Reference: https://bugs.python.org/issue12904
|
||||
(major, minor, _) = platform.python_version_tuple()
|
||||
if (int(major) < 3) or ((int(major) == 3) and (int(minor) <= 2)):
|
||||
self.assertAlmostEquals(time1, time2, places=5)
|
||||
else:
|
||||
self.assertEqual(time1, time2)
|
||||
|
||||
def _set_mtime(self, path, mtime):
|
||||
atime = os.stat(path).st_atime
|
||||
os.utime(path, (atime, mtime))
|
||||
self._assertTimeStampEquals(os.stat(path).st_mtime, mtime)
|
||||
self.assertEqual(os.stat(path).st_mtime, mtime)
|
||||
|
||||
def test_cache_loaded_when_exists(self):
|
||||
'''test cache is loaded when it exists, is newer than profile, and features match'''
|
||||
|
@ -458,7 +440,7 @@ class AAParserCachingTests(AAParserCachingCommon):
|
|||
|
||||
stat = os.stat(self.cache_file)
|
||||
self.assertNotEqual(orig_stat.st_ino, stat.st_ino)
|
||||
self._assertTimeStampEquals(profile_mtime, stat.st_mtime)
|
||||
self.assertEqual(profile_mtime, stat.st_mtime)
|
||||
|
||||
def test_abstraction_newer_rewrites_cache(self):
|
||||
'''test cache is rewritten if abstraction is newer'''
|
||||
|
@ -475,7 +457,7 @@ class AAParserCachingTests(AAParserCachingCommon):
|
|||
|
||||
stat = os.stat(self.cache_file)
|
||||
self.assertNotEqual(orig_stat.st_ino, stat.st_ino)
|
||||
self._assertTimeStampEquals(abstraction_mtime, stat.st_mtime)
|
||||
self.assertEqual(abstraction_mtime, stat.st_mtime)
|
||||
|
||||
def test_parser_newer_uses_cache(self):
|
||||
'''test cache is not skipped if parser is newer'''
|
||||
|
@ -521,7 +503,7 @@ class AAParserAltCacheTests(AAParserCachingTests):
|
|||
check_orig_cache = True
|
||||
|
||||
def setUp(self):
|
||||
super(AAParserAltCacheTests, self).setUp()
|
||||
super().setUp()
|
||||
|
||||
alt_cache_loc = tempfile.mkdtemp(prefix='aa-alt-cache', dir=self.tmp_dir)
|
||||
os.chmod(alt_cache_loc, 0o755)
|
||||
|
@ -534,7 +516,7 @@ class AAParserAltCacheTests(AAParserCachingTests):
|
|||
def tearDown(self):
|
||||
if self.check_orig_cache and len(os.listdir(self.orig_cache_dir)) > 0:
|
||||
self.fail('original cache dir \'%s\' not empty' % self.orig_cache_dir)
|
||||
super(AAParserAltCacheTests, self).tearDown()
|
||||
super().tearDown()
|
||||
|
||||
def test_cache_purge_leaves_original_cache_alone(self):
|
||||
'''test cache purging only touches alt cache'''
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
# TODO
|
||||
# - finish adding suppressions for valgrind false positives
|
||||
|
||||
from argparse import ArgumentParser # requires python 2.7 or newer
|
||||
from argparse import ArgumentParser
|
||||
import os
|
||||
import sys
|
||||
import tempfile
|
||||
|
|
|
@ -13,7 +13,6 @@
|
|||
#
|
||||
# ----------------------------------------------------------------------
|
||||
# No old version logs, only 2.6 + supported
|
||||
from __future__ import division, with_statement
|
||||
import os
|
||||
import re
|
||||
import shutil
|
||||
|
@ -23,6 +22,7 @@ import time
|
|||
import traceback
|
||||
import atexit
|
||||
import tempfile
|
||||
from shutil import which
|
||||
|
||||
import apparmor.config
|
||||
import apparmor.logparser
|
||||
|
@ -33,7 +33,7 @@ from copy import deepcopy
|
|||
from apparmor.aare import AARE
|
||||
|
||||
from apparmor.common import (AppArmorException, AppArmorBug, cmd, is_skippable_file, open_file_read, valid_path, hasher,
|
||||
combine_profname, split_name, type_is_str, open_file_write, DebugLogger)
|
||||
combine_profname, split_name, open_file_write, DebugLogger)
|
||||
|
||||
import apparmor.ui as aaui
|
||||
|
||||
|
@ -176,18 +176,6 @@ def check_for_apparmor(filesystem='/proc/filesystems', mounts='/proc/mounts'):
|
|||
break
|
||||
return aa_mountpoint
|
||||
|
||||
def which(file):
|
||||
"""Returns the executable fullpath for the file, None otherwise"""
|
||||
if sys.version_info >= (3, 3):
|
||||
return shutil.which(file)
|
||||
env_dirs = os.getenv('PATH').split(':')
|
||||
for env_dir in env_dirs:
|
||||
env_path = os.path.join(env_dir, file)
|
||||
# Test if the path is executable or not
|
||||
if os.access(env_path, os.X_OK):
|
||||
return env_path
|
||||
return None
|
||||
|
||||
def get_full_path(original_path):
|
||||
"""Return the full path after resolving any symlinks"""
|
||||
path = original_path
|
||||
|
@ -626,7 +614,7 @@ def change_profile_flags(prof_filename, program, flag, set_flag):
|
|||
found = False
|
||||
depth = -1
|
||||
|
||||
if not flag or (type_is_str(flag) and flag.strip() == ''):
|
||||
if not flag or (type(flag) is str and flag.strip() == ''):
|
||||
raise AppArmorBug('New flag for %s is empty' % prof_filename)
|
||||
|
||||
with open_file_read(prof_filename) as f_in:
|
||||
|
@ -1529,28 +1517,28 @@ def save_profiles(is_mergeprof=False):
|
|||
ans, arg = q.promptUser()
|
||||
|
||||
q.selected = arg # remember selection
|
||||
which = options[arg]
|
||||
which_ = options[arg]
|
||||
|
||||
if ans == 'CMD_SAVE_SELECTED':
|
||||
write_profile_ui_feedback(which)
|
||||
reload_base(which)
|
||||
write_profile_ui_feedback(which_)
|
||||
reload_base(which_)
|
||||
q.selected = 0 # saving the selected profile removes it from the list, therefore reset selection
|
||||
|
||||
elif ans == 'CMD_VIEW_CHANGES':
|
||||
oldprofile = None
|
||||
if aa[which][which].get('filename', False):
|
||||
oldprofile = aa[which][which]['filename']
|
||||
if aa[which_][which_].get('filename', False):
|
||||
oldprofile = aa[which_][which_]['filename']
|
||||
else:
|
||||
oldprofile = get_profile_filename_from_attachment(which, True)
|
||||
oldprofile = get_profile_filename_from_attachment(which_, True)
|
||||
|
||||
serialize_options = {'METADATA': True}
|
||||
newprofile = serialize_profile(split_to_merged(aa), which, serialize_options)
|
||||
newprofile = serialize_profile(split_to_merged(aa), which_, serialize_options)
|
||||
|
||||
aaui.UI_Changes(oldprofile, newprofile, comments=True)
|
||||
|
||||
elif ans == 'CMD_VIEW_CHANGES_CLEAN':
|
||||
oldprofile = serialize_profile(split_to_merged(original_aa), which, {})
|
||||
newprofile = serialize_profile(split_to_merged(aa), which, {})
|
||||
oldprofile = serialize_profile(split_to_merged(original_aa), which_, {})
|
||||
newprofile = serialize_profile(split_to_merged(aa), which_, {})
|
||||
|
||||
aaui.UI_Changes(oldprofile, newprofile)
|
||||
|
||||
|
@ -2385,10 +2373,7 @@ def check_qualifiers(program):
|
|||
|
||||
def get_subdirectories(current_dir):
|
||||
"""Returns a list of all directories directly inside given directory"""
|
||||
if sys.version_info < (3, 0):
|
||||
return os.walk(current_dir).next()[1]
|
||||
else:
|
||||
return os.walk(current_dir).__next__()[1]
|
||||
return next(os.walk(current_dir))[1]
|
||||
|
||||
def loadincludes():
|
||||
loadincludes_dir('tunables', True)
|
||||
|
|
|
@ -14,9 +14,9 @@
|
|||
|
||||
import re
|
||||
|
||||
from apparmor.common import convert_regexp, type_is_str, AppArmorBug, AppArmorException
|
||||
from apparmor.common import convert_regexp, AppArmorBug, AppArmorException
|
||||
|
||||
class AARE(object):
|
||||
class AARE:
|
||||
'''AARE (AppArmor Regular Expression) wrapper class'''
|
||||
|
||||
def __init__(self, regex, is_path, log_event=None):
|
||||
|
@ -68,7 +68,7 @@ class AARE(object):
|
|||
expression = expression.regex
|
||||
else:
|
||||
return self.is_equal(expression) # better safe than sorry
|
||||
elif not type_is_str(expression):
|
||||
elif type(expression) is not str:
|
||||
raise AppArmorBug('AARE.match() called with unknown object: %s' % str(expression))
|
||||
|
||||
if self._regex_compiled is None:
|
||||
|
@ -81,7 +81,7 @@ class AARE(object):
|
|||
|
||||
if type(expression) == AARE:
|
||||
return self.regex == expression.regex
|
||||
elif type_is_str(expression):
|
||||
elif type(expression) is str:
|
||||
return self.regex == expression
|
||||
else:
|
||||
raise AppArmorBug('AARE.is_equal() called with unknown object: %s' % str(expression))
|
||||
|
|
|
@ -14,7 +14,7 @@
|
|||
# ----------------------------------------------------------------------
|
||||
import apparmor.aa as apparmor
|
||||
|
||||
class Prof(object):
|
||||
class Prof:
|
||||
def __init__(self, filename):
|
||||
apparmor.init_aa()
|
||||
self.aa = apparmor.aa
|
||||
|
@ -22,7 +22,7 @@ class Prof(object):
|
|||
self.include = apparmor.include
|
||||
self.filename = filename
|
||||
|
||||
class CleanProf(object):
|
||||
class CleanProf:
|
||||
def __init__(self, same_file, profile, other):
|
||||
#If same_file we're basically comparing the file against itself to check superfluous rules
|
||||
self.same_file = same_file
|
||||
|
|
|
@ -9,7 +9,6 @@
|
|||
#
|
||||
# ------------------------------------------------------------------
|
||||
|
||||
from __future__ import print_function
|
||||
import codecs
|
||||
import collections
|
||||
import glob
|
||||
|
@ -118,10 +117,7 @@ def cmd(command):
|
|||
except OSError as ex:
|
||||
return [127, str(ex)]
|
||||
|
||||
if sys.version_info[0] >= 3:
|
||||
out = sp.communicate()[0].decode('ascii', 'ignore')
|
||||
else:
|
||||
out = sp.communicate()[0]
|
||||
out = sp.communicate()[0].decode('ascii', 'ignore')
|
||||
|
||||
return [sp.returncode, out]
|
||||
|
||||
|
@ -134,10 +130,7 @@ def cmd_pipe(command1, command2):
|
|||
except OSError as ex:
|
||||
return [127, str(ex)]
|
||||
|
||||
if sys.version_info[0] >= 3:
|
||||
out = sp2.communicate()[0].decode('ascii', 'ignore')
|
||||
else:
|
||||
out = sp2.communicate()[0]
|
||||
out = sp2.communicate()[0].decode('ascii', 'ignore')
|
||||
|
||||
return [sp2.returncode, out]
|
||||
|
||||
|
@ -202,14 +195,7 @@ def open_file_anymode(mode, path, encoding='UTF-8'):
|
|||
# This avoids a crash when reading a logfile with special characters that
|
||||
# are not utf8-encoded (for example a latin1 "ö"), and also avoids crashes
|
||||
# at several other places we don't know yet ;-)
|
||||
errorhandling = 'surrogateescape'
|
||||
|
||||
if sys.version_info[0] < 3:
|
||||
errorhandling = 'replace'
|
||||
|
||||
orig = codecs.open(path, mode, encoding, errors=errorhandling)
|
||||
|
||||
return orig
|
||||
return codecs.open(path, mode, encoding, errors='surrogateescape')
|
||||
|
||||
def readkey():
|
||||
'''Returns the pressed key'''
|
||||
|
@ -268,15 +254,6 @@ def user_perm(prof_dir):
|
|||
return False
|
||||
return True
|
||||
|
||||
if sys.version_info[0] > 2:
|
||||
unicode = str # python 3 dropped the unicode type. To keep type_is_str() simple (and pyflakes3 happy), re-create it as alias of str.
|
||||
|
||||
def type_is_str(var):
|
||||
''' returns True if the given variable is a str (or unicode string when using python 2)'''
|
||||
if type(var) in (str, unicode): # python 2 sometimes uses the 'unicode' type
|
||||
return True
|
||||
else:
|
||||
return False
|
||||
|
||||
def split_name(full_profile):
|
||||
if '//' in full_profile:
|
||||
|
@ -301,7 +278,7 @@ def combine_profname(name_parts):
|
|||
return '//'.join(name_parts)
|
||||
|
||||
|
||||
class DebugLogger(object):
|
||||
class DebugLogger:
|
||||
'''Unified debug facility. Logs to file or stderr.
|
||||
|
||||
Does not log anything by default. Will only log if environment variable
|
||||
|
|
|
@ -11,29 +11,12 @@
|
|||
# GNU General Public License for more details.
|
||||
#
|
||||
# ----------------------------------------------------------------------
|
||||
from __future__ import with_statement
|
||||
import os
|
||||
import shlex
|
||||
import shutil
|
||||
import stat
|
||||
import sys
|
||||
import tempfile
|
||||
if sys.version_info < (3, 0):
|
||||
import ConfigParser as configparser
|
||||
|
||||
# Class to provide the object[section][option] behavior in Python2
|
||||
class configparser_py2(configparser.ConfigParser):
|
||||
def __getitem__(self, section):
|
||||
section_val = self.items(section)
|
||||
section_options = dict()
|
||||
for option, value in section_val:
|
||||
section_options[option] = value
|
||||
return section_options
|
||||
|
||||
|
||||
else:
|
||||
import configparser
|
||||
|
||||
from configparser import ConfigParser
|
||||
|
||||
from apparmor.common import AppArmorException, open_file_read # , warn, msg,
|
||||
|
||||
|
@ -41,7 +24,7 @@ from apparmor.common import AppArmorException, open_file_read # , warn, msg,
|
|||
# CFG = None
|
||||
# REPO_CFG = None
|
||||
# SHELL_FILES = ['easyprof.conf', 'notify.conf', 'parser.conf']
|
||||
class Config(object):
|
||||
class Config:
|
||||
def __init__(self, conf_type, conf_dir='/etc/apparmor'):
|
||||
self.CONF_DIR = conf_dir
|
||||
# The type of config file that'll be read and/or written
|
||||
|
@ -55,7 +38,7 @@ class Config(object):
|
|||
if self.conf_type == 'shell':
|
||||
config = {'': dict()}
|
||||
elif self.conf_type == 'ini':
|
||||
config = configparser.ConfigParser()
|
||||
config = ConfigParser()
|
||||
return config
|
||||
|
||||
def read_config(self, filename):
|
||||
|
@ -65,21 +48,10 @@ class Config(object):
|
|||
if self.conf_type == 'shell':
|
||||
config = self.read_shell(filepath)
|
||||
elif self.conf_type == 'ini':
|
||||
if sys.version_info > (3, 0):
|
||||
config = configparser.ConfigParser()
|
||||
else:
|
||||
config = configparser_py2()
|
||||
config = ConfigParser()
|
||||
# Set the option form to string -prevents forced conversion to lowercase
|
||||
config.optionxform = str
|
||||
if sys.version_info > (3, 0):
|
||||
config.read(filepath)
|
||||
else:
|
||||
try:
|
||||
config.read(filepath)
|
||||
except configparser.ParsingError:
|
||||
tmp_filepath = py2_parser(filepath)
|
||||
config.read(tmp_filepath.name)
|
||||
##config.__get__()
|
||||
config.read(filepath)
|
||||
return config
|
||||
|
||||
def write_config(self, filename, config):
|
||||
|
@ -275,18 +247,3 @@ class Config(object):
|
|||
for option in options:
|
||||
line = ' ' + option + ' = ' + config[section][option] + '\n'
|
||||
f_out.write(line)
|
||||
|
||||
def py2_parser(filename):
|
||||
"""Returns the de-dented ini file from the new format ini"""
|
||||
tmp = tempfile.NamedTemporaryFile('rw')
|
||||
if os.path.exists(filename):
|
||||
with open(tmp.name, 'w') as f_out, open_file_read(filename) as f_in:
|
||||
for line in f_in:
|
||||
# The ini format allows for multi-line entries, with the subsequent
|
||||
# entries being indented deeper hence simple lstrip() is not appropriate
|
||||
if line[:2] == ' ':
|
||||
line = line[2:]
|
||||
elif line[0] == '\t':
|
||||
line = line[1:]
|
||||
f_out.write(line)
|
||||
return tmp
|
||||
|
|
|
@ -8,8 +8,6 @@
|
|||
#
|
||||
# ------------------------------------------------------------------
|
||||
|
||||
from __future__ import with_statement
|
||||
|
||||
import codecs
|
||||
import copy
|
||||
import glob
|
||||
|
@ -21,8 +19,8 @@ import shutil
|
|||
import subprocess
|
||||
import sys
|
||||
import tempfile
|
||||
from shutil import which
|
||||
|
||||
from apparmor.aa import which
|
||||
from apparmor.common import AppArmorException
|
||||
|
||||
|
||||
|
|
|
@ -8,8 +8,6 @@
|
|||
#
|
||||
# ------------------------------------------------------------------
|
||||
|
||||
from __future__ import print_function # needed in py2 for print('...', file=sys.stderr)
|
||||
|
||||
import cgitb
|
||||
import os
|
||||
import sys
|
||||
|
|
|
@ -79,9 +79,6 @@ class ReadLog:
|
|||
"""Parse the event from log into key value pairs"""
|
||||
msg = msg.strip()
|
||||
self.debug_logger.info('parse_event: %s' % msg)
|
||||
if sys.version_info < (3, 0):
|
||||
# parse_record fails with u'foo' style strings hence typecasting to string
|
||||
msg = str(msg)
|
||||
event = LibAppArmor.parse_record(msg)
|
||||
ev = dict()
|
||||
ev['resource'] = event.info
|
||||
|
@ -288,8 +285,7 @@ class ReadLog:
|
|||
except AppArmorException as e:
|
||||
ex_msg = ('%(msg)s\n\nThis error was caused by the log line:\n%(logline)s' %
|
||||
{'msg': e.value, 'logline': line})
|
||||
# when py3 only: Drop the original AppArmorException by passing None as the parent exception
|
||||
raise AppArmorBug(ex_msg) # py3-only: from None
|
||||
raise AppArmorBug(ex_msg) from None
|
||||
|
||||
self.LOG.close()
|
||||
self.logmark = ''
|
||||
|
|
|
@ -14,7 +14,7 @@
|
|||
# ----------------------------------------------------------------------
|
||||
|
||||
|
||||
from apparmor.common import AppArmorBug, AppArmorException, type_is_str
|
||||
from apparmor.common import AppArmorBug, AppArmorException
|
||||
|
||||
from apparmor.rule.abi import AbiRule, AbiRuleset
|
||||
from apparmor.rule.capability import CapabilityRule, CapabilityRuleset
|
||||
|
@ -108,14 +108,14 @@ class ProfileStorage:
|
|||
|
||||
# allow writing str or None to some keys
|
||||
elif key in ('flags', 'filename'):
|
||||
if type_is_str(value) or value is None:
|
||||
if type(value) is str or value is None:
|
||||
self.data[key] = value
|
||||
else:
|
||||
raise AppArmorBug('Attempt to change type of "%s" from %s to %s, value %s' % (key, type(self.data[key]), type(value), value))
|
||||
|
||||
# allow writing str values
|
||||
elif type_is_str(self.data[key]):
|
||||
if type_is_str(value):
|
||||
elif type(self.data[key]) is str:
|
||||
if type(value) is str:
|
||||
self.data[key] = value
|
||||
else:
|
||||
raise AppArmorBug('Attempt to change type of "%s" from %s to %s, value %s' % (key, type(self.data[key]), type(value), value))
|
||||
|
@ -268,10 +268,10 @@ def split_flags(flags):
|
|||
def add_or_remove_flag(flags, flags_to_change, set_flag):
|
||||
'''add (if set_flag == True) or remove the given flags_to_change to flags'''
|
||||
|
||||
if type_is_str(flags) or flags is None:
|
||||
if type(flags) is str or flags is None:
|
||||
flags = split_flags(flags)
|
||||
|
||||
if type_is_str(flags_to_change) or flags_to_change is None:
|
||||
if type(flags_to_change) is str or flags_to_change is None:
|
||||
flags_to_change = split_flags(flags_to_change)
|
||||
|
||||
if set_flag:
|
||||
|
|
|
@ -13,15 +13,17 @@
|
|||
#
|
||||
# ----------------------------------------------------------------------
|
||||
|
||||
from abc import abstractmethod
|
||||
|
||||
from apparmor.aare import AARE
|
||||
from apparmor.common import AppArmorBug, type_is_str
|
||||
from apparmor.common import AppArmorBug
|
||||
|
||||
# setup module translations
|
||||
from apparmor.translations import init_translation
|
||||
_ = init_translation()
|
||||
|
||||
|
||||
class BaseRule(object):
|
||||
class BaseRule:
|
||||
'''Base class to handle and store a single rule'''
|
||||
|
||||
# type specific rules should inherit from this class.
|
||||
|
@ -76,7 +78,7 @@ class BaseRule(object):
|
|||
|
||||
if rulepart == self.ALL:
|
||||
return None, True
|
||||
elif type_is_str(rulepart):
|
||||
elif type(rulepart) is str:
|
||||
if len(rulepart.strip()) == 0:
|
||||
raise AppArmorBug('Passed empty %(partname)s to %(classname)s: %(rulepart)s' %
|
||||
{'partname': partname, 'classname': self.__class__.__name__, 'rulepart': str(rulepart)})
|
||||
|
@ -104,8 +106,8 @@ class BaseRule(object):
|
|||
else:
|
||||
return False
|
||||
|
||||
# @abstractmethod FIXME - uncomment when python3 only
|
||||
@classmethod
|
||||
@abstractmethod
|
||||
def _match(cls, raw_rule):
|
||||
'''parse raw_rule and return regex match object'''
|
||||
raise NotImplementedError("'%s' needs to implement _match(), but didn't" % (str(cls)))
|
||||
|
@ -117,14 +119,14 @@ class BaseRule(object):
|
|||
rule.raw_rule = raw_rule.strip()
|
||||
return rule
|
||||
|
||||
# @abstractmethod FIXME - uncomment when python3 only
|
||||
@classmethod
|
||||
@abstractmethod
|
||||
def _parse(cls, raw_rule):
|
||||
'''returns a Rule object created from parsing the raw rule.
|
||||
required to be implemented by subclasses; raise exception if not'''
|
||||
raise NotImplementedError("'%s' needs to implement _parse(), but didn't" % (str(cls)))
|
||||
|
||||
# @abstractmethod FIXME - uncomment when python3 only
|
||||
@abstractmethod
|
||||
def get_clean(self, depth=0):
|
||||
'''return clean rule (with default formatting, and leading whitespace as specified in the depth parameter)'''
|
||||
raise NotImplementedError("'%s' needs to implement get_clean(), but didn't" % (str(self.__class__)))
|
||||
|
@ -157,7 +159,7 @@ class BaseRule(object):
|
|||
# still here? -> then the common part is covered, check rule-specific things now
|
||||
return self.is_covered_localvars(other_rule)
|
||||
|
||||
# @abstractmethod FIXME - uncomment when python3 only
|
||||
@abstractmethod
|
||||
def is_covered_localvars(self, other_rule):
|
||||
'''check if the rule-specific parts of other_rule is covered by this rule object'''
|
||||
raise NotImplementedError("'%s' needs to implement is_covered_localvars(), but didn't" % (str(self)))
|
||||
|
@ -238,7 +240,7 @@ class BaseRule(object):
|
|||
# still here? -> then it is equal
|
||||
return True
|
||||
|
||||
# @abstractmethod FIXME - uncomment when python3 only
|
||||
@abstractmethod
|
||||
def is_equal_localvars(self, other_rule, strict):
|
||||
'''compare if rule-specific variables are equal'''
|
||||
raise NotImplementedError("'%s' needs to implement is_equal_localvars(), but didn't" % (str(self)))
|
||||
|
@ -273,24 +275,24 @@ class BaseRule(object):
|
|||
|
||||
return headers
|
||||
|
||||
# @abstractmethod FIXME - uncomment when python3 only
|
||||
@abstractmethod
|
||||
def logprof_header_localvars(self):
|
||||
'''return the headers (human-readable version of the rule) to display in aa-logprof for this rule object
|
||||
returns {'label1': 'value1', 'label2': 'value2'} '''
|
||||
raise NotImplementedError("'%s' needs to implement logprof_header(), but didn't" % (str(self)))
|
||||
|
||||
# @abstractmethod FIXME - uncomment when python3 only
|
||||
@abstractmethod
|
||||
def edit_header(self):
|
||||
'''return the prompt for, and the path to edit when using '(N)ew' '''
|
||||
raise NotImplementedError("'%s' needs to implement edit_header(), but didn't" % (str(self)))
|
||||
|
||||
# @abstractmethod FIXME - uncomment when python3 only
|
||||
@abstractmethod
|
||||
def validate_edit(self, newpath):
|
||||
'''validate the new path.
|
||||
Returns True if it covers the previous path, False if it doesn't.'''
|
||||
raise NotImplementedError("'%s' needs to implement validate_edit(), but didn't" % (str(self)))
|
||||
|
||||
# @abstractmethod FIXME - uncomment when python3 only
|
||||
@abstractmethod
|
||||
def store_edit(self, newpath):
|
||||
'''store the changed path.
|
||||
This is done even if the new path doesn't match the original one.'''
|
||||
|
@ -314,7 +316,7 @@ class BaseRule(object):
|
|||
return '%s%s' % (auditstr, allowstr)
|
||||
|
||||
|
||||
class BaseRuleset(object):
|
||||
class BaseRuleset:
|
||||
'''Base class to handle and store a collection of rules'''
|
||||
|
||||
# decides if the (G)lob and Glob w/ (E)xt options are displayed
|
||||
|
@ -499,7 +501,7 @@ def check_and_split_list(lst, allowed_keywords, all_obj, classname, keyword_name
|
|||
|
||||
if lst == all_obj:
|
||||
return None, True, None
|
||||
elif type_is_str(lst):
|
||||
elif type(lst) is str:
|
||||
result_list = {lst}
|
||||
elif type(lst) in (list, tuple, set) and (len(lst) > 0 or allow_empty_list):
|
||||
result_list = set(lst)
|
||||
|
|
|
@ -30,10 +30,9 @@ class AbiRule(IncludeRule):
|
|||
def __init__(self, path, ifexists, ismagic, audit=False, deny=False, allow_keyword=False,
|
||||
comment='', log_event=None):
|
||||
|
||||
super(AbiRule, self).__init__(path, ifexists, ismagic,
|
||||
audit=audit, deny=deny, allow_keyword=allow_keyword,
|
||||
comment=comment,
|
||||
log_event=log_event)
|
||||
super().__init__(path, ifexists, ismagic,
|
||||
audit=audit, deny=deny, allow_keyword=allow_keyword,
|
||||
comment=comment, log_event=log_event)
|
||||
|
||||
# abi doesn't support 'if exists'
|
||||
if ifexists:
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
# ----------------------------------------------------------------------
|
||||
|
||||
from apparmor.regex import RE_PROFILE_ALIAS, strip_quotes
|
||||
from apparmor.common import AppArmorBug, AppArmorException, type_is_str
|
||||
from apparmor.common import AppArmorBug, AppArmorException
|
||||
from apparmor.rule import BaseRule, BaseRuleset, parse_comment, quote_if_needed
|
||||
|
||||
# setup module translations
|
||||
|
@ -29,10 +29,8 @@ class AliasRule(BaseRule):
|
|||
def __init__(self, orig_path, target, audit=False, deny=False, allow_keyword=False,
|
||||
comment='', log_event=None):
|
||||
|
||||
super(AliasRule, self).__init__(audit=audit, deny=deny,
|
||||
allow_keyword=allow_keyword,
|
||||
comment=comment,
|
||||
log_event=log_event)
|
||||
super().__init__(audit=audit, deny=deny, allow_keyword=allow_keyword,
|
||||
comment=comment, log_event=log_event)
|
||||
|
||||
# aliass don't support audit or deny
|
||||
if audit:
|
||||
|
@ -40,14 +38,14 @@ class AliasRule(BaseRule):
|
|||
if deny:
|
||||
raise AppArmorBug('Attempt to initialize %s with deny flag' % self.__class__.__name__)
|
||||
|
||||
if not type_is_str(orig_path):
|
||||
if type(orig_path) is not str:
|
||||
raise AppArmorBug('Passed unknown type for orig_path to %s: %s' % (self.__class__.__name__, orig_path))
|
||||
if not orig_path:
|
||||
raise AppArmorException('Passed empty orig_path to %s: %s' % (self.__class__.__name__, orig_path))
|
||||
if not orig_path.startswith('/'):
|
||||
raise AppArmorException("Alias path doesn't start with '/'")
|
||||
|
||||
if not type_is_str(target):
|
||||
if type(target) is not str:
|
||||
raise AppArmorBug('Passed unknown type for target to %s: %s' % (self.__class__.__name__, target))
|
||||
if not target:
|
||||
raise AppArmorException('Passed empty target to %s: %s' % (self.__class__.__name__, target))
|
||||
|
|
|
@ -14,7 +14,7 @@
|
|||
# ----------------------------------------------------------------------
|
||||
|
||||
from apparmor.regex import RE_PROFILE_BOOLEAN
|
||||
from apparmor.common import AppArmorBug, AppArmorException, type_is_str
|
||||
from apparmor.common import AppArmorBug, AppArmorException
|
||||
from apparmor.rule import BaseRule, BaseRuleset, parse_comment
|
||||
|
||||
# setup module translations
|
||||
|
@ -30,10 +30,8 @@ class BooleanRule(BaseRule):
|
|||
def __init__(self, varname, value, audit=False, deny=False, allow_keyword=False,
|
||||
comment='', log_event=None):
|
||||
|
||||
super(BooleanRule, self).__init__(audit=audit, deny=deny,
|
||||
allow_keyword=allow_keyword,
|
||||
comment=comment,
|
||||
log_event=log_event)
|
||||
super().__init__(audit=audit, deny=deny, allow_keyword=allow_keyword,
|
||||
comment=comment, log_event=log_event)
|
||||
|
||||
# boolean variables don't support audit or deny
|
||||
if audit:
|
||||
|
@ -41,12 +39,12 @@ class BooleanRule(BaseRule):
|
|||
if deny:
|
||||
raise AppArmorBug('Attempt to initialize %s with deny flag' % self.__class__.__name__)
|
||||
|
||||
if not type_is_str(varname):
|
||||
if type(varname) is not str:
|
||||
raise AppArmorBug('Passed unknown type for boolean variable to %s: %s' % (self.__class__.__name__, varname))
|
||||
if not varname.startswith('$'):
|
||||
raise AppArmorException("Passed invalid boolean to %s (doesn't start with '$'): %s" % (self.__class__.__name__, varname))
|
||||
|
||||
if not type_is_str(value):
|
||||
if type(value) is not str:
|
||||
raise AppArmorBug('Passed unknown type for value to %s: %s' % (self.__class__.__name__, value))
|
||||
if not value:
|
||||
raise AppArmorException('Passed empty value to %s: %s' % (self.__class__.__name__, value))
|
||||
|
@ -131,4 +129,4 @@ class BooleanRuleset(BaseRuleset):
|
|||
if rule.varname == knownrule.varname:
|
||||
raise AppArmorException(_('Redefining existing variable %(variable)s: %(value)s') % { 'variable': rule.varname, 'value': rule.value })
|
||||
|
||||
super(BooleanRuleset, self).add(rule, cleanup)
|
||||
super().add(rule, cleanup)
|
||||
|
|
|
@ -16,7 +16,7 @@
|
|||
import re
|
||||
|
||||
from apparmor.regex import RE_PROFILE_CAP
|
||||
from apparmor.common import AppArmorBug, AppArmorException, type_is_str
|
||||
from apparmor.common import AppArmorBug, AppArmorException
|
||||
from apparmor.rule import BaseRule, BaseRuleset, logprof_value_or_all, parse_modifiers
|
||||
|
||||
# setup module translations
|
||||
|
@ -29,7 +29,7 @@ class CapabilityRule(BaseRule):
|
|||
|
||||
# Nothing external should reference this class, all external users
|
||||
# should reference the class field CapabilityRule.ALL
|
||||
class __CapabilityAll(object):
|
||||
class __CapabilityAll:
|
||||
pass
|
||||
|
||||
ALL = __CapabilityAll
|
||||
|
@ -39,10 +39,8 @@ class CapabilityRule(BaseRule):
|
|||
def __init__(self, cap_list, audit=False, deny=False, allow_keyword=False,
|
||||
comment='', log_event=None):
|
||||
|
||||
super(CapabilityRule, self).__init__(audit=audit, deny=deny,
|
||||
allow_keyword=allow_keyword,
|
||||
comment=comment,
|
||||
log_event=log_event)
|
||||
super().__init__(audit=audit, deny=deny, allow_keyword=allow_keyword,
|
||||
comment=comment, log_event=log_event)
|
||||
# Because we support having multiple caps in one rule,
|
||||
# initializer needs to accept a list of caps.
|
||||
self.all_caps = False
|
||||
|
@ -50,7 +48,7 @@ class CapabilityRule(BaseRule):
|
|||
self.all_caps = True
|
||||
self.capability = set()
|
||||
else:
|
||||
if type_is_str(cap_list):
|
||||
if type(cap_list) is str:
|
||||
self.capability = {cap_list}
|
||||
elif type(cap_list) == list and len(cap_list) > 0:
|
||||
self.capability = set(cap_list)
|
||||
|
|
|
@ -14,7 +14,7 @@
|
|||
# ----------------------------------------------------------------------
|
||||
|
||||
from apparmor.regex import RE_PROFILE_CHANGE_PROFILE, strip_quotes
|
||||
from apparmor.common import AppArmorBug, AppArmorException, type_is_str
|
||||
from apparmor.common import AppArmorBug, AppArmorException
|
||||
from apparmor.rule import BaseRule, BaseRuleset, parse_modifiers, logprof_value_or_all, quote_if_needed
|
||||
|
||||
# setup module translations
|
||||
|
@ -27,7 +27,7 @@ class ChangeProfileRule(BaseRule):
|
|||
|
||||
# Nothing external should reference this class, all external users
|
||||
# should reference the class field ChangeProfileRule.ALL
|
||||
class __ChangeProfileAll(object):
|
||||
class __ChangeProfileAll:
|
||||
pass
|
||||
|
||||
ALL = __ChangeProfileAll
|
||||
|
@ -43,10 +43,8 @@ class ChangeProfileRule(BaseRule):
|
|||
CHANGE_PROFILE RULE = 'change_profile' [ [ EXEC MODE ] EXEC COND ] [ -> PROGRAMCHILD ]
|
||||
'''
|
||||
|
||||
super(ChangeProfileRule, self).__init__(audit=audit, deny=deny,
|
||||
allow_keyword=allow_keyword,
|
||||
comment=comment,
|
||||
log_event=log_event)
|
||||
super().__init__(audit=audit, deny=deny, allow_keyword=allow_keyword,
|
||||
comment=comment, log_event=log_event)
|
||||
|
||||
if execmode:
|
||||
if execmode != 'safe' and execmode != 'unsafe':
|
||||
|
@ -59,7 +57,7 @@ class ChangeProfileRule(BaseRule):
|
|||
self.all_execconds = False
|
||||
if execcond == ChangeProfileRule.ALL:
|
||||
self.all_execconds = True
|
||||
elif type_is_str(execcond):
|
||||
elif type(execcond) is str:
|
||||
if not execcond.strip():
|
||||
raise AppArmorBug('Empty exec condition in change_profile rule')
|
||||
elif execcond.startswith('/') or execcond.startswith('@'):
|
||||
|
@ -73,7 +71,7 @@ class ChangeProfileRule(BaseRule):
|
|||
self.all_targetprofiles = False
|
||||
if targetprofile == ChangeProfileRule.ALL:
|
||||
self.all_targetprofiles = True
|
||||
elif type_is_str(targetprofile):
|
||||
elif type(targetprofile) is str:
|
||||
if targetprofile.strip():
|
||||
self.targetprofile = targetprofile
|
||||
else:
|
||||
|
|
|
@ -68,7 +68,7 @@ class DbusRule(BaseRule):
|
|||
|
||||
# Nothing external should reference this class, all external users
|
||||
# should reference the class field DbusRule.ALL
|
||||
class __DbusAll(object):
|
||||
class __DbusAll:
|
||||
pass
|
||||
|
||||
ALL = __DbusAll
|
||||
|
@ -78,10 +78,8 @@ class DbusRule(BaseRule):
|
|||
def __init__(self, access, bus, path, name, interface, member, peername, peerlabel,
|
||||
audit=False, deny=False, allow_keyword=False, comment='', log_event=None):
|
||||
|
||||
super(DbusRule, self).__init__(audit=audit, deny=deny,
|
||||
allow_keyword=allow_keyword,
|
||||
comment=comment,
|
||||
log_event=log_event)
|
||||
super().__init__(audit=audit, deny=deny, allow_keyword=allow_keyword,
|
||||
comment=comment, log_event=log_event)
|
||||
|
||||
self.access, self.all_access, unknown_items = check_and_split_list(access, access_keywords, DbusRule.ALL, 'DbusRule', 'access')
|
||||
if unknown_items:
|
||||
|
|
|
@ -14,7 +14,7 @@
|
|||
|
||||
from apparmor.aare import AARE
|
||||
from apparmor.regex import RE_PROFILE_FILE_ENTRY, strip_quotes
|
||||
from apparmor.common import AppArmorBug, AppArmorException, type_is_str
|
||||
from apparmor.common import AppArmorBug, AppArmorException
|
||||
from apparmor.rule import BaseRule, BaseRuleset, check_and_split_list, logprof_value_or_all, parse_modifiers, quote_if_needed
|
||||
|
||||
# setup module translations
|
||||
|
@ -34,9 +34,9 @@ class FileRule(BaseRule):
|
|||
|
||||
# Nothing external should reference this class, all external users
|
||||
# should reference the class field FileRule.ALL
|
||||
class __FileAll(object):
|
||||
class __FileAll:
|
||||
pass
|
||||
class __FileAnyExec(object):
|
||||
class __FileAnyExec:
|
||||
pass
|
||||
|
||||
ALL = __FileAll
|
||||
|
@ -58,8 +58,8 @@ class FileRule(BaseRule):
|
|||
- leading_perms: bool
|
||||
'''
|
||||
|
||||
super(FileRule, self).__init__(audit=audit, deny=deny, allow_keyword=allow_keyword,
|
||||
comment=comment, log_event=log_event)
|
||||
super().__init__(audit=audit, deny=deny, allow_keyword=allow_keyword,
|
||||
comment=comment, log_event=log_event)
|
||||
|
||||
# rulepart partperms is_path log_event
|
||||
self.path, self.all_paths = self._aare_or_all(path, 'path', True, log_event)
|
||||
|
@ -69,7 +69,7 @@ class FileRule(BaseRule):
|
|||
self.can_glob_ext = not self.all_paths
|
||||
self.can_edit = not self.all_paths
|
||||
|
||||
if type_is_str(perms):
|
||||
if type(perms) is str:
|
||||
perms, tmp_exec_perms = split_perms(perms, deny)
|
||||
if tmp_exec_perms:
|
||||
raise AppArmorBug('perms must not contain exec perms')
|
||||
|
@ -96,7 +96,7 @@ class FileRule(BaseRule):
|
|||
raise AppArmorBug("link rules can't have execute permissions")
|
||||
elif exec_perms == self.ANY_EXEC:
|
||||
self.exec_perms = exec_perms
|
||||
elif type_is_str(exec_perms):
|
||||
elif type(exec_perms) is str:
|
||||
if deny:
|
||||
if exec_perms != 'x':
|
||||
raise AppArmorException(_("file deny rules only allow to use 'x' as execute mode, but not %s" % exec_perms))
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
# ----------------------------------------------------------------------
|
||||
|
||||
from apparmor.regex import RE_INCLUDE, re_match_include_parse
|
||||
from apparmor.common import AppArmorBug, AppArmorException, is_skippable_file, type_is_str
|
||||
from apparmor.common import AppArmorBug, AppArmorException, is_skippable_file
|
||||
from apparmor.rule import BaseRule, BaseRuleset, parse_comment
|
||||
import os
|
||||
|
||||
|
@ -30,10 +30,8 @@ class IncludeRule(BaseRule):
|
|||
def __init__(self, path, ifexists, ismagic, audit=False, deny=False, allow_keyword=False,
|
||||
comment='', log_event=None):
|
||||
|
||||
super(IncludeRule, self).__init__(audit=audit, deny=deny,
|
||||
allow_keyword=allow_keyword,
|
||||
comment=comment,
|
||||
log_event=log_event)
|
||||
super().__init__(audit=audit, deny=deny, allow_keyword=allow_keyword,
|
||||
comment=comment, log_event=log_event)
|
||||
|
||||
# include doesn't support audit or deny
|
||||
if audit:
|
||||
|
@ -45,7 +43,7 @@ class IncludeRule(BaseRule):
|
|||
raise AppArmorBug('Passed unknown type for ifexists to %s: %s' % (self.__class__.__name__, ifexists))
|
||||
if type(ismagic) is not bool:
|
||||
raise AppArmorBug('Passed unknown type for ismagic to %s: %s' % (self.__class__.__name__, ismagic))
|
||||
if not type_is_str(path):
|
||||
if type(path) is not str:
|
||||
raise AppArmorBug('Passed unknown type for path to %s: %s' % (self.__class__.__name__, path))
|
||||
if not path:
|
||||
raise AppArmorBug('Passed empty path to %s: %s' % (self.__class__.__name__, path))
|
||||
|
|
|
@ -16,7 +16,7 @@
|
|||
import re
|
||||
|
||||
from apparmor.regex import RE_PROFILE_NETWORK
|
||||
from apparmor.common import AppArmorBug, AppArmorException, type_is_str
|
||||
from apparmor.common import AppArmorBug, AppArmorException
|
||||
from apparmor.rule import BaseRule, BaseRuleset, logprof_value_or_all, parse_modifiers
|
||||
|
||||
# setup module translations
|
||||
|
@ -49,7 +49,7 @@ class NetworkRule(BaseRule):
|
|||
|
||||
# Nothing external should reference this class, all external users
|
||||
# should reference the class field NetworkRule.ALL
|
||||
class __NetworkAll(object):
|
||||
class __NetworkAll:
|
||||
pass
|
||||
|
||||
ALL = __NetworkAll
|
||||
|
@ -59,16 +59,14 @@ class NetworkRule(BaseRule):
|
|||
def __init__(self, domain, type_or_protocol, audit=False, deny=False, allow_keyword=False,
|
||||
comment='', log_event=None):
|
||||
|
||||
super(NetworkRule, self).__init__(audit=audit, deny=deny,
|
||||
allow_keyword=allow_keyword,
|
||||
comment=comment,
|
||||
log_event=log_event)
|
||||
super().__init__(audit=audit, deny=deny, allow_keyword=allow_keyword,
|
||||
comment=comment, log_event=log_event)
|
||||
|
||||
self.domain = None
|
||||
self.all_domains = False
|
||||
if domain == NetworkRule.ALL:
|
||||
self.all_domains = True
|
||||
elif type_is_str(domain):
|
||||
elif type(domain) is str:
|
||||
if domain in network_domain_keywords:
|
||||
self.domain = domain
|
||||
else:
|
||||
|
@ -80,7 +78,7 @@ class NetworkRule(BaseRule):
|
|||
self.all_type_or_protocols = False
|
||||
if type_or_protocol == NetworkRule.ALL:
|
||||
self.all_type_or_protocols = True
|
||||
elif type_is_str(type_or_protocol):
|
||||
elif type(type_or_protocol) is str:
|
||||
if type_or_protocol in network_protocol_keywords:
|
||||
self.type_or_protocol = type_or_protocol
|
||||
elif type_or_protocol in network_type_keywords:
|
||||
|
|
|
@ -45,7 +45,7 @@ class PtraceRule(BaseRule):
|
|||
|
||||
# Nothing external should reference this class, all external users
|
||||
# should reference the class field PtraceRule.ALL
|
||||
class __PtraceAll(object):
|
||||
class __PtraceAll:
|
||||
pass
|
||||
|
||||
ALL = __PtraceAll
|
||||
|
@ -55,10 +55,8 @@ class PtraceRule(BaseRule):
|
|||
def __init__(self, access, peer, audit=False, deny=False, allow_keyword=False,
|
||||
comment='', log_event=None):
|
||||
|
||||
super(PtraceRule, self).__init__(audit=audit, deny=deny,
|
||||
allow_keyword=allow_keyword,
|
||||
comment=comment,
|
||||
log_event=log_event)
|
||||
super().__init__(audit=audit, deny=deny, allow_keyword=allow_keyword,
|
||||
comment=comment, log_event=log_event)
|
||||
|
||||
self.access, self.all_access, unknown_items = check_and_split_list(access, access_keywords, PtraceRule.ALL, 'PtraceRule', 'access')
|
||||
if unknown_items:
|
||||
|
|
|
@ -16,7 +16,7 @@
|
|||
import re
|
||||
|
||||
from apparmor.regex import RE_PROFILE_RLIMIT, strip_quotes
|
||||
from apparmor.common import AppArmorBug, AppArmorException, type_is_str
|
||||
from apparmor.common import AppArmorBug, AppArmorException
|
||||
from apparmor.rule import BaseRule, BaseRuleset, parse_comment, quote_if_needed
|
||||
|
||||
# setup module translations
|
||||
|
@ -41,7 +41,7 @@ class RlimitRule(BaseRule):
|
|||
|
||||
# Nothing external should reference this class, all external users
|
||||
# should reference the class field RlimitRule.ALL
|
||||
class __RlimitAll(object):
|
||||
class __RlimitAll:
|
||||
pass
|
||||
|
||||
ALL = __RlimitAll
|
||||
|
@ -51,15 +51,13 @@ class RlimitRule(BaseRule):
|
|||
def __init__(self, rlimit, value, audit=False, deny=False, allow_keyword=False,
|
||||
comment='', log_event=None):
|
||||
|
||||
super(RlimitRule, self).__init__(audit=audit, deny=deny,
|
||||
allow_keyword=allow_keyword,
|
||||
comment=comment,
|
||||
log_event=log_event)
|
||||
super().__init__(audit=audit, deny=deny, allow_keyword=allow_keyword,
|
||||
comment=comment, log_event=log_event)
|
||||
|
||||
if audit or deny or allow_keyword:
|
||||
raise AppArmorBug('The audit, allow or deny keywords are not allowed in rlimit rules.')
|
||||
|
||||
if type_is_str(rlimit):
|
||||
if type(rlimit) is str:
|
||||
if rlimit in rlimit_all:
|
||||
self.rlimit = rlimit
|
||||
else:
|
||||
|
@ -72,7 +70,7 @@ class RlimitRule(BaseRule):
|
|||
self.all_values = False
|
||||
if value == RlimitRule.ALL:
|
||||
self.all_values = True
|
||||
elif type_is_str(value):
|
||||
elif type(value) is str:
|
||||
if not value.strip():
|
||||
raise AppArmorBug('Empty value in rlimit rule')
|
||||
|
||||
|
|
|
@ -66,7 +66,7 @@ class SignalRule(BaseRule):
|
|||
|
||||
# Nothing external should reference this class, all external users
|
||||
# should reference the class field SignalRule.ALL
|
||||
class __SignalAll(object):
|
||||
class __SignalAll:
|
||||
pass
|
||||
|
||||
ALL = __SignalAll
|
||||
|
@ -76,10 +76,8 @@ class SignalRule(BaseRule):
|
|||
def __init__(self, access, signal, peer, audit=False, deny=False, allow_keyword=False,
|
||||
comment='', log_event=None):
|
||||
|
||||
super(SignalRule, self).__init__(audit=audit, deny=deny,
|
||||
allow_keyword=allow_keyword,
|
||||
comment=comment,
|
||||
log_event=log_event)
|
||||
super().__init__(audit=audit, deny=deny, allow_keyword=allow_keyword,
|
||||
comment=comment, log_event=log_event)
|
||||
|
||||
self.access, self.all_access, unknown_items = check_and_split_list(access, access_keywords, SignalRule.ALL, 'SignalRule', 'access')
|
||||
if unknown_items:
|
||||
|
|
|
@ -14,7 +14,7 @@
|
|||
# ----------------------------------------------------------------------
|
||||
|
||||
from apparmor.regex import RE_PROFILE_VARIABLE, strip_quotes
|
||||
from apparmor.common import AppArmorBug, AppArmorException, type_is_str
|
||||
from apparmor.common import AppArmorBug, AppArmorException
|
||||
from apparmor.rule import BaseRule, BaseRuleset, parse_comment, quote_if_needed
|
||||
|
||||
import re
|
||||
|
@ -32,10 +32,8 @@ class VariableRule(BaseRule):
|
|||
def __init__(self, varname, mode, values, audit=False, deny=False, allow_keyword=False,
|
||||
comment='', log_event=None):
|
||||
|
||||
super(VariableRule, self).__init__(audit=audit, deny=deny,
|
||||
allow_keyword=allow_keyword,
|
||||
comment=comment,
|
||||
log_event=log_event)
|
||||
super().__init__(audit=audit, deny=deny, allow_keyword=allow_keyword,
|
||||
comment=comment, log_event=log_event)
|
||||
|
||||
# variables don't support audit or deny
|
||||
if audit:
|
||||
|
@ -43,14 +41,14 @@ class VariableRule(BaseRule):
|
|||
if deny:
|
||||
raise AppArmorBug('Attempt to initialize %s with deny flag' % self.__class__.__name__)
|
||||
|
||||
if not type_is_str(varname):
|
||||
if type(varname) is not str:
|
||||
raise AppArmorBug('Passed unknown type for varname to %s: %s' % (self.__class__.__name__, varname))
|
||||
if not varname.startswith('@{'):
|
||||
raise AppArmorException("Passed invalid varname to %s (doesn't start with '@{'): %s" % (self.__class__.__name__, varname))
|
||||
if not varname.endswith('}'):
|
||||
raise AppArmorException("Passed invalid varname to %s (doesn't end with '}'): %s" % (self.__class__.__name__, varname))
|
||||
|
||||
if not type_is_str(mode):
|
||||
if type(mode) is not str:
|
||||
raise AppArmorBug('Passed unknown type for variable assignment mode to %s: %s' % (self.__class__.__name__, mode))
|
||||
if mode not in ('=', '+='):
|
||||
raise AppArmorBug('Passed unknown variable assignment mode to %s: %s' % (self.__class__.__name__, mode))
|
||||
|
@ -151,7 +149,7 @@ class VariableRuleset(BaseRuleset):
|
|||
if rule.varname == knownrule.varname:
|
||||
raise AppArmorException(_('Redefining existing variable %(variable)s: %(value)s') % { 'variable': rule.varname, 'value': rule.values })
|
||||
|
||||
super(VariableRuleset, self).add(rule, cleanup)
|
||||
super().add(rule, cleanup)
|
||||
|
||||
def get_merged_variables(self):
|
||||
''' Get merged variables of this VariableRuleset.
|
||||
|
|
|
@ -8,7 +8,7 @@
|
|||
#
|
||||
# ------------------------------------------------------------------
|
||||
|
||||
class _Raw_Rule(object):
|
||||
class _Raw_Rule:
|
||||
audit = False
|
||||
deny = False
|
||||
|
||||
|
|
|
@ -9,7 +9,6 @@
|
|||
# ------------------------------------------------------------------
|
||||
|
||||
from apparmor.common import AppArmorException, debug, error, msg, cmd
|
||||
from apparmor.aa import which
|
||||
import apparmor.easyprof
|
||||
import optparse
|
||||
import os
|
||||
|
@ -20,6 +19,7 @@ import socket
|
|||
import sys
|
||||
import tempfile
|
||||
import time
|
||||
from shutil import which
|
||||
|
||||
def check_requirements(binary):
|
||||
'''Verify necessary software is installed'''
|
||||
|
@ -129,10 +129,7 @@ def aa_exec(command, opt, environ={}, verify_rules=[]):
|
|||
debug("\n%s" % policy)
|
||||
|
||||
with tempfile.NamedTemporaryFile(prefix='%s-' % policy_name) as tmp:
|
||||
if sys.version_info[0] >= 3:
|
||||
tmp.write(bytes(policy, 'utf-8'))
|
||||
else:
|
||||
tmp.write(policy)
|
||||
tmp.write(bytes(policy, 'utf-8'))
|
||||
|
||||
debug("using '%s' template" % opt.template)
|
||||
# TODO: get rid of this
|
||||
|
@ -543,10 +540,7 @@ EndSection
|
|||
|
||||
tmp, xorg_conf = tempfile.mkstemp(prefix='aa-sandbox-xorg.conf-')
|
||||
self.tempfiles.append(xorg_conf)
|
||||
if sys.version_info[0] >= 3:
|
||||
os.write(tmp, bytes(conf, 'utf-8'))
|
||||
else:
|
||||
os.write(tmp, conf)
|
||||
os.write(tmp, bytes(conf, 'utf-8'))
|
||||
os.close(tmp)
|
||||
|
||||
xvfb_args.append('--xvfb=Xorg')
|
||||
|
|
|
@ -11,11 +11,10 @@
|
|||
# GNU General Public License for more details.
|
||||
#
|
||||
# ----------------------------------------------------------------------
|
||||
from __future__ import with_statement
|
||||
import re
|
||||
from apparmor.common import AppArmorException, open_file_read, warn, convert_regexp # , msg, error, debug
|
||||
|
||||
class Severity(object):
|
||||
class Severity:
|
||||
def __init__(self, dbname=None, default_rank=10):
|
||||
"""Initialises the class object"""
|
||||
self.PROF_DIR = '/etc/apparmor.d' # The profile directory
|
||||
|
|
|
@ -14,6 +14,7 @@
|
|||
# ----------------------------------------------------------------------
|
||||
import os
|
||||
import sys
|
||||
from shutil import which
|
||||
|
||||
import apparmor.aa as apparmor
|
||||
import apparmor.ui as aaui
|
||||
|
@ -61,9 +62,9 @@ class aa_tools:
|
|||
program = fq_path
|
||||
profile = apparmor.get_profile_filename_from_attachment(fq_path, True)
|
||||
else:
|
||||
which = apparmor.which(p)
|
||||
if which is not None:
|
||||
program = apparmor.get_full_path(which)
|
||||
which_ = which(p)
|
||||
if which_ is not None:
|
||||
program = apparmor.get_full_path(which_)
|
||||
profile = apparmor.get_profile_filename_from_attachment(program, True)
|
||||
elif os.path.exists(os.path.join(apparmor.profile_dir, p)):
|
||||
program = None
|
||||
|
|
|
@ -31,10 +31,6 @@ _ = init_translation()
|
|||
# Set up UI logger for separate messages from UI module
|
||||
debug_logger = DebugLogger('UI')
|
||||
|
||||
# If Python3, wrap input in raw_input so make check passes
|
||||
if 'raw_input' not in dir(__builtins__):
|
||||
raw_input = input
|
||||
|
||||
ARROWS = {'A': 'UP', 'B': 'DOWN', 'C': 'RIGHT', 'D': 'LEFT'}
|
||||
|
||||
UI_mode = 'text'
|
||||
|
@ -70,7 +66,7 @@ def set_text_mode():
|
|||
# reads the response on command line for json and verifies the response
|
||||
# for the dialog type
|
||||
def json_response(dialog_type):
|
||||
string = raw_input('\n')
|
||||
string = input('\n')
|
||||
rh = json.loads(string.strip())
|
||||
if rh["dialog"] != dialog_type:
|
||||
raise AppArmorException('Expected response %s got %s.' % (dialog_type, string))
|
||||
|
@ -222,7 +218,7 @@ def UI_GetString(text, default):
|
|||
else: # text mode
|
||||
readline.set_startup_hook(lambda: readline.insert_text(default))
|
||||
try:
|
||||
string = raw_input('\n' + text)
|
||||
string = input('\n' + text)
|
||||
except EOFError:
|
||||
string = ''
|
||||
finally:
|
||||
|
@ -362,7 +358,7 @@ CMDS = {'CMD_ALLOW': _('(A)llow'),
|
|||
}
|
||||
|
||||
|
||||
class PromptQuestion(object):
|
||||
class PromptQuestion:
|
||||
title = None
|
||||
headers = None
|
||||
explanation = None
|
||||
|
|
|
@ -26,11 +26,11 @@ import os
|
|||
import shutil
|
||||
import sys
|
||||
|
||||
class Install(_install, object):
|
||||
class Install(_install):
|
||||
'''Override setuptools to install the files where we want them.'''
|
||||
def run(self):
|
||||
# Now byte-compile everything
|
||||
super(Install, self).run()
|
||||
super().run()
|
||||
|
||||
prefix = self.prefix
|
||||
if self.root != None:
|
||||
|
|
|
@ -58,7 +58,7 @@ class InterceptingOptionParser(optparse.OptionParser):
|
|||
raise InterceptedError(error_message=msg)
|
||||
|
||||
|
||||
class Manifest(object):
|
||||
class Manifest:
|
||||
def __init__(self, profile_name):
|
||||
self.security = dict()
|
||||
self.security['profiles'] = dict()
|
||||
|
|
|
@ -15,7 +15,6 @@ from common_test import read_file, write_file
|
|||
|
||||
import os
|
||||
import shutil
|
||||
import sys
|
||||
|
||||
import apparmor.aa # needed to set global vars in some tests
|
||||
from apparmor.aa import (check_for_apparmor, get_output, get_reqs, get_interpreter_and_abstraction, create_new_profile,
|
||||
|
@ -99,14 +98,7 @@ class AATest_get_reqs(AATest):
|
|||
)
|
||||
|
||||
def _run_test(self, params, expected):
|
||||
# for some reason, setting the ldd config option does not get
|
||||
# honored in python2.7
|
||||
# XXX KILL when python 2.7 is dropped XXX
|
||||
if sys.version_info[0] < 3:
|
||||
print("Skipping on python < 3.x")
|
||||
return
|
||||
apparmor.aa.cfg['settings']['ldd'] = './fake_ldd'
|
||||
|
||||
self.assertEqual(get_reqs(params), expected)
|
||||
|
||||
class AaTest_create_new_profile(AATest):
|
||||
|
@ -118,12 +110,6 @@ class AaTest_create_new_profile(AATest):
|
|||
)
|
||||
def _run_test(self, params, expected):
|
||||
apparmor.aa.cfg['settings']['ldd'] = './fake_ldd'
|
||||
# for some reason, setting the ldd config option does not get
|
||||
# honored in python2.7
|
||||
# XXX KILL when python 2.7 is dropped XXX
|
||||
if sys.version_info[0] < 3:
|
||||
print("Skipping on python < 3.x")
|
||||
return
|
||||
|
||||
self.createTmpdir()
|
||||
|
||||
|
|
|
@ -13,19 +13,7 @@ import unittest
|
|||
from common_test import AATest, setup_all_loops
|
||||
from apparmor.common import AppArmorBug
|
||||
|
||||
from apparmor.common import type_is_str, split_name, combine_profname
|
||||
|
||||
class TestIs_str_type(AATest):
|
||||
tests = (
|
||||
('foo', True),
|
||||
(u'foo', True),
|
||||
(42, False),
|
||||
(True, False),
|
||||
([], False),
|
||||
)
|
||||
|
||||
def _run_test(self, params, expected):
|
||||
self.assertEqual(type_is_str(params), expected)
|
||||
from apparmor.common import split_name, combine_profname
|
||||
|
||||
class AaTest_split_name(AATest):
|
||||
tests = (
|
||||
|
|
|
@ -14,16 +14,13 @@
|
|||
import os
|
||||
import shutil
|
||||
import subprocess
|
||||
import sys
|
||||
import unittest
|
||||
from common_test import AATest, setup_all_loops, setup_aa
|
||||
|
||||
import apparmor.aa as apparmor
|
||||
from common_test import read_file
|
||||
|
||||
python_interpreter = 'python'
|
||||
if sys.version_info >= (3, 0):
|
||||
python_interpreter = 'python3'
|
||||
python_interpreter = 'python3'
|
||||
|
||||
class MinitoolsTest(AATest):
|
||||
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
#!/usr/bin/python
|
||||
#!/usr/bin/python3
|
||||
#
|
||||
# Copyright (C) 2012 Canonical Ltd.
|
||||
#
|
||||
|
@ -9,7 +9,6 @@
|
|||
# Written by Steve Beattie <steve@nxnw.org>, based on work by
|
||||
# Christian Boltz <apparmor@cboltz.de>
|
||||
|
||||
from __future__ import with_statement
|
||||
import re
|
||||
import subprocess
|
||||
import sys
|
||||
|
|
Loading…
Add table
Reference in a new issue