동적 링크 라이브러리 검색 순서

동일한 DLL(동적 연결 라이브러리)의 여러 버전이 OS(운영 체제) 내의 다른 파일 시스템 위치에 존재하는 것이 일반적입니다. 전체 경로를 지정하여 지정된 DLL이 로드되는 특정 위치를 제어할 있습니다. 그러나 해당 메서드를 사용하지 않는 경우 시스템은 이 항목에 설명된 대로 로드 시 DLL을 검색합니다. DLL 로더는 DLL을 로드하고 DLL에 대한 참조를 확인하는 운영 체제(OS)의 일부입니다.

패키지된 앱과 패키지되지 않은 앱에 대한 정의는 앱 패키징의 장점 및 단점을 참조하세요.

검색에 영향을 주는 요소

다음은 이 항목에서 설명하는 몇 가지 특별한 검색 요소입니다. DLL 검색 순서의 일부로 간주할 수 있습니다. 이 항목의 뒷부분 섹션에서는 특정 앱 유형에 대한 적절한 검색 순서와 다른 검색 위치로 이러한 요소를 나열합니다. 이 섹션은 개념을 소개하고 항목의 뒷부분에서 참조하는 데 사용할 이름을 제공하기 위한 것입니다.

  • DLL 리디렉션. 자세한 내용은 동적 링크 라이브러리 리디렉션을 참조하세요.
  • API 집합. 자세한 내용은 Windows API 집합을 참조하세요.
  • SxS(Side-by-Side) 매니페스트 리디렉션 - 데스크톱 앱만(UWP 앱 아님) 애플리케이션 매니페스트(병렬 애플리케이션 매니페스트 또는 Fusion 매니페스트라고도 함)를 사용하여 리디렉션할 수 있습니다. 자세한 내용은 매니페스트를 참조하세요.
  • 로드된 모듈 목록입니다. 시스템에서 동일한 모듈 이름을 가진 DLL이 이미 메모리에 로드되었는지 확인할 수 있습니다(로드된 폴더에 관계없이).
  • 알려진 DLL. DLL이 애플리케이션이 실행 중인 Windows 버전의 알려진 DLL 목록에 있는 경우 시스템은 알려진 DLL의 복사본(및 알려진 DLL의 종속 DLL(있는 경우)을 사용합니다. 현재 시스템의 알려진 DLL 목록은 레지스트리 키 를 참조하세요 HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\KnownDLLs.

DLL에 종속성이 있는 경우 시스템은 모듈 이름만 사용하여 로드된 것처럼 종속 DLL을 검색합니다. 첫 번째 DLL이 전체 경로를 지정하여 로드된 경우에도 마찬가지입니다.

패키지된 앱에 대한 검색 순서

패키지된 앱이 LoadPackagedLibrary 함수를 호출하여 패키지된 모듈(특히 라이브러리 모듈- .dll 파일)을 로드하는 경우 DLL은 프로세스의 패키지 종속성 그래프에 있어야 합니다. 자세한 내용은 LoadPackagedLibrary를 참조하세요. 패키지된 앱이 다른 방법으로 모듈을 로드하고 전체 경로를 지정하지 않는 경우 시스템은 이 섹션에 설명된 대로 로드 시 DLL 및 해당 종속성을 검색합니다.

시스템에서 모듈 또는 해당 종속성을 검색할 때는 항상 패키지된 앱에 대한 검색 순서를 사용합니다. 종속성이 패키지된 앱 코드가 아닌 경우에도 입니다.

패키지된 앱에 대한 표준 검색 순서

시스템은 다음 순서로 검색합니다.

  1. DLL 리디렉션.
  2. API 집합.
  3. 데스크톱 앱만(UWP 앱 아님) SxS 매니페스트 리디렉션.
  4. 로드된 모듈 목록입니다.
  5. 알려진 DLL.
  6. 프로세스의 패키지 종속성 그래프입니다. 애플리케이션의 패키지와 애플리케이션 패키지 매니페스트의 섹션에 <Dependencies> 지정된 <PackageDependency> 종속성입니다. 종속성은 매니페스트에 표시되는 순서대로 검색됩니다.
  7. 호출 프로세스가 로드된 폴더(실행 파일의 폴더)입니다.
  8. 시스템 폴더(%SystemRoot%\system32)입니다.

DLL에 종속성이 있는 경우 시스템은 모듈 이름만 사용하여 로드된 것처럼 종속 DLL을 검색합니다(첫 번째 DLL이 전체 경로를 지정하여 로드된 경우에도).

패키지된 앱에 대한 대체 검색 순서

모듈이 LOAD_WITH_ALTERED_SEARCH_PATHLoadLibraryEx 함수를 호출하여 표준 검색 순서를 변경하는 경우 검색 순서는 7단계에서 시스템이 실행 파일의 폴더 대신 지정된 모듈이 로드된 폴더(최상위 로딩 모듈의 폴더)에서 검색한다는 점을 제외하고 표준 검색 순서와 동일합니다.

패키지되지 않은 앱에 대한 검색 순서

패키지되지 않은 앱이 모듈을 로드하고 전체 경로를 지정하지 않으면 시스템은 이 섹션에 설명된 대로 로드 시 DLL을 검색합니다.

중요

공격자가 검색된 디렉터리 중 하나를 제어하는 경우 해당 폴더에 DLL의 악의적인 복사본을 배치할 수 있습니다. 이러한 공격을 방지하는 방법은 동적 링크 라이브러리 보안을 참조하세요.

패키지되지 않은 앱에 대한 표준 검색 순서

시스템에서 사용하는 표준 DLL 검색 순서는 안전한 DLL 검색 모드 가 사용되는지 여부에 따라 달라집니다.

안전 DLL 검색 모드(기본적으로 사용하도록 설정됨)는 사용자의 현재 폴더를 나중에 검색 순서로 이동합니다. 안전한 DLL 검색 모드를 HKEY_LOCAL_MACHINE\System\CurrentControlSet\Control\Session Manager\SafeDllSearchMode 사용하지 않도록 설정하려면 레지스트리 값을 만들고 0으로 설정합니다. SetDllDirectory 함수를 호출하면 안전한 DLL 검색 모드를 효과적으로 사용하지 않도록 설정하고(지정된 폴더가 검색 경로에 있는 동안) 이 항목에 설명된 대로 검색 순서를 변경합니다.

안전한 DLL 검색 모드를 사용하는 경우 검색 순서는 다음과 같습니다.

  1. DLL 리디렉션.
  2. API 집합.
  3. SxS 매니페스트 리디렉션.
  4. 로드된 모듈 목록입니다.
  5. 알려진 DLL.
  6. Windows 11 버전 21H2(10.0; 빌드 22000) 이상. 프로세스의 패키지 종속성 그래프입니다. 애플리케이션의 패키지와 애플리케이션 패키지 매니페스트의 섹션에 <Dependencies> 지정된 <PackageDependency> 종속성입니다. 종속성은 매니페스트에 표시되는 순서대로 검색됩니다.
  7. 애플리케이션이 로드된 폴더입니다.
  8. 시스템 폴더입니다. GetSystemDirectory 함수를 사용하여 이 폴더의 경로를 검색합니다.
  9. 16비트 시스템 폴더입니다. 이 폴더의 경로를 가져오는 함수는 없지만 검색됩니다.
  10. Windows 폴더입니다. GetWindowsDirectory 함수를 사용하여 이 폴더의 경로를 가져옵니다.
  11. 현재 폴더입니다.
  12. 환경 변수에 PATH 나열된 디렉터리입니다. 여기에는 App Paths 레지스트리 키로 지정된 애플리케이션별 경로가 포함되지 않습니다. 앱 경로 키는 DLL 검색 경로를 계산할 때 사용되지 않습니다.

안전한 DLL 검색 모드를 사용하지 않도록 설정하면 현재 폴더 가 7단계 바로 뒤의 시퀀스에서 위치 11에서 위치 8로 이동한다는 점을 제외하고 검색 순서는 동일합니다. 애플리케이션이 로드된 폴더입니다.)

패키지되지 않은 앱에 대한 대체 검색 순서

시스템에서 사용하는 표준 검색 순서를 변경하려면 LOAD_WITH_ALTERED_SEARCH_PATHLoadLibraryEx 함수를 호출할 수 있습니다. SetDllDirectory 함수를 호출하여 표준 검색 순서를 변경할 수도 있습니다.

참고

프로세스의 표준 검색 순서는 현재 프로세스가 시작되기 전에 부모 프로세스에서 SetDllDirectory 함수를 호출하여 영향을 받습니다.

대체 검색 전략을 지정하는 경우 연결된 모든 실행 모듈이 배치될 때까지 해당 동작이 계속됩니다. 시스템이 DLL 초기화 루틴 처리를 시작하면 시스템이 표준 검색 전략으로 되돌아갑니다.

호출이 LOAD_WITH_ALTERED_SEARCH_PATH 지정하고 lpFileName 매개 변수가 절대 경로를 지정하는 경우 LoadLibraryEx 함수는 대체 검색 순서를 지원합니다.

  • 표준 검색 전략은 호출 애플리케이션의 폴더에서 (초기 단계 이후) 시작됩니다.
  • LoadLibraryEx에서 LOAD_WITH_ALTERED_SEARCH_PATH 사용하여 지정한 대체 검색 전략은 LoadLibraryEx가 로드하는 실행 모듈의 폴더에서 (초기 단계 이후) 시작됩니다.

이것이 그들이 다른 유일한 방법입니다.

안전한 DLL 검색 모드를 사용하는 경우 대체 검색 순서는 다음과 같습니다.

1~6단계는 표준 검색 순서와 동일합니다.

  1. lpFileName으로 지정된 폴더입니다.
  2. 시스템 폴더입니다. GetSystemDirectory 함수를 사용하여 이 폴더의 경로를 검색합니다.
  3. 16비트 시스템 폴더입니다. 이 폴더의 경로를 가져오는 함수는 없지만 검색됩니다.
  4. Windows 폴더입니다. GetWindowsDirectory 함수를 사용하여 이 폴더의 경로를 가져옵니다.
  5. 현재 폴더입니다.
  6. 환경 변수에 PATH 나열된 디렉터리입니다. 여기에는 App Paths 레지스트리 키로 지정된 애플리케이션별 경로가 포함되지 않습니다. 앱 경로 키는 DLL 검색 경로를 계산할 때 사용되지 않습니다.

안전한 DLL 검색 모드를 사용하지 않도록 설정한 경우 현재 폴더 가 7단계 직후 시퀀스에서 위치 11에서 위치 8로 이동한다는 점을 제외하고 대체 검색 순서는 동일합니다 . lpFileName으로 지정된 폴더).

lpPathName 매개 변수가 경로를 지정하는 경우 SetDllDirectory 함수는 대체 검색 순서를 지원합니다. 대체 검색 순서는 다음과 같습니다.

1~6단계는 표준 검색 순서와 동일합니다.

  1. 애플리케이션이 로드된 폴더입니다.
  2. SetDllDirectorylpPathName 매개 변수로 지정된 폴더입니다.
  3. 시스템 폴더입니다.
  4. 16비트 시스템 폴더입니다.
  5. Windows 폴더입니다.
  6. 환경 변수에 PATH 나열된 디렉터리입니다.

lpPathName 매개 변수가 빈 문자열인 경우 호출은 검색 순서에서 현재 폴더를 제거합니다.

SetDllDirectory 는 지정된 폴더가 검색 경로에 있는 동안 안전한 DLL 검색 모드를 효과적으로 사용하지 않도록 설정합니다. SafeDllSearchMode 레지스트리 값을 기반으로 안전한 DLL 검색 모드를 복원하고 현재 폴더를 검색 순서로 복원하려면 lpPathName을 NULL로 사용하여 SetDllDirectory를 호출합니다.

LOAD_LIBRARY_SEARCH 플래그를 사용하여 순서 검색

LoadLibraryEx 함수와 함께 하나 이상의 LOAD_LIBRARY_SEARCH 플래그를 사용하여 검색 순서를 지정할 수 있습니다. SetDefaultDllDirectories 함수와 함께 LOAD_LIBRARY_SEARCH 플래그를 사용하여 프로세스에 대한 DLL 검색 순서를 설정할 수도 있습니다. AddDllDirectory 또는 SetDllDirectory 함수를 사용하여 프로세스 DLL 검색 순서에 대한 추가 디렉터리를 지정할 수 있습니다.

검색되는 디렉터리는 SetDefaultDllDirectories 또는 LoadLibraryEx로 지정된 플래그에 따라 달라집니다. 둘 이상의 플래그를 사용하는 경우 해당 디렉터리를 다음 순서로 검색합니다.

  1. LOAD_LIBRARY_SEARCH_DLL_LOAD_DIR. DLL이 포함된 폴더가 검색됩니다. 이 폴더는 로드할 DLL의 종속성에 대해서만 검색됩니다.
  2. LOAD_LIBRARY_SEARCH_APPLICATION_DIR. 애플리케이션 폴더가 검색됩니다.
  3. LOAD_LIBRARY_SEARCH_USER_DIRS. AddDllDirectory 함수 또는 SetDllDirectory 함수를 사용하여 명시적으로 추가된 경로가 검색됩니다. 둘 이상의 경로를 추가하면 경로를 검색하는 순서가 지정되지 않습니다.
  4. LOAD_LIBRARY_SEARCH_SYSTEM32. 시스템 폴더가 검색됩니다.

LOAD_LIBRARY_SEARCH 플래그 없이 LoadLibraryEx를 호출하거나 프로세스에 대한 DLL 검색 순서를 설정하는 경우 시스템은 표준 검색 순서 또는 대체 검색 순서를 사용하여 DLL을 검색합니다.