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

📄 nlp.c

📁 安全支持提供器接口(SSPI)源码
💻 C
📖 第 1 页 / 共 5 页
字号:

Routine Description:

    This routine converts the buffer address in the specified string to
    be a byte offset from BaseAddress.

Parameters:

    BaseAddress - A pointer to make the destination address relative to.

    String - A pointer to a NT string to make relative.

Return Values:

    None.

--*/

{
    ASSERT( BaseAddress != NULL );
    ASSERT( String != NULL );
    ASSERT( sizeof(ULONG_PTR) == sizeof(String->Buffer) );

    if ( String->Buffer != NULL ) {
        *((PULONG_PTR)(&String->Buffer)) =
            (ULONG_PTR)((PUCHAR)String->Buffer - (PUCHAR)BaseAddress);
    }

    return;
}


VOID
NlpRelativeToAbsolute(
    IN PVOID BaseAddress,
    IN OUT PULONG_PTR RelativeValue
    )

/*++

Routine Description:

    This routine converts the byte offset from BaseAddress to be an
    absolute address.

Parameters:

    BaseAddress - A pointer the destination address is relative to.

    RelativeValue - A pointer to a relative value to make absolute.

Return Values:

    None.

--*/

{
    ASSERT( BaseAddress != NULL );
    ASSERT( RelativeValue != NULL );

    if ( *((PUCHAR *)RelativeValue) != NULL ) {
        *RelativeValue = (ULONG_PTR)((PUCHAR)BaseAddress + (*RelativeValue));
    }

    return;
}


BOOLEAN
NlpFindActiveLogon(
    IN PLUID LogonId,
    OUT PACTIVE_LOGON **ActiveLogon
    )

/*++

Routine Description:

    This routine finds the specified Logon Id in the ActiveLogon table.
    It returns a boolean indicating whether the Logon Id exists in the
    ActiveLogon Table.  If so, this routine also returns a pointer to a
    pointer to the appropriate entry in the table.  If not, this routine
    returns a pointer to where such an entry would be inserted in the table.

    This routine must be called with the NlpActiveLogonLock locked.

Parameters:

    LogonId - The LogonId of the logon to find in the table.

    ActiveLogon - If the specified logon Id exists, returns a pointer to a
        pointer to the appropriate entry in the table.  Otherwise,
        returns a pointer to where such an entry would be inserted in the
        table.

Return Values:

    TRUE - The specified LogonId already exists in the table.

    FALSE - The specified LogonId does not exist in the table.

--*/

{
    PACTIVE_LOGON *Logon;

    //
    // Loop through the table looking for this particular LogonId.
    //

    for( Logon = &NlpActiveLogons; *Logon != NULL; Logon = &((*Logon)->Next) ) {
        if (RtlCompareMemory( &(*Logon)->LogonId, LogonId, sizeof(*LogonId))
                == sizeof(*LogonId) ) {

            *ActiveLogon = Logon;
            return TRUE;
        }
    }

    //
    // By returning a pointer to the NULL at the end of the list, we
    //  are forcing new entries to be placed at the end.  The list is
    //  thereby maintained in the order that the logon occurred.
    //  MsV1_0EnumerateUsers relies on this behavior.
    //

    *ActiveLogon = Logon;
    return FALSE;
}


ULONG
NlpCountActiveLogon(
    IN PUNICODE_STRING LogonDomainName,
    IN PUNICODE_STRING UserName
    )

/*++

Routine Description:

    This routine counts the number of time a particular user is logged on
    in the Active Logon Table.

Parameters:

    LogonDomainName - Domain in which this user account is defined.

    UserName - The user name to count the active logons for.

Return Values:

    The count of active logons for the specified user.

--*/

{
    PACTIVE_LOGON Logon;
    ULONG LogonCount = 0;


    //
    // Loop through the table looking for this particular LogonId.
    //

    NlpLockActiveLogons();

    for( Logon = NlpActiveLogons; Logon != NULL; Logon = Logon->Next ) {

        if(RtlEqualUnicodeString( UserName, &Logon->UserName, (BOOLEAN) TRUE) &&
           RtlEqualDomainName(LogonDomainName,&Logon->LogonDomainName )){
            LogonCount ++;
        }

    }

    NlpUnlockActiveLogons();

    return LogonCount;
}



NTSTATUS
NlpAllocateInteractiveProfile (
    IN PLSA_CLIENT_REQUEST ClientRequest,
    OUT PMSV1_0_INTERACTIVE_PROFILE *ProfileBuffer,
    OUT PULONG ProfileBufferSize,
    IN  PNETLOGON_VALIDATION_SAM_INFO2 NlpUser
    )

/*++

Routine Description:

    This allocates and fills in the clients interactive profile.

Arguments:

    ClientRequest - Is a pointer to an opaque data structure
        representing the client's request.

    ProfileBuffer - Is used to return the address of the profile
        buffer in the client process.  This routine is
        responsible for allocating and returning the profile buffer
        within the client process.  However, if the caller subsequently
        encounters an error which prevents a successful logon, then
        then it will take care of deallocating the buffer.  This
        buffer is allocated with the AllocateClientBuffer() service.

     ProfileBufferSize - Receives the Size (in bytes) of the
        returned profile buffer.

    NlpUser - Contains the validation information which is
        to be copied in the ProfileBuffer.

Return Value:

    STATUS_SUCCESS - Indicates the service completed successfully.

    STATUS_QUOTA_EXCEEDED -  This error indicates that the logon
        could not be completed because the client does not have
        sufficient quota to allocate the return buffer.

--*/

{
    NTSTATUS Status;
    CLIENT_BUFFER_DESC ClientBufferDesc;
    PMSV1_0_INTERACTIVE_PROFILE LocalProfileBuffer;

    //
    // Alocate the profile buffer to return to the client
    //

    NlpInitClientBuffer( &ClientBufferDesc, ClientRequest );

    *ProfileBuffer = NULL;

    *ProfileBufferSize = sizeof(MSV1_0_INTERACTIVE_PROFILE) +
        NlpUser->LogonScript.Length + sizeof(WCHAR) +
        NlpUser->HomeDirectory.Length + sizeof(WCHAR) +
        NlpUser->HomeDirectoryDrive.Length + sizeof(WCHAR) +
        NlpUser->FullName.Length + sizeof(WCHAR) +
        NlpUser->ProfilePath.Length + sizeof(WCHAR) +
        NlpUser->LogonServer.Length + sizeof(WCHAR);

    Status = NlpAllocateClientBuffer( &ClientBufferDesc,
                                      sizeof(MSV1_0_INTERACTIVE_PROFILE),
                                      *ProfileBufferSize );


    if ( !NT_SUCCESS( Status ) ) {
        goto Cleanup;
    }

    LocalProfileBuffer = (PMSV1_0_INTERACTIVE_PROFILE) ClientBufferDesc.MsvBuffer;

    //
    // Copy the scalar fields into the profile buffer.
    //

    LocalProfileBuffer->MessageType = MsV1_0InteractiveProfile;
    LocalProfileBuffer->LogonCount = NlpUser->LogonCount;
    LocalProfileBuffer->BadPasswordCount= NlpUser->BadPasswordCount;
    OLD_TO_NEW_LARGE_INTEGER( NlpUser->LogonTime,
                              LocalProfileBuffer->LogonTime );
    OLD_TO_NEW_LARGE_INTEGER( NlpUser->LogoffTime,
                              LocalProfileBuffer->LogoffTime );
    OLD_TO_NEW_LARGE_INTEGER( NlpUser->KickOffTime,
                              LocalProfileBuffer->KickOffTime );
    OLD_TO_NEW_LARGE_INTEGER( NlpUser->PasswordLastSet,
                              LocalProfileBuffer->PasswordLastSet );
    OLD_TO_NEW_LARGE_INTEGER( NlpUser->PasswordCanChange,
                              LocalProfileBuffer->PasswordCanChange );
    OLD_TO_NEW_LARGE_INTEGER( NlpUser->PasswordMustChange,
                              LocalProfileBuffer->PasswordMustChange );
    LocalProfileBuffer->UserFlags = NlpUser->UserFlags;

    //
    // Copy the Unicode strings into the profile buffer.
    //

    NlpPutClientString( &ClientBufferDesc,
                        &LocalProfileBuffer->LogonScript,
                        &NlpUser->LogonScript );

    NlpPutClientString( &ClientBufferDesc,
                        &LocalProfileBuffer->HomeDirectory,
                        &NlpUser->HomeDirectory );

    NlpPutClientString( &ClientBufferDesc,
                        &LocalProfileBuffer->HomeDirectoryDrive,
                        &NlpUser->HomeDirectoryDrive );

    NlpPutClientString( &ClientBufferDesc,
                        &LocalProfileBuffer->FullName,
                        &NlpUser->FullName );

    NlpPutClientString( &ClientBufferDesc,
                        &LocalProfileBuffer->ProfilePath,
                        &NlpUser->ProfilePath );

    NlpPutClientString( &ClientBufferDesc,
                        &LocalProfileBuffer->LogonServer,
                        &NlpUser->LogonServer );

    //
    // Flush the buffer to the client's address space.
    //

    Status = NlpFlushClientBuffer( &ClientBufferDesc,
                                   (PVOID *) ProfileBuffer );

Cleanup:

    //
    // If the copy wasn't successful,
    //  cleanup resources we would have returned to the caller.
    //

    if ( !NT_SUCCESS(Status) ) {
        NlpFreeClientBuffer( &ClientBufferDesc );
    }

    return Status;

}



NTSTATUS
NlpAllocateNetworkProfile (
    IN PLSA_CLIENT_REQUEST ClientRequest,
    OUT PMSV1_0_LM20_LOGON_PROFILE *ProfileBuffer,
    OUT PULONG ProfileBufferSize,
    IN  PNETLOGON_VALIDATION_SAM_INFO2 NlpUser,
    IN  ULONG ParameterControl
    )

/*++

Routine Description:

    This allocates and fills in the clients network profile.

Arguments:

    ClientRequest - Is a pointer to an opaque data structure
        representing the client's request.

    ProfileBuffer - Is used to return the address of the profile
        buffer in the client process.  This routine is
        responsible for allocating and returning the profile buffer
        within the client process.  However, if the caller subsequently
        encounters an error which prevents a successful logon, then
        then it will take care of deallocating the buffer.  This
        buffer is allocated with the AllocateClientBuffer() service.

     ProfileBufferSize - Receives the Size (in bytes) of the
        returned profile buffer.

    NlpUser - Contains the validation information which is
        to be copied in the ProfileBuffer.  Will be NULL to indicate a
        NULL session.

Return Value:

    STATUS_SUCCESS - Indicates the service completed successfully.

    STATUS_QUOTA_EXCEEDED -  This error indicates that the logon
        could not be completed because the client does not have
        sufficient quota to allocate the return buffer.

--*/

{
    NTSTATUS Status;
    NTSTATUS SubAuthStatus = STATUS_SUCCESS;

    CLIENT_BUFFER_DESC ClientBufferDesc;
    PMSV1_0_LM20_LOGON_PROFILE LocalProfile;

    //
    // Alocate the profile buffer to return to the client
    //

    NlpInitClientBuffer( &ClientBufferDesc, ClientRequest );

    *ProfileBuffer = NULL;
    *ProfileBufferSize = sizeof(MSV1_0_LM20_LOGON_PROFILE);

    if ( NlpUser != NULL ) {
        *ProfileBufferSize += NlpUser->LogonDomainName.Length + sizeof(WCHAR) +
                              NlpUser->LogonServer.Length + sizeof(WCHAR) +
                              NlpUser->HomeDirectoryDrive.Length + sizeof(WCHAR);
    }


    Status = NlpAllocateClientBuffer( &ClientBufferDesc,
                                      sizeof(MSV1_0_LM20_LOGON_PROFILE),
                                      *ProfileBufferSize );


    if ( !NT_SUCCESS( Status ) ) {
        goto Cleanup;
    }

    LocalProfile = (PMSV1_0_LM20_LOGON_PROFILE) ClientBufferDesc.MsvBuffer;
    LocalProfile->MessageType = MsV1_0Lm20LogonProfile;


    //
    // For a NULL session, return a constant profile buffer
    //

    if ( NlpUser == NULL ) {

        LocalProfile->KickOffTime.HighPart = 0x7FFFFFFF;
        LocalProfile->KickOffTime.LowPart = 0xFFFFFFFF;
        LocalProfile->LogoffTime.HighPart = 0x7FFFFFFF;
        LocalProfile->LogoffTime.LowPart = 0xFFFFFFFF;
        LocalProfile->UserFlags = 0;
        RtlZeroMemory( LocalProfile->UserSessionKey,
                       sizeof(LocalProfile->UserSessionKey));
        RtlZeroMemory( LocalProfile->LanmanSessionKey,
                       sizeof(LocalProfile->LanmanSessionKey));
        RtlInitUnicodeString( &LocalProfile->LogonDomainName, NULL );
        RtlInitUnicodeString( &LocalProfile->LogonServer, NULL );
        RtlInitUnicodeString( &LocalProfile->UserParameters, NULL );


    //
    // For non-null sessions,
    //  fill in the profile buffer.
    //

    } else {

        //
        // Copy the individual scalar fields into the profile buffer.
        //

        if ((ParameterControl & MSV1_0_RETURN_PASSWORD_EXPIRY) != 0) {
            OLD_TO_NEW_LARGE_INTEGER( NlpUser->PasswordMustChange,
                                      LocalProfile->LogoffTime);
        } else {
            OLD_TO_NEW_LARGE_INTEGER( NlpUser->LogoffTime,
                                      LocalProfile->LogoffTime);
        }
        OLD_TO_NEW_LARGE_INTEGER( NlpUser->KickOffTime,
                                  LocalProfile->KickOffTime);
        LocalProfile->UserFlags = NlpUser->UserFlags;

        RtlCopyMemory( LocalProfile->UserSessionKey,
                       &NlpUser->UserSessionKey,
                       sizeof(LocalProfile->UserSessionKey) );

        ASSERT( SAMINFO_LM_SESSION_KEY_SIZE ==
                sizeof(LocalProfile->LanmanSessionKey) );
        RtlCopyMemory(
            LocalProfile->LanmanSessionKey,
            &NlpUser->ExpansionRoom[SAMINFO_LM_SESSION_KEY],
            SAMINFO_LM_SESSION_KEY_SIZE );


        // We need to extract the true status sent back for subauth users,
        // but not by a sub auth package

        SubAuthStatus = NlpUser->ExpansionRoom[SAMINFO_SUBAUTH_STATUS];

        //
        // Copy the Unicode strings into the profile buffer.
        //

        NlpPutClientString( &ClientBufferDesc,
                            &LocalProfile->LogonDomainName,
                            &NlpUser->LogonDomainName );

        NlpPutClientString( &ClientBufferDesc,
                            &LocalProfile->LogonServer,
                            &NlpUser->LogonServer );

⌨️ 快捷键说明

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