fuchsia: Remove run_tests.py functionality

This removes the rotted functionality for running tests on Fuchsia. It
had previously been broken by other platform changes. Other tools are
from previous SDKs being removed too; this approach is no longer going
to work.

The preferred way is to connect via SSH to the device, however, that
requires using the femu.sh from the SDK, which in turn requires `sudo`
to create a network device, so it won't directly work on bots anyway.

I started trying to update the to use femu.sh, fserve.sh, & fpublish.sh,
but that requires building a .far, which uses GN templates which
differ from the in-tree versions, and don't seem (?) to support
packaging resources into the package.

So, for now because it was confusing people (see linked bug) give up and
delete the code for the time being.

Bug: fuchsia:54031
Change-Id: Iac7af80094b150d11e71474cba4bd93eb8e80639
Reviewed-on: https://chromium-review.googlesource.com/c/crashpad/crashpad/+/2354160
Commit-Queue: Scott Graham <scottmg@chromium.org>
Reviewed-by: Mark Mentovai <mark@chromium.org>
This commit is contained in:
Scott Graham 2020-08-13 15:08:40 -07:00 committed by Commit Bot
parent 7547d0aa87
commit b472408135
3 changed files with 0 additions and 322 deletions

20
DEPS
View File

@ -81,26 +81,6 @@ deps = {
'condition': 'checkout_fuchsia and host_os == "linux"', 'condition': 'checkout_fuchsia and host_os == "linux"',
'dep_type': 'cipd' 'dep_type': 'cipd'
}, },
'crashpad/third_party/fuchsia/qemu/mac-amd64': {
'packages': [
{
'package': 'fuchsia/qemu/mac-amd64',
'version': 'latest'
},
],
'condition': 'checkout_fuchsia and host_os == "mac"',
'dep_type': 'cipd'
},
'crashpad/third_party/fuchsia/qemu/linux-amd64': {
'packages': [
{
'package': 'fuchsia/qemu/linux-amd64',
'version': 'latest'
},
],
'condition': 'checkout_fuchsia and host_os == "linux"',
'dep_type': 'cipd'
},
'crashpad/third_party/fuchsia/sdk/mac-amd64': { 'crashpad/third_party/fuchsia/sdk/mac-amd64': {
'packages': [ 'packages': [
{ {

View File

@ -1,145 +0,0 @@
#!/usr/bin/env python
# Copyright 2017 The Crashpad Authors. All rights reserved.
#
# 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.
"""Helper script to [re]start or stop a helper Fuchsia QEMU instance to be used
for running tests without a device.
"""
from __future__ import print_function
import getpass
import os
import random
import signal
import subprocess
import sys
import tempfile
import time
try:
from subprocess import DEVNULL
except ImportError:
DEVNULL = open(os.devnull, 'r+b')
CRASHPAD_ROOT = os.path.join(os.path.dirname(os.path.abspath(__file__)),
os.pardir)
def _Stop(pid_file):
if os.path.isfile(pid_file):
with open(pid_file, 'rb') as f:
pid = int(f.read().strip())
try:
os.kill(pid, signal.SIGTERM)
except:
print('Unable to kill pid %d, continuing' % pid, file=sys.stderr)
os.unlink(pid_file)
def _CheckForTun():
"""Check for networking. TODO(scottmg): Currently, this is Linux-specific.
"""
returncode = subprocess.call(
['tunctl', '-b', '-u',
getpass.getuser(), '-t', 'qemu'],
stdout=DEVNULL,
stderr=DEVNULL)
if returncode != 0:
print('To use QEMU with networking on Linux, configure TUN/TAP. See:',
file=sys.stderr)
print(
' https://fuchsia.googlesource.com/zircon/+/HEAD/docs/qemu.md#enabling-networking-under-qemu-x86_64-only',
file=sys.stderr)
return 2
return 0
def _Start(pid_file):
tun_result = _CheckForTun()
if tun_result != 0:
return tun_result
arch = 'mac-amd64' if sys.platform == 'darwin' else 'linux-amd64'
fuchsia_dir = os.path.join(CRASHPAD_ROOT, 'third_party', 'fuchsia')
qemu_path = os.path.join(fuchsia_dir, 'qemu', arch, 'bin',
'qemu-system-x86_64')
kernel_data_dir = os.path.join(fuchsia_dir, 'sdk', arch, 'target', 'x86_64')
kernel_path = os.path.join(kernel_data_dir, 'zircon.bin')
initrd_path = os.path.join(kernel_data_dir, 'bootdata.bin')
mac_tail = ':'.join('%02x' % random.randint(0, 255) for x in range(3))
instance_name = (
'crashpad_qemu_' +
''.join(chr(random.randint(ord('A'), ord('Z'))) for x in range(8)))
# These arguments are from the Fuchsia repo in zircon/scripts/run-zircon.
# yapf: disable
popen = subprocess.Popen([
qemu_path,
'-m', '2048',
'-nographic',
'-kernel', kernel_path,
'-initrd', initrd_path,
'-smp', '4',
'-serial', 'stdio',
'-monitor', 'none',
'-machine', 'q35',
'-cpu', 'host,migratable=no,+invtsc',
'-enable-kvm',
'-netdev', 'type=tap,ifname=qemu,script=no,downscript=no,id=net0',
'-device', 'e1000,netdev=net0,mac=52:54:00:' + mac_tail,
'-append', 'TERM=dumb zircon.nodename=' + instance_name,
],
stdin=DEVNULL,
stdout=DEVNULL,
stderr=DEVNULL)
# yapf: enable
with open(pid_file, 'wb') as f:
f.write('%d\n' % popen.pid)
for i in range(10):
netaddr_path = os.path.join(fuchsia_dir, 'sdk', arch, 'tools',
'netaddr')
if subprocess.call([netaddr_path, '--nowait', instance_name],
stdout=open(os.devnull),
stderr=open(os.devnull)) == 0:
break
time.sleep(.5)
else:
print('instance did not respond after start', file=sys.stderr)
return 1
return 0
def main(args):
if len(args) != 1 or args[0] not in ('start', 'stop'):
print('usage: run_fuchsia_qemu.py start|stop', file=sys.stderr)
return 1
command = args[0]
pid_file = os.path.join(tempfile.gettempdir(), 'crashpad_fuchsia_qemu_pid')
_Stop(pid_file)
if command == 'start':
return _Start(pid_file)
return 0
if __name__ == '__main__':
sys.exit(main(sys.argv[1:]))

View File

@ -313,144 +313,6 @@ def _RunOnAndroidTarget(binary_dir, test, android_device, extra_command_line):
_adb_shell(['rm', '-rf', device_temp_dir]) _adb_shell(['rm', '-rf', device_temp_dir])
def _GetFuchsiaSDKRoot():
arch = 'mac-amd64' if sys.platform == 'darwin' else 'linux-amd64'
return os.path.join(CRASHPAD_DIR, 'third_party', 'fuchsia', 'sdk', arch)
def _GenerateFuchsiaRuntimeDepsFiles(binary_dir, tests):
"""Ensures a <binary_dir>/<test>.runtime_deps file exists for each test."""
targets_file = os.path.join(binary_dir, 'targets.txt')
with open(targets_file, 'wb') as f:
f.write('//:' + '\n//:'.join(tests) + '\n')
gn_path = _FindGNFromBinaryDir(binary_dir)
subprocess.check_call([
gn_path, '--root=' + CRASHPAD_DIR, 'gen', binary_dir,
'--runtime-deps-list-file=' + targets_file
])
# Run again so that --runtime-deps-list-file isn't in the regen rule. See
# https://crbug.com/814816.
subprocess.check_call(
[gn_path, '--root=' + CRASHPAD_DIR, 'gen', binary_dir])
def _HandleOutputFromFuchsiaLogListener(process, done_message):
"""Pass through the output from |process| (which should be an instance of
Fuchsia's loglistener) until a special termination |done_message| is
encountered.
Also attempts to determine if any tests failed by inspecting the log output,
and returns False if there were failures.
"""
success = True
while True:
line = process.stdout.readline().rstrip()
if 'FAILED TEST' in line:
success = False
elif done_message in line and 'echo ' not in line:
break
print(line)
return success
def _RunOnFuchsiaTarget(binary_dir, test, device_name, extra_command_line):
"""Runs the given Fuchsia |test| executable on the given |device_name|. The
device must already be booted.
Copies the executable and its runtime dependencies as specified by GN to the
target in /tmp using `netcp`, runs the binary on the target, and logs output
back to stdout on this machine via `loglistener`.
"""
sdk_root = _GetFuchsiaSDKRoot()
# Run loglistener and filter the output to know when the test is done.
loglistener_process = subprocess.Popen(
[os.path.join(sdk_root, 'tools', 'loglistener'), device_name],
stdout=subprocess.PIPE,
stdin=open(os.devnull),
stderr=open(os.devnull))
runtime_deps_file = os.path.join(binary_dir, test + '.runtime_deps')
with open(runtime_deps_file, 'rb') as f:
runtime_deps = f.read().splitlines()
def netruncmd(*args):
"""Runs a list of commands on the target device. Each command is escaped
by using pipes.quote(), and then each command is chained by shell ';'.
"""
netruncmd_path = os.path.join(sdk_root, 'tools', 'netruncmd')
final_args = ' ; '.join(
' '.join(pipes.quote(x) for x in command) for command in args)
subprocess.check_call([netruncmd_path, device_name, final_args])
try:
unique_id = uuid.uuid4().hex
test_root = '/tmp/%s_%s' % (test, unique_id)
tmp_root = test_root + '/tmp'
staging_root = test_root + '/pkg'
# Make a staging directory tree on the target.
directories_to_create = [
tmp_root,
'%s/bin' % staging_root,
'%s/assets' % staging_root
]
netruncmd(['mkdir', '-p'] + directories_to_create)
def netcp(local_path):
"""Uses `netcp` to copy a file or directory to the device. Files
located inside the build dir are stored to /pkg/bin, otherwise to
/pkg/assets. .so files are stored somewhere completely different,
into /boot/lib (!). This is because the loader service does not yet
correctly handle the namespace in which the caller is being run, and
so can only load .so files from a couple hardcoded locations, the
only writable one of which is /boot/lib, so we copy all .so files
there. This bug is filed upstream as ZX-1619.
"""
in_binary_dir = local_path.startswith(binary_dir + '/')
if in_binary_dir:
if local_path.endswith('.so'):
target_path = os.path.join('/boot/lib',
local_path[len(binary_dir) + 1:])
else:
target_path = os.path.join(staging_root, 'bin',
local_path[len(binary_dir) + 1:])
else:
relative_path = os.path.relpath(local_path, CRASHPAD_DIR)
target_path = os.path.join(staging_root, 'assets',
relative_path)
netcp_path = os.path.join(sdk_root, 'tools', 'netcp')
subprocess.check_call(
[netcp_path, local_path, device_name + ':' + target_path],
stderr=open(os.devnull))
# Copy runtime deps into the staging tree.
for dep in runtime_deps:
local_path = os.path.normpath(os.path.join(binary_dir, dep))
if os.path.isdir(local_path):
for root, dirs, files in os.walk(local_path):
for f in files:
netcp(os.path.join(root, f))
else:
netcp(local_path)
done_message = 'TERMINATED: ' + unique_id
namespace_command = [
'namespace', '/pkg=' + staging_root, '/tmp=' + tmp_root,
'/svc=/svc', '--replace-child-argv0=/pkg/bin/' + test, '--',
staging_root + '/bin/' + test
] + extra_command_line
netruncmd(namespace_command, ['echo', done_message])
success = _HandleOutputFromFuchsiaLogListener(loglistener_process,
done_message)
if not success:
raise subprocess.CalledProcessError(1, test)
finally:
netruncmd(['rm', '-rf', test_root])
def _RunOnIOSTarget(binary_dir, test, is_xcuitest=False): def _RunOnIOSTarget(binary_dir, test, is_xcuitest=False):
"""Runs the given iOS |test| app on iPhone 8 with the default OS version.""" """Runs the given iOS |test| app on iPhone 8 with the default OS version."""
@ -544,7 +406,6 @@ def main(args):
target_os = _BinaryDirTargetOS(args.binary_dir) target_os = _BinaryDirTargetOS(args.binary_dir)
is_android = target_os == 'android' is_android = target_os == 'android'
is_fuchsia = target_os == 'fuchsia'
is_ios = target_os == 'ios' is_ios = target_os == 'ios'
tests = [ tests = [
@ -575,21 +436,6 @@ def main(args):
return 2 return 2
android_device = devices[0] android_device = devices[0]
print('Using autodetected Android device:', android_device) print('Using autodetected Android device:', android_device)
elif is_fuchsia:
zircon_nodename = os.environ.get('ZIRCON_NODENAME')
if not zircon_nodename:
netls = os.path.join(_GetFuchsiaSDKRoot(), 'tools', 'netls')
popen = subprocess.Popen([netls, '--nowait'],
stdout=subprocess.PIPE)
devices = popen.communicate()[0].splitlines()
if popen.returncode != 0 or len(devices) != 1:
print("Please set ZIRCON_NODENAME to your device's hostname",
file=sys.stderr)
return 2
zircon_nodename = devices[0].strip().split()[1]
print('Using autodetected Fuchsia device:', zircon_nodename)
_GenerateFuchsiaRuntimeDepsFiles(
args.binary_dir, [t for t in tests if not t.endswith('.py')])
elif is_ios: elif is_ios:
tests.append('ios_crash_xcuitests') tests.append('ios_crash_xcuitests')
elif IS_WINDOWS_HOST: elif IS_WINDOWS_HOST:
@ -618,9 +464,6 @@ def main(args):
if is_android: if is_android:
_RunOnAndroidTarget(args.binary_dir, test, android_device, _RunOnAndroidTarget(args.binary_dir, test, android_device,
extra_command_line) extra_command_line)
elif is_fuchsia:
_RunOnFuchsiaTarget(args.binary_dir, test, zircon_nodename,
extra_command_line)
elif is_ios: elif is_ios:
_RunOnIOSTarget(args.binary_dir, _RunOnIOSTarget(args.binary_dir,
test, test,