Monday, December 24, 2012

The Hows and Whys of Rooting the Droid Razr

There's no standard way of getting root access to an Android device.  I currently want to root a Droid Razr running 4.0.4 and I found some instructions for how to do so here.  The rooting process is nice in that it doesn't require running any special code that some Internet rando developed, but the instructions don't actually say what is going on.

Since I can be a little paranoid, I'm not about to run whatever commands someone on the internet tells me to.  First, I want to figure out what those commands are doing.

(Note that while the instructions work for the most part, they originally said to put the su binary in /system/xbin, I found that it actually needed to be placed in /system/bin and I've changed these instructions accordingly).

So let's get in to it, going step by step through the commands outlined in the instructions.

Hook your phone up to your computer in debugging mode and connect to it with adb.

adb shell

# cd /sdcard
# cp su /data/local/12m/
# cp debugfs /data/local/12m/

These commands are copying the su and debugfs programs from your sdcard to a local directory on your phone where they can be used later.  su, as I'm sure you all know, is a program that allows a user to elevate their privilege level to root under the right conditions.  debugfs isn't quite as common.  It allows the user to easily examine and modify characteristics of the filesystem.  In this case it will allow us to change permissions as a part of the rooting process.  It isn't clear to me where the best place to get these programs is, so I'll leave that to you.

# cd /data/local/12m
# chmod 755 su
# chmod 755 debugfs

Here we're making sure any user can read and execute su and debugfs. Pretty standard stuff.

# mv batch batch.bak
# ln -s /dev/block/mmcblk1p20 batch

This is a little strange. Why are we moving 'batch' and replacing it with a link to some random device?

We'll start with looking at what exactly /dev/block/mmcblk1p20 is.

cat /proc/partitions
major minor  #blocks  name      alias

   7        1      17703 loop1
 179        0   15552512 mmcblk1
 179        1        128 mmcblk1p1
 179        2        512 mmcblk1p2
 179        3        512 mmcblk1p3
 179        4          1 mmcblk1p4
 179        5        512 mmcblk1p5
 179        6        512 mmcblk1p6
 179        7       4096 mmcblk1p7      pds
 179        8        512 mmcblk1p8      utags
 179        9       1024 mmcblk1p9
 179       10       2048 mmcblk1p10
 179       11        512 mmcblk1p11
 179       12        512 mmcblk1p12
 179       13       4096 mmcblk1p13
 179       14       8192 mmcblk1p14     boot
 179       15       9216 mmcblk1p15     recovery
 179       16     217088 mmcblk1p16     cdrom
 179       17        512 mmcblk1p17     misc
 179       18        512 mmcblk1p18     cid
 179       19       4096 mmcblk1p19     kpanic
 179       20     655360 mmcblk1p20     system
 179       21    1048576 mmcblk1p21     cache
 179       22     622592 mmcblk1p22     preinstall
 179       23    1364992 mmcblk1p23     webtop
 179       24    3203072 mmcblk1p24     userdata
 179       25    8401792 mmcblk1p25     emstorage
 179       26        128 mmcblk1p26
 179       64       1024 mmcblk1boot1
 179       32       1024 mmcblk1boot0
 179       96   15558144 mmcblk0
 179       97   15554048 mmcblk0p1
 254        1      17703 dm-1

We can see that mmcblk1p20 is an alias for 'system'.  Now, looking at the 'mount' output, we see that /dev/block/system is mounted to /system.

/dev/block/system /system ext3 ro,noatime,nodiratime,barrier=1,data=ordered 0 0

So we're making /data/local/12m/batch point to /system instead of whatever it pointed to before.  Why would we do that?

Now let's take a closer look at that the /data/local/12m directory:

 ls -l /data/local/12m
drwxrwx--x mot_tcmd shell             2011-10-20 22:48 batch

We can see that here the shell group has read, write and execute access.

According to djrbliss:
Since the contents of /data/local are group “shell” and group-writable, we can modify the contents of this directory using ADB. By logging into the device and replacing one of the sub-directories listed here with a symbolic link, then when the device reboots it will change the ownership of the symlink target to group “shell”. This can be used to edit property files to manipulate the behavior of ADB to achieve root.
So, by creating this symbolic link and rebooting the device, we're changing the permissions of /system to allow the shell group to have read and write access, which is exactly what we need to get root.

# exit
adb reboot

adb wait-for-device shell
Wait android shell:

Now that we've made those changes we reboot to get them to take effect.

# cd /data/local/12m
# rm batch
# mv batch.bak batch

This puts the batch directory back the way we found it; though /system will still have the updated permissions.

# /data/local/12m/debugfs -w /dev/block/mmcblk1p20
This opens the mmcblk1p20 device (that contains /system) in readwrite mode within debugfs.

Now, at the debugfs prompt:

debugfs: # cd bin
debugfs: # write /data/local/12m/su su
debugfs: # set_inode_field su mode 0104755
debugfs: # set_inode_field su uid 0
debugfs: # set_inode_field su gid 0
debugfs: # quit

This puts the su binary in /system/bin, sets to allow anyone to execute it, has the root user own it puts it in the root group.

# cd /data/local/12m
# rm su
# rm debugfs
# exit
adb reboot

This removes the temporary files we put in /data/local/12m and then reboots.  When the system comes back up, we should have root.

The rest of the instructions tell you how to install superuser, make sure you have root and how to keep it.  That's all pretty standard stuff, so I won't go in to it here.  Have fun.