Brutus — SSH Brute-Force, Interactive Root Access, and a Persistent Sudo Account
- Tools
- grep, awk, cut, sort, uniq, wtmpdb, last
- Skill demonstrated
- Linux authentication-log and session-accounting forensic correlation
- Tags
At a glance
Section titled “At a glance”| Field | Value |
|---|---|
| Target environment | Linux host; supplied evidence limited to authentication logs and session-accounting data |
| Starting position | Provided evidence — auth.log and a legacy session record (wtmp.legacy) |
| Objective | Reconstruct a defensible incident timeline from SSH authentication and session-accounting artifacts and identify persistence and post-compromise activity |
| Outcome | Interactive root access followed by a sudo-enabled local account; confirmed compromise |
Summary
Section titled “Summary”Brutus is a Hack The Box Sherlock that reconstructs a Linux SSH compromise from authentication and session-accounting artifacts. Correlating an authentication burst, successful privileged logins, terminal-session records, and account-management events yields one defensible timeline: a password brute-force against SSH opened interactive root access, the attacker created a local account in the sudo group, and that account read the credential store and fetched an enumeration script. Account names, source addresses, ports, and remote script locations are replaced with role-based placeholders; command syntax is preserved.
Attack path: SSH password brute-force → interactive root session → local account creation + sudo group → privileged /etc/shadow read and enumeration-script retrieval
Context and Objective
Section titled “Context and Objective”- Provided evidence: the Sherlock supplies
auth.logand a legacywtmpsession-accounting file (wtmp.legacy). - Environment: a Linux host reachable over SSH; the artifacts are authentication and session records only.
- Objective: build a defensible incident timeline and determine what the evidence does and does not establish about compromise, persistence, and follow-on activity.
- Constraints: analysis is confined to the supplied artifacts. Timestamps are recorded as they appear in each artifact; the session-accounting query was run with
TZ=UTC.
Approach and Evidence
Section titled “Approach and Evidence”1. Authentication Volume Triage
Section titled “1. Authentication Volume Triage”Observation: raw authentication records are dominated by one service, so event volume indicates where to focus.
Action: count events by service name.
awk '{print $5}' auth.log | cut -d'[' -f1 | cut -d: -f1 | sort | uniq -c | sort -nr257 sshd104 CRON 8 systemd-logind 6 sudo: 3 groupadd 2 usermod 2 systemd: 1 useradd 1 passwd 1 chfnSignificance: sshd accounts for most events in a 385-line log; a distribution this skewed points to automated authentication attempts rather than normal interactive use.
Result: SSH authentication activity is the anomaly to investigate.
2. Source Attribution
Section titled “2. Source Attribution”Observation: if the activity is a brute-force campaign, one external address should dominate the authentication events.
Action: extract and rank source addresses.
grep -oE '[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+' auth.log | sort | uniq -c | sort -nr214 <EXTERNAL_SOURCE> 1 <SECONDARY_SOURCE> 1 <INTERNAL_SOURCE>Significance: a single address produced 214 references against one each from the others, consistent with one automated source rather than ordinary traffic.
Result: <EXTERNAL_SOURCE> is the source of the authentication volume.
3. Successful Access and Session Correlation
Section titled “3. Successful Access and Session Correlation”Observation: accepted-password events from the dominant address date the successful logins, and a session record independently bounds the interactive window.
Action: filter accepted logins from that source, then query the converted session database.
grep 'Accepted.*<EXTERNAL_SOURCE>' auth.log<DATE> 06:31:40 ... Accepted password for <PRIVILEGED_ACCOUNT> from <EXTERNAL_SOURCE> port <SOURCE_PORT_1> ssh2<DATE> 06:32:44 ... Accepted password for <PRIVILEGED_ACCOUNT> from <EXTERNAL_SOURCE> port <SOURCE_PORT_2> ssh2<DATE> 06:37:34 ... Accepted password for <PERSISTENCE_ACCOUNT> from <EXTERNAL_SOURCE> port <SOURCE_PORT_3> ssh2TZ=UTC wtmpdb last -F -f ./wtmp<PRIVILEGED_ACCOUNT> pts/1 <EXTERNAL_SOURCE> Wed Mar 6 06:32:45 2024 - Wed Mar 6 06:37:24 2024 (00:04)grep '06:32:44.*New session' auth.log<DATE> 06:32:44 ... New session <SESSION_ID> of user <PRIVILEGED_ACCOUNT>.Significance: the first accepted event (06:31:40) has no matching terminal session, while the second (06:32:44) is followed one second later by a session start and a recorded session identifier — separating a transient authentication from sustained interactive access.
Result: interactive privileged access began at 2024-03-06 06:32:45 in session <SESSION_ID>, authenticated from <EXTERNAL_SOURCE>.
4. Persistence — Local Account Creation
Section titled “4. Persistence — Local Account Creation”Observation: account-management events appear within the same window as the compromise.
Action: extract account-creation and group-modification records.
grep -E 'useradd.*new user|usermod.*sudo' auth.loguseradd[<PID>]: new user: name=<PERSISTENCE_ACCOUNT>, UID=<UID>, ...usermod[<PID>]: add '<PERSISTENCE_ACCOUNT>' to group 'sudo'Significance: a freshly created local account added to the sudo group is durable persistence — it survives the original session and can regain root at will. This matches MITRE ATT&CK T1136.001, Create Account: Local Account.
Result: <PERSISTENCE_ACCOUNT> was created and granted administrative-group membership.
5. Post-Compromise Activity
Section titled “5. Post-Compromise Activity”Observation: privileged command records show what the compromised access was used for after the first session.
Action: list recorded sudo commands.
grep 'COMMAND=' auth.logsudo: <PERSISTENCE_ACCOUNT> : ... COMMAND=/usr/bin/cat /etc/shadowsudo: <PERSISTENCE_ACCOUNT> : ... COMMAND=/usr/bin/curl <REMOTE_SCRIPT_URL>Significance: reading /etc/shadow through sudo is credential-store access (T1003, OS Credential Dumping); fetching a remote enumeration script prepares for discovery.
Result: credential-store access and enumeration-tool retrieval are recorded under the persistence account.
6. Incident Timeline Correlation
Section titled “6. Incident Timeline Correlation”Observation: each artifact places events on a partial clock; together they order the incident.
Action: bound the first session’s end, then align the account, command, and persistence events.
grep 'session closed for user' auth.loggrep 'Removed session' auth.log<DATE> 06:37:24 ... session closed for user <PRIVILEGED_ACCOUNT><DATE> 06:37:24 ... Removed session <SESSION_ID>.| Time | Artifact | Event |
|---|---|---|
| 2024-03-06 06:31:40 | auth.log | First Accepted password for <PRIVILEGED_ACCOUNT> from <EXTERNAL_SOURCE> (transient; no session record) |
| 2024-03-06 06:32:44 | auth.log | Second Accepted password for <PRIVILEGED_ACCOUNT>; New session <SESSION_ID> |
| 2024-03-06 06:32:45 | wtmp (UTC) | Interactive session starts: <PRIVILEGED_ACCOUNT> pts/1 <EXTERNAL_SOURCE> |
| 2024-03-06 06:37:24 | auth.log + wtmp | Session <SESSION_ID> closes; duration 279 s |
| after 06:37:24 | auth.log | useradd <PERSISTENCE_ACCOUNT>, usermod → sudo, /etc/shadow read, enumeration-script fetch |
| 2024-03-06 06:37:34 | auth.log | Accepted password for <PERSISTENCE_ACCOUNT> (persistence login) |
Significance: the authenticated login, terminal start, and session identifier align within one second, and the session close agrees across both artifacts — cross-artifact agreement strengthens the timeline.
Result: the evidence supports a single, ordered compromise sequence on 2024-03-06; the ordering of the post-session account and command events follows the full log sort.
Challenges and Decisions
Section titled “Challenges and Decisions”The legacy session file was not directly readable: last -f ./wtmp.legacy returned file is not a database, because the artifact is a legacy binary wtmp while the wtmpdb reader expects SQLite. Converting it once with wtmpdb import produced a queryable database while the original artifact was preserved. No audit-policy change or log-clearing activity was observed in the supplied artifacts, so no defense-evasion stage is included.
Outcome
Section titled “Outcome”The evidence establishes a confirmed compromise on the target host. Limitations: the artifacts do not show the enumeration script’s execution or output, additional persistence mechanisms, credential reuse, or activity on other hosts.
Lessons and Recommendations
Section titled “Lessons and Recommendations”Each finding pairs the observed root cause with its demonstrated impact and a prioritized action. The actions are recommendations; none was validated.
- Password authentication on SSH. A single external source produced hundreds of authentication events and eventually succeeded against a privileged account. Recommendation: prefer key-based SSH, disable password authentication for privileged accounts, and rate-limit or block repeated failures. Detection: alert on authentication-failure bursts followed by a success from the same source.
- Unmonitored privileged local accounts. The compromise added a new local account to the
sudogroup, granting durable root-equivalent access. Recommendation: restrict account creation andsudogroup changes, and alert on them. Detection: monitoruseradd/usermodevents and auditsudogroup membership for changes. - Sensitive-file reads and remote tooling from a privileged shell. The persistence account read
/etc/shadowand fetched remote enumeration tooling. Recommendation: enforce least privilege so routine access does not require reading the credential store, and restrict outbound script retrieval from servers. Detection: investigate non-baselinesudoreads of/etc/shadowand outbound fetches of remote scripts. - Response readiness. Recommendation: on confirmation, isolate the host, disable unauthorized accounts, rotate
rootand local credentials, reviewauthorized_keys,sudoers, and scheduled tasks, and preserveauth.logand the session artifacts for further analysis.
References
Section titled “References”- Hack The Box — Sherlock Brutus (retired Sherlock)
- MITRE ATT&CK T1078 — Valid Accounts
- MITRE ATT&CK T1136.001 — Create Account: Local Account
- MITRE ATT&CK T1003 — OS Credential Dumping
- wtmpdb — Y2038-safe wtmp implementation (project repository)
last/wtmpdbmanual page (Debian manpages)- GNU Coreutils —
cut,sort,uniq - GNU grep
- GNU Awk (gawk)