# Copyright 2018 The Chromium Authors. All rights reserved. # Use of this source code is governed by a BSD-style license that can be # found in the LICENSE file. import logging import os import platform import socket import subprocess import sys DIR_SOURCE_ROOT = os.path.abspath( os.path.join(os.path.dirname(__file__), os.pardir, os.pardir)) IMAGES_ROOT = os.path.join( DIR_SOURCE_ROOT, 'third_party', 'fuchsia-sdk', 'images') SDK_ROOT = os.path.join(DIR_SOURCE_ROOT, 'third_party', 'fuchsia-sdk', 'sdk') def EnsurePathExists(path): """Checks that the file |path| exists on the filesystem and returns the path if it does, raising an exception otherwise.""" if not os.path.exists(path): raise IOError('Missing file: ' + path) return path def GetHostOsFromPlatform(): host_platform = sys.platform if host_platform.startswith('linux'): return 'linux' elif host_platform.startswith('darwin'): return 'mac' raise Exception('Unsupported host platform: %s' % host_platform) def GetHostArchFromPlatform(): host_arch = platform.machine() if host_arch == 'x86_64': return 'x64' elif host_arch == 'aarch64': return 'arm64' raise Exception('Unsupported host architecture: %s' % host_arch) def GetHostToolPathFromPlatform(tool): host_arch = platform.machine() return os.path.join(SDK_ROOT, 'tools', GetHostArchFromPlatform(), tool) def GetEmuRootForPlatform(emulator): return os.path.join( DIR_SOURCE_ROOT, 'third_party', '{0}-{1}-{2}'.format( emulator, GetHostOsFromPlatform(), GetHostArchFromPlatform())) def ConnectPortForwardingTask(target, local_port, remote_port = 0): """Establishes a port forwarding SSH task to a localhost TCP endpoint hosted at port |local_port|. Blocks until port forwarding is established. Returns the remote port number.""" forwarding_flags = ['-O', 'forward', # Send SSH mux control signal. '-R', '%d:localhost:%d' % (remote_port, local_port), '-v', # Get forwarded port info from stderr. '-NT'] # Don't execute command; don't allocate terminal. if remote_port != 0: # Forward to a known remote port. task = target.RunCommand([], ssh_args=forwarding_flags) if task.returncode != 0: raise Exception('Could not establish a port forwarding connection.') return task = target.RunCommandPiped([], ssh_args=forwarding_flags, stdout=subprocess.PIPE, stderr=open('/dev/null')) output = task.stdout.readlines() task.wait() if task.returncode != 0: raise Exception('Got an error code when requesting port forwarding: %d' % task.returncode) parsed_port = int(output[0].strip()) logging.debug('Port forwarding established (local=%d, device=%d)' % (local_port, parsed_port)) return parsed_port def GetAvailableTcpPort(): """Finds a (probably) open port by opening and closing a listen socket.""" sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) sock.bind(("", 0)) port = sock.getsockname()[1] sock.close() return port