デバイスを贈り物として受け取りました。新しいデバイスを受け取るたびに、私はそれをざっと調べます。特に、かなり個人的なデータやビジネス上重要なデータを呼び込むデバイスの場合はそうです。今回の場合でも、私は Ratta という会社が私のデータを保護するために最善を尽くしてくれると多かれ少なかれ信頼していますが、(一部)中国企業であるため、彼らができることには限界があると考えています。私たちは皆、中国のプライバシー法と規制の現状をめぐる議論を知っています。また、デバイスが同じく中国本土にあるサードパーティの OEM メーカーによって製造されていると信じる理由があり、デバイスで他に何が起こっているのかを確認したいと思いました。
TL;DRデバイスは複数の攻撃ベクトルを通じてルート化される可能性があります。ソフトウェアベースとハードウェアベース。
良いニュースです。デバイスを調べたところ、スパイウェアやその他の侵入行為に関して明らかに危険を冒すものは見つかりませんでした。 Ratta アプリの一部には、部分的に難読化された Tencent コンポーネントが埋め込まれています。デバイスはテレメトリ設定を尊重しているようですが (Google、Apple などに注意してください)、少なくとも位置情報や使用パターンに関してユーザーを追跡している可能性のあるアップデートを非常に定期的にチェックしています。一部のサーバーは明らかに中国にあるため、中国政府に公開されている可能性があります。同社はこの話題を認識しており、米国でサーバーを展開しているようですが。物事を大局的に考えると、Google や Amazon の組み込みデバイス、一般的なオペレーティング システム、スマートフォン、または一般的なソーシャル メディア アプリは、ここで見つけたものよりも多くの情報を収集します。
警告:デバイスが使用できなくなる可能性が非常に高いため、実際にこの記述に従うことはお勧めしません。これらの多くは記憶に基づいて書き留められています。私の場合、これはあまり信頼できません。そのため、保証が無効になるだけでなく、デバイスが使用できなくなるリスクを高めるエラーや欠落が存在する可能性があります。
2022/08/08 更新: 2 週間ほど前に Ratta に通知して、この情報を公開することを伝えました。予想どおり、ラッタは親切に答え、問題に取り組むことを約束しました。また、ここで私は決して中国=悪を暗示しているわけではないことも指摘しておきたい。私は、自分のデータが安全でプライベートであることを一般的に望んでおり、中国と同様に米国、ヨーロッパ、インド、ロシアなどのプライバシー慣行にも問題があると考えています。
上記を参照してください。物理的なアクセスを考慮すると、このデバイスは機密性の高いデータに対して安全であるとは考えられません。
Android の古いバージョンの性質とセキュリティ対策の欠如を考慮すると、私はいかなる状況であっても私のデバイスを信頼できない第三者に利用可能にするつもりはありません。また、これらの攻撃の一部は完全に自動化された方法で実行される可能性があるため、未知のコンピューターや公共の充電ケーブルには決して接続しないことをお勧めします。
私はセキュリティ担当者ではありません。そのため、公開されているデータを収集するために 2 週間の週末を費やすことになりました。十分にやる気があり、私よりも才能のある人や団体はもっと速いでしょう。また、Ratta はとにかくサイドローディングを許可すると約束しており、プリインストールされた su バイナリ、公開テスト キー、オープン ブート ローダー、(無効化され、簡単にロック解除できる) adb コンソール インターフェイス、その他のオープン ドアがデバイスに大きく開かれるのを確認しているため、これによって何も作成されないと思います。思わぬ不都合。
いずれにしても、この文書は一般公開の 2 週間前である 2022 年 7 月 27 日に電子メールでラッタに提供されました。
いいえ。いかなる場合でも、私は著作権などで多少なりとも保護される可能性のあるファイルを配布しません。自分が何をしようとしているのかを知っている場合、この記事には十分すぎる情報が含まれています。そうでない場合は、デバイスをそのままにして、デバイスへのシェル/ルート アクセスを Ratta に依頼してください。
Kindle アプリをインストールすることで、限られた量のデバイスの仕様を確認できます。このアプリは、この記事の執筆時点では、デバイスの統合された「アプリ ストア」で利用できる唯一のアプリです。または、OTA update.zip を解凍するだけです。
このデバイスは、1,5GHz クアッドコア ARM Cortex-A35、2 ギガバイトの RAM、および 1404x1872 eink ディスプレイで構成される Rockchip PX30 プラットフォーム上で Android 8.1 を実行します。 Rockchip プラットフォームは、カーラジオやユーザー インターフェイスを備えたその他の組み込みデバイスでよく見られるようです。そのため、グーグルで検索するだけで、公式情報や非公式情報をたくさん見つけることができます。
同様に:rockchip.fr/PX30%20datasheet%20V1.1.pdf あるいは:opensource.rock-chips.com/wiki_Main_Page
reddit に /r/supernote と /r/supernote_beta があるという事実から推測すると、このデバイスにはベータ プログラムが存在します。
Ratta は、リリースとベータ アップデートの両方に関する情報を Web サイトと同様に提供しています。
現在の非ベータ版はここからダウンロードできます: support.supernote.com/article/3/how-to-update-your-supernote
SupernoteSettings.apk
で確認できるように、ベータ版の配布はデバイスのシリアル番号に関連付けられているため、現在インストールされているバージョンとは関係なく、同じサーバーと URL に接続するため、ベータ版はできません。さらに詳しい情報については、以下を参照してください。
アップデートは一般的な非暗号化 Android OTA ファイルであり、無料で利用できるツールを使用して簡単に解凍して分析できます。詳細については、以下を参照してください。
解凍された .br brotli イメージを含む update.zip :
update.zip:/システム
デバイスは、 device.supernote.com.cn
のサーバーと連携して更新し、利用可能な新しい更新があるかどうかを確認します。
curl -X POST -k -H 'Content-Type: application/json' -i 'https://device.supernote.com/official/system/business/android/update/download' --data '{"language":"EN", "equipmentNo":"SN100Bxxxxxxxx", "logicVersion":"Chauvet 2.4.15(566)", "configureList":[{"type":"1", "version":"Chauvet.D002.2203101001.566_release"}]}'
エラーメッセージは中国語ですが、 「デバイスはアップデートを必要としません」 、 「シリアル番号が不明です」などの通常のメッセージです。
アップデートが利用可能な場合、デバイスは完全な変更ログなどとともにダウンロード URL を受け取ります。
{"success":true,"errorCode":null,"errorMsg":null,"configureList":[{"type":"1","version":"Chauvet.xxxx.xxxxxxxxxx.xxx_xxxxxxx","fileName" :"Chauvet.xxxx.xxxxxxxxx.xxx_xxxxxxx.zip","名前":null,"パッケージ名":null,"バージョンいいえ":null,"url":"https://prod-ratta-firmware.s3.ap-northeast-1.amazonaws.com/xxxxxx/update.zip","size":xxxxxxxx,"md5":" abcdefabcdefabcdefabcdef"}],"totalSize":xxxxxxxx,"fixPointList":[{"current":false,"version":"ショーヴェxxxx(xxx)","fixPoint":"
...
","opTime":"xxxx-xx-xx xx:xx:xx"}],"logicVersion":" Chauvet xxxx(xxx)","deployDate":"xxxx-xx-xx xx:xx:xx"}
その後、ダウンロードされて回復システムに渡されます。
手動アップデートの手順に従って、デバイスの/EXPORT/
フォルダーに update.zip ファイルを置き、USB ケーブルを抜いても、同じことが起こります。デバイスはファイルを検出し、インストールを続行するかどうかを尋ねます。
正確なメカニズムは次のコードから推測できます。
com.ratta.supernote.update.NetWorkConstant
public static final String DEV_BASE_URL = "http://10.20.22.32:9000" ;
public static final String DOWN_LOAD_URL = "" ;
public static final String NET_BASE_URL_PRODUCT = "http://10.20.22.32:8075/" ;
public static final String NET_BASE_URL_TEST = "https://test-ms-device.ratta.com.cn/" ;
public static final String RELEASE_BASE_URL = "https://device.supernote.com.cn/" ;
public static final String UAT_BASE_URL = "https://device.supernote.com" ;
public static final File DOWN_LOAD_PATH = new File ( "/cache" );
public static final String USBDisk_Path = Environment . getExternalStorageDirectory () + File . separator ;
public static final String FILE_TEST = USBDisk_Path + "EXPORT/test" ;
public static final String FILE_PRODUCT = USBDisk_Path + "EXPORT/product" ;
public static final String FILE_UAT = USBDisk_Path + "EXPORT/uat" ;
com.ratta.networklibrary.utils.C0598Utils
String str = Build . DISPLAY ; // i.E. Chauvet.D002.2203101001.566_release
boolean exists = new File ( Constant . FILE_USA ). exists ();
int lastIndexOf = str . lastIndexOf ( "_" );
if ( lastIndexOf != - 1 ) {
String substring = str . substring ( lastIndexOf + 1 );
String str2 = (( TextUtils . equals ( substring , "root" ) || TextUtils . equals ( substring , "hard" )) && exists ) ? Constant . USA_BASE_URL : Constant . RELEASE_BASE_URL ;
if ( new File ( Constant . FILE_TEST ). exists () || TextUtils . equals ( substring , "test" )) {
str2 = exists ? Constant . TEST_USA_BASE_URL : Constant . TEST_BASE_URL ;
} else if ( new File ( Constant . FILE_PRODUCT ). exists ()) {
str2 = Constant . DEV_BASE_URL ;
} else if ( new File ( Constant . FILE_UAT ). exists () || TextUtils . equals ( substring , "uat" )) {
str2 = Constant . UAT_BASE_URL ;
}
if (! TextUtils . equals ( substring , "release" ) && ! TextUtils . equals ( substring , "beta" )) {
return str2 ;
}
if ( exists ) {
return Constant . USA_BASE_URL ;
}
}
return Constant . RELEASE_BASE_URL ;
com.ratta.supernote.update.DownLoadService
@ POST ( "official/system/business/android/update/download" )
Call < DownResponse > downLoadFileInfo ( @ Body RequestBody requestBody );
com.ratta.supernote.update.UpDateAppService
LocalSystemInfoBean localSystemInfoBean = new LocalSystemInfoBean (); // see CURL request above for example values
localSystemInfoBean . setEquipmentNo ( DownPresenter . getDeviceVersion ());
localSystemInfoBean . setLanguage ( DownPresenter . getLanguage ( this ));
localSystemInfoBean . setLogicVersion ( DownPresenter . getLogicVersion ());
localSystemInfoBean . setConfigureList ( DownPresenter . getSystemAllPackageVersion ( this , new ArrayList ()));
RetrofitUtils retrofitUtils = RetrofitUtils . getInstance ();
final DownResponse downResponse = ( DownResponse ) retrofitUtils . execute ((( DownLoadService ) retrofitUtils . getService ( DownLoadService . class )). downLoadFileInfo ( DownLoadModel . getRequestBody ( localSystemInfoBean )));
com.ratta.supernote.update.UpDateAppService
if ( new File ( NetWorkConstant . DOWN_LOAD_PATH , "update.zip" ). exists ()) {
CacheInfoUtils . saveData ( CacheInfoUtils . updateFlagPath , UpDateAppService . USB_UPDATE_FLAG );
RecoverySystem . installPackage ( UpDateAppService . this , new File ( NetWorkConstant . DOWN_LOAD_PATH , "update.zip" )); // if unfamiliar: https://developer.android.com/reference/android/os/RecoverySystem
}
com.ratta.supernote.update.UpDateAppService
private void checkRestartUpdate () {
String str = SystemProperties . get ( ConstanceUtil . restartKey , Constance . FILE_SEVER_UFILE ); // FILE_SEVER_UFILE = "0"; restartKey = "ratta.launcher.restart";
LogUtils . m187d ( "ratta: " + str );
if (! str . equals ( "1" )) {
SystemProperties . set ( ConstanceUtil . restartKey , "1" );
this . firstSelectVersion = true ;
if ( new File ( Environment . getExternalStorageDirectory (). getAbsolutePath () + File . separator + "EXPORT" , "update.zip" ). exists ()) {
this . firstSelectVersion = false ;
usbUpdate ();
return ;
}
LogUtils . m187d ( "checkRestartUpdate: getVersionList" );
getVersionList ();
}
}
public void usbUpdate () {
if ( this . usbUpdateFlag ) {
return ;
}
final File file = new File ( Environment . getExternalStorageDirectory (). getAbsolutePath () + File . separator + "EXPORT" , "update.zip" );
if (! file . exists ()) {
LogUtils . m187d ( "onReceive: No USB upgrade file" );
return ;
}
GestureService . lockStatusbar = true ;
GestureService . lockSlidebar = true ;
this . usbUpdateFlag = true ;
LogUtils . m187d ( "usb update GestureService.lockStatusbar true" );
DialogUtils . getInstance (). build ( this ). createDefaultDelayDialog ( getString ( C0688R . string . usb_detection_tips ), 30 , new LibDialogDelayDefaultListener () { // "The upgrade pack is detected, do you want to install?"
// goes on with housekeeping like removing any existing update.zip and a couple of checks for enough battery etc and then moves the update.zip to /cache as seen above
ご覧のとおり、健全性チェックやいかなる種類の復号化も行われていません。したがって、基本的には任意のファイルを取得し、それを /EXPORT/ フォルダーに移動し、システムにそれをリカバリーに渡すことができます。
確認したことはありませんが、コードを読むと、USB 経由でデバイスを自由にアップグレードおよびダウングレードできると思われます。
ただし、これは標準の Android 回復メカニズム (私にはあまり詳しくありません) なので、ファイルが既知の秘密キーで署名されているかどうかがチェックされます。
このデバイスには、クローズドダウンされた ADB インターフェイスが付属しています。 adb reboot
コマンドを使用すると、リカバリadb reboot recovery
だけでなく、fastboot adb reboot fastboot
またはブートローダー モードadb reboot loader
にすることもできます。
リカバリモードでは、デバイスは root として実行されるシェルを許可します。使用できるコマンド セットは限られていますが、busybox がインストールされているので気にする必要はありません。論理的な手順は、次のようなスクリプトを作成して、adb へのフルアクセスのロックを解除することです。
#! /bin/bash
echo " rebooting to recovery "
adb reboot recovery
ANSWER=0
while [ " $ANSWER " != " 1 " ] ; do
sleep 2
ANSWER= $( adb devices | grep rockchipplatform -c )
done
echo " device online, patching "
adb shell busybox mount -o rw,seclabel,relatime,data=ordered,inode_readahead_blks=8 /dev/block/by-name/system /system
adb shell sed -i " s/ro.debuggable=0/ro.debuggable=1/ " /system/etc/prop.default
echo " rebooting to system "
adb reboot
その後、デバイスは基本的に、root に昇格できる標準の adb シェルを介して完全にアクセスできるようになります。
技術者以外のユーザーの場合: これは、デバイスがすべてのファイルとともに基本的に開いていることを意味します。やる気のあるユーザーであれば、USB アクセスがあれば、いつでもデバイス上のファイルをコピーまたは変更できます。
ブートローダーのロックが解除されているため、デバイスをこのモードで再起動し、 fastboot flash boot boot.img
実行することで、いつでもカーネルまたはパーティションをフラッシュできます。
技術者以外のユーザーの場合: これは、ユーザーが気付かない方法でデバイスが自由に変更される可能性があり、データとプライバシーが危険にさらされる可能性があることを意味します。
このモードでは、デバイスは RKDevTool などの Rockchip 開発者ツールによって「LOADER MODE」として検出されます。ここからパーティションを上書きしたり、パーティションのレイアウトを変更したりできます...
...そしてデバイスをマスククロムモードにすることができます。詳細については以下をご覧ください。
技術者以外のユーザーの場合: これは、ユーザーが気づかない方法でデバイスが自由に変更される可能性があり、データとプライバシーが危険にさらされる可能性があることを意味します。
/system/build.prop
を見てみると、
ro.build.description=px30_ht_eink-userdebug 8.1.0 OPM8.190505.001 Chauvet.D002.2206171001.629_beta test-keys
ro.build.fingerprint=Android/htfy_px30:/Chauvet.D002.2206171001.629_beta_:userdebug
test-keys
あまり良い兆候ではありません。あなたが開発者なら。システムへの大きく開かれた扉を探している場合、これは美しい兆候です。
Android OTA の詳細については説明しませんが、ここで読むことができます。
update.zip: /META-INF/com/android/otacert
を参照すると、アップデートの公開証明書を確認できます。
-----証明書を開始-----
MIID+zCCAuOgAwIBAgiIJAJKlKMdz16FBMA0GCSqGSIb3DQEBCwUAMIGUMQswCQYD
VQQGEwJVUzETMBEGA1UECAwKQ2FsaWZvcm5pYTEWMBQGA1UEBwwNTW91bnRhaW4g
VmlldzEQMA4GA1UECgwHQW5kcm9pZDEQMA4GA1UECwwHQW5kcm9pZDEQMA4GA1UE
AwwHQW5kcm9pZDEiMCAGCSqGSIb3DQEJARYTYW5kcm9pZEBhbmRyb2lkLmNvbTAe
Fw0xNDEyMjMwNjQ0MDhaFw00MjA1MTAwNjQ0MDhaMIGUMQswCQYDVQQGEwJVUzET
MBEGA1UECAwKQ2FsaWZvcm5pYTEWMBQGA1UEBwwNTW91bnRhaW4gVmlldzEQMA4G
A1UECgwHQW5kcm9pZDEQMA4GA1UECwwHQW5kcm9pZDEQMA4GA1UEAwwHQW5kcm9p
ZDEiMCAGCSqGSIb3DQEJARYTYW5kcm9pZEBhbmRyb2lkLmNvbTCCASAwDQYJKoZI
hvcNAQEBBQADggENADCCAQgCggEBALLl71fjESroAzdrkBKrApCrK9qnZfH38S3U3
6jhBOQtrwxnh/AaRC3hOyO5ihjwv1MlSuTA1DygGMznwP8rOQbc9eH4uqdnerE87
v0bc8lPCj22AAterZBZESqgfRwND/25S6A22wA/kpR/CiXMuWHlQfS6Q9CHBOwVQ
5ZZUge2KC1TbH8EtDkxDacOeTbhN6UQxxm3jgaIzkwyrEEcYB1m93CrTFOtVV7Jw
wo7XE5LGwo6nTzNieXJqoYxcNAMpv9seKW+GZ1EGl78e9B37SMoxq0I7HuStz5tD
tS2Er2YrjQig+1ZqgroIvPfEJAEyoEr0r6kK7jBh878usWOuWB0CAQOjuUDBOMB0G
A1UdDgQWBBTV37ltjIiA28uNs8Z1hb6zasy5UzAfBgNVHSMEGDAWgBTV37ltjIiA
28uNs8Z1hb6zasy5UzAMBgNVHRMEBTADAQH/MA0GCSqGSIb3DQEBCwUAA4IBAQAZ
7pvK3yDr+O0G8ggDfaISkEeg0agocRcXGT/MRiPBz+n45+bEoym4hC2SdCxvHXES
5AHkFxjWavoQqAD8We955NCmpGzDip4hUctlXzqxYfSTvGiLArG92+Hcbu5RNx/7
o3Of39Mdge2jVKQuKAALWnb8TgJ/2k3KAUFzVqMXPY4asmnWtyW2FIKLdZU/yYTX
+8Tp0AhP+N84HUGg5BwQRD10/OGGY54rLfFy2aSLPxUZQ+VTSZB9Z9XRLxohsF/V
XBcZyCdPP254wDYL5R0HGWZv7CeBlVjw3FqDRI9aljdYfLpak+clnRBwWWHsiOE
pJXgkkLmpq0uDXsSMJZ2
-----証明書終了-----
証明書の一部をグーグルで検索すると、xda-developers.com から、誰かが Android 8.1 Rockchip PX5 デバイスに侵入しようとしているという結果が少なくとも 1 つ表示されます。
それはさらに悪い兆候です。あるいは、私にとってはさらに美しいものです。
次に、PX30 プラットフォームに関する SDK を検索したところ、ここで SDK を見つけました。
en.t-firefly.com/doc/download/page/id/63.html#other_206
ここのドキュメントと一緒に:
wiki.t-firefly.com/en/Core-PX30-JD4/Android_development.html
そしてここで:
wiki.t-firefly.com/en/Firefly-RK3399/customize_android_firmware.html
SDK をダウンロードすると、7z アーカイブを解凍し、含まれている git リポジトリを次のように初期化できます。
git clone PX30_Android8.1.0_LVDS_190706 directory_to_clone_into
長いクローンを作成した後、 /build/make/target/product/security
で SDK テスト キーを見つければ準備完了です。
興味深い事実: そのフォルダー内の README には次のように記載されています。
このディレクトリ内のテスト キーは開発のみで使用され、公開リリースされたイメージ内のパッケージの署名には決して使用しないでください (重大なセキュリティ ホールが発生する可能性があるため)。
はい、確認されました。
このテクニックはあなたにお任せします。Windows で作業している間、私は Multi Image Kitchen を使用して Android OTA を解凍、再パックし、署名します。 testkey.x509.pem
とtestkey.pk8
ツールのbin
フォルダーに移動する必要があります。そこから変更された更新を作成できるようになります。デバイスは、EXPORT フォルダーに配置するときにインストールする以外に選択肢がありません。 。
まあ、おそらく。
ここから行うことはすべて、エラーが発生しやすく、デバイスがソフトブリックする可能性が非常に高いです。私の知る限り、すべての Rockchip デバイスは、基本的にオープン プログラミング インターフェイスであるマスククロム モードを常に備えているため、完全にソフト ブリックすることはできません。
通常、このインターフェイスには、CPU の 2 つのピンを短絡することでアクセスできます。これはスーパーノートでも同様に機能しますが、デバイスを開いて、おそらく残りの保証を無効にする必要があります。
PX30 マスククロムに関するすべての情報とデバイスを回復する方法については、以下を参照してください。
ルート ADB シェル内のすべてのパーティションをバックアップします。
adb shell
たとえば、次のコマンドを発行します。
cat /dev/block/mmcblk1p1 > /sdcard/EXPORT/uboot.img
cat /dev/block/mmcblk1p2 > /sdcard/EXPORT/trust.img
cat /dev/block/mmcblk1p3 > /sdcard/EXPORT/misc.img
cat /dev/block/mmcblk1p4 > /sdcard/EXPORT/resource.img
cat /dev/block/mmcblk1p5 > /sdcard/EXPORT/kernel.img
cat /dev/block/mmcblk1p6 > /sdcard/EXPORT/boot.img
cat /dev/block/mmcblk1p7 > /sdcard/EXPORT/recovery.img
cat /dev/block/mmcblk1p8 > /sdcard/EXPORT/backup.img
cat /dev/block/mmcblk1p9 > /sdcard/EXPORT/security.img
cat /dev/block/mmcblk1p10 > /sdcard/EXPORT/cache.img
cat /dev/block/mmcblk1p11 > /sdcard/EXPORT/system.img
cat /dev/block/mmcblk1p12 > /sdcard/EXPORT/metadata.img
cat /dev/block/mmcblk1p13 > /sdcard/EXPORT/vendor.img
cat /dev/block/mmcblk1p14 > /sdcard/EXPORT/oem.img
cat /dev/block/mmcblk1p15 > /sdcard/EXPORT/frp.img
ユーザーデータも保存できる可能性があります。
dd if=/dev/block/by-name/userdata bs=4096 count=1048576 of=/sdcard/EXPORT/userdata-1.img
dd if=/dev/block/by-name/userdata bs=4096 skip=1048576 count=1048576 of=/sdcard/EXPORT/userdata-2.img
dd if=/dev/block/by-name/userdata bs=4096 skip=2097152 count=1048576 of=/sdcard/EXPORT/userdata-3.img
dd if=/dev/block/by-name/userdata bs=4096 skip=3145728 count=1048576 of=/sdcard/EXPORT/userdata-4.img
dd if=/dev/block/by-name/userdata bs=4096 skip=4194304 count=1048576 of=/sdcard/EXPORT/userdata-5.img
dd if=/dev/block/by-name/userdata bs=4096 skip=5242880 count=1048576 of=/sdcard/EXPORT/userdata-6.img
backup -> /dev/block/mmcblk1p8
boot -> /dev/block/mmcblk1p6
cache -> /dev/block/mmcblk1p10
frp -> /dev/block/mmcblk1p15
kernel -> /dev/block/mmcblk1p5
metadata -> /dev/block/mmcblk1p12
misc -> /dev/block/mmcblk1p3
oem -> /dev/block/mmcblk1p14
recovery -> /dev/block/mmcblk1p7
resource -> /dev/block/mmcblk1p4
security -> /dev/block/mmcblk1p9
system -> /dev/block/mmcblk1p11
trust -> /dev/block/mmcblk1p2
uboot -> /dev/block/mmcblk1p1
userdata -> /dev/block/mmcblk1p16
vendor -> /dev/block/mmcblk1p13
rootfs / rootfs ro,seclabel,size=981980k,nr_inodes=245495 0 0
/dev/block/by-name/system /system ext4 ro,seclabel,relatime,data=ordered,inode_readahead_blks=8 0 0
/dev/block/by-name/vendor /vendor ext4 ro,seclabel,relatime,data=ordered,inode_readahead_blks=8 0 0
/dev/block/by-name/oem /oem ext4 ro,seclabel,noatime,nodiratime,block_validity,delalloc,barrier,noauto_da_alloc,user_xattr 0 0
/dev/block/by-name/cache /cache ext4 rw,seclabel,nosuid,nodev,noatime,nodiratime,discard,noauto_da_alloc,data=ordered 0 0
/dev/block/by-name/metadata /metadata ext4 rw,seclabel,nosuid,nodev,noatime,nodiratime,discard,noauto_da_alloc,data=ordered 0 0
/dev/block/by-name/userdata /data f2fs rw,lazytime,seclabel,nosuid,nodev,noatime,nodiratime,background_gc=on,discard,no_heap,user_xattr,inline_xattr,inline_data,inline_dentry,flush_merge,extent_cache,mode=adaptive,active_logs=6,alloc_mode=default,fsync_mode=posix 0 0
tmpfs /storage tmpfs rw,seclabel,relatime,mode=755,gid=1000 0 0
adb /dev/usb-ffs/adb functionfs rw,relatime 0 0
/data/media /mnt/runtime/default/emulated sdcardfs rw,nosuid,nodev,noexec,noatime,fsuid=1023,fsgid=1023,gid=1015,multiuser,mask=6,derive_gid 0 0
/data/media /storage/emulated sdcardfs rw,nosuid,nodev,noexec,noatime,fsuid=1023,fsgid=1023,gid=1015,multiuser,mask=6,derive_gid 0 0
/data/media /mnt/runtime/read/emulated sdcardfs rw,nosuid,nodev,noexec,noatime,fsuid=1023,fsgid=1023,gid=9997,multiuser,mask=23,derive_gid 0 0
/data/media /mnt/runtime/write/emulated sdcardfs rw,nosuid,nodev,noexec,noatime,fsuid=1023,fsgid=1023,gid=9997,multiuser,mask=7,derive_gid 0 0
私のデバイスにあるアップデートには、すでに su バイナリと、ルート ADB インターフェイスに簡単にアクセスできる多くのショートカットが付属していました。
私が実験したいくつかの変更は次のとおりです。
/system/etc/prop.default
security.perf_harden=0
ro.debuggable=1
sys.rkadb.root=1
ro.debug.build=true
ro.oem_unlock_supported=1
ro.secure=0
ro.adb.secure=0
persist.sys.usb.config=mtp,adb
そして、そこにいる間、非常に頻繁な更新チェックとオプションのテレメトリをブロックしました(組み込みのApp Storeもブロックしますが、アプリをデバイスにサイドロードできるようになったので、これはほとんど役に立ちません)
/システム/etc/ホスト
127.0.0.1 device.supernote.com.cn
127.0.0.1 supernote.com.cn
127.0.0.1 www.supernote.com.cn
127.0.0.1 device.supernote.com
127.0.0.1 supernote.com
127.0.0.1 www.supernote.com
127.0.0.1 test-ms-device.ratta.com.cn
127.0.0.1 uat-ms-device.ratta.com.cn
127.0.0.1 ratta.com.cn
ここからルート ADB インターフェイスが動作し、アプリをサイドロードし、 mount -o remount,rw /system
発行した後に好みに合わせて /system を完全に変更できます。
そこで私が行った最初のステップは、適切に動作する SuperSU システムベースのルート ソリューションをインストールすることでした。そのために、最新の supersu.zip をダウンロードして解凍し、インストール スクリプトを確認して、非常にハックな方法でファイルを手動で配置しました。
/system/.ext/.su # useless I think? Didn't bother to understand
/system/xbin/daemonsu
/system/xbin/su
/system/xbin/sugote
/system/xbin/sugote-mksh
/system/xbin/supolicy
/system/lib64/libsupol.so
/system/app/SuperSU/SuperSU.apk
そして、 /system/bin/install-recovery.sh
を次のように変更します。
/system/xbin/daemonsu --auto-daemon &
/system/etc/install-recovery-2.sh
次に、 system_file_contexts.txt
を次のように変更して、ファイル コンテキストとアクセス権を変更します。
/system/app/SuperSU/SuperSU.apk u:object_r:system_file:s0
/system/xbin/su u:object_r:system_file:s0
/system/bin/.ext/.su u:object_r:system_file:s0
/system/xbin/daemonsu u:object_r:system_file:s0
/system/xbin/sugote u:object_r:zygote_exec:s0
/system/xbin/supolicy u:object_r:system_file:s0
/system/lib64/libsupol.so u:object_r:system_file:s0
/system/xbin/sugote-mksh u:object_r:system_file:s0
system_fs_config.txt
の末尾は次のようになります。
system/app/SuperSU 0 0 0755
system/app/SuperSU/SuperSU.apk 0 0 0644
system/xbin/su 0 2000 0755
system/bin/.ext 0 2000 0755
system/bin/.ext/.su 0 2000 0755
system/xbin/daemonsu 0 2000 0755
system/xbin/sugote 0 2000 0755
system/xbin/supolicy 0 2000 0755
system/lib64/libsupol.so 0 0 0644
system/xbin/sugote-mksh 0 2000 0755
完璧にうまくいきました。
簡単なスクリプトを実装するのは簡単だっただろうが、この時点では Android ルートにアクセスしたばかりだったので、適切な magisk システムレス ルートをインストールする計画でした。
Magisk は、未変更の boot.img を供給することで、事前に変更された「ルート化された」boot.img カーネルと RAM ディスクを生成できます。
update.zip
のルートからboot.img
取得し、 /storage/emulated/0/Download
にコピーします。
最新のMagiskを次のようにサイドロードします。
adb install Magisk-v25.x.apk
デバイスでSettings > Apps > My apps
に移動して、システムにアプリのリストを更新させ、サイドバーに Magisk を追加させます。ランチャー UI は明らかに多くのアプリを使用する人向けに作られていないため、ランチャー UI を見つけるにはスクロールする必要があるかもしれません。
Magisk でパッチを適用するファイルを選択するには、DocumentProvider をインストールする必要がありました。無料で非常に便利なため、Total Commander (ダウンロード) を選択しました。サイドロードされたもの:
adb install tcandroidxxxx-universal.apk
サイドバーに表示するには、上記と同じ操作を行います。それを開いて右上を盲目的にタップして「空の」メニューを開き、最後にすべてを正しく表示するために、最後から 2 番目の項目をタップして暗いテーマから明るいテーマに切り替えてみます。
Magisk を開き (root アクセスを許可し)、「更新」をタップし、すべてをそのままにして「次へ」をタップし、「ファイルを選択してパッチを適用する」をタップし、プロバイダーとして Total Commander (url...) を選択してから、boot.img を選択します。
結果のmagisk_patched-xxx.img
、デフォルトの作業フォルダー/storage/emulated/0/Download
から再度コピーしてコンピューターに戻します。
デバイスの起動から fastboot まで:
adb reboot fastboot
そして規格を発行します。
fastboot flash boot magisk_patched-xxx.img
そして
fastboot reboot
すべてがうまくいけば、デバイスがシステムで起動し、magisk を開くと、 Ramdisk とともにインストールされているバージョンが報告されます: yes 。以前に SuperSU をインストールしたことがある場合、またはプリインストールされた su バイナリを削除していない場合は、インストールが破損していることを警告し、以前のルートを削除するように求められます。これを行うには、追加したすべてのファイル、またはプリインストールされているsu
とlibsupol.so
だけを削除します。
スーパーユーザーに正常に動作していることを確認するよう要求するアプリを開くと、おなじみのスーパーユーザー プロンプトが表示されます。
v1.0.1(077) に遡って以前のファームウェア ファイルのリストを作成しました。
時間ができたら完成させます。
デバイスに何かが起こった場合は、デバイスを開いて CPU からシールドを取り外し、電源スイッチの横にあるリセット スイッチを押しながら次の 2 つのピン ヘッダーをショートさせます。
これにより、デバイスがマスククロムモードになります。デバイスを正確に回復する方法については詳しく説明しませんが、最も関連性の高い情報と、デバイスに変更を加える前にすべてのパーティションのバックアップを作成するというアドバイスを残しておきます。
次に、マスクROMドライバーをインストールします(Windowsで署名のないドライバーを有効にしてから、 RKImageMaker
やAFPTool
などのツールを使用して、マスクROMのRKDevTool(ここから)を通じてフラッシュできるupdate.imgを作成します。RKDevToolには、マスクROMを作成するために必要な前述の2つのバイナリが含まれています)アップデートパッケージ。
RKDevTool はデフォルトで中国語で提供されており、多かれ少なかれ役に立たないファームウェアの検証チェックが含まれていますが、.ini を使用して無効にすることができます。
[Language]
Selected=2
そして
FW_NOT_CHECK=TRUE
RB_CHECK_OFF=TRUE
CHECK_MACHINE_MODEL=FALSE
Rockchip SDK とツールの状況は非常に細分化されているため、全体として、このプロセスを理解するのは楽しい経験でした。
これらのファイルは完全な update.img に必要です。これらは、作成したパーティションのバックアップなどの場所から入手したり、部分的には上記の SDK やグーグルから入手したりできます。
krnl ファイルが存在するのは、生の .img ファイルを Rockchip 互換形式 (.img.krnl) に変換する imgRePackerRK (ダウンロード) というツールを使用するツールチェーンを作成したためです。
このツールは明らかに RKImageMaker と AFPTool を置き換え、Rockchip update.img を作成するためのオールインワン ソリューションとなるように作られています。しかし、それは私にとって一貫した結果を生み出すことはありません。
ただし、Rockchip リカバリと互換性のあるカーネル、ブート、およびリカバリ イメージを変換します。
Imageboot.img.krnl と Imageboot.img
そこで、これを使用して .krnl ファイルを簡単に作成し、次に、toolchain.bat を実行して、元の .img ファイルと .krnl ファイルを保持したまま、機能する update.img を構築します。
move Imageboot.img Imageboot.img.tmp
move Imagerecovery.img Imagerecovery.img.tmp
move Imagekernel.img Imagekernel.img.tmp
move Imageboot.img.krnl Imageboot.img
move Imagerecovery.img.krnl Imagerecovery.img
move Imagekernel.img.krnl Imagekernel.img
copy Imageparameter.txt .parameter
Afptool -pack ./ Imagetmp-update.img
RKImageMaker.exe -RKPX30 ImageMiniLoaderAll.bin Imagetmp-update.img update.img -os_type:androidos
move Imageboot.img Imageboot.img.krnl
move Imagerecovery.img Imagerecovery.img.krnl
move Imagekernel.img Imagekernel.img.krnl
move Imageboot.img.tmp Imageboot.img
move Imagerecovery.img.tmp Imagerecovery.img
move Imagekernel.img.tmp Imagekernel.img
del Imagetmp-update.img
pause
途中で役立つように、互換性のある/Image/parameter.txt
もここにあります。