다음을 통해 공유


처리 만들기

파일 시스템의 경우 대부분의 흥미로운 보안 작업은 IRP_MJ_CREATE 처리하는 동안 발생합니다. 들어오는 요청을 분석하고 호출자에게 작업을 수행할 적절한 권한이 있는지 여부를 확인하고 작업을 적절하게 부여하거나 거부해야 하는 단계입니다. 다행히 파일 시스템 개발자의 경우 대부분의 의사 결정 메커니즘은 보안 참조 모니터 내에서 구현됩니다. 따라서 대부분의 경우 파일 시스템은 적절한 보안 참조 모니터 루틴을 호출하여 액세스를 올바르게 결정해야 합니다. 파일 시스템에 대한 위험은 필요에 따라 이러한 루틴을 호출하지 못하고 호출자에 대한 액세스 권한을 부적절하게 부여할 때 발생합니다.

FAT 파일 시스템과 같은 표준 파일 시스템의 경우 IRP_MJ_CREATE 일부로 수행되는 검사는 주로 의미 체계 검사입니다. 예를 들어 FAT 파일 시스템에는 파일 또는 디렉터리의 상태에 따라 IRP_MJ_CREATE 처리가 허용되는지 확인하기 위한 수많은 검사가 있습니다. FAT 파일 시스템에서 수행한 이러한 검사에는 읽기 전용 미디어에 대한 검사(예: 읽기 전용 미디어에서 덮어쓰기 또는 대체와 같은 파괴적인 "만들기" 작업을 수행하려는 시도는 허용되지 않음), 공유 액세스 검사 및 oplock 검사가 포함됩니다. 이 분석에서 가장 어려운 부분 중 하나는 다른 수준 리소스의 상태(예: 볼륨 수준)로 인해 한 수준(예: 파일 수준)의 작업이 실제로 허용되지 않을 수 있음을 깨닫는 것입니다. 예를 들어 다른 프로세스가 볼륨을 단독으로 잠근 경우 파일을 열지 못할 수 있습니다. 검사 일반적인 경우는 다음과 같습니다.

  • 파일 수준이 열려 있는 경우 볼륨 수준 상태와 호환되는가요? 볼륨 수준 잠금을 준수해야 합니다. 따라서 한 프로세스에 배타적 볼륨 수준 잠금이 있는 경우 해당 프로세스 내의 스레드만 파일을 열 수 있습니다. 다른 프로세스의 스레드는 파일을 열 수 없습니다.

  • 파일 수준이 열려 있는 경우 미디어 상태와 호환되는가요? 특정 "만들기" 작업은 "만들기" 작업의 일부로 파일을 수정합니다. 여기에는 덮어쓰기, 대체 및 파일의 마지막 액세스 시간 업데이트가 포함됩니다. 이러한 "만들기" 작업은 읽기 전용 미디어에서 허용되지 않으며 마지막 액세스 시간은 업데이트되지 않습니다.

  • 볼륨 수준이 열려 있는 경우 파일 수준 상태와 호환되는가요? 볼륨에 열려 있는 기존 파일이 있는 경우 단독 볼륨 열기가 허용되지 않습니다. 이는 새 개발자가 볼륨을 열고 실패하는 것을 발견하려고 하기 때문에 일반적인 문제입니다. 이 오류가 발생하면 FSCTL_DISMOUNT_VOLUME 사용하여 열린 핸들을 무효화하고 강제로 분리하여 새로 탑재된 볼륨에 대한 단독 액세스를 허용할 수 있습니다.

또한 파일 특성은 호환되어야 합니다. 읽기 전용 특성이 있는 파일은 쓰기 액세스를 위해 열 수 없습니다. 일반 권한의 확장이 확장된 후 원하는 액세스를 확인해야 합니다. 예를 들어 FASTFAT 파일 시스템 내의 이 검사 FatCheckFileAccess 함수에 있습니다(WDK에 포함된 fastfat 샘플의 Acchksup.c 소스 파일 참조).

다음 코드 예제는 FAT 의미 체계와 관련이 있습니다. 또한 DACL을 구현하는 파일 시스템은 보안 참조 모니터 루틴(예: SeAccessCheck)을 사용하여 추가 보안 검사 수행합니다.

    //
    //  check for a read-only Dirent
    //

    if (FlagOn(DirentAttributes, FAT_DIRENT_ATTR_READ_ONLY)) {

        //
        //  Check the desired access for a read-only Dirent
        // Don't allow 
        //  WRITE, FILE_APPEND_DATA, FILE_ADD_FILE,
        //  FILE_ADD_SUBDIRECTORY, and FILE_DELETE_CHILD
        //

        if (FlagOn(*DesiredAccess, ~(DELETE |
                                     READ_CONTROL |
                                     WRITE_OWNER |
                                     WRITE_DAC |
                                     SYNCHRONIZE |
                                     ACCESS_SYSTEM_SECURITY |
                                     FILE_READ_DATA |
                                     FILE_READ_EA |
                                     FILE_WRITE_EA |
                                     FILE_READ_ATTRIBUTES |
                                     FILE_WRITE_ATTRIBUTES |
                                     FILE_EXECUTE |
                                     FILE_LIST_DIRECTORY |
                                     FILE_TRAVERSE))) {

            DebugTrace(0, Dbg, "Cannot open readonly\n", 0);

            try_return( Result = FALSE );
        }

FASTFAT에서 구현하는 더 미묘한 검사 호출자가 요청한 액세스가 FAT 파일 시스템이 인식하는 액세스인지 확인하는 것입니다(WDK에 포함된 fastfat 샘플의 Acchksup.c의 FatCheckFileAccess 함수에서).

다음 코드 예제에서는 파일 시스템 보안에 대 한 중요 한 개념을 보여 줍니다. 파일 시스템에 전달된 내용이 예상한 범위를 벗어나지 않는지 확인합니다. 보안 관점에서 보수적이고 적절한 접근 방식은 액세스 요청을 이해하지 못하면 해당 요청을 거부해야 한다는 것입니다.

    //
    // Check the desired access for the object. 
    // Reject what we do not understand.
    // The model of file systems using ACLs is that
    // they do not type the ACL to the object that the 
    // ACL is on. 
    // Permissions are not checked for consistency vs.
    // the object type - dir/file.
    //

    if (FlagOn(*DesiredAccess, ~(DELETE |
                                 READ_CONTROL |
                                 WRITE_OWNER |
                                 WRITE_DAC |
                                 SYNCHRONIZE |
                                 ACCESS_SYSTEM_SECURITY |
                                 FILE_WRITE_DATA |
                                 FILE_READ_EA |
                                 FILE_WRITE_EA |
                                 FILE_READ_ATTRIBUTES |
                                 FILE_WRITE_ATTRIBUTES |
                                 FILE_LIST_DIRECTORY |
                                 FILE_TRAVERSE |
                                 FILE_DELETE_CHILD |
                                 FILE_APPEND_DATA))) {

        DebugTrace(0, Dbg, "Cannot open object\n", 0);

        try_return( Result = FALSE );
    }

다행히 파일 시스템의 경우 초기 만들기 처리 중에 보안 검사 완료되면 I/O 관리자가 후속 보안 검사를 수행합니다. 따라서 예를 들어 I/O 관리자는 사용자 모드 애플리케이션이 읽기 액세스에 대해서만 열린 파일에 대해 쓰기 작업을 수행하지 않도록 합니다. 실제로 파일 시스템은 IRP_MJ_WRITE 디스패치 루틴 중에 읽기 전용으로만 열린 경우에도 파일 개체에 대해 읽기 전용 의미 체계를 적용하려고 시도해서는 안 됩니다. 이는 메모리 관리자가 특정 파일 개체를 지정된 섹션 개체와 연결하는 방식 때문입니다. 파일이 읽기 전용으로 열려 있더라도 해당 섹션을 통한 후속 쓰기는 파일 개체에 대한 IRP_MJ_WRITE 작업으로 전송됩니다. 즉, ObReferenceObjectByHandle에 의해 Nt 시스템 서비스 진입점에서 파일 핸들이 해당 파일 개체로 변환되면 액세스 적용이 수행됩니다.

파일 시스템 내에는 의미 체계 보안 검사를 "만들기" 처리와 유사하게 수행해야 하는 두 개의 추가 위치가 있습니다.

  • 이름 바꾸기 또는 하드 링크 처리 중.

  • 파일 시스템 제어 작업을 처리하는 경우.

처리 이름 바꾸기 및 파일 시스템 제어 처리는 후속 섹션에서 설명합니다.

이는 "만들기" 처리와 관련된 의미 체계 문제의 전체 목록이 아닙니다. 이 섹션의 목적은 파일 시스템 개발자를 위해 이러한 문제에 주의를 기울이는 것입니다. 특정 파일 시스템에 대한 모든 의미 체계 문제를 식별하고, 특정 의미 체계를 충족하도록 구현하고, 구현이 다양한 사례를 처리하는지 테스트해야 합니다.