-
Notifications
You must be signed in to change notification settings - Fork 85
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
testcases/OpTestKexec.py: add new test cases with -s and -c options #816
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -48,6 +48,7 @@ | |
kexec, except for the kexec in loop test. | ||
''' | ||
|
||
import os | ||
import unittest | ||
import OpTestLogger | ||
|
||
|
@@ -58,6 +59,7 @@ | |
|
||
log = OpTestLogger.optest_logger_glob.get_logger(__name__) | ||
|
||
|
||
class OpTestKexec(unittest.TestCase): | ||
"""kexec test class""" | ||
|
||
|
@@ -75,10 +77,8 @@ def populate_kernel_initrd_image(self): | |
and initrd_image instance variable | ||
""" | ||
|
||
distro = self.op_test_util.distro_name() | ||
|
||
# Skip the test for unsupported distro | ||
if distro == "unknown": | ||
if self.distro == "unknown": | ||
self.skipTest("Unsupported distro") | ||
|
||
# Find kexec kernel version. If user provided the kernel source | ||
|
@@ -99,13 +99,13 @@ def populate_kernel_initrd_image(self): | |
# Set kernel_image and initrd_image instance variable with | ||
# corresponding filenames path | ||
k_ver = str(k_ver) | ||
if distro == "rhel": | ||
if self.distro == "rhel": | ||
self.kernel_image = "vmlinuz-" + k_ver | ||
self.initrd_image = "initramfs-" + k_ver + ".img" | ||
elif distro == "sles": | ||
elif self.distro == "sles": | ||
self.kernel_image = "vmlinux-" + k_ver | ||
self.initrd_image = "initrd-" + k_ver | ||
elif distro == "ubuntu": | ||
elif self.distro == "ubuntu": | ||
self.kernel_image = "vmlinux-" + k_ver | ||
self.initrd_image = "initrd.img-" + k_ver | ||
|
||
|
@@ -115,7 +115,7 @@ def setUp(self): | |
self.cv_SYSTEM = conf.system() | ||
self.c = self.cv_SYSTEM.console | ||
self.cv_HOST = conf.host() | ||
self.distro = None | ||
self.distro = self.op_test_util.distro_name() | ||
self.num_of_iterations = conf.args.num_of_iterations | ||
self.kernel_image = conf.args.kernel_image | ||
self.initrd_image = conf.args.initrd_image | ||
|
@@ -132,7 +132,7 @@ def setUp(self): | |
self.os_level_secureboot = sb_utilities.check_os_level_secureboot_state() | ||
|
||
def get_kexec_load_cmd(self, load_opt=True, copy_cmdline=True, | ||
file_load=False, add_arg=None): | ||
syscall_load=False, file_load=False, add_arg=None): | ||
""" | ||
Generates a kexec command for loading a kernel image with various | ||
optional arguments. | ||
|
@@ -159,6 +159,9 @@ def get_kexec_load_cmd(self, load_opt=True, copy_cmdline=True, | |
if file_load: | ||
kexec_cmd = kexec_cmd + " -s" | ||
|
||
if syscall_load: | ||
kexec_cmd = "%s -c" % kexec_cmd | ||
|
||
if copy_cmdline: | ||
kexec_cmd = kexec_cmd + " --append=\"`cat /proc/cmdline`\"" | ||
|
||
|
@@ -350,10 +353,59 @@ def test_load_and_exec(self): | |
ret = self.load_kexec_kernel(kexec_load_cmd) | ||
self.assertTrue(ret, "Kexec load failed") | ||
|
||
kexec_exec_cmd = self.get_kexec_exec_command(exec_opt=True) | ||
ret = self.execute_kexec_cmd(kexec_exec_cmd, raw_pty_console=True) | ||
self.assertTrue(ret, "kexec exec failed: %s " % kexec_exec_cmd) | ||
|
||
def test_file_load_and_exec(self): | ||
""" | ||
Test kexec functionality by loading with kexec-file-syscall and exec | ||
into kexec kernel. | ||
|
||
First load the kexec kernel using -s, -l and --append(command line | ||
arguments of currently running kenrel form /proc/cmdline) option. | ||
Then exec into kexec kernel. | ||
|
||
Test passes if both the kexec load and the execution into the | ||
kexec kernel go fine; otherwise, it fails." | ||
""" | ||
|
||
kexec_load_cmd = self.get_kexec_load_cmd(file_load=True) | ||
ret = self.load_kexec_kernel(kexec_load_cmd) | ||
self.assertTrue(ret, "Kexec load failed") | ||
|
||
kexec_exec_cmd = self.get_kexec_exec_command(exec_opt=True) | ||
ret = self.execute_kexec_cmd(kexec_exec_cmd, raw_pty_console=True) | ||
self.assertTrue(ret, "kexec exec failed: " + kexec_exec_cmd) | ||
|
||
def test_syscall_load_and_exec(self): | ||
""" | ||
Test kexec functionality by loading with kexec-syscall and exec | ||
into kexec kernel. | ||
|
||
First load the kexec kernel using -c, -l and --append(command line | ||
arguments of currently running kenrel form /proc/cmdline) option. | ||
Then exec into kexec kernel. | ||
|
||
Test passes if both the kexec load and the execution into the | ||
kexec kernel go fine; otherwise, it fails." | ||
""" | ||
|
||
kexec_load_cmd = self.get_kexec_load_cmd(syscall_load=True) | ||
ret = self.load_kexec_kernel(kexec_load_cmd) | ||
if self.os_level_secureboot: | ||
self.assertFalse(ret, "Kexec load pass, with -c option") | ||
else: | ||
self.assertTrue(ret, "Kexec load failed, with -c option") | ||
|
||
kexec_exec_cmd = self.get_kexec_exec_command(exec_opt=True) | ||
if self.os_level_secureboot: | ||
ret = self.execute_kexec_cmd(kexec_exec_cmd) | ||
self.assertFalse(ret, "Kexec exec pass, with -c option") | ||
else: | ||
ret = self.execute_kexec_cmd(kexec_exec_cmd, raw_pty_console=True) | ||
self.assertTrue(ret, "Kexec exec failed, with -c option") | ||
|
||
def test_kexec_force(self): | ||
""" | ||
Test kexec load and exec into kexec kernel using --force (-f) option. | ||
|
@@ -397,6 +449,65 @@ def test_kexec_in_loop(self): | |
self.assertTrue(ret, "kexec failed, at iteration cnt: " + str(i)) | ||
log.info("Completed kexec iteration cnt %s." % str(i)) | ||
|
||
def test_kexec_unsigned_kernel(self): | ||
""" | ||
Tests the unsigned kernel when secure boot is enabled. | ||
|
||
From the signed kernel image, create unsigned kernel image. The same | ||
used for 'kexec' when secure boot is enabled. Expected failure while | ||
loading kexec. | ||
""" | ||
if self.os_level_secureboot: | ||
if self.op_test_util.check_kernel_signature(): | ||
if self.distro in ["unknown", "ubuntu"]: | ||
self.skipTest("Unsupported Linux distribution.") | ||
install_cmd = "wget" | ||
wget_bool = True | ||
res = self.cv_HOST.host_run_command('which %s' % install_cmd, | ||
timeout=120) | ||
if install_cmd not in res[0]: | ||
wget_bool = False | ||
if not wget_bool: | ||
if self.distro == "rhel": | ||
install_cmd = "yum install -y %s" % install_cmd | ||
elif self.distro == "sles": | ||
install_cmd = "zypper install -y %s" % install_cmd | ||
self.cv_HOST.host_run_command(install_cmd, timeout=120) | ||
try: | ||
url = "https://raw.githubusercontent.com/torvalds/linux/master/scripts/extract-module-sig.pl" | ||
self.cv_HOST.host_run_command("wget %s -P /tmp/" % url, timeout=120) | ||
except CommandFailed: | ||
self.skipTest("Can't get extract-module-sig.pl file.") | ||
module_sig_file = '/tmp/extract-module-sig.pl' | ||
self.cv_HOST.host_run_command("chmod u+x %s" % module_sig_file) | ||
self.kernel_image = "/boot/%s" % self.kernel_image | ||
cmd = "%s -0 %s > %s.unsigned" % \ | ||
(module_sig_file, self.kernel_image, self.kernel_image) | ||
out = self.cv_HOST.host_run_command(cmd) | ||
if '0' not in out[3]: | ||
self.skipTest("Can not create unsigned binary. Using- %s" | ||
% cmd) | ||
cmd = "kexec -s -l %s.unsigned" % self.kernel_image | ||
ret = self.execute_kexec_cmd(cmd) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. execute_kexec_cmd () will attempt to perform kexec reboot correct? If so is the test here to actually attempt to perform kexec with unsigned image or just an attempt to load an unsigned image. If its the later then can't we use load_kexec_kernel() instead? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This function creates the unsigned kernel image from the existing signed kernel image and tries to load when guest secure boot is enabled. |
||
if ret: | ||
self.fail("kexec loaded unsigned kernel when secure boot" | ||
" is enabled.") | ||
else: | ||
log.info("kexec loading with unsigned kernel failed. " | ||
"Which is expected.") | ||
else: | ||
self.skipTest("secure boot is disabled.") | ||
|
||
def tearDown(self): | ||
unsigned_kernel = "%s.unsigned" % self.kernel_image | ||
if 'boot' not in unsigned_kernel: | ||
unsigned_kernel = "/boot/%s" % unsigned_kernel | ||
if os.path.exists(unsigned_kernel): | ||
os.remove(unsigned_kernel) | ||
sign_file = "/tmp/extract-module-sig.pl" | ||
if os.path.exists(sign_file): | ||
os.remove(sign_file) | ||
|
||
|
||
def kexec_suite(): | ||
"""kexec test suite""" | ||
|
@@ -406,5 +517,8 @@ def kexec_suite(): | |
suite.addTest(OpTestKexec('test_load_and_exec')) | ||
suite.addTest(OpTestKexec('test_kexec_force')) | ||
suite.addTest(OpTestKexec('test_kexec_single_step')) | ||
suite.addTest(OpTestKexec('test_file_load_and_exec')) | ||
suite.addTest(OpTestKexec('test_syscall_load_and_exec')) | ||
suite.addTest(OpTestKexec('test_kexec_in_loop')) | ||
suite.addTest(OpTestKexec('test_kexec_unsigned_kernel')) | ||
return suite |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please use
%s
to concatenate stringThere was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please address this style issue and where ever it required