var _gaq = _gaq || []; _gaq.push(['_setAccount', 'UA-333696-1']); _gaq.push(['_trackPageview']); _gaq.push(['_trackPageLoadTime']); (function() { var ga = document.createElement('script'); ga.type = 'text/javascript'; ga.async = true; ga.src = ('https:' == document.location.protocol ? 'https://ssl' : 'http://www') + '.google-analytics.com/ga.js'; var s = document.getElementsByTagName('script')[0]; s.parentNode.insertBefore(ga, s); })();
  • 2011年09月16日

    单台PC通过adb连接多个设备

    分类:

    adb只能支持16台设备并发运行,adb 服务器(adb fork-server server)扫描设备端口号范围为5554~5585,其中偶数端口用作控制台连接,基数号端口用作adb连接,相邻的两个基偶数端口组合起来控制一台设备。

     

    本地虚拟机adb的连接上限定义在宏ADB_LOCAL_TRANSPORT_MAXtranspoft_local.c):

    #define  ADB_LOCAL_TRANSPORT_MAX  16

    其连接端口为宏DEFAULT_ADB_LOCAL_TRANSPORT_PORTadb.h):

    #define DEFAULT_ADB_PORT 5037

    #define DEFAULT_ADB_LOCAL_TRANSPORT_PORT 5555

    transpoft_local.c中静态函数client_socket_threadfor循环创建ADB_LOCAL_TRANSPORT_MAX个连接(local_connect,它调用local_connect_arbitrary_ports,传入参数为相邻的端口号从(DEFAULT_ADB_LOCAL_TRANSPORT_PORT-1)开始;在函数local_connect_arbitrary_ports中调用socket_network_clientsocket_network_client.c)以判断是否能连接上给定IP的端口,如果能够连上则用register_socket_transport注册),端口号自DEFAULT_ADB_LOCAL_TRANSPORT_PORT起自增2client_socket_thread又被local_init调用。在adb.cadb_main函数对ADB HOST调用了local_init(DEFAULT_ADB_LOCAL_TRANSPORT_PORT)

     

    ddmlib这个库被许多Android工具所使用,比较有名的有ddmsEclipse ADT插件集成)、hierarchyviewer,它没有重用连接只有有指令就会创建一个新的adb连接很容易使得多台机器连接出不稳定的情况,亲见过hierarchyviewer在连接很多台手机时刷新很慢很慢、Eclipse在控制台输出许多连接被拒的信息。如Dalvik Debug Monitor ServiceDDMS)在单个PC上同时连接多个手机设备会超时,这主要源自文件AdbHelper.java中函数executeRemoteCommandmaxTimeToOutputResponse进行超时判断, 超时则抛出ShellCommandUnresponsiveException异常;在Device.javamaxTimeToOutputResponse被赋值为DdmPreferences.getTimeOut()DdmPreferences定义在文件DdmPreferences.java中,其函数getTimeOut返回sTimeOut,而sTimeOut被赋值为DEFAULT_TIMEOUT,在文件DdmPreferences.javaDEFAULT_TIMEOUT固定为5000毫秒。

     

    所以当16+设备连接到单台pc上时不要开Eclipseddmshierarchyviewer、豌豆荚和91手机助手 for Android,用线程池控制最大16个并发,每个并发代表一台设备,每个并发中一条指令执行完后顺序执行下条指令。除了这个并发,还有两个问题:1.adb devices列举的设备数不稳定,测试过程中出现有时多有时少,有时能列全连接的设备有时又不能,目前的处理是连续多次运行adb devices把每次列举出的设备都记录最后保留最大数字的那个,目前的多次是12次;2.指令连接设备的过程中会出现异常:a.设备offline b.设备对指令无响应,对b异常目前是设置了等待超时,超时后杀掉abd并记录该操作步骤失败设置该测试用例失败,远期会实现补救因为发现了现象:先执行adb kill-server,再adb devices两次之后会连接上原先断开的设备,这个重试的时机应该放在所有正常的设备自动化测试都做完之后进行,以免影响正常自动化测试的执行。目前采取的连接30台设备到一台PC的策略是:用Ubuntu Linux连接设备以避免安装驱动,但还是有部分设备还得在Windows下连接,如中兴 U880在Ubuntu下用命令usb devices无法显示设备号,华为C8500和Vodafone 845在Ubuntu下用命令usb devices显示设备号为“????????????”,但用命令连接设备时“adb –s ???????????? shell”无法连接上。

     

    关于adb的延伸阅读见浅析linux开发工具adb具体实现再次浅析adb shell,pc daemon和手机daemon三者之间的数据交互流程浅析adb创建流程。命令行驱动adbADBCommandAndroid运行shell或者一个可执行程序。线程池直接用Java自带的java.util.concurrent.Executors.newFixedThreadPool

     

    另外,Android 3.1+引入了USB Host,具体使用见Android Usb Host Tutorial - AdbTest

    分享到:

    历史上的今天:

    Robotium 使用 2011年09月16日
    显示IE9 状态栏 2010年09月16日