T1552

Unsecured Credentials

Adversaries may search compromised systems to find and obtain insecurely stored credentials. These credentials can be stored and/or misplaced in many locations on a system, including plaintext files, operating system or application-specific repositories, shell history files, private key files, cloud instance metadata APIs, container environment variables, and group policy preference files. Tools like LaZagne, NirSoft utilities, and custom scripts are commonly used to automate credential harvesting across multiple storage locations simultaneously.

Microsoft Sentinel / Defender
kusto
let CredentialFilePatterns = dynamic([
  "password", "passwd", "credentials", "creds", "secret", "apikey", "api_key",
  ".aws\\credentials", "unattend.xml", "sysprep.xml", "web.config",
  "id_rsa", "id_dsa", "id_ecdsa", "id_ed25519", ".pem", ".pfx", ".p12",
  "vnc.ini", "filezilla", "winscp.ini", "putty", "bash_history", ".ssh"
]);
let CredentialHarvestingTools = dynamic([
  "lazagne", "nirsoft", "netpass", "credentialfileview", "passwordfox",
  "webbrowserpassview", "mailpassview", "vaultpassview", "credentialsfileview",
  "mimikatz", "wce.exe", "pwdump", "fgdump", "gsecdump"
]);
let CredentialRegistryPaths = dynamic([
  "\\SOFTWARE\\ORL\\WinVNC3\\Password",
  "\\SOFTWARE\\TightVNC\\Server",
  "\\SOFTWARE\\RealVNC\\WinVNC4",
  "\\SYSTEM\\CurrentControlSet\\Services\\SNMP\\Parameters\\ValidCommunities",
  "\\SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Winlogon",
  "\\SOFTWARE\\SimonTatham\\PuTTY\\Sessions",
  "\\SOFTWARE\\OpenSSH",
  "DefaultPassword", "AltDefaultPassword"
]);
// Branch 1: Suspicious file access patterns indicating credential file enumeration
let FileCredentialAccess = DeviceFileEvents
| where Timestamp > ago(24h)
| where ActionType in ("FileAccessed", "FileRead")
| where FolderPath has_any (CredentialFilePatterns) or FileName has_any (CredentialFilePatterns)
| where InitiatingProcessFileName !in~ ("svchost.exe", "SearchIndexer.exe", "MsMpEng.exe", "OneDrive.exe")
| extend DetectionBranch = "CredentialFileAccess"
| project Timestamp, DeviceName, AccountName, FileName, FolderPath,
         InitiatingProcessFileName, InitiatingProcessCommandLine,
         InitiatingProcessParentFileName, DetectionBranch;
// Branch 2: Known credential harvesting tools
let HarvestingTools = DeviceProcessEvents
| where Timestamp > ago(24h)
| where FileName has_any (CredentialHarvestingTools)
   or ProcessCommandLine has_any (CredentialHarvestingTools)
   or InitiatingProcessFileName has_any (CredentialHarvestingTools)
| extend DetectionBranch = "CredentialHarvestingTool"
| project Timestamp, DeviceName, AccountName, FileName, ProcessCommandLine,
         InitiatingProcessFileName, InitiatingProcessCommandLine,
         InitiatingProcessParentFileName, DetectionBranch;
// Branch 3: Registry queries to credential storage locations
let RegistryCredentialQuery = DeviceRegistryEvents
| where Timestamp > ago(24h)
| where RegistryKey has_any (CredentialRegistryPaths) or RegistryValueName has_any ("Password", "DefaultPassword", "AltDefaultPassword")
| where ActionType in ("RegistryKeyQueried", "RegistryValueQueried")
| where InitiatingProcessFileName !in~ ("svchost.exe", "lsass.exe", "services.exe")
| extend DetectionBranch = "RegistryCredentialQuery"
| project Timestamp, DeviceName, AccountName=InitiatingProcessAccountName,
         FileName=InitiatingProcessFileName, ProcessCommandLine=InitiatingProcessCommandLine,
         InitiatingProcessFileName=InitiatingProcessParentFileName,
         InitiatingProcessCommandLine=InitiatingProcessParentCommandLine,
         InitiatingProcessParentFileName="", DetectionBranch;
// Branch 4: PowerShell or cmd searching for credential content in files
let ScriptedCredentialSearch = DeviceProcessEvents
| where Timestamp > ago(24h)
| where FileName in~ ("powershell.exe", "pwsh.exe", "cmd.exe", "bash", "sh")
| where ProcessCommandLine has_any (
    "Get-Content", "gc ", "cat ", "type ", "findstr", "grep",
    "Select-String", "sls "
  )
  and ProcessCommandLine has_any (
    "password", "passwd", "credentials", "secret", "apikey", "api_key",
    "connectionstring", "pwd", "passw"
  )
| extend DetectionBranch = "ScriptedCredentialSearch"
| project Timestamp, DeviceName, AccountName, FileName, ProcessCommandLine,
         InitiatingProcessFileName, InitiatingProcessCommandLine,
         InitiatingProcessParentFileName, DetectionBranch;
union FileCredentialAccess, HarvestingTools, RegistryCredentialQuery, ScriptedCredentialSearch
| sort by Timestamp desc
high severity medium confidence

Data Sources

File: File Access Process: Process Creation Windows Registry: Windows Registry Key Access Command: Command Execution Microsoft Defender for Endpoint

Required Tables

DeviceFileEvents DeviceProcessEvents DeviceRegistryEvents

False Positives

  • Password managers (KeePass, Bitwarden, 1Password desktop) legitimately accessing their own credential files
  • SSH clients (PuTTY, OpenSSH, WinSCP) reading .pem or known_hosts files as part of normal connection workflow
  • Configuration management tools (Ansible, Puppet, Chef) reading web.config or unattend.xml during deployments
  • Security scanners (Tenable, Qualys) that enumerate credential file locations as part of vulnerability assessments
  • Backup software reading all file types including credential-related files as part of scheduled backup jobs

Unlock Pro Content

Get the full detection package for T1552 including response playbook, investigation guide, and atomic red team tests.

Response PlaybookInvestigation GuideHunting QueriesAtomic Red Team TestsTuning Guidance

Related Detections