php / php/php-src

PHP on Windows should not rely on PATH for loading its DLL dependencies

オープン
#10,082 コメント 5 件 リアクション 1 件 担当者 0 名 GitHub で見る

まだ誰も着手していません。

Category: Engine Feature OS: Windows Status: Needs Triage
主要言語
C
スター
40.4k
フォーク
8.1k
平均マージ
2日 13時間
マージ済み PR(30日)
96

説明

There is a longstanding issue with mod_php for Apache when PHP extensions can't be loaded without adding PHP directory to PATH because they rely on some libraries which are in the root PHP directory, and the OS looks for them in the root Apache directory by default. Also, it causes an issue when a user has a few versions of PHP installed (with separate copies of Apache), one of them is in the PATH, and all the others try to load their extensions from that directory in PATH, and fail.

It is possible to resolve this issue by adding the directory of php_mod dll into the list of dll directories of current process. You should use the AddDllDirectory (supported in Windows 7+ since 2011) to specify additional DLL search path. It could be made in the DllMain of the php8apache2_4.dll like this:

#define WIN32_LEAN_AND_MEAN
#include <windows.h>
#include <shlwapi.h>

BOOL APIENTRY DllMain(HMODULE hmodule, DWORD dwreason, LPVOID lpreserved)
{
	static DLL_DIRECTORY_COOKIE dircookie = nullptr;

	switch (dwreason)
	{
	case DLL_PROCESS_ATTACH:

		SetDefaultDllDirectories(LOAD_LIBRARY_SEARCH_DEFAULT_DIRS);

		TCHAR path[MAX_PATH];
		if (GetModuleFileName(hmodule, path, MAX_PATH))
		{
			PathRemoveFileSpec(path);
			dircookie = AddDllDirectory(path);
		}

		break;

	case DLL_PROCESS_DETACH:

		if (dircookie)
		{
			RemoveDllDirectory(dircookie);
			dircookie = nullptr;
		}

		break;
	}

	return TRUE;
}

Another option would be using AddDllDirectory during early initialization and passing LOAD_LIBRARY_SEARCH_DEFAULT_DIRS to every LoadLibrary call.

It makes sense to implement this for better security because a lot of unexpected things can be in PATH and load instead of what was expected. It will also resolve issues like #10076. This issue was already discussed in the mailing list and Christoph M. Becker agreed that it is OK to include such change.

コントリビューションガイド

コントリビューションガイドを開く

はじめの一歩

  1. issue を最後まで読み、次にプロジェクトのコントリビューションガイドを読みます。
  2. 着手することを issue にコメントします — 二人が同じ作業をするのを防げます。
  3. リポジトリをフォークし、ブランチを切って変更します。
  4. issue 番号を参照したプルリクエストを送ります。

調査の方向性

まず、Windows Apache モジュールのエントリポイントである php8apache2_4.dll と、既存の LoadLibrary 呼び出しをすべて特定します。提案されている DllMain/AddDllDirectory アプローチと、その Windows 7 サポート要件を確認し、その後、PHP と Apache を分離してインストールした環境で拡張機能の読み込みを検証します。依存関係が PATH なしで読み込まれ、関連する #10076 の失敗がプロセスのクリーンアップを壊すことなく解決されれば完了です。

索引モデルが issue の本文から書いたものです。

評価

技術スタック
c, php
領域
backend, operating-systems, security
issue の種類
バグ
難易度
4/5
見積もり時間
3〜5日
活発さ
停滞
明瞭さ
おおむね明確
初心者へのやさしさ
35/100

新しい issue をメールで受け取る

初心者向けの GitHub issue を短くまとめたダイジェスト。