Skip to content
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

async API #569

Merged
merged 11 commits into from
Jul 28, 2022
Prev Previous commit
Next Next commit
target: Expose Target(max_async=50) parameter
Allow the user to set a maximum number of conrruent connections used to
dispatch non-blocking commands when using the async API.
  • Loading branch information
douglas-raillard-arm committed Jul 26, 2022
commit 6eb24a60d801e79726c71b38026a57bf2f9e3cb8
38 changes: 31 additions & 7 deletions devlib/target.py
Original file line number Diff line number Diff line change
@@ -306,9 +306,11 @@ def __init__(self,
load_default_modules=True,
shell_prompt=DEFAULT_SHELL_PROMPT,
conn_cls=None,
is_container=False
is_container=False,
max_async=50,
):
self._async_pool = None
self._async_pool_size = None
self._unused_conns = set()

self._is_rooted = None
@@ -352,7 +354,7 @@ def __init__(self,
self.modules = merge_lists(*module_lists, duplicates='first')
self._update_modules('early')
if connect:
self.connect()
self.connect(max_async=max_async)

def __getstate__(self):
# tls_property will recreate the underlying value automatically upon
@@ -363,12 +365,25 @@ def __getstate__(self):
for k, v in inspect.getmembers(self.__class__)
if isinstance(v, _BoundTLSProperty)
}
ignored.update((
'_async_pool',
'_unused_conns',
))
return {
k: v
for k, v in self.__dict__.items()
if k not in ignored
}

def __setstate__(self, dct):
self.__dict__ = dct
pool_size = self._async_pool_size
if pool_size is None:
self._async_pool = None
else:
self._async_pool = ThreadPoolExecutor(pool_size)
self._unused_conns = set()

# connection and initialization

@asyn.asyncf
@@ -433,6 +448,7 @@ def make_conn(_):
max_conns = len(conns)

self.logger.debug(f'Detected max number of async commands: {max_conns}')
self._async_pool_size = max_conns
self._async_pool = ThreadPoolExecutor(max_conns)

@asyn.asyncf
@@ -1547,6 +1563,7 @@ def __init__(self,
shell_prompt=DEFAULT_SHELL_PROMPT,
conn_cls=SshConnection,
is_container=False,
max_async=50,
):
super(LinuxTarget, self).__init__(connection_settings=connection_settings,
platform=platform,
@@ -1557,7 +1574,8 @@ def __init__(self,
load_default_modules=load_default_modules,
shell_prompt=shell_prompt,
conn_cls=conn_cls,
is_container=is_container)
is_container=is_container,
max_async=max_async)

def wait_boot_complete(self, timeout=10):
pass
@@ -1752,6 +1770,7 @@ def __init__(self,
conn_cls=AdbConnection,
package_data_directory="/data/data",
is_container=False,
max_async=50,
):
super(AndroidTarget, self).__init__(connection_settings=connection_settings,
platform=platform,
@@ -1762,7 +1781,8 @@ def __init__(self,
load_default_modules=load_default_modules,
shell_prompt=shell_prompt,
conn_cls=conn_cls,
is_container=is_container)
is_container=is_container,
max_async=max_async)
self.package_data_directory = package_data_directory
self._init_logcat_lock()

@@ -2823,6 +2843,7 @@ def __init__(self,
shell_prompt=DEFAULT_SHELL_PROMPT,
conn_cls=LocalConnection,
is_container=False,
max_async=50,
):
super(LocalLinuxTarget, self).__init__(connection_settings=connection_settings,
platform=platform,
@@ -2833,7 +2854,8 @@ def __init__(self,
load_default_modules=load_default_modules,
shell_prompt=shell_prompt,
conn_cls=conn_cls,
is_container=is_container)
is_container=is_container,
max_async=max_async)

def _resolve_paths(self):
if self.working_directory is None:
@@ -2906,7 +2928,8 @@ def __init__(self,
load_default_modules=True,
shell_prompt=DEFAULT_SHELL_PROMPT,
package_data_directory="/data/data",
is_container=False
is_container=False,
max_async=50,
):

self.supports_android = None
@@ -2932,7 +2955,8 @@ def __init__(self,
load_default_modules=load_default_modules,
shell_prompt=shell_prompt,
conn_cls=SshConnection,
is_container=is_container)
is_container=is_container,
max_async=max_async)

# We can't determine if the target supports android until connected to the linux host so
# create unconditionally.
13 changes: 8 additions & 5 deletions doc/target.rst
Original file line number Diff line number Diff line change
@@ -3,7 +3,7 @@
Target
======

.. class:: Target(connection_settings=None, platform=None, working_directory=None, executables_directory=None, connect=True, modules=None, load_default_modules=True, shell_prompt=DEFAULT_SHELL_PROMPT, conn_cls=None)
.. class:: Target(connection_settings=None, platform=None, working_directory=None, executables_directory=None, connect=True, modules=None, load_default_modules=True, shell_prompt=DEFAULT_SHELL_PROMPT, conn_cls=None, max_async=50)

:class:`~devlib.target.Target` is the primary interface to the remote
device. All interactions with the device are performed via a
@@ -76,6 +76,9 @@ Target
:param conn_cls: This is the type of connection that will be used to
communicate with the device.

:param max_async: Maximum number of opened connections to the target used to
issue non-blocking commands when using the async API.

.. attribute:: Target.core_names

This is a list containing names of CPU cores on the target, in the order in
@@ -606,7 +609,7 @@ Target
Linux Target
------------

.. class:: LinuxTarget(connection_settings=None, platform=None, working_directory=None, executables_directory=None, connect=True, modules=None, load_default_modules=True, shell_prompt=DEFAULT_SHELL_PROMPT, conn_cls=SshConnection, is_container=False,)
.. class:: LinuxTarget(connection_settings=None, platform=None, working_directory=None, executables_directory=None, connect=True, modules=None, load_default_modules=True, shell_prompt=DEFAULT_SHELL_PROMPT, conn_cls=SshConnection, is_container=False, max_async=50)

:class:`LinuxTarget` is a subclass of :class:`~devlib.target.Target`
with customisations specific to a device running linux.
@@ -615,7 +618,7 @@ Linux Target
Local Linux Target
------------------

.. class:: LocalLinuxTarget(connection_settings=None, platform=None, working_directory=None, executables_directory=None, connect=True, modules=None, load_default_modules=True, shell_prompt=DEFAULT_SHELL_PROMPT, conn_cls=SshConnection, is_container=False,)
.. class:: LocalLinuxTarget(connection_settings=None, platform=None, working_directory=None, executables_directory=None, connect=True, modules=None, load_default_modules=True, shell_prompt=DEFAULT_SHELL_PROMPT, conn_cls=SshConnection, is_container=False, max_async=50)

:class:`LocalLinuxTarget` is a subclass of
:class:`~devlib.target.LinuxTarget` with customisations specific to using
@@ -625,7 +628,7 @@ Local Linux Target
Android Target
---------------

.. class:: AndroidTarget(connection_settings=None, platform=None, working_directory=None, executables_directory=None, connect=True, modules=None, load_default_modules=True, shell_prompt=DEFAULT_SHELL_PROMPT, conn_cls=AdbConnection, package_data_directory="/data/data")
.. class:: AndroidTarget(connection_settings=None, platform=None, working_directory=None, executables_directory=None, connect=True, modules=None, load_default_modules=True, shell_prompt=DEFAULT_SHELL_PROMPT, conn_cls=AdbConnection, package_data_directory="/data/data", max_async=50)

:class:`AndroidTarget` is a subclass of :class:`~devlib.target.Target` with
additional features specific to a device running Android.
@@ -773,7 +776,7 @@ Android Target
ChromeOS Target
---------------

.. class:: ChromeOsTarget(connection_settings=None, platform=None, working_directory=None, executables_directory=None, android_working_directory=None, android_executables_directory=None, connect=True, modules=None, load_default_modules=True, shell_prompt=DEFAULT_SHELL_PROMPT, package_data_directory="/data/data")
.. class:: ChromeOsTarget(connection_settings=None, platform=None, working_directory=None, executables_directory=None, android_working_directory=None, android_executables_directory=None, connect=True, modules=None, load_default_modules=True, shell_prompt=DEFAULT_SHELL_PROMPT, package_data_directory="/data/data", max_async=50)

:class:`ChromeOsTarget` is a subclass of :class:`LinuxTarget` with
additional features specific to a device running ChromeOS for example,