Android не показывает вывода из считывателя входного потока и обрабатывает код возврата выхода 1

#java #android #kotlin #adb #adb-shell

Вопрос:

я пытаюсь запустить процесс и прочитать его данные из InputStreamReader, но это странным образом не удается.

Исполняемый файл — «ip-шоу ржания».

При попытке выполнить команду с подключенного устройства через оболочку adb команда выполняется нормально, а также правильно отображает данные.

Но при попытке выполнить его из кода kotlin он завершается с кодом выхода 1, а InputStreamReader также показывает пустые данные.

Вот как я это пытаюсь сделать :

 val p = Runtime.getRuntime().exec("ip neigh show") InputStreamReader(p!!.inputStream).forEachLine fori@{ line -gt;  val teDhenat = line.split("\s ".toRegex())  if (teDhenat[0] == ip) {  if (teDhenat.size lt; 4) {  return@fori  } else {  uGjet = true  macAddress = teDhenat[4]  return@fori  }  }  }  

Проблема, похоже, возникает в этой строке : val p = Runtime.getRuntime().exec("ip neigh show") но я не понимаю, почему.

Также пробовал, val p = Runtime.getRuntime().exec("/system/bin/ip neigh show") и это все то же самое.

Также я пробовал использовать ProcessBuilder() , и это тоже не работает.

SDK для компиляции и назначения составляет 31 Телефон Xiaomi под управлением Android 11 (SDK 30)

PS: Также я использую ту же логику для других исполняемых файлов, и они работают очень хорошо, как «пинг», «топ» и т. Д…

Ответ №1:

Начиная с Android 11 (SDK 30) :

Кроме того, непривилегированные приложения не могут получить доступ к MAC-адресу устройства; видны только сетевые интерфейсы с IP-адресом. Это влияет на методы getifaddr() и NetworkInterface.getHardwareAddress (), а также на отправку сообщений RTM_GETLINK Netlink.

Ниже приведен список способов, которыми это изменение влияет на приложения:

Функция NetworkInterface.getHardwareAddress() возвращает значение null для каждого интерфейса.

Приложения не могут использовать функцию bind() в сокетах NETLINK_ROUTE.

Команда ip не возвращает информацию об интерфейсах.

Приложения не могут отправлять сообщения RTM_GETLINK. Обратите внимание, что большинству разработчиков следует использовать API более высокого уровня ConnectivityManager, а не API более низкого уровня, такие как NetworkInterface, getifaddrs () или сокеты Netlink. Например, приложение, которому нужна актуальная информация о текущих маршрутах, может получить эту информацию, прослушивая изменения в сети с помощью ConnectivityManager.registerNetworkCallback() и вызывая связанные с сетью LinkProperties.getRoutes().