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

📄 nlp.c

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

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;
    STRING PrimaryKeyValue;

    RtlInitString( &PrimaryKeyValue, MSV1_0_PRIMARY_KEY );

    Status = (*Lsa.DeleteCredential)( LogonId,
                                    MspAuthenticationPackageId,
                                    &PrimaryKeyValue );

    return Status;

}


NTSTATUS
NlpChangePassword(
    IN PUNICODE_STRING DomainName,
    IN PUNICODE_STRING UserName,
    IN PUNICODE_STRING Password
    )

/*++

Routine Description:

    Change the password for the specified user in all currently stored
    credentials.

Arguments:

    DomainName - The Netbios name of the domain in which the account exists.

    UserName - The name of the account whose password is to be changed.

    Password - The new password.

Return Value:

    STATUS_SUCCESS - If the operation was successful.

--*/
{
    NTSTATUS Status = STATUS_SUCCESS;
    PACTIVE_LOGON Logon;
    ULONG LogonCount = 0;

    PMSV1_0_PRIMARY_CREDENTIAL Credential = NULL;
    ULONG CredentialSize;

    MSV1_0_PRIMARY_CREDENTIAL TempCredential;

    LUID LogonId;
    BOOLEAN Found = FALSE;
    BOOLEAN MatchedCaller = FALSE;
    SECPKG_CLIENT_INFO ClientInfo;

    //
    // Get the logon ID of the caller.
    //
    Status = LsaFunctions->GetClientInfo(&ClientInfo);
    if (!NT_SUCCESS(Status)) {
        return(Status);
    }

    //
    // Compute the OWFs of the password.
    //

    NlpPutOwfsInPrimaryCredential( Password, &TempCredential );


    //
    // Loop through the table looking for this particular UserName/DomainName.
    //

    NlpLockActiveLogons();

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

        if(RtlEqualUnicodeString( UserName, &Logon->UserName, (BOOLEAN) TRUE) &&
           RtlEqualDomainName( DomainName, &Logon->LogonDomainName )){

            if (!MatchedCaller) {
                LogonId = Logon->LogonId;
            }
            Found = TRUE;

            //
            // If this is the LUID of the caller, remember the caller's
            // logon id.
            //

            if (RtlEqualLuid(
                    &LogonId,
                    &ClientInfo.LogonId
                    ))
            {
                MatchedCaller = TRUE;
            }

            //
            // Get the current credential for this logonid.
            //

            Status = NlpGetPrimaryCredential( &Logon->LogonId,
                                              &Credential,
                                              &CredentialSize );

            if ( !NT_SUCCESS(Status) ) {
                break;
            }

            //
            // Delete it from the LSA.
            //

            Status = NlpDeletePrimaryCredential( &Logon->LogonId );

            if ( !NT_SUCCESS(Status) ) {
                (*Lsa.FreeLsaHeap)( Credential );
                break;
            }

            //
            // Change the passwords in it
            //

            Credential->LmOwfPassword = TempCredential.LmOwfPassword;
            Credential->LmPasswordPresent = TempCredential.LmPasswordPresent;
            Credential->NtOwfPassword = TempCredential.NtOwfPassword;
            Credential->NtPasswordPresent = TempCredential.NtPasswordPresent;

            //
            // Add it back to the LSA.
            //

            Status = NlpAddPrimaryCredential( &Logon->LogonId,
                                              Credential,
                                              CredentialSize );

            (*Lsa.FreeLsaHeap)( Credential );

            if ( !NT_SUCCESS(Status) ) {
                break;
            }

        }

    }

    NlpUnlockActiveLogons();

    //
    // Pass the change back to the LSA. Note - this only changes it for the
    // last element in the list.
    //

    if (Found) {
        SECPKG_PRIMARY_CRED PrimaryCredentials;

        RtlZeroMemory(
            &PrimaryCredentials,
            sizeof(SECPKG_PRIMARY_CRED)
            );
        PrimaryCredentials.LogonId = LogonId;
        PrimaryCredentials.Password = *Password;
        PrimaryCredentials.Flags = PRIMARY_CRED_UPDATE | PRIMARY_CRED_CLEAR_PASSWORD;


        (VOID) LsaFunctions->UpdateCredentials(
                    &PrimaryCredentials,
                    NULL        // no supplemental credentials
                    );

    }
    //
    // Pass the new password on to the logon cache
    //

    NlpChangeCachePassword(
                DomainName,
                UserName,
                &TempCredential.LmOwfPassword,
                &TempCredential.NtOwfPassword );

    return Status;
}


NTSTATUS
NlpChangePasswordByLogonId(
    IN PLUID LogonId,
    IN PUNICODE_STRING Password
    )

/*++

Routine Description:

    Change the password for the specified user in all currently stored
    credentials.

Arguments:

    LogonId - Logon ID of user whose password changed.

    Password - New password.

Return Value:

    STATUS_SUCCESS - If the operation was successful.

--*/
{
    NTSTATUS Status = STATUS_SUCCESS;
    PACTIVE_LOGON Logon;
    ULONG LogonCount = 0;
    PMSV1_0_PRIMARY_CREDENTIAL Credential = NULL;
    ULONG CredentialSize;
    ANSI_STRING     LmPasswordString;
    CHAR            LmPassword[LM20_PWLEN+1];
    LM_OWF_PASSWORD LmOwfPassword;
    NT_OWF_PASSWORD NtOwfPassword;

    LmPasswordString.Buffer = LmPassword;
    LmPasswordString.Length = 0;
    LmPasswordString.MaximumLength = sizeof( LmPassword );
    Status = RtlUpcaseUnicodeStringToOemString( &LmPasswordString,
                                                Password,
                                                FALSE );
    if ( NT_SUCCESS(Status) ) {
        Status = RtlCalculateLmOwfPassword( LmPassword, &LmOwfPassword );

        ASSERT( NT_SUCCESS(Status) );

    }
    Status = RtlCalculateNtOwfPassword( Password,
                                        &NtOwfPassword );

    ASSERT( NT_SUCCESS(Status) );


    //
    // Loop through the table looking for this particular UserName/DomainName.
    //

    NlpLockActiveLogons();

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

        if(RtlEqualLuid( LogonId, &Logon->LogonId) ){


            //
            // Get the current credential for this logonid.
            //

            Status = NlpGetPrimaryCredential( &Logon->LogonId,
                                              &Credential,
                                              &CredentialSize );

            if ( !NT_SUCCESS(Status) ) {
                break;
            }

            //
            // Delete it from the LSA.
            //

            Status = NlpDeletePrimaryCredential( &Logon->LogonId );

            if ( !NT_SUCCESS(Status) ) {
                (*Lsa.FreeLsaHeap)( Credential );
                break;
            }

            //
            // Change the passwords in it
            //

            Credential->LmOwfPassword = LmOwfPassword;
            Credential->NtOwfPassword = NtOwfPassword;

            //
            // Add it back to the LSA.
            //

            Status = NlpAddPrimaryCredential( &Logon->LogonId,
                                              Credential,
                                              CredentialSize );

            (*Lsa.FreeLsaHeap)( Credential );

            if ( !NT_SUCCESS(Status) ) {
                break;
            }

            //
            // Pass the new password on to the logon cache
            //

            NlpChangeCachePassword(
                        &Logon->LogonDomainName,
                        &Logon->UserName,
                        &LmOwfPassword,
                        &NtOwfPassword );

        }

    }

    NlpUnlockActiveLogons();


    return Status;
}


VOID
NlpGetAccountNames(
    IN  PNETLOGON_LOGON_IDENTITY_INFO LogonInfo,
    IN  PNETLOGON_VALIDATION_SAM_INFO2 NlpUser,
    OUT PUNICODE_STRING SamAccountName,
    OUT PUNICODE_STRING NetbiosDomainName,
    OUT PUNICODE_STRING DnsDomainName,
    OUT PUNICODE_STRING Upn
    )

/*++

Routine Description:

    Get the sundry account names from the LogonInfo and NlpUser

Arguments:

    LogonInfo   - pointer to NETLOGON_INTERACTIVE_INFO structure which contains
                  the domain name, user name and password for this user. These
                  are what the user typed to WinLogon

    NlpUser - pointer to NETLOGON_VALIDATION_SAM_INFO2 structure which
                  contains this user's specific interactive logon information

    SamAccountName - Returns the SamAccountName of the logged on user.
        The returned buffer is within the LogonInfo or NlpUser.

    NetbiosDomainName - Returns the NetbiosDomainName of the logged on user.
        The returned buffer is within the LogonInfo or NlpUser.

    DnsDomainName - Returns the DnsDomainName of the logged on user.
        The returned buffer is within the LogonInfo or NlpUser.
        The returned length will be zero if DnsDomainName is not known.

    UPN - Returns the UPN of the logged on user.
        The returned buffer is within the LogonInfo or NlpUser.
        The returned length will be zero if UPN is not known.

Return Value:

    None.

--*/
{

    //
    // Return the SamAccountName and Netbios Domain Name
    //
    *SamAccountName = NlpUser->EffectiveName;
    *NetbiosDomainName = NlpUser->LogonDomainName;

    //
    // Determine the DNS domain name of the user's domain.
    //
    //  BUGBUG: This should be in NlpUser.
    //

    RtlInitUnicodeString( DnsDomainName, NULL );

    //
    // Determine the UPN of the account
    //
    // The caller passed in a UPN if all of the following are true:
    //  The is no domain name.
    //  The passed in user name isn't the one returned from the DC.
    //  The passed in user name has an @ in it.
    //
    //

    RtlInitUnicodeString( Upn, NULL );

    if ( LogonInfo->LogonDomainName.Length == 0 &&
         !RtlEqualUnicodeString( &LogonInfo->UserName, &NlpUser->EffectiveName, (BOOLEAN) TRUE ) ) {

         ULONG i;

         for ( i=0; i<LogonInfo->UserName.Length/sizeof(WCHAR); i++) {

             if ( LogonInfo->UserName.Buffer[i] == L'@') {
                 *Upn = LogonInfo->UserName;
                 break;
             }
         }

    }
}


//+-------------------------------------------------------------------------
//
//  Function:   NlpCopyDomainRelativeSid
//
//  Synopsis:   Given a domain Id and a relative ID create the corresponding
//              SID at the location indicated by TargetSid
//
//  Effects:
//
//  Arguments:  TargetSid - target memory location
//              DomainId - The template SID to use.
//
//                  RelativeId - The relative Id to append to the DomainId.
//
//  Requires:
//
//  Returns:    Size - Size of the sid copied
//
//  Notes: 
//
//
//--------------------------------------------------------------------------

DWORD
NlpCopyDomainRelativeSid(
    OUT PSID TargetSid,
    IN PSID  DomainId,
    IN ULONG RelativeId
    )
{
    UCHAR DomainIdSubAuthorityCount;
    ULONG Size;

    //
    // Allocate a Sid which has one more sub-authority than the domain ID.
    //

    DomainIdSubAuthorityCount = *(RtlSubAuthorityCountSid( DomainId ));
    Size = RtlLengthRequiredSid(DomainIdSubAuthorityCount+1);

    //
    // Initialize the new SID to have the same inital value as the
    // domain ID.
    //

    if ( !NT_SUCCESS( RtlCopySid( Size, TargetSid, DomainId ) ) ) {
        return 0;
    }

    //
    // Adjust the sub-authority count and
    //  add the relative Id unique to the newly allocated SID
    //

    (*(RtlSubAuthorityCountSid( TargetSid ))) ++;
    *RtlSubAuthoritySid( TargetSid, DomainIdSubAuthorityCount ) = RelativeId;


    return Size;
}

⌨️ 快捷键说明

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