blob: 192739fcee791dfd7980c0e60e5e0b4475bbe4e3 [file] [log] [blame]
#!/usr/bin/env python3
#
# Copyright (C) 2021 The Android Open Source Project
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
"""Unittests for the seccomp policy linter module."""
from pathlib import Path
import tempfile
import unittest
import seccomp_policy_lint
class CheckSeccompPolicyTests(unittest.TestCase):
"""Tests for check_seccomp_policy."""
def setUp(self):
self.tempdir = Path(tempfile.mkdtemp())
def _write_file(self, filename, contents):
"""Helper to write out a file for testing."""
path = self.tempdir / filename
path.write_text(contents)
return path
def test_check_simple(self):
"""Allow simple policy files."""
path = self._write_file(
'test.policy', """
# Comment.\n
read: 1\n
write: 1\n
""")
exp_out = seccomp_policy_lint.CheckPolicyReturn(
f'seccomp: {path.resolve()} does not contain any dangerous'
' syscalls, so does not require review from'
' chromeos-security@',
[])
with path.open('r', encoding='utf-8') as check_file:
self.assertEqual(seccomp_policy_lint.check_seccomp_policy(
check_file, seccomp_policy_lint.DANGEROUS_SYSCALLS),
exp_out)
def test_check_dangerous_comment(self):
"""Dangerous syscalls must have a comment and need to be reviewed."""
path = self._write_file(
'test.policy', """
# Comment.\n\n\n
clone: 1\n
write: 1\n
""")
exp_out = seccomp_policy_lint.CheckPolicyReturn(
f'seccomp: {path.resolve()} contains dangerous syscalls,'
' so requires review from chromeos-security@',
[])
with path.open('r', encoding='utf-8') as check_file:
self.assertEqual(seccomp_policy_lint.check_seccomp_policy(
check_file, seccomp_policy_lint.DANGEROUS_SYSCALLS),
exp_out)
def test_check_dangerous_no_comment(self):
"""Dangerous syscalls without a comment should cause an error."""
path = self._write_file(
'test.policy', """
# Comment.\n
mount: 1\n
clone: 1\n
""")
exp_out = seccomp_policy_lint.CheckPolicyReturn(
f'seccomp: {path.resolve()} contains dangerous syscalls,'
' so requires review from chromeos-security@',
[(f'{path.resolve()}, line 5: clone syscall is a dangerous '
'syscall so requires a comment on the preceding line')])
with path.open('r', encoding='utf-8') as check_file:
self.assertEqual(seccomp_policy_lint.check_seccomp_policy(
check_file, seccomp_policy_lint.DANGEROUS_SYSCALLS),
exp_out)
def test_check_duplicate_syscall(self):
"""Policy files cannot have duplicate syscalls.."""
path = self._write_file(
'test.policy', """
# Comment.\n
clone: 1\n
clone: arg0 == 3
""")
exp_out = seccomp_policy_lint.CheckPolicyReturn(
f'seccomp: {path.resolve()} contains dangerous syscalls,'
' so requires review from chromeos-security@',
[(f'{path.resolve()}, line 5: repeat syscall: clone')])
with path.open('r', encoding='utf-8') as check_file:
self.assertEqual(seccomp_policy_lint.check_seccomp_policy(
check_file, seccomp_policy_lint.DANGEROUS_SYSCALLS),
exp_out)
if __name__ == '__main__':
unittest.main()