Skip to content
KitploitKITPLOIT
ツールエクスプロイトブログ
Log in
提出
ツールエクスプロイトブログ
提出

ハッキング、侵入テスト、サイバーセキュリティツールをあなたのセキュリティアーセナルに!

Kitploitはハッキング、サイバーセキュリティ、ペネトレーションテストのツールディレクトリです。最新のプロジェクトアップデートを見つけて、脆弱性の発見、システム分析、テストの自動化、セキュリティの強化を行いましょう。

フィードお問い合わせプライバシー© 2026 Kitploit

ツールディレクトリ

カテゴリ

すべてのカテゴリを見る
Loading categories
OrganizerTransaction — CVE-2021-39749のPoC。Android 12L Betaで任意のActivityを起動できるようにするもの。 | Kitploit
ツール/GitHubGitHub/michalbednarski/organizertransaction
Androidセキュリティ脆弱性分析エクスプロイトモバイルアプリペンテストモバイルセキュリティ
GitHubmichalbednarski/organizertransaction

OrganizerTransaction

CVE-2021-39749のPoC。Android 12L Betaで任意のActivityを起動できるようにするもの。

リポジトリを見る

人気

すべて見る →

コミュニティで最も使われているツールを見つけましょう。

すべてのツールを探索

ツールコレクションを閲覧

すべてのツールを見る →
共有
3711724年前Kitploit レビュー済み

これはCVE-2021-39749のPoCであり、Android 12L Betaで、他のアプリのpermissionやexported設定に関係なく、そのアクティビティを起動できるようにするものです。

Android 12Lでは、TaskFragmentOrganizerへのアクセスは(意図的に)MANAGE_ACTIVITY_TASKS権限を必要としなくなりました

ここで提供されるアプリを使用するには、Hidden API Checksを無効にする必要があります。adb shell settings put global hidden_api_policy 1で無効にできます。これらはセキュリティ境界ではなく、既知のアプリベースのバイパスが存在します

このバグ(および元のレポートで言及された関連するいくつかのバグ)を修正するコミットは次のとおりです。

  1. startActivityInTaskFragmentがBinder.getCallingUid()に依存しなくなった
  2. ResolverActivityでrelinquishTaskIdentityが有効になった
  3. (他のアクティビティの起動には不要ですが、画面上での再配置、透明化、タップジャックを可能にします)TaskFragmentのSurfaceControlが提供されなくなった
  4. (ここではコードに示されていません。元のレポートでのみ言及されている問題です)ActivityRecord#appTokenをTaskFragmentOrganizerに送信するかどうかの決定が、pidベースからuidベースに変更された

android-12.1.0_r4をチェックアウトし、最初の3つのコミット(または最初の2つ。アプリは(ShutdownActivityを起動することで)デバイスをシャットダウンできますが、「ズームしてアルファを設定」チェックボックスは機能しません)をリバートできます。

(そのリストの最初のコミットは、リバートしようとするとテストでマージ競合が発生しますが、これらは無視できます)

常にシステムuidを返すBinder.getCallingUid()

Binder.getCallingUid()メソッドは、現在処理中のBinderトランザクションを送信したプロセスのuidを返します。そのuidはスレッドローカル変数に格納されます。トランザクションを処理するコードは、Binder.clearCallingIdentity()を呼び出して、その変数を自身のプロセスのuidに設定し、トランザクション処理中に後で呼び出されるメソッドに対して、権限チェックがBinderトランザクションの呼び出し元ではなく自身に対して行われるべきであることを示すことができます。

Binder.clearCallingIdentity()の後に常に呼び出されるため、常に自身のプロセスのuidを返すBinder.getCallingUid()が存在することがあります。これは意図的に行われる場合もあります。例えば、ActivityTaskManagerService#startDreamActivityなどです(ただし、これはProcess.myUid()やOs.getuid()を行うかなり回りくどい方法ですが)

私は自分用に、(Sootベースの)静的解析ツールを作成しました。これは、Binder.clearCallingIdentity()の後にのみ発生し得る、そのようなBinder.getCallingUid()呼び出し(およびその他の権限チェック)を報告します。(Sootが提供するJimple/Shimple IRを処理するカスタムロジックがありますが、Sootでそれを行うより良い方法があるかもしれません。しかし、それが現在私が持っているものです)

Android 12L Betaで、そのツールはActivityStartController#startActivityInTaskFragmentに1つ発見しました(注:Betaリリースはオープンソースではないため、当時ソースコードは利用できませんでしたが、Shimpleは一般的に読み取り可能なので、SootをJavaデコンパイラとしても使用していました)

startActivityInTaskFragmentの呼び出し方

静的解析レポートの一部として、onTransact()実装(Binder呼び出しが開始される場所)からstartActivityInTaskFragmentへの呼び出し階層を取得しました。

  1. IWindowOrganizerControllerのaidl生成コード内のonTransact
  2. WindowOrganizerController#applyTransaction(CallerInfo引数なし)
  3. WindowOrganizerController#applyTransaction(CallerInfo引数あり)
  4. WindowOrganizerController#applyHierarchyOp
  5. ActivityStartController#startActivityInTaskFragment

applyTransactionへのBinder呼び出しがTaskFragmentOrganizerクラスに存在することを発見し、すべてのBinder呼び出しを直接行うよりも便利なラッパーとして使用することにしました(どちらも公開APIではないため、いずれにせよリフレクションを使用する必要がありました)

まず、メソッド「2.」はenforceTaskPermissionを呼び出します。これはAndroid 12.0では、取得できないsignatureのみのMANAGE_ACTIVITY_TASKS権限をチェックしていましたが、Android 12Lではルールが緩和され、特定のトランザクションは権限なしで実行できるようになりました。startActivityInTaskFragmentの実行に必要な操作はどれも権限を必要としないことが判明しました(トランザクションにTaskFragmentOrganizerが関連付けられている場合)

したがって、HIERARCHY_OP_TYPE_START_ACTIVITY_IN_TASK_FRAGMENTを実行したいと考えています。そのためには、TaskFragmentをmLaunchTaskFragmentsに登録する必要があります。そうしないと、"Not allowed to operate with invalid fragment token"例外が報告されます。

HIERARCHY_OP_TYPE_CREATE_TASK_FRAGMENTを通じて、そのようなTaskFragmentを登録できます。これはcreateTaskFragment()を呼び出します。

(PoCコードでは、これらのトランザクションはSecondActivityで送信されます。HIERARCHY_OP_TYPE_CREATE_TASK_FRAGMENTはinitOrganizerAndFragment()によって送信され、HIERARCHY_OP_TYPE_START_ACTIVITY_IN_TASK_FRAGMENTはstartActivityInOrganizerによって送信されます)

これにより、startActivityInTaskFragmentを呼び出せるようになり、ここで起動されたアクティビティのインテントはシステムuidから送信されたものと見なされますが、それ自体では何もできないことが判明しました。システムによって起動されたアクティビティはURIグラントを実行できず、別のアプリのアクティビティを起動しようとすると、canEmbedActivityチェックによって停止されるためです。

canEmbedActivityのバイパス

canEmbedActivityをもう一度見てみましょう。taskFragment.getTask().effectiveUidがシステムのuidであるか、起動されたアプリのuidと一致する場合、埋め込みが許可されます。effectiveUidがシステムであるタスクに存在する必要があります。

ツールをダウンロード