Use a buffer named "devlib" instead of using the top-level default
buffer. That will improve interop with other tools trying to collect a
trace at the same time as devlib.
Replaced all references to devlib.Target with devlib.LinuxTarget to correctly
utilise appropriate interface.
Also added relevant functionality to corectly
create the root directories of the CGroup hierarchies, handling any error that
occurs in that case.
The value for `max_async` when creating a target was being ignored
if a connection was not established as part of the __init__ method.
Save this value for use via `connect` if called directly.
Remove the "future" dependency as devlib does not support Python 2
anymore.
Also remove the "from __future__ import division" as this is the default
in Python 3.
* Remove check_output_lock as the issue has been fixed in Python 3.4
* Use Popen process as a context manager. Technically,
Popen.communicate() already achieves those but the context manager
will ensure this is done even if an exception happens at any point.
adb_root() restarts the server, leading to aborting commands ran by
other connections and also apparently leading to command hanging in some
situations.
Therefore, only allow adb_root() when there is only one connection
active. That should not be a big issue as this is typically called by
the first connection ever made when the Target is created.
Add a memoize_method decorator that works for async methods. It will not
leak memory since the memoization cache is held in the instance
__dict__, and it does not rely on hacks to hash unhashable data.
use_governor() was trying to set concurrently both per-cpu and global tunables for
each governor, which lead to a write conflict.
Split the work into the per-governor global tunables and the per-cpu
tunables, and do all that in concurrently. Each task is therefore
responsible of a distinct set of files and all is well.
Also remove @memoized on async functions. It will be reintroduced in a
later commit when there is a safe alternative for async functions.
The conncetion returned by Target.get_connection() does not have its
.busybox attribute initialized. This is expected for the first
connection, but connections created for new threads should have busybox
set.
Currently the cgroups module will pull all available controllers from
/proc/cgroups and then try to mount them, including the disabled ones.
This will result in the entire mount failing.
Lines in /proc/cgroups ending in 0 correspond to disabled controllers.
Filtering those out solves the issue.
With recent versions of adb, adb root can fail if the
daemon is already running as root.
Check the raised error message for this case and avoid
raising an error in this scenario.
When no entry has been recorded by the collector, return an empty string
rather than returning the full dmesg log.
Also fix get_data() that would fail try to add None + '\n' if dmesg_out
property returns None.
Both move_all_tasks_to() and move_tasks() take a list of grep patterns
to exclude.
It turned out that move_all_tasks_to() was calling move_tasks() with a
string instead of a list, leading to broken quoting.
Fix that by passing the pattern list to move_tasks() and let
move_tasks() add the "-e" option in front of it. Also add a
DeprecationWarning in move_tasks() if someone passes a string instead of
an iterable of strings.
Rather than systematically clearing the buffer on reset(), record the
timestamp of the last entry and use it to filter-out old entries in
DmesgCollector.entries property.
This also allows detecting if the ring buffer has ran out of memory, or
if something has cleared the buffer while collecting, leading to missing
entries.
Currently, it is not possible to push/pull files with a relative path when
the destination doesn't exist. This is due to the basename resolution. Fix
this behaviour.
Change default FtraceCollector(tracing_path=...) to None, and
auto-detect mount point when None is given.
Also expose an FtraceCollector.find_tracing_path() method so that user
code can also access this path without having to instantiate an
FtraceCollector.
Check that the function exists and then run it, to avoid endless
copy-pasting.
Also call it with "$@", which will achieve proper CLI params forwarding
unlike "$*" which will not.
The command used to detect the presence of a filepath can return
the wrong value if only accessible by the superuser.
Pass the `as_root` parameter to the detection function to ensure
that files that are to be pulled with elevated permissions are
also queried with elevated permission.
Some Android devices do not have 'su'. But if they are already
rooted, there's no reason to fail. Circumvent this scenario by never
using 'su' for device already rooted.
Use target.list_directory(as_root=target.is_rooted) instead of doing it
as a normal user for paths in /sys/kernel/debug. Since this
list_directory() call can be used with multiple path, we do not force
as_root=True but we increase the chance of it working.
__getstate__ is also used by the copy module, but allows pickling the
class as well. This is useful when using the multiprocessing API, which
requires pickling the Target object to send it to the new process.