enable `su` in adb command line

This commit is contained in:
HappyZ 2018-11-18 04:38:34 -06:00
parent 15abfc1827
commit c02f389336
8 changed files with 214 additions and 38 deletions

View File

@ -0,0 +1,17 @@
#!/system/bin/sh
# If you're implementing this in a custom kernel/firmware,
# I suggest you use a different script name, and add a service
# to launch it from init.rc
# Launches SuperSU in daemon mode only on Android 4.3+.
# Nothing will happen on 4.2.x or older, unless SELinux+Enforcing.
# If you want to force loading the daemon, use "--daemon" instead
/system/xbin/daemonsu --auto-daemon &
# Some apps like to run stuff from this script as well, that will
# obviously break root - in your code, just search this file
# for "install-recovery-2.sh", and if present, write there instead.
/system/etc/install-recovery-2.sh

Binary file not shown.

Binary file not shown.

BIN
python_api/assets/su Normal file

Binary file not shown.

BIN
python_api/assets/supolicy Normal file

Binary file not shown.

View File

@ -123,6 +123,50 @@ class DPT():
cmd = "[[ -d {} ]] && echo 'YESS' || echo 'NONO'".format(folderp)
return 'YESS' in self.diagnosis_write(cmd)
def diagnosis_set_perm(self, fp, owner='0.0', perm='0777'):
'''
set permission of a file
'''
self.info_print('Set {0}: owner={1} perm={2}'.format(fp, owner, perm))
self.diagnosis_write('chown {0} {1}'.format(owner, fp))
self.diagnosis_write('chmod {0} {1}'.format(perm, fp))
def diagnosis_mkdir(self, folder):
'''
mkdir -p folder
'''
if not self.diagnosis_isfolder(folder):
self.info_print("{} already exist".format(folder))
return True
if not self.diagnosis_write('mkdir -p {}'.format(folder)):
self.err_print('Failed to create folder {}'.format(folder))
return False
return True
def diagnosis_ln(self, srcf, destf):
'''
ln -s srcfolder, targetfolder
'''
if not self.diagnosis_write('ln -s {0} {1}'.format(srcf, destf)):
self.err_print('Failed to link file')
return False
return True
def diagnosis_mount_system(self):
'''
mount system partition to mountpoint
'''
mountpoint = '/mnt/Lucifer'
if not self.diagnosis_mkdir(folder):
return ""
# umount first just in case
self.diagnosis_write('umount {}'.format(mountpoint))
# mount system partition (/dev/mmcblk0p9)
self.diagnosis_write('mount /dev/mmcblk0p9 {}'.format(mountpoint))
if self.diagnosis_isfolder('{}/xbin'.format(mountpoint)):
return mountpoint
return ""
def diagnosis_backup_boot(self):
'''
back up boot partition to /tmp/ folder
@ -149,8 +193,9 @@ class DPT():
'''
write cmd and read feedbacks
'''
resp = ''
if self.serial is None:
return ""
return resp
if 'less ' in cmd:
self.err_print('do not support less/more')
try:
@ -159,7 +204,10 @@ class DPT():
self.serial.write(cmd.encode() + b'\n')
# change timeout to (nearly) blocking first to read
self.serial.timeout = timeout
resp = self.serial.read_until(b'# ')
tmpresp = b''
while not '@FPX-' in resp:
tmpresp = self.serial.read_until(b'# ')
resp += tmpresp.decode("utf-8").replace("\r\r\n", '')
# change back the original timeout
self.serial.timeout = self.serialReadTimeout
except serial.SerialTimeoutException as e:
@ -181,10 +229,8 @@ class DPT():
except BaseException as e:
self.err_print(str(e))
return ""
if echo:
resp = resp.decode("utf-8").replace("\r\r\n", '')
else:
resp = resp.decode("utf-8").replace("\r\r\n", '').replace(cmd, '')
if not echo:
resp = resp.replace(cmd, '')
self.dbg_print("len of {}; dbg: ".format(len(resp), resp.splitlines()))
return resp

View File

@ -7,10 +7,49 @@ import subprocess
# import traceback
def validate_required_files(dpt):
'''
Web Interface API Related
'''
def update_firmware(dpt):
'''
update firmware interface
'''
dpt.info_print(
'Please make sure you have charged your battery before this action.')
try:
resp = input('>>> Please enter the pkg file path: ')
if not os.path.isfile(resp):
dpt.err_print('File `{}` does not exist!'.format(resp))
return False
resp2 = input('>>> Pleae confirm {} is the pkg file to use [yes/no]: ')
if resp2 == 'yes':
if not dpt.update_firmware(open(resp, 'rb')):
dpt.err_print('Failed to upload pkg {}'.format(resp))
return False
dpt.info_print('Success!')
return True
elif resp == 'no':
dpt.info_print('Okay!')
else:
dpt.err_print('Unrecognized response: {}'.format(resp))
except BaseException as e:
dpt.err_print(str(e))
return False
def validate_required_files(dpt, purpose='diagnosis'):
if purpose == 'su-binary':
requiredFiles = [
'python_api/shankerzhiwu_disableidcheck.pkg',
'python_api/shankerzhiwu_changepwd.pkg'
'python_api/assets/su',
'python_api/assets/supolicy',
'python_api/assets/libsupol.so',
'python_api/assets/install-recovery.sh'
]
else:
requiredFiles = [
'python_api/assets/shankerzhiwu_disableidcheck.pkg',
'python_api/assets/shankerzhiwu_changepwd.pkg'
]
dpt.dbg_print('Checking required files...')
for file in requiredFiles:
@ -24,7 +63,7 @@ def disable_id_check(dpt):
'''
disable the id check (thanks to shankerzhiwu and his/her friend)
'''
fp = 'python_api/shankerzhiwu_disableidcheck.pkg'
fp = 'python_api/assets/shankerzhiwu_disableidcheck.pkg'
try:
resp = input('>>> Have you disabled the id check already? [yes/no]: ')
if resp == 'no':
@ -52,7 +91,7 @@ def reset_root_password(dpt):
'''
reset the root password (thanks to shankerzhiwu and his/her friend)
'''
fp = 'python_api/shankerzhiwu_changepwd.pkg'
fp = 'python_api/assets/shankerzhiwu_changepwd.pkg'
try:
if not dpt.update_firmware(open(fp, 'rb')):
dpt.err_print('Failed to upload shankerzhiwu_changepwd pkg')
@ -87,31 +126,9 @@ def obtain_diagnosis_access(dpt):
return True
def update_firmware(dpt):
'''
update firmware interface
Diagnosis Related
'''
dpt.info_print(
'Please make sure you have charged your battery before this action.')
try:
resp = input('>>> Please enter the pkg file path: ')
if not os.path.isfile(resp):
dpt.err_print('File `{}` does not exist!'.format(resp))
return False
resp2 = input('>>> Pleae confirm {} is the pkg file to use [yes/no]: ')
if resp2 == 'yes':
if not dpt.update_firmware(open(resp, 'rb')):
dpt.err_print('Failed to upload pkg {}'.format(resp))
return False
dpt.info_print('Success!')
return True
elif resp == 'no':
dpt.info_print('Okay!')
else:
dpt.err_print('Unrecognized response: {}'.format(resp))
except BaseException as e:
dpt.err_print(str(e))
return False
def print_diagnosis_info():
@ -127,6 +144,7 @@ Supported commands:
`pull-file` -- transfer file from DPT
`backup-bootimg` -- backup the boot img and download it to local device
`restore-bootimg` -- restore the boot img
`get-su-bin` -- enable `su` (root) in adb (beta, not well tested)
`exit`/`quit` -- leave the tool
and many unix cmds (do not support less/head)
""")
@ -315,6 +333,98 @@ def diagnosis_backup_bootimg(dpt):
return False
def diagnosis_get_su_bin(dpt):
'''
get sudo access in adb mode (so it would be much much eaiser to
make changes (no painful serial data transfer)
after doing this, adb should handle most necessary modifications
here we use system-method (push binary files to system)
'''
if not validate_required_files(dpt, purpose='su-binary'):
return False
dpt.info_print("Mounting /system partition..")
mountpoint = dpt.diagnosis_mount_system()
dpt.info_print("Mounted to {}".format(mountpoint))
if not mountpoint:
dpt.err_print("Nothing happened..")
return False
dpt.info_print("Uploading su file to /system/xbin..")
sufp = diagnosis_push_file(
dpt,
localfp='python_api/assets/su',
folder='{}/xbin'.format(mountpoint),
overwrite=True)
if sufp is None:
dpt.err_print("Due to previous failure, we stopped..")
return False
dpt.diagnosis_set_perm(sufp, owner='0.0', perm='0755')
daemonsufp = sufp[:-2] + 'daemonsu'
dpt.diagnosis_write('cp {0} {1}'.format(sufp, daemonsufp))
extfolder = "{}/bin/.ext".format(mountpoint)
dpt.diagnosis_mkdir(extfolder)
dpt.diagnosis_set_perm(extfolder, owner='0.0', perm='0777')
dpt.diagnosis_write('cp {0} {1}/su'.format(sufp, extfolder))
dpt.info_print("Uploading supolicy file to /system/xbin..")
supolicyfp = diagnosis_push_file(
dpt,
localfp='python_api/assets/supolicy',
folder='{}/xbin'.format(mountpoint),
overwrite=True)
if supolicyfp is None:
dpt.err_print("Due to previous failure, we stopped..")
return False
dpt.diagnosis_set_perm(supolicyfp, owner='0.0', perm='0755')
libsupolsofp = diagnosis_push_file(
dpt,
localfp='python_api/assets/libsupol.so',
folder='{}/lib'.format(mountpoint),
overwrite=True)
if libsupolsofp is None:
dpt.err_print("Due to previous failure, we stopped..")
return False
dpt.diagnosis_set_perm(libsupolsofp, owner='0.0', perm='0644')
dpt.info_print("Uploading install-recovery.sh to /system/bin..")
installrecfp = diagnosis_push_file(
dpt,
localfp='python_api/assets/install-recovery.sh',
folder='{}/bin'.format(mountpoint),
overwrite=True)
if installrecfp is None:
dpt.err_print("Due to previous failure, we stopped..")
return False
dpt.diagnosis_set_perm(installrecfp, owner='0.0', perm='0755')
dpt.info_print("Tweaking /system/bin/app_process..")
appprocessfp = '{0}/bin/app_process'.format(mountpoint)
dpt.diagnosis_write('mv {0} {0}_bak'.format(appprocessfp))
dpt.diagnosis_ln(daemonsufp, "/system/bin/app_process")
dpt.info_print("Tweaking /system/bin/app_process32..")
appprocess32fp = '{0}32'.format(appprocessfp)
if dpt.diagnosis_isfile("{}_original".format(appprocess32fp)):
dpt.diagnosis_remove_file(appprocess32fp)
else:
dpt.diagnosis_write("mv {0} {0}_original".format(appprocessfp))
dpt.diagnosis_ln(daemonsufp, "/system/bin/app_process32")
dpt.info_print("Tweaking /system/bin/app_process_init..")
if not dpt.diagnosis_isfile("{}_init".format(appprocessfp)):
dpt.diagnosis_write(
"cp {0}_ori {1}_init".format(appprocess32fp, appprocessfp))
dpt.diagnosis_set_perm(
"{}_init".format(appprocessfp), owner='0.2000', perm='0755')
dpt.info_print("Misc: add /system/etc/.installed_su_daemon")
miscfp = "{}/etc/.installed_su_daemon".format(mountpoint)
dpt.diagnosis_write("echo 1 > {}".format(miscfp))
dpt.diagnosis_set_perm(miscfp, owner='0.0', perm='0644')
dpt.info_print("Done!")
def diagnosis_restore_bootimg(dpt, usetmpfp=None, bootimgfp=None):
'''
restore boot img
@ -374,6 +484,9 @@ def diagnosis_cmd(dpt):
elif cmd == 'restore-bootimg':
diagnosis_restore_bootimg(dpt)
continue
elif cmd == 'get-su-bin':
diagnosis_get_su_bin(dpt)
continue
rawresp = dpt.diagnosis_write(cmd)
# ignore first and last echos
tmp = rawresp.splitlines()