Получение вывода из команд busybox в приложении для Android

На всю жизнь я не могу заставить свое приложение получать ответ от процесса, вызывающего busybox из оболочки su.

Я пробовал три разных метода, а также пробовал комбинацию из трех, чтобы заставить его работать, но я никогда не могу получить результат ни от чего, используя busybox, только остальные команды.

Чтобы быть более конкретным, я могу заставить его возвращать такие команды, как «ls /data» и «cat такой-то и такой-то.файл», но все, что начинается с «busybox» (т.

Этот метод оказался наиболее близким для меня, этот код работает с "ls /data", но не с "busybox free"

Этот метод запускал команду (по большей части) и возвращал пустой строка вместо бесконечного цикла из входного потока.

        Process p;
        try {
            p = Runtime.getRuntime().exec(new String[]{"su", "-c", "/system/bin/sh"});
        DataOutputStream stdin = new DataOutputStream(p.getOutputStream());
        stdin.writeBytes("ls /data\n");
        DataInputStream stdout = new DataInputStream(p.getInputStream());
        byte[] buffer = new byte[4096];
        int read = 0;
        String out = new String();
        while(true){
            read = stdout.read(buffer);
            out += new String(buffer, 0, read);
            if(read<4096){
                break;
            }
        }
        Toast.makeText(getApplicationContext(), out, Toast.LENGTH_SHORT).show();
        } catch (IOException e) {
            e.printStackTrace();
        }

В нижней части всплывающего уведомления отображается все, начиная с «ls /data», но при изменении на что-либо для busybox оно становится пустым или нулевым.

Я пробовал и то, и другое, но ни одно из них не сработало. (Я передал им процесс после запуска команды.)

И то, и другое всегда приводило к зависанию приложения сразу после нажатия кнопки методов.

String termReader(Process process){
    BufferedReader reader = new BufferedReader(
        new InputStreamReader(process.getInputStream()));   
    try {

    int i;
    char[] buffer = new char[4096];
    StringBuffer output = new StringBuffer();
    while ((i = reader.read(buffer)) > 0) output.append(buffer, 0, i);
    reader.close();
    return output.toString();
    } catch (IOException e) {
    e.printStackTrace();
    return e.getMessage();
    }
}



String processReader(Process process){
    InputStream stdout = process.getInputStream();
    byte[] buffer = new byte[1024];
    int read;
    String out = new String();
    while(true){
        try {
            read = stdout.read(buffer);
        out += new String(buffer, 0, read);
        if(read<1024){
            break;
        }
        } catch (IOException e) {
            e.printStackTrace();

        }
    }
    return out;
}

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

Отредактировано с кодом, предложенным ниже, гм, ниже :D Я немного изменил его, чтобы его можно было запускать одним щелчком мыши для облегчения устранения неполадок и тестирования.

Это также зависает, когда он пытается прочитать входной поток, и если я вызываю stdin.writeBytes("exit\n") перед попыткой прочитать поток, это дает мне пустой ответ от закрытия терминала, если я вызываю его после , он бесконечно зацикливается.

        void Run() {
                String command = "busybox traceroute\n";



        StringBuffer theRun = null;
        try {
            Process process = Runtime.getRuntime().exec("su");
            DataOutputStream stdin = new DataOutputStream(process.getOutputStream());
            stdin.writeBytes(command);
            BufferedReader reader = new BufferedReader(
                    new InputStreamReader(process.getInputStream()));
            int read;
            char[] buffer = new char[4096];
            StringBuffer output = new StringBuffer();
            while ((read = reader.read(buffer)) > 0) {
                theRun = output.append(buffer, 0, read);
            }
            reader.close();
            process.waitFor();

        } catch (IOException e) {
            throw new RuntimeException(e);
        } catch (InterruptedException e) {
            throw new RuntimeException(e);
        }
        Toast.makeText(getApplicationContext(), theRun, Toast.LENGTH_SHORT).show();
    }

Похоже, что он пропускает первую строку (информационная строка busybox, которую вы получаете каждый раз, когда запускаете команду) и не перехватывает остальные данные. Я перепробовал все возможные варианты, чтобы заставить это работать правильно :/

Если у кого-нибудь есть понимание этого, я был бы очень признателен :)

6
задан z3nful 9 April 2012 в 04:51
поделиться