
CVE-2021-43408の技術的分析および概念実証エクスプロイト。WordPressプラグインDuplicate Postバージョン1.1.9におけるSQLインジェクション脆弱性を対象とし、段階的な悪用ガイドと修正アドバイスを含みます。
WordPressは、オープンソースのCMS(コンテンツ管理システム)ソフトウェアです。HTMLコーディング言語を使用する代わりに、WordPressはPHPプログラミング言語で記述され、MySQLデータベースプラットフォームを使用しています。WordPressはプログラマーのMatt Mullenweg氏とMike Little氏によって設立されました。現在WordPressは、米国カリフォルニア州サンフランシスコに拠点を置くAutomattic社が所有しています。
WordPressプラグインDuplicate Postのバージョン1.1.9以下にSQLインジェクションの脆弱性が存在します。この種の攻撃により、攻撃者はSQLクエリを注入し、データベース内のリソースを読み取り、変更、さらには削除することができます。
この脆弱性は、プラグインDuplicate Postの機能を使用できる認証済みユーザーであれば誰でも悪用される可能性があります。デフォルトでは管理者のみがこの権限を持っていますが、権限は編集者、投稿者、寄稿者、さらには購読者でもこのプラグインを使用できるように変更される可能性があります。
CVE-2021-43408は2021年11月19日に発見され、CVSSスコアでHIGH(高)の評価を受けています。

この脆弱性の根本的な原因は、ユーザーからのリクエストで送信されたデータがSQL実行前にサニタイズされていないことにあります。
具体的には、post/handler.phpファイルのcdp_insert_post()関数内です。
function cdp_insert_post($id, $data, $times, $areWePro, $isChild = false, $p_ids = null, $site) {
// Get Wordpress database
global $wpdb;
// Create empty array for new id(s) and error(s)
$results = array('ids' => array(), 'error' => 0, 'counter' => 0);
// Get Counter value
$prefix = (($site != -1) ? $wpdb->get_blog_prefix($site) : $wpdb->get_blog_prefix());
$newestId = $wpdb->get_results("SELECT post_id FROM {$prefix}postmeta WHERE meta_key = '_cdp_origin' AND meta_value = {$id} ORDER BY post_id DESC LIMIT 1", ARRAY_A);
$idは攻撃者によって制御されます
変数$idは、サニタイズされずにSQLクエリを含む関数に渡されます。この関数はWordPress Ajaxのwp_ajax_cdp_action_handlingを介して呼び出されます。
パラメータidはcdp_sanitize_array関数を経由して渡され、ここで投稿のデータフィールドはsanitize_text_field関数を通過し、データ文字列内の引用符'をエスケープします。

データフィールドは
sanitize_text_fieldで処理されます
しかし、コードには整数フィールド(idフィールド)のデータをSQL実行クエリに渡す際の脆弱性があり、攻撃者はこれを悪用してこのフィールドの値に追加のSQL文を注入することができます。したがって、SQLクエリを制御するために、攻撃者は引用符'の使用を避けるだけで済みます。
Step 1: 管理者ユーザーとしてログインし、プラグインDuplicate Postバージョン1.1.9をインストールします。このプラグインは、既存の投稿を複製する機能を提供します。

Step 2: 「投稿」セクションにアクセスし、1つの投稿を選択し、アクションコピーを選択して適用をクリックします。

Step 3: 「設定:デフォルト」を選択し、コピーをクリックします。

Step 4: HTTPリクエストをインターセプトします。ここで注目すべきデータフィールドはidです。このフィールドのデータは整数型であることがわかります。

Step 5: SQLインジェクションペイロードを挿入し、リクエストを送信すると、9秒後にサーバーから応答が返ってきます -> SQLインジェクションが成功しました。
ペイロード: 1 and (select*from(select(sleep(9)))a)--

