Что такое событие windows 4624 успешный вход в вход


3 min read

5 базовых рекомендаций по расследованию инцидентов на Windows

Семейство операционных систем Windows на сегодняшний день является наиболее распространённой средой как для работы, так и для личного использования. Поэтому встретить вектор атак на него нередкое явление. Для корректного распознавания аномальных поведений на базовом уровне предлагаем пройтись по пунктам, которые будут полезны всем пользователям Windows:

Что такое событие windows 4624 успешный вход в вход
Что такое событие windows 4624 успешный вход в вход
Что такое событие windows 4624 успешный вход в вход
Что такое событие windows 4624 успешный вход в вход

Для более детальной картины нужно задать фильтры – время, ID, наименование провайдера, какое правило было добавлено. Результат ниже:

Что такое событие windows 4624 успешный вход в вход
Что такое событие windows 4624 успешный вход в вход

Общий вид просмотра политики создание/завершение процессов Windows:

Что такое событие windows 4624 успешный вход в вход

Подробный вид просмотра политики создание/завершение процессов Windows:

Что такое событие windows 4624 успешный вход в вход

Надеемся, что данный материал был полезен для вас.

Ensuring the security of IT systems is a crucial task. Identifying suspicious activities, such as numerous failed login attempts, is an important measure to mitigate potential threats. The provided script written in PowerShell serves as a versatile tool to assist IT professionals and MSPs in obtaining insights into failed login events.

Background

The Script

#Requires -Version 3.0 -RunAsAdministrator

<#
.SYNOPSIS
    Returns the number of recent failed login attempts.
.DESCRIPTION
    Returns the number of recent failed login attempts of all users or of a specific user. If a user is specified then just a number is returned.
.EXAMPLE
    No parameters needed.
    Returns all users, of the local machine, with a could of failed login attempts.
Output Example:
UserName  FailedLoginAttempts
--------  -------------------
Fred                        4
Bob                         0
.EXAMPLE
     -UserName "Fred"
    Returns the number of failed login attempts of the user Fred on the local machine.
Output Example:
4
.EXAMPLE
     -ComputerName "FredPC" -UserName "Fred"
    Returns the number of failed login attempts of the user Fred on the computer named FredPC.
Output Example:
4
.EXAMPLE
     -ComputerName "FredPC" -UserName "Fred" -Detailed
    Returns the number of failed login attempts of the user Fred on the computer named FredPC, but will more details of each failed and successful logins.
Output Example:

TimeGenerated   : 10/18/2019 7:52:43 AM
EventID         : 4624
Category        : 12544
ADUsername      : Fred
Domain          : FredPC
UserSID         : S-1-0-0
Workstation     : -
SourceIP        : -
Port            : -
FailureReason   : Interactive
FailureStatus   : Incorrect password
FailureSubStatus: Other
.EXAMPLE
    PS C:> Monitor-Failed-Password-Attempts.ps1 -ComputerName "FredPC" -UserName "Fred"
    Returns the number of failed login attempts of the user Fred on the computer named FredPC.
Output Example:
4
.OUTPUTS
    System.Int32 Number of failed login attempts.
.OUTPUTS
    PSCustomObject List of user names and a count of failed login attempts.
.NOTES
    Minimum OS Architecture Supported: Windows 7, Windows Server 2012
    If ComputerName is specified, then be sure that the computer that this script is running on has network and permissions to access the Event Log on the remote computer.
    Release Notes:
    Initial Release
By using this script, you indicate your acceptance of the following legal terms as well as our Terms of Use at https://www.ninjaone.com/terms-of-use.
    Ownership Rights: NinjaOne owns and will continue to own all right, title, and interest in and to the script (including the copyright). NinjaOne is giving you a limited license to use the script in accordance with these legal terms. 
    Use Limitation: You may only use the script for your legitimate personal or internal business purposes, and you may not share the script with another party. 
    Republication Prohibition: Under no circumstances are you permitted to re-publish the script in any script library or website belonging to or under the control of any other software provider. 
    Warranty Disclaimer: The script is provided “as is” and “as available”, without warranty of any kind. NinjaOne makes no promise or guarantee that the script will be free from defects or that it will meet your specific needs or expectations. 
    Assumption of Risk: Your use of the script is at your own risk. You acknowledge that there are certain inherent risks in using the script, and you understand and assume each of those risks. 
    Waiver and Release: You will not hold NinjaOne responsible for any adverse or unintended consequences resulting from your use of the script, and you waive any legal or equitable rights or remedies you may have against NinjaOne relating to your use of the script. 
    EULA: If you are a NinjaOne customer, your use of the script is subject to the End User License Agreement applicable to you (EULA).
.COMPONENT
    ManageUsers
#>

param (
    # The name of a remote computer to get event logs for failed logins
    [Parameter(Mandatory = $false)]
    [String]
    $ComputerName = [System.Net.Dns]::GetHostName(),
    # A username
    [Parameter(Mandatory = $false)]
    [String]
    $UserName,
    # Returns all relevant events, sorted by TimeGenerated
    [Switch]
    $Detailed
)

# Support functions
# Returns the matching FailureReason like Incorrect password
function Get-FailureReason {
    Param($FailureReason)
    switch ($FailureReason) {
        '0xC0000064' { "Account does not exist"; break; }
        '0xC000006A' { "Incorrect password"; break; }
        '0xC000006D' { "Incorrect username or password"; break; }
        '0xC000006E' { "Account restriction"; break; }
        '0xC000006F' { "Invalid logon hours"; break; }
        '0xC000015B' { "Logon type not granted"; break; }
        '0xc0000070' { "Invalid Workstation"; break; }
        '0xC0000071' { "Password expired"; break; }
        '0xC0000072' { "Account disabled"; break; }
        '0xC0000133' { "Time difference at DC"; break; }
        '0xC0000193' { "Account expired"; break; }
        '0xC0000224' { "Password must change"; break; }
        '0xC0000234' { "Account locked out"; break; }
        '0x0' { "0x0"; break; }
        default { "Other"; break; }
    }
}
function Get-LogonType {
    Param($LogonType)
    switch ($LogonType) {
        '0' { 'Interactive'; break; }
        '2' { 'Interactive'; break; }
        '3' { 'Network'; break; }
        '4' { 'Batch'; break; }
        '5' { 'Service'; break; }
        '6' { 'Proxy'; break; }
        '7' { 'Unlock'; break; }
        '8' { 'Networkcleartext'; break; }
        '9' { 'NewCredentials'; break; }
        '10' { 'RemoteInteractive'; break; }
        '11' { 'CachedInteractive'; break; }
        '12' { 'CachedRemoteInteractive'; break; }
        '13' { 'CachedUnlock'; break; }
        Default {}
    }
}
#-Newest $Records
$Events = Get-EventLog -ComputerName $ComputerName -LogName 'security' -InstanceId 4625, 4624 | Sort-Object -Property TimeGenerated | ForEach-Object {
    if ($_.InstanceId -eq 4625) {
        $_ | Select-Object -Property @(
            @{Label = 'TimeGenerated'; Expression = { $_.TimeGenerated } },
            @{Label = 'EventID'; Expression = { $_.InstanceId } },
            @{Label = 'Category'; Expression = { $_.CategoryNumber } },
            @{Label = 'Username'; Expression = { $_.ReplacementStrings[5] } },
            @{Label = 'Domain'; Expression = { $_.ReplacementStrings[6] } },
            @{Label = 'UserSID'; Expression = { (($_.Message -Split 'rn' | Select-String 'Security ID')[1] -Split 's+')[3] } },
            # @{Label = 'UserSID'; Expression = { $_.ReplacementStrings[0] } },
            @{Label = 'Workstation'; Expression = { $_.ReplacementStrings[13] } },
            @{Label = 'SourceIP'; Expression = { $_.ReplacementStrings[19] } },
            @{Label = 'Port'; Expression = { $_.ReplacementStrings[20] } },
            @{Label = 'LogonType'; Expression = { $_.ReplacementStrings[8] } },
            @{Label = 'FailureStatus'; Expression = { Get-FailureReason($_.ReplacementStrings[7]) } },
            @{Label = 'FailureSubStatus'; Expression = { Get-FailureReason($_.ReplacementStrings[9]) } }
        )
    }
    elseif ($_.InstanceId -eq 4624 -and (Get-LogonType($_.ReplacementStrings[8])) -notlike 'Service') {
        $_ | Select-Object -Property @(
            @{Label = 'TimeGenerated'; Expression = { $_.TimeGenerated } },
            @{Label = 'EventID'; Expression = { $_.InstanceId } },
            @{Label = 'Category'; Expression = { $_.CategoryNumber } },
            @{Label = 'Username'; Expression = { $_.ReplacementStrings[5] } },
            @{Label = 'Domain'; Expression = { $_.ReplacementStrings[6] } },
            @{Label = 'UserSID'; Expression = { $_.ReplacementStrings[0] } },
            @{Label = 'Workstation'; Expression = { $_.ReplacementStrings[11] } },
            @{Label = 'SourceIP'; Expression = { $_.ReplacementStrings[18] } },
            @{Label = 'Port'; Expression = { $_.ReplacementStrings[19] } },
            @{Label = 'LogonType'; Expression = { Get-LogonType($_.ReplacementStrings[8]) } },
            @{Label = 'LogonID'; Expression = { Get-FailureReason($_.ReplacementStrings[7]) } },
            @{Label = 'LogonProcess'; Expression = { Get-FailureReason($_.ReplacementStrings[9]) } }
        )
    }
}

if ($Detailed) {
    if ($UserName) {
        $Events | Where-Object {
            $_.Username -like $UserName
        }
    }
    else {
        $Events | Where-Object {
            $_.Username -notlike "DWM*" -and
            $_.Username -notlike "UMFD*" -and
            $_.Username -notlike "SYSTEM"
        }
    }
}
else {
    $UserNames = if ($UserName) {
        ($Events | Select-Object -Property Username -Unique).Username | Where-Object {
            $_ -like "$UserName"
        }
    }
    else {
        ($Events | Select-Object -Property Username -Unique).Username | Where-Object {
            $_ -notlike "DWM*" -and
            $_ -notlike "UMFD*" -and
            $_ -notlike "SYSTEM"
        }
    }
    
    $UserNames | ForEach-Object {
        $CurrentUserName = $_
        $FailedLoginCount = 0
        for ($i = 0; $i -lt $Events.Count; $i++) {
            if ($Events[$i].EventID -eq 4625 -and $Events[$i].Username -like $CurrentUserName) {
                # User failed to login X times
                # Count the number of failed logins
                $FailedLoginCount++
            }
            elseif ($Events[$i].EventID -eq 4624 -and $Events[$i].Username -like $CurrentUserName) {
                # User logged in successfully
                # Reset the number of failed logins to 0
                $FailedLoginCount = 0
            }
        }
        if ($UserName) {
            # If a UserName was specified, then return only the failed login count
            $FailedLoginCount
        }
        else {
            # If no UserName was specified, then return the user name and failed login count
            [PSCustomObject]@{
                UserName            = $CurrentUserName
                FailedLoginAttempts = $FailedLoginCount
            }
        }
    }
}

Access 300+ scripts in the NinjaOne Dojo

Detailed Breakdown of the Script

At its core, the script fetches data from the Event Logs of a given computer, targeting specific Event IDs that represent failed and successful login attempts.

  • Parameters: The script begins by defining parameters like ComputerName, UserName, and Detailed. This allows the user to specify the machine, the user, and the level of detail for the login attempts.
  • Functions: Two functions, Get-FailureReason and Get-LogonType, translate coded information from the event logs into human-readable data regarding the type of login and the reason for a failed login.
  • Fetching Events: The script then fetches the event logs, filtering them to retain only the necessary information. This involves picking the instances with the relevant Event IDs.
  • Processing: Depending on whether detailed data is requested, the script either provides a comprehensive breakdown of each login attempt or a summary of failed attempts for each user.
:/>  System нагружает диск на 100 windows 10. В Windows 10 загрузка диска на 100 процентов: решение от специалиста WiFiGid

Potential Use Cases

Alternative Approach

There are several methods to track failed login attempts. Windows’ built-in security auditing, for instance, lets you view the security logs via Event Viewer. While this approach is straightforward, it can be time-consuming. Our PowerShell script streamlines the process, offering a more efficient and customizable solution.

FAQs

  • How does the script identify a failed login event?
    The script looks for specific Event IDs in the Event Log, such as 4625 for failed logins.
  • Can I fetch data from a remote machine?
    Yes, by providing the ComputerName parameter, you can obtain data from a remote computer.

Implications

Recommendations

  • Ensure you have the necessary permissions to fetch event logs.
  • Regularly run the script, especially for systems holding sensitive information.
  • Investigate any patterns of failed logins and notify the concerned users.

Final Thoughts

In the era of increasing cyber threats, tools like our PowerShell script are essential. For a comprehensive security solution, platforms like NinjaOne can be integrated, ensuring real-time monitoring and management. NinjaOne, combined with proactive scripts like the one discussed, provides additional defense against cyber threats.

Оставьте комментарий