Commit Graph

92 Commits

Author SHA1 Message Date
topjohnwu
9820296e92 Update files.cpp in libutils 2020-04-02 02:17:45 -07:00
topjohnwu
5f1174de27 Introduce new boot flow to handle SAR 2SI
The existing method for handling legacy SAR is:
1. Mount /sbin tmpfs overlay
2. Dump all patched/new files into /sbin
3. Magic mount root dir and re-exec patched stock init

With Android 11 removing the /sbin folder, it is quite obvious that
things completely break down right in step 1.

To overcome this issue, we have to find a way to swap out the init
binary AFTER we re-exec stock init. This is where 2SI comes to rescue!

2SI normal boot procedure is:
1st stage -> Load sepolicy -> 2nd stage -> boot continue...

2SI Magisk boot procedure is:
MagiskInit 1st stage -> Stock 1st stage -> MagiskInit 2nd Stage ->
-> Stock init load sepolicy -> Stock 2nd stage -> boot continue...

As you can see, the trick is to make stock 1st stage init re-exec back
into MagiskInit so we can do our setup. This is possible by manipulating
some ramdisk files on initramfs based 2SI devices (old ass non SAR
devices AND super modern devices like Pixel 3/4), but not possible
on device that are stuck using legacy SAR (device that are not that
modern but not too old, like Pixel 1/2. Fucking Google logic!!)

This commit introduces a new way to intercept stock init re-exec flow:
ptrace init with forked tracer, monitor PTRACE_EVENT_EXEC, then swap
out the init file with bind mounts right before execv returns!

Going through this flow however will lose some necessary backup files,
so some bookkeeping has to be done by making the tracer hold these
files in memory and act as a daemon. 2nd stage MagiskInit will ack the
daemon to release these files at the correct time.

It just works™  ¯\_(ツ)_/¯
2020-04-01 04:39:28 -07:00
topjohnwu
543ce937ec Don't need to find system_dev 2020-03-31 22:41:25 -07:00
topjohnwu
a0998009c1 Small native code reorganization 2020-03-09 01:50:30 -07:00
topjohnwu
696ab677be New pre-init magic mount implementation 2020-02-21 00:49:58 -08:00
topjohnwu
84e4bd3d41 Move readlinkat fix into xwrap 2020-02-03 13:24:02 +08:00
Shaka Huang
0ecfb63cd6 Fix crash during boot in x86 platform
readlinkat() may return random value instead of the number of bytes placed in buf and crashing the system in two ways:
1. segmentation fault (buf[-7633350] = ‘\0’)
2. wrong link of watchdogd, resulting dog timeout

Confirmed working in ZenFone 2 x86 series, may fix #2247 and #2356

Signed-off-by: Shaka Huang <shakalaca@gmail.com>
2020-02-03 13:02:30 +08:00
topjohnwu
ba55e2bc32 Backup proper magiskinit in A-only 2SI 2020-01-22 05:12:04 +08:00
topjohnwu
b39f407596 Load libsqlite dynamically 2020-01-11 03:20:59 +08:00
topjohnwu
3a0e3c98f7 Minor adjustments to prevent crashes 2020-01-09 23:42:27 +08:00
topjohnwu
b2cb2b8b75 Reduce socket name length
Some detectors simply ban long abstract sockets
2019-12-28 21:27:55 +08:00
topjohnwu
4f4f54a059 Remove unused code 2019-12-13 08:31:24 -05:00
topjohnwu
12fda29280 Add support for pre-init custom sepolicy patches
Close #1685
2019-12-13 06:05:12 -05:00
topjohnwu
af060b3132 General QoL changes 2019-12-13 00:37:06 -05:00
topjohnwu
8c500709e4 Remove SAR compatibility mode 2019-12-12 03:25:48 -05:00
topjohnwu
08177c3dd8 Mount persist partition mirror pre-init 2019-12-09 04:09:23 -05:00
topjohnwu
d22b9c26b6 Pull out common logic 2019-12-06 15:31:49 -05:00
topjohnwu
7681fde4d0 Record mounts to be cleaned up in a vector 2019-11-19 00:16:20 -05:00
topjohnwu
d3b7b41927 Fix kmsg logging in magiskinit 2019-11-18 17:18:56 -05:00
topjohnwu
75306f658f Revert "Drop API 17 (Android 4.2) support"
Turns out that we cannot use AndroidKeystore anyways, so we don't
actually need to drop API 17. Revert this change.
2019-10-20 07:13:03 -04:00
topjohnwu
9c27d691dd Drop API 17 (Android 4.2) support 2019-10-19 03:11:54 -04:00
topjohnwu
748a35774f Support patching fstab in ramdisk for A-only 2SI 2019-09-22 05:30:04 -04:00
topjohnwu
a52a3e38ed Change some class names 2019-09-22 05:20:51 -04:00
topjohnwu
ee0cef06a6 Add support for A-only 2SI 2019-09-22 05:15:31 -04:00
topjohnwu
736729f5ef Maintain a list of pre-init mounts
Keep track of everything to unmount
2019-07-16 23:54:52 -07:00
topjohnwu
7ba8202af5 Introduce new root overlay system 2019-07-16 01:08:28 -07:00
topjohnwu
52fd508fea Do not use std::random_device
Directly read from urandom instead of using std::random_device.
libc++ will use iostream under-the-hood, which brings significant
binary size increase that is not welcomed, especially in magiskinit.
2019-07-14 21:56:21 -07:00
topjohnwu
41045b62dc Introduce more randomness
- Use C++ random generator instead of old and broken rand()
- Randomize string length to piss off stupid detectors
2019-07-14 17:42:49 -07:00
topjohnwu
7233285437 Use relative symbolic links 2019-07-04 17:58:46 -07:00
topjohnwu
05658cafc7 Fix typo causing sbin clone failure 2019-06-30 19:24:14 -07:00
topjohnwu
ff3710de66 Minor code changes across all sources 2019-06-30 19:09:31 -07:00
topjohnwu
db8dd9f186 Init code rearrangement 2019-06-30 11:39:13 -07:00
topjohnwu
e8b73ba6d1 Add separate product partition support 2019-06-29 14:19:10 -07:00
topjohnwu
f1112fdf37 Logical Resizable Android Partitions support
The way how logical partition, or "Logical Resizable Android Partitions"
as they say in AOSP source code, is setup makes it impossible to early
mount the partitions from the shared super partition with just
a few lines of code; in fact, AOSP has a whole "fs_mgr" folder which
consist of multiple complex libraries, with 15K lines of code just
to deal with the device mapper shenanigans.

In order to keep the already overly complicated MagiskInit more
managable, I chose NOT to go the route of including fs_mgr directly
into MagiskInit. Luckily, starting from Android Q, Google decided to
split init startup into 3 stages, with the first stage doing _only_
early mount. This is great news, because we can simply let the stock
init do its own thing for us, and we intercept the bootup sequence.

So the workflow can be visualized roughly below:

Magisk First Stage --> First Stage Mount --> Magisk Second Stage --+
   (MagiskInit)         (Original Init)         (MagiskInit)       +
                                                                   +
                                                                   +
     ...Rest of the boot... <-- Second Stage <-- Selinux Setup  <--+
      (__________________ Original Init ____________________)

The catch here is that after doing all the first stage mounting, /init
will pivot /system as root directory (/), leaving us impossible to
regain control after we hand it over. So the solution here is to patch
fstab in /first_stage_ramdisk on-the-fly to redirect /system to
/system_root, making the original init do all the hard work for
us and mount required early mount partitions, but skips the step of
switching root directory. It will also conveniently hand over execution
back to MagiskInit, which we will reuse the routine for patching
root directory in normal system-as-root situations.
2019-06-29 01:25:54 -07:00
topjohnwu
e29b712108 Start Magisk in SAR 2019-06-25 23:31:59 -07:00
topjohnwu
a462435f2f Load custom sepolicy 2019-06-25 21:34:02 -07:00
topjohnwu
911b8273fe Fix typo in sbin clone 2019-06-25 03:35:25 -07:00
topjohnwu
aac9e85e04 More Q cleanup 2019-06-25 02:38:34 -07:00
topjohnwu
bb67a837d3 Adjust class structures 2019-06-24 01:50:47 -07:00
topjohnwu
6cde695194 Remove Q dirty hacks in SARCompat 2019-06-24 01:31:42 -07:00
topjohnwu
a1a1ac0bbb Add sbin overlay to system-as-root 2019-06-24 01:21:33 -07:00
topjohnwu
9ec8bc2166 Boot MagiskInit as actual system-as-root
WIP, no customization. DO NOT USE YET!
2019-06-23 15:14:47 -07:00