⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 datastore.c

📁 miniFilter.rar所有框架代码以及对应的PPT资料,可以直接拿来进行修改即可完成各种驱动,是你开发微软新过滤构架驱动所必下资料
💻 C
📖 第 1 页 / 共 3 页
字号:
    }


    return status;;

}



NTSTATUS
FmmSetMetadataOpenTriggerFileObject (
    __inout PFLT_CALLBACK_DATA Cbd
    )
/*++

Routine Description:

    This routine sets the MetadataOpenTriggerFileObject in the instance context
    to the file object of the volume that triggered the release of the metadata file
    references.

Arguments:

    Cbd                 - Supplies a pointer to the callbackData which
                          declares the requested operation.

Return Value:

    Status

Note:

    This routine takes care of the synchronization needed to access the metadata
    file object and handle


--*/
{
    NTSTATUS status = STATUS_SUCCESS;
    PFMM_INSTANCE_CONTEXT instanceContext = NULL;

    PAGED_CODE();

    //
    //  Get the instance context
    //

    status = FltGetInstanceContext( Cbd->Iopb->TargetInstance,
                                    &instanceContext );
    if (!NT_SUCCESS( status )) {

        DebugTrace( DEBUG_TRACE_ERROR | DEBUG_TRACE_METADATA_OPERATIONS,
                    ("[Fmm]: FmmSetMetadataOpenTriggerFileObject -> Failed to get instance context.\n") );

        goto FmmSetMetadataOpenTriggerFileObjectCleanup;
    }

    //
    //  Acquire exclusive access to the instance context
    //

    FmmAcquireResourceExclusive( &instanceContext->MetadataResouce );

    if (FlagOn( instanceContext->Flags, INSTANCE_CONTEXT_F_TRANSITION)) {

        //
        //  If this instance context is in a transition state, it implies that
        //  the instance context lock has been released while sending an operation
        //  down to the file system. The reason for doing so is to prevent a potential
        //  deadlock if an underlying filter sends an IO to the top of the filter
        //  stack while we are holding the resource
        //
        //  We have managed to acquire this resource in this state of transition.
        //  It would be incorrect to use or modify the instance context in any way
        //  in this situation. So we simply let go.
        //

        status = STATUS_FILE_LOCK_CONFLICT;

        DebugTrace( DEBUG_TRACE_ERROR | DEBUG_TRACE_METADATA_OPERATIONS,
                    ("[Fmm]: FmmSetMetadataOpenTriggerFileObject -> Failed to get exclusive access to instance context since it is in a state of transition.\n") );
    } else {

        DebugTrace( DEBUG_TRACE_METADATA_OPERATIONS,
                    ("[Fmm]: FmmSetMetadataOpenTriggerFileObject -> Setting MetadataOpenTriggerFileObject to %p (OldValue = %p).\n",
                     Cbd->Iopb->TargetFileObject,
                     instanceContext->MetadataOpenTriggerFileObject) );


        //
        //  Save the volume file object as the trigger file object
        //

        ASSERT((instanceContext->MetadataOpenTriggerFileObject == NULL) ||
               (instanceContext->MetadataOpenTriggerFileObject = Cbd->Iopb->TargetFileObject));

        instanceContext->MetadataOpenTriggerFileObject = Cbd->Iopb->TargetFileObject;
    }

    //
    //  Relinquish exclusive access to the instance context
    //

    FmmReleaseResource( &instanceContext->MetadataResouce);


FmmSetMetadataOpenTriggerFileObjectCleanup:

    //
    // Release the references we have acquired
    //

    if (instanceContext != NULL) {

        FltReleaseContext( instanceContext );
    }


    return status;;
}

FORCEINLINE
VOID
FmmBeginFileSystemOperation (
    IN PFMM_INSTANCE_CONTEXT InstanceContext
    )
/*++

Routine Description:

    This routine must be called before the filter performs a file system operation
    if it is holding an exclusive lock to the instance context resource at the
    time it needs to perform the file system operation

Arguments:

    InstanceContext     - Supplies the instance context for this instance.

Return Value:

    Returns the status of this operation.

Note:

    The caller must hold the instance context resource exclusive when this routine is called.

--*/
{
    PAGED_CODE();

    //
    //  Release the instance context lock before sending an operation down to the
    //  file system. The reason for doing so is to prevent a potential deadlock if
    //  an underlying filter sends an IO to the top of the filter stack while we
    //  are holding the resource
    //
    //  Before we release the lock we mark the instance context to indicate it is
    //  in a transition state. Any other thread that finds the instance context in a
    //  transition state will not use or modify the  instance context
    //
    //  This thread can however continue to use/modify the instance context since it
    //  is guaranteed exclusive access. Other threads that see the instance context
    //  in a transition state will not use or modify the context
    //

    ASSERT( !FlagOn( InstanceContext->Flags, INSTANCE_CONTEXT_F_TRANSITION ) );

    SetFlag( InstanceContext->Flags, INSTANCE_CONTEXT_F_TRANSITION );

    //
    //  Relinquish exclusive access to the instance context
    //

    FmmReleaseResource( &InstanceContext->MetadataResouce);

}

FORCEINLINE
VOID
FmmEndFileSystemOperation (
    IN PFMM_INSTANCE_CONTEXT InstanceContext
    )
/*++

Routine Description:

    This routine must be called after the filter performs a file system operation
    if it was holding an exclusive lock to the instance context resource at the
    time it needed to perform the file system operation

Arguments:

    InstanceContext     - Supplies the instance context for this instance.

Return Value:

    Returns the status of this operation.

Note:

    The caller will hold the instance context resource exclusive when this routine returns.

--*/
{
    PAGED_CODE();

    //
    //  Acquire exclusive access to the instance context
    //

    FmmAcquireResourceExclusive( &InstanceContext->MetadataResouce );


    //
    //  Sanity - nothing should have changed this flag while we dropped the resource
    //  because all other threads will not use or modify the instance context while
    //  this flag is set
    //

    ASSERT( FlagOn( InstanceContext->Flags, INSTANCE_CONTEXT_F_TRANSITION ) );


    //
    //  Reset the flag to indicate that the instance context is no longer in
    //  a transition state
    //

    ClearFlag( InstanceContext->Flags, INSTANCE_CONTEXT_F_TRANSITION );

}



#if VERIFY_METADATA_OPENED

NTSTATUS
FmmIsMetadataOpen (
    __inout PFLT_CALLBACK_DATA Cbd,
    __out BOOLEAN* MetadataOpen
    )
/*++

Routine Description:

    This routine returns if the metadata file is open on the specified instance.

Arguments:

    Cbd                 - Supplies a pointer to the callbackData which
                          declares the requested operation.
    MetadataOpen        - Returns if the metadata file is open

Return Value:

    Status

Note:

    This routine takes care of the synchronization needed to access the metadata
    file object and handle


--*/
{
    NTSTATUS status = STATUS_SUCCESS;
    PFMM_INSTANCE_CONTEXT instanceContext = NULL;


    //
    //  Get the instance context
    //

    status = FltGetInstanceContext( Cbd->Iopb->TargetInstance,
                                    &instanceContext );
    if (!NT_SUCCESS( status )) {

        DebugTrace( DEBUG_TRACE_ERROR | DEBUG_TRACE_METADATA_OPERATIONS,
                    ("[Fmm]: FmmIsMetadataOpen -> Failed to get instance context.\n") );

        goto FmmIsMetadataOpenCleanup;
    }

    //
    //  Acquire exclusive access to the instance context
    //

    FmmAcquireResourceShared( &instanceContext->MetadataResouce );

    if (FlagOn( instanceContext->Flags, INSTANCE_CONTEXT_F_TRANSITION)) {

        //
        //  If this instance context is in a transition state, it implies that
        //  the instance context lock has been released while sending an operation
        //  down to the file system. The reason for doing so is to prevent a potential
        //  deadlock if an underlying filter sends an IO to the top of the filter
        //  stack while we are holding the resource
        //
        //  We have managed to acquire this resource in this state of transition.
        //  It would be incorrect to use or modify the instance context in any way
        //  in this situation. So we simply let go.
        //

        status = STATUS_FILE_LOCK_CONFLICT;

        DebugTrace( DEBUG_TRACE_ERROR | DEBUG_TRACE_METADATA_OPERATIONS,
                    ("[Fmm]: FmmIsMetadataOpen -> Failed to get exclusive access to instance context since it is in a state of transition.\n") );
    } else {

        //
        //  Return if the metadata is opened
        //

        *MetadataOpen = (BOOLEAN) FlagOn( instanceContext->Flags, INSTANCE_CONTEXT_F_METADATA_OPENED );

        //
        //  Sanity - verify that this flag is reflecting the correct state of the metadata file
        //

        ASSERT ( (FlagOn( instanceContext->Flags, INSTANCE_CONTEXT_F_METADATA_OPENED ) &&
                  (instanceContext->MetadataFileObject != NULL) &&
                  (instanceContext->MetadataHandle != NULL)) ||
                 (!FlagOn( instanceContext->Flags, INSTANCE_CONTEXT_F_METADATA_OPENED ) &&
                  (instanceContext->MetadataFileObject == NULL) &&
                  (instanceContext->MetadataHandle == NULL)) );

    }

    //
    //  Relinquish exclusive access to the instance context
    //

    FmmReleaseResource( &instanceContext->MetadataResouce);


FmmIsMetadataOpenCleanup:

    //
    // Release the references we have acquired
    //

    if (instanceContext != NULL) {

        FltReleaseContext( instanceContext );
    }


    return status;
}


#endif


⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -