1

I am trying to run

String command = "su -c 'busybox ls /data'";
p = Runtime.getRuntime().exec(command);

in my app, but it seems like the syntax is somehow wrong. I have no problem running it from the terminal emulator app on the phone, though, so I just can't understand why it is not working when called from within my app.

Any help is deeply appreciated!

ObiWanKenobi
  • 322
  • 3
  • 12
  • Does your app have superuser privileges? App permissions are different from terminal permissions. – onit Feb 21 '12 at 19:08
  • My knowledge is limited, but I had understood that an app can't have superuser privileges, only spawn processes that do. Btw the Superuser app notifies me that root privileges have been granted if I run say "su -c id", and the output is correct.. What do you suggest? Thanks a lot – ObiWanKenobi Feb 22 '12 at 09:09
  • 1
    Not exactly sure what is wrong. However, there seems to be a lot of other topics on stackoverflow that might help you if you search. http://stackoverflow.com/questions/7216071/how-to-run-multiple-shell-commands-through-an-app-in-android. http://stackoverflow.com/questions/6896618/read-command-output-inside-su-process – onit Feb 22 '12 at 14:54
  • found the first link already, tbh I think I've crawled thru tons of topics XD I'm going to try what's suggested on the other one tho, seems promising.. I'll update asap – ObiWanKenobi Feb 22 '12 at 15:41
  • Works just fine! How can I thank you? :) – ObiWanKenobi Feb 22 '12 at 17:34
  • Just give an upvote to the answer that helped. Also, maybe post your solution and accept it, in case someone runs across the same problem. – onit Feb 22 '12 at 18:26

2 Answers2

3

SOLUTION FOUND! Thanks to the link suggested by onit here. See the code below: for superuser shell commands to work properly, you first need to create a superuser shell and assign it to a process, then write and read on it's input and output streams respectively.

Process p = Runtime.getRuntime().exec(new String[]{"su", "-c", "system/bin/sh"});
DataOutputStream stdin = new DataOutputStream(p.getOutputStream());
//from here all commands are executed with su permissions
stdin.writeBytes("ls /data\n"); // \n executes the command
InputStream stdout = p.getInputStream();
byte[] buffer = new byte[BUFF_LEN];
int read;
String out = new String();
//read method will wait forever if there is nothing in the stream
//so we need to read it in another way than while((read=stdout.read(buffer))>0)
while(true){
    read = stdout.read(buffer);
    out += new String(buffer, 0, read);
    if(read<BUFF_LEN){
        //we have read everything
        break;
    }
}
//do something with the output
Community
  • 1
  • 1
ObiWanKenobi
  • 322
  • 3
  • 12
  • it doesn't work! , and what is BUFF_LEN, please copy carefully. down vote – famfamfam Feb 28 '16 at 09:16
  • @famfamfam BUFF_LEN is a global variable that stores the length of the input buffer, no reason to downvote because you don't know things. Also this code was written years ago and the current Android API may do things very differently now. – ObiWanKenobi Mar 01 '16 at 16:19
0

Use the function below:

public void shellCommandRunAsRoot(String Command)
{
 try 
  {
     Process RunProcess= Runtime.getRuntime().exec("su");
     DataOutputStream os;
     os = new DataOutputStream(RunProcess.getOutputStream()); 

     os.writeBytes(cmds+"\n");
         os.writeBytes("exit+\n");
     os.flush();

  }
  catch (IOException e)
  {
     // Handle Exception 
  }    
}

Usage:

shellCommandRunAsRoot("pkill firefox");
Petr R.
  • 1,247
  • 2
  • 22
  • 30