Browse Source
ubuntu.aarch64 provides a script to create an Ubuntu 18.04 VM. Another new file is also added aarch64vm.py, which is a module with common methods used by aarch64 VMs, such as how to create the flash images. Signed-off-by: Robert Foley <robert.foley@linaro.org> Reviewed-by: Peter Puhov <peter.puhov@linaro.org> Signed-off-by: Alex Bennée <alex.bennee@linaro.org> Message-Id: <20200601211421.1277-6-robert.foley@linaro.org> Message-Id: <20200701135652.1366-10-alex.bennee@linaro.org>pull/107/head
committed by
Alex Bennée
5 changed files with 217 additions and 0 deletions
@ -0,0 +1,106 @@ |
|||
#!/usr/bin/env python3 |
|||
# |
|||
# VM testing aarch64 library |
|||
# |
|||
# Copyright 2020 Linaro |
|||
# |
|||
# Authors: |
|||
# Robert Foley <robert.foley@linaro.org> |
|||
# |
|||
# This code is licensed under the GPL version 2 or later. See |
|||
# the COPYING file in the top-level directory. |
|||
# |
|||
import os |
|||
import sys |
|||
import subprocess |
|||
import basevm |
|||
from qemu.accel import kvm_available |
|||
|
|||
# This is the config needed for current version of QEMU. |
|||
# This works for both kvm and tcg. |
|||
CURRENT_CONFIG = { |
|||
'cpu' : "max", |
|||
'machine' : "virt,gic-version=max", |
|||
} |
|||
|
|||
# The minimum minor version of QEMU we will support with aarch64 VMs is 3. |
|||
# QEMU versions less than 3 have various issues running these VMs. |
|||
QEMU_AARCH64_MIN_VERSION = 3 |
|||
|
|||
# The DEFAULT_CONFIG will default to a version of |
|||
# parameters that works for backwards compatibility. |
|||
DEFAULT_CONFIG = {'kvm' : {'cpu' : "host", |
|||
'machine' : "virt,gic-version=host"}, |
|||
'tcg' : {'cpu' : "cortex-a57", |
|||
'machine' : "virt"}, |
|||
} |
|||
|
|||
def get_config_defaults(vmcls, default_config): |
|||
"""Fetch the configuration defaults for this VM, |
|||
taking into consideration the defaults for |
|||
aarch64 first, followed by the defaults for this VM.""" |
|||
config = default_config |
|||
config.update(aarch_get_config_defaults(vmcls)) |
|||
return config |
|||
|
|||
def aarch_get_config_defaults(vmcls): |
|||
"""Set the defaults for current version of QEMU.""" |
|||
config = CURRENT_CONFIG |
|||
args, argv = basevm.parse_args(vmcls) |
|||
qemu_path = basevm.get_qemu_path(vmcls.arch, args.build_path) |
|||
qemu_version = basevm.get_qemu_version(qemu_path) |
|||
if qemu_version < QEMU_AARCH64_MIN_VERSION: |
|||
error = "\nThis major version of QEMU {} is to old for aarch64 VMs.\n"\ |
|||
"The major version must be at least {}.\n"\ |
|||
"To continue with the current build of QEMU, "\ |
|||
"please restart with QEMU_LOCAL=1 .\n" |
|||
print(error.format(qemu_version, QEMU_AARCH64_MIN_VERSION)) |
|||
exit(1) |
|||
if qemu_version == QEMU_AARCH64_MIN_VERSION: |
|||
# We have an older version of QEMU, |
|||
# set the config values for backwards compatibility. |
|||
if kvm_available('aarch64'): |
|||
config.update(DEFAULT_CONFIG['kvm']) |
|||
else: |
|||
config.update(DEFAULT_CONFIG['tcg']) |
|||
return config |
|||
|
|||
def create_flash_images(flash_dir="./", efi_img=""): |
|||
"""Creates the appropriate pflash files |
|||
for an aarch64 VM.""" |
|||
flash0_path = get_flash_path(flash_dir, "flash0") |
|||
flash1_path = get_flash_path(flash_dir, "flash1") |
|||
fd_null = open(os.devnull, 'w') |
|||
subprocess.check_call(["dd", "if=/dev/zero", "of={}".format(flash0_path), |
|||
"bs=1M", "count=64"], |
|||
stdout=fd_null, stderr=subprocess.STDOUT) |
|||
# A reliable way to get the QEMU EFI image is via an installed package or |
|||
# via the bios included with qemu. |
|||
if not os.path.exists(efi_img): |
|||
sys.stderr.write("*** efi argument is invalid ({})\n".format(efi_img)) |
|||
sys.stderr.write("*** please check --efi-aarch64 argument or "\ |
|||
"install qemu-efi-aarch64 package\n") |
|||
exit(3) |
|||
subprocess.check_call(["dd", "if={}".format(efi_img), |
|||
"of={}".format(flash0_path), |
|||
"conv=notrunc"], |
|||
stdout=fd_null, stderr=subprocess.STDOUT) |
|||
subprocess.check_call(["dd", "if=/dev/zero", |
|||
"of={}".format(flash1_path), |
|||
"bs=1M", "count=64"], |
|||
stdout=fd_null, stderr=subprocess.STDOUT) |
|||
fd_null.close() |
|||
|
|||
def get_pflash_args(flash_dir="./"): |
|||
"""Returns a string that can be used to |
|||
boot qemu using the appropriate pflash files |
|||
for aarch64.""" |
|||
flash0_path = get_flash_path(flash_dir, "flash0") |
|||
flash1_path = get_flash_path(flash_dir, "flash1") |
|||
pflash_args_str = "-drive file={},format=raw,if=pflash "\ |
|||
"-drive file={},format=raw,if=pflash" |
|||
pflash_args = pflash_args_str.format(flash0_path, flash1_path) |
|||
return pflash_args.split(" ") |
|||
|
|||
def get_flash_path(flash_dir, name): |
|||
return os.path.join(flash_dir, "{}.img".format(name)) |
|||
@ -0,0 +1,68 @@ |
|||
#!/usr/bin/env python3 |
|||
# |
|||
# Ubuntu aarch64 image |
|||
# |
|||
# Copyright 2020 Linaro |
|||
# |
|||
# Authors: |
|||
# Robert Foley <robert.foley@linaro.org> |
|||
# Originally based on ubuntu.i386 Fam Zheng <famz@redhat.com> |
|||
# |
|||
# This code is licensed under the GPL version 2 or later. See |
|||
# the COPYING file in the top-level directory. |
|||
# |
|||
|
|||
import sys |
|||
import basevm |
|||
import aarch64vm |
|||
import ubuntuvm |
|||
|
|||
DEFAULT_CONFIG = { |
|||
'cpu' : "cortex-a57", |
|||
'machine' : "virt,gic-version=3", |
|||
'install_cmds' : "apt-get update,"\ |
|||
"apt-get build-dep -y --arch-only qemu,"\ |
|||
"apt-get install -y libfdt-dev pkg-config language-pack-en", |
|||
# We increase beyond the default time since during boot |
|||
# it can take some time (many seconds) to log into the VM |
|||
# especially using softmmu. |
|||
'ssh_timeout' : 60, |
|||
} |
|||
|
|||
class UbuntuAarch64VM(ubuntuvm.UbuntuVM): |
|||
name = "ubuntu.aarch64" |
|||
arch = "aarch64" |
|||
image_name = "ubuntu-18.04-server-cloudimg-arm64.img" |
|||
image_link = "https://cloud-images.ubuntu.com/releases/18.04/release/" + image_name |
|||
image_sha256="0fdcba761965735a8a903d8b88df8e47f156f48715c00508e4315c506d7d3cb1" |
|||
BUILD_SCRIPT = """ |
|||
set -e; |
|||
cd $(mktemp -d); |
|||
sudo chmod a+r /dev/vdb; |
|||
tar --checkpoint=.10 -xf /dev/vdb; |
|||
./configure {configure_opts}; |
|||
make --output-sync {target} -j{jobs} {verbose}; |
|||
""" |
|||
def boot(self, img, extra_args=None): |
|||
aarch64vm.create_flash_images(self._tmpdir, self._efi_aarch64) |
|||
default_args = aarch64vm.get_pflash_args(self._tmpdir) |
|||
if extra_args: |
|||
extra_args.extend(default_args) |
|||
else: |
|||
extra_args = default_args |
|||
# We always add these performance tweaks |
|||
# because without them, we boot so slowly that we |
|||
# can time out finding the boot efi device. |
|||
if '-smp' not in extra_args and \ |
|||
'-smp' not in self._config['extra_args'] and \ |
|||
'-smp' not in self._args: |
|||
# Only add if not already there to give caller option to change it. |
|||
extra_args.extend(["-smp", "8"]) |
|||
|
|||
# We have overridden boot() since aarch64 has additional parameters. |
|||
# Call down to the base class method. |
|||
super(UbuntuAarch64VM, self).boot(img, extra_args=extra_args) |
|||
|
|||
if __name__ == "__main__": |
|||
defaults = aarch64vm.get_config_defaults(UbuntuAarch64VM, DEFAULT_CONFIG) |
|||
sys.exit(basevm.main(UbuntuAarch64VM, defaults)) |
|||
Loading…
Reference in new issue