2011년 7월 12일 Windows VISTA Service Pack 1(SP1)에 대한 지원이 종료됩니다. 서비스 팩 2(Windows)를 Windows Vista를 실행 중인지 확인합니다. 자세한 내용은 이 Microsoft 웹 페이지를 참조하세요. 지원은일부 버전의 에 대한 Windows.

애플리케이션이 완전히 자격을 갖춘 경로를 지정하지 않고 DLL(동적 링크 라이브러리)을 동적으로 로드하는 경우 Windows 잘 정의된 디렉터 집합을 검색하여 DLL을 찾습니다. 공격자가 디렉터 중 하나를 제어하는 경우 애플리케이션이 예상한 DLL 대신 DLL의 악의적인 복사본을 로드할 수 있습니다. 이러한 공격은 "DLL 미리 로드 공격"으로 알려져 있으며 공유 DLL 라이브러리를 동적으로 로드하는 모든 운영 체제에 일반적입니다. 이러한 공격의 효과는 공격자가 애플리케이션을 실행하는 사용자의 컨텍스트에서 코드를 실행할 수 있다는 것입니다. 애플리케이션이 관리자 권한으로 실행되는 경우 권한의 로컬 상승으로 이어질 수 있습니다. 이러한 공격에 대한 관심이 갱신된 것을 알고 있습니다. 이 문제가 상호 고객에게 영향을 미치기 위해 개발자 커뮤니티에 이 문서를 공개하여 이 문제를 알고 애플리케이션에서 문제를 해결하기 위해 필요한 도구를 제공합니다.

요약

DLL 미리 로드 공격에 대한 설명

LoadLibrary 기반 공격

애플리케이션이 완전히 자격을 갖춘 경로를 지정하지 않고 DLL을 동적으로 로드하는 경우 Windows 잘 정의된 디렉터 집합(DLL 검색 순서)을 통해 선형으로 검색하여 이 DLL을 찾습니다. DLL Windows 검색 순서 내에서 DLL을 찾으면 해당 DLL이 로드됩니다. 그러나 DLL Windows 디렉터에서 DLL을 찾지 못하면 DLL 로드 작업에 오류가 반환됩니다. 다음은 DL을 동적으로 로드하는 데 사용되는 LoadLibraryLoadLibraryEx함수에 대한 DLL 검색 순서입니다.

  1. 응용 프로그램이 로드되는 디렉터리

  2. 시스템 디렉터리

  3. 16비트 시스템 디렉터리

  4. Windows 디렉터리

  5. 현재 작업 디렉터리(CWD)

  6. PATH 환경 변수에 나열되는 디렉터리

다음 시나리오를 고려합니다.

  • 애플리케이션은 애플리케이션의 CWD에서 찾을 것으로 예상되는 정식 경로를 지정하지 않고 DLL을 로드합니다.

  • 애플리케이션은 DLL을 찾지 못하면 대소문자 처리를 완전히 준비합니다.

  • 공격자는 애플리케이션에 대한 이 정보를 알고 있으며 CWD를 제어합니다.

  • 공격자는 CWD에서 자체적으로 만든 DLL 버전을 복사합니다. 이 경우 공격자가 이 작업을 할 수 있는 권한이 있는 것으로 가정합니다.

  • Windows DLL 검색 순서의 디렉터를 검색하고 애플리케이션의 CWD에서 DLL을 찾습니다.

이 시나리오에서는 특수하게 만들어진 DLL이 애플리케이션 내에서 실행하고 현재 사용자의 권한을 얻습니다.이 공격을 방지하기 위해 애플리케이션은 빈 문자열("")을 사용하여 SetDllDirectory API를 호출하여 DLL 검색 경로에서 현재 작업 디렉터리(CWD)를 제거할 수 있습니다. 애플리케이션이 현재 디렉터리에서 DLL을 로드하는 데 의존하는 경우 현재 작업 디렉터리를 구하고 해당 디렉터리를 사용하여 LoadLibrary의정식 경로를 전달합니다.또한 일부 개발자는 LoadLibrary를 사용하여 특정 DLL이 있는지 여부를 검사하여 사용자가 실행되는 Windows 확인할 수 있습니다. 애플리케이션이 취약해질 수 있다는 것을 알고 있어야 합니다. 애플리케이션이 실행되는 Windows 릴리스에 영향을 받는 라이브러리가 실제로 없는 경우 공격자는 동일한 이름의 라이브러리를 CWD에 도입할 수 있습니다. 이 기술을 사용하는 것이 좋습니다. 대신 MSDN 문서인 "시스템 버전 다운로드"에 설명된 권장되는 기술을 사용합니다. 타사 플러그 인을 로드하고 해당 LoadLibrary 호출에 대해 자격을 갖춘 경로를 사용할 수 없는 애플리케이션은 SetDllDirectory("")를 호출하여 CWD를 제거한 다음 SetDllDirectory("플러그 인 설치 위치")를 호출하여 플러그 인 설치 디렉터리를 DLL 검색 경로에 추가해야 합니다.

SearchPath 기반 공격

애플리케이션이 SearchPath API를 사용하여 DLL을 찾고 SearchPath에서 반환되는 경로를 동적으로 로드하는 경우 비슷한 공격이 있습니다. 다음은 SearchPath API에 대한 기본 검색 순서입니다.

  • 응용 프로그램이 로드되는 디렉터리

  • 현재 작업 디렉터리(CWD)

  • 시스템 디렉터리

  • 16비트 시스템 디렉터리

  • Windows 디렉터리

  • PATH 환경 변수에 나열되는 디렉터리

안전하지 않은 경우 이 패턴을 권장하지 않습니다. 출력의 의도된 사용이 LoadLibrary 함수에 대한 호출에 있는 .dll 파일을 찾기 위한 방법으로 SearchPath 함수를 사용하지 않는 것이 좋습니다. SearchPath 함수의 검색 순서가 LoadLibrary 함수에서 .dll 검색 순서와 다르기 때문에 잘못된 검색 파일을 찾을 수 있습니다. 파일을 찾아 로드해야 하는 .dll LoadLibrary 함수를 사용 합니다.

ShellExecute 및 CreateProcess

개발자가 ShellExecuteCreateProcess와같은 유사한 함수를 호출하여 외부 실행을 로드할 때 이러한 문제의 변형이 있을 수도 있습니다. 개발자는 이진을 로드할 때 주의하고 완전히 자격을 갖춘 경로를 지정하는 것이 좋습니다. 라이브러리 대신 이진을 로드할 때 복잡성이 줄어 집니다.

소프트웨어 개발자를 위한 권장 단계

개발자는 다음을 하는 것이 좋습니다.

  • 비보안 라이브러리 로드의 인스턴스에 대한 애플리케이션의 유효성을 검사합니다(각 예제는 이 문서의 나중에 제공). 여기에는 다음이 포함됩니다.

    • SearchPath를 사용하여 라이브러리 또는 구성 요소의 위치를 식별합니다.

    • LoadLibrary를 사용하여 운영 체제의 버전을 식별합니다.

  • LoadLibrary, CreateProcesss 및 ShellExecute에 대한 모든 호출에 대해 완전히 자격을 갖춘 경로를 사용할 수 있습니다.

  • 빈 문자열(")을 사용하여 SetDllDirectory에 대한 호출을 구현하여 필요한 기본 DLL 검색 순서에서 현재 작업 디렉터리를 제거합니다. SetDllDirectory는 전체 프로세스에 영향을 미치고 있습니다. 따라서 LoadLibrary에 대한 호출 전후가 아닌 프로세스 초기화 초기에 이 작업을 해야 합니다. SetDllDirectory는 전체 프로세스에 영향을 주기 때문에 다른 값을 사용하여 SetDllDirectory를 호출하는 여러 스레드가 정의되지 않은 동작을 일으킬 수 있습니다. 또한 프로세스가 타사 DL을 로드하도록 디자인된 경우 프로세스 전체 설정을 수행하면 비호반성 문제가 발생할지 여부를 확인하는 테스트가 필요합니다. 알려진 문제는 애플리케이션이 Visual Basic for Applications 프로세스 전체 설정으로 인해 비호반성 문제가 발생할 수 있습니다.

  • SetSearchPathMode함수를 사용하여 프로세스에 대한 안전한 프로세스 검색 모드를 사용하도록 설정합니다. 그러면 프로세스의 수명에 대한 SearchPath 검색 목록의 마지막 장소로 현재 작업 디렉터리가 이동됩니다.

  • 안전 검색 모드를 사용하도록 설정되어 있는 경우에도 DLL 미리 로드 공격이 발생할 수 있기 때문에 SearchPath를 사용하여 완전히 자격을 갖춘 경로를 지정하지 않고 DLL의 존재를 확인하지 않도록 합니다.

안전하지 않은 라이브러리 부하 식별에 대한 지침

소스 코드에서 비보안 라이브러리 로드의 예는 다음과 같습니다.

  • 다음 코드 예제에서 애플리케이션은 최소 보안 검색 경로를 사용하여 "schannel.dll"를 검색합니다. 공격자가 CWD에 schannel.dll 수 있는 경우 애플리케이션이 적절한 라이브러리에 대한 Windows 검색하기 전에도 로드됩니다.

    DWORD retval = SearchPath(NULL, "schannel", ".dll", err, result, NULL); HMODULE handle = LoadLibrary(result);
  • 다음 코드 예제에서 애플리케이션은 LoadLibrary() 호출에 대해 이 문서의 시작부에 설명된 다양한 애플리케이션 및 운영 체제 위치에서 라이브러리를 로드합니다. 파일이 없는 위험이 있는 경우 애플리케이션이 현재 작업 디렉터리에서 파일을 로드하려고 할 수 있습니다. 이 시나리오는 이전 예제보다 약간 덜 위험합니다. 그러나 환경이 완전히 예측할 수 없는 경우 애플리케이션 사용자가 위험에 노출됩니다.

    HMODULE handle = LoadLibrary("schannel.dll");

다음은 더 안전하고 안전한 라이브러리 로드의 예입니다.

  • 다음 코드 예제에서는 완전히 자격을 갖춘 경로를 사용하여 라이브러리를 직접 로드합니다. 애플리케이션의 대상 디렉터리에 대한 쓰기 권한이 없는 경우 공격자가 악성 코드를 도입할 위험이 없습니다.

    HMODULE handle = LoadLibrary("c:\\windows\\system32\\schannel.dll");

    참고 시스템 디렉터리를 결정하는 방법에 대한 자세한 내용은 다음 리소스인 GetSystemDirectory를 참조하세요.

    http://msdn.microsoft.com/en-us/library/ms724373%28VS.85%29.aspxSHGetKnownFolderPath

    http://msdn.microsoft.com/en-us/library/bb762188%28v=VS.85%29.aspx

  • 다음 코드 예제에서 LoadLibrary를 호출하기 전에 현재 작업 디렉터리가 검색 경로에서 제거됩니다. 이렇게 하면 공격자가 DLL 미리 로드 공격을 사용하기 위해 애플리케이션 디렉터리, Windows 디렉터리 또는 사용자 경로에 지정된 디렉터리를 제어해야 하기 때문에 위험이 크게 줄어듭니다.

    SetDllDirectory ("");HMODULE handle = LoadLibrary("schannel.dll");
  • 보안 업데이트 963027(MS09-014에서 설명)을설치한 모든 시스템에서 다음 코드는 검색 순서의 마지막 자리로 CWD를 영구적으로 이동합니다. 나중에 검색 모드를 변경하려고 하는 프로세스 내부에서 SetSearchPathMode 함수에 대한 호출이 실패합니다.

    SetDllDirectory ("");HMODULE handle = LoadLibrary("schannel.dll");
  • 다음 코드 예제에서 LoadLibrary를 호출하기 전에 현재 작업 디렉터리가 검색 경로에서 제거됩니다. 이렇게 하면 공격자가 DLL 미리 로드 공격을 사용하기 위해 애플리케이션 디렉터리, Windows 디렉터리 또는 사용자 경로에 지정된 디렉터리를 제어해야 하기 때문에 위험이 크게 줄어듭니다.

    SetSearchPathMode (BASE_SEARCH_PATH_ENABLE_SAFE_SEARCHMODE | BASE_SEARCH_PATH_PERMANENT );HMODULE handle = LoadLibrary("schannel.dll");

프로세스 모니터를 사용하여 비보안 부하를 동적으로 감지

Microsoft는 프로세스 모니터라는 도구를 게시합니다. 이 도구를 사용하면 개발자와 관리자가 실행 중인 프로세스의 동작을 면밀하게 추적할 수 있습니다. 프로세스 모니터를 사용하여 애플리케이션 중 하나가 이러한 종류의 문제로 취약할 수 있는지 여부를 동적으로 감지할 수 있습니다.

  • 프로세스 모니터를 다운로드하려면 다음 Microsoft 웹 페이지를 방문합니다.

    http://technet.microsoft.com/en-us/sysinternals/bb896645.aspx

  • CWD 집합을 특정 디렉터리로 설정하여 애플리케이션을 시작해 시도합니다. 예를 들어 파일 처리기가 애플리케이션에 할당된 확장이 있는 파일을 두 번 클릭합니다.

  • 다음 필터를 사용하여 프로세스 모니터 대체 텍스트

  • 취약한 경로가 적중되는 경우 DLL을 로드하기 위해 원격 파일 공유에 대한 호출이 대체 텍스트취약한 프로그램인 것을 나타냅니다.

추가 정보

자세한 내용은 다음 Microsoft 웹 페이지: 동적 링크 라이브러리 검색 순서를 방문하세요.

http://msdn.microsoft.com/en/library/ms682586(VS.85).aspxSearchPath 함수의 MSDN 설명서

http://msdn.microsoft.com/en/library/aa365527(VS.85).aspxLoadLibrary 함수에 대한 MSDN 설명서

http://msdn.microsoft.com/en-us/library/ms684175(VS.85).aspxSetDllDirectory 함수에 대한 MSDN 설명서

http://msdn.microsoft.com/en/library/ms686203(VS.85).aspxSetSearchPathMode 함수의 MSDN 설명서

http://msdn.microsoft.com/en/library/dd266735(VS.85).aspx데이비드 Leblanc, 보안 엔지니어가 블로그 게시물을 Microsoft Office

http://blogs.msdn.com/b/david_leblanc/archive/2008/02/20/dll-preloading-attacks.aspxDLL 미리 로드 공격에 대한 MSRC 엔지니어링 팀인 Andrew Roths의 블로그 게시물

http://blogs.technet.com/b/srd/archive/2009/04/14/ms09-014-addressing-the-safari-carpet-bomb-vulnerability.aspx

추가 리소스

도움이 더 필요하세요?

더 많은 옵션을 원하세요?

구독 혜택을 살펴보고, 교육 과정을 찾아보고, 디바이스를 보호하는 방법 등을 알아봅니다.

커뮤니티를 통해 질문하고 답변하고, 피드백을 제공하고, 풍부한 지식을 갖춘 전문가의 의견을 들을 수 있습니다.