← All hunts high TLP:CLEAR Part 2 of 2

Knight Office Token Theft and Device Persistence

An adversary has stolen Microsoft 365 session tokens via a device-code phishing flow and secured persistence by enrolling an unauthorized rogue device into the Entra ID tenant.

Based on research by Huntress 2026-09-20 10 steps · 3 queries T1090.003 T1098 T1566

Brief

Why this hunt

Huntress recently analyzed the Knight Office phishing kit (https://www.huntress.com/blog/inside-knight-office-m365-aitm-attack), a toolset that bypasses MFA using the Microsoft device-code flow. Unlike standard Adversary-in-the-Middle (AiTM) kits that proxy traffic, Knight Office tricks users into authorizing a code. This grants the attacker a session token. The adversary then secures persistence by enrolling a rogue device into the victim's Entra ID tenant. This hunt targets that specific transition from token theft to persistence.

How the Hunt Flows

The first phase scopes the environment for signs of kit interaction using the hb_http_activity surface. The query identifies any internal host or identity visiting the Microsoft device login endpoint or known kit management infrastructure. This step filters the noise, focusing the investigation on users who potentially engaged with the phishing prompt. By looking for the devicelogin path specifically, the hunt narrows the leads to the exact authentication flow the kit exploits. The second phase runs two investigations in parallel. One query stacks User-Agents seen in traffic to authentication endpoints like login.microsoft.com. Automated tools used by the kit, such as the python-requests library, often appear as rare outliers compared to standard browser strings in a corporate environment. The hunt looks for User-Agents that appear on three or fewer hosts to find these automated signatures. Simultaneously, the hunt checks the hb_devices surface for newly enrolled devices where the provider is azure_ad. A rogue host registration provides the attacker a foothold that survives password resets and MFA changes because the device itself is trusted. The final phase uses an agent to correlate these leads. It settles a verdict by matching users who visited the kit infrastructure with those who have a corresponding rare User-Agent and a newly registered cloud device. This correlation separates successful compromises from harmless visits to the login page. If the agent confirms both the kit interaction and the rogue device enrollment, we proceed to remediation.

What it Cannot See

The hunt faces two primary blind spots. First, endpoint-based HTTP telemetry only captures the victim's initial interaction. The subsequent token replay and API activity from the attacker’s own infrastructure remain invisible to these sensors. Capturing that behavior requires native Entra ID sign-in logs which record all global auth attempts and User-Agents. Second, cloud inventory sync delays can create a temporary gap between the moment an attacker registers a device and when it appears in the hb_devices surface. A successful enrollment might not show up for several minutes or hours depending on the inventory collector's cycle.

Running the Hunt

This hunt is an open-source playbook in the hunt.md format. You can import it into Huntbase or any runtime that supports the hunt.md standard. It provides a structured path from network leads to cloud identity verification, allowing practitioners to verify the integrity of their Entra ID tenant against this specific AiTM kit. The playbook includes specific steps for session revocation and manual verification of Windows Hello persistence to ensure no backdoors remain.

In this series

Steps

  1. Lead interaction with kit infrastructure

    Query · scoping

    Identify hosts and identities interacting with the device-code login flow or known kit management IPs.

    reads hb_http_activitysql
    SELECT DISTINCT device_hostname, actor_user_name, dst_endpoint_ip, url_hostname, url_path, time FROM hb_http_activity WHERE ((instr(LOWER(url_hostname), 'microsoft.com') > 0 AND instr(LOWER(url_path), 'devicelogin') > 0) OR instr(',' || '{{attacker_ips}}' || ',', ',' || dst_endpoint_ip || ',') > 0) AND time >= datetime('now', '-{{lookback_days}} days')

    What a hit looks like. Internal identities and hostnames visiting the device login page or kit management infrastructure. Results scope the subsequent behavioral queries.

  2. Rare User-Agents to authentication endpoints

    Query · baseline

    Stack-count User-Agents on interaction with login infrastructure to find automated kit tools like python-requests.

    reads hb_http_activitysql
    SELECT user_agent, url_hostname, device_hostname, COUNT(DISTINCT device_hostname) AS host_count, MIN(time) AS first_seen FROM hb_http_activity WHERE (instr(LOWER(url_hostname), 'microsoft.com') > 0 OR instr(LOWER(url_hostname), 'login') > 0) AND ('{{scope_hosts}}' = '' OR instr(',' || '{{scope_hosts}}' || ',', ',' || device_hostname || ',') > 0) AND time >= datetime('now', '-{{lookback_days}} days') GROUP BY user_agent, url_hostname HAVING host_count <= 3 ORDER BY host_count ASC

    What a hit looks like. Rare User-Agents like python-requests or Microsoft Authentication Broker associated with a small number of hosts.

  3. New Entra ID device registration

    Query · detection candidate

    Find newly enrolled cloud devices that may represent the attacker's persistence mechanism.

    reads hb_devicessql
    SELECT hostname, device_owner, os_name, os_version, device_uid, provider, time FROM hb_devices WHERE provider = 'azure_ad' AND time >= datetime('now', '-{{lookback_days}} days') ORDER BY time DESC

    What a hit looks like. Newly registered devices in Entra ID. The hostname typically differs from the victim's standard machine, identifying the rogue enrollment.

  4. Triage Knight Office indicators

    Agent triage

    Correlate kit traffic, rare User-Agents, and new device enrollments to confirm a successful AiTM compromise.

  5. Route on Knight Office verdict

    Decision

    Direct the response based on the agent's confidence in the identity compromise.

  6. Revoke sessions and remove device

    Response action

    Neutralize the attacker's persistence by revoking authentication and removing the rogue device.

  7. Verify Windows Hello persistence

    Analyst task

    Manually check for Windows Hello for Business (WHfB) keys that survive standard token revocation.

  8. Hunt closure

    Analyst task

    Document findings and update organizational blocklists.

  9. Analyst manual investigation

    Analyst task

    Resolve cases where the automated triage was inconclusive or data was unavailable.

Coverage

Scenario coverage

StageCoveredHow, or why not
AiTM Token Theft via Device Code Flow
T1566 · T1090.003
Yes kit-interaction-lead, rare-user-agents-to-microsoft
Entra ID Rogue Device Registration
T1098
Yes rogue-device-registration
DocuSign-themed Phishing Delivery
T1566
Out of scope Belongs to another part of the 'Inside Knight Office, a New M365 AiTM Phishing Kit' series.
Multi-stage URL Redirection
T1090.003
Out of scope Belongs to another part of the 'Inside Knight Office, a New M365 AiTM Phishing Kit' series.
Windows Hello for Business Key Binding
T1098
Out of scope Belongs to another part of the 'Inside Knight Office, a New M365 AiTM Phishing Kit' series.

Blind spots

  • Needs Native Entra ID sign-in logs. Corporate HTTP telemetry only sees the victim's interaction with the kit; the subsequent authentication from the attacker's infrastructure is invisible to endpoint-based sensors. It would answer Whether a stolen token was replayed from an external VPS via python-requests. Remediation: Ingest M365/Entra ID Unified Audit Logs (UAL) to capture all authentication attempts and User-Agents globally.
  • Needs hb_devices (azure_ad provider). Cloud inventory collectors may have a lag between a device registration event and its appearance in the hb_devices surface, leading to a temporary coverage gap. It would answer Whether a newly registered device has populated the inventory during the lookback window.

Parameters & data

Parameters

ParameterTypeDefaultWhat it is
attacker_ipslist[ip]104.37.188.94, 154.127.53.78Known Knight Office management and delivery IPs.
lookback_daysnumber14Days of history to examine.
scope_hostslist[host]Hosts identified in the lead step; leave empty for a global check.

Telemetry

SourceCategoryTelemetry
Endpoint telemetry (hb_ surfaces)endpointendpoint
Identity / sign-in telemetryidentityidentity
Web server / proxy logssiemnetwork

Source

Download hunt.md Definition (JSON) An open hunt.md file; it runs anywhere that reads the format.
---
analysis: A simple rule might fire on a kit IP, but this hunt correlates the initial
  deviceauth flow on the endpoint with the follow-on persistence mechanism in the
  cloud. It uses a baseline to find rare User-Agents that standard rules would miss
  and pivots between network activity and identity inventory to settle the verdict.
blind_spots:
- id: external-token-replay-visibility
  question: Whether a stolen token was replayed from an external VPS via python-requests
  remediation: Ingest M365/Entra ID Unified Audit Logs (UAL) to capture all authentication
    attempts and User-Agents globally.
  requires: Native Entra ID sign-in logs
  risk: Corporate HTTP telemetry only sees the victim's interaction with the kit;
    the subsequent authentication from the attacker's infrastructure is invisible
    to endpoint-based sensors.
  stage: aitm-device-code-theft
- id: device-inventory-sync-delay
  question: Whether a newly registered device has populated the inventory during the
    lookback window
  requires: hb_devices (azure_ad provider)
  risk: Cloud inventory collectors may have a lag between a device registration event
    and its appearance in the hb_devices surface, leading to a temporary coverage
    gap.
  stage: rogue-device-persistence
coverage:
- stage: aitm-device-code-theft
  status: covered
  steps:
  - kit-interaction-lead
  - rare-user-agents-to-microsoft
- stage: rogue-device-persistence
  status: covered
  steps:
  - rogue-device-registration
- reason: Belongs to another part of the 'Inside Knight Office, a New M365 AiTM Phishing
    Kit' series.
  stage: phishing-lure-delivery
  status: out_of_scope
- reason: Belongs to another part of the 'Inside Knight Office, a New M365 AiTM Phishing
    Kit' series.
  stage: redirect-chain-obfuscation
  status: out_of_scope
- reason: Belongs to another part of the 'Inside Knight Office, a New M365 AiTM Phishing
    Kit' series.
  stage: whfb-key-binding
  status: out_of_scope
guardrails:
  claims: no_unsupported
  evidence: citation_required
  missing_data: not_benign
  telemetry: untrusted
hunt:
  applicability: campaign-specific
  handoff: keep-as-periodic-hunt
  justification: Knight Office specifically bypass MFA by stealing persistent session
    tokens; a negative result over the enrolled estate confirms that no rogue devices
    have been registered through this specific kit chain, which is a critical persistence
    indicator.
  methodology: model-assisted
  trigger: intel-report
hypothesis: An adversary has stolen Microsoft 365 session tokens via a device-code
  phishing flow and secured persistence by enrolling an unauthorized rogue device
  into the Entra ID tenant.
labels:
- hunt
- attack.t1566
- attack.t1090.003
- attack.t1098
name: Knight Office Token Theft and Device Persistence
parameters:
  attacker_ips:
    default:
    - 104.37.188.94
    - 154.127.53.78
    description: Known Knight Office management and delivery IPs.
    from:
      kind: article
      observed: '2026-09-02'
      ref: huntress-knight-office
    type: list[ip]
  lookback_days:
    default: '14'
    description: Days of history to examine.
    from:
      kind: manual
      observed: '2026-09-02'
      ref: hunt-standard
    type: number
  scope_hosts:
    default: []
    description: Hosts identified in the lead step; leave empty for a global check.
    from:
      kind: manual
      observed: '2026-09-02'
      ref: analyst-scoping
    type: list[host]
provenance:
  authors:
  - name: Huntbase hunt generation
    org: huntbase.io
  generated:
    by: huntbase-hunt-generation
    from: https://www.huntress.com/blog/inside-knight-office-m365-aitm-attack
    gates:
    - dry-run
    - lint
    model: hb_google/gemini-3-flash-preview
rationale: The lead query identifies users interacting with the deviceauth flow, which
  is the kit's primary method for token theft. Focus on identities that visited the
  Microsoft devicelogin page followed by any interaction with the identified kit IPs.
  If the HTTP surface is encrypted or unavailable, prioritize the rogue-device-registration
  check.
references:
- name: Inside Knight Office, a New M365 AiTM Phishing Kit
  url: https://www.huntress.com/blog/inside-knight-office-m365-aitm-attack
related:
- hunt: phishing-redirect-obfuscation
  reason: The redirect chain involving Monday.com and compromised Joomla sites is
    better handled on proxy or web-filter logs.
  relation: out-of-scope-alternative
- hunt: knight-office-delivery-redirection
  relation: follows
scenario:
  stages:
  - name: DocuSign-themed Phishing Delivery
    observables:
    - 'IP: 154.127.53.78'
    - 'Subject: Reminder: Signature Required - Approval Pending Your Review!!!'
    - 'Character substitution: lmportant, Slgnature, VERlVIED (l instead of i)'
    slug: phishing-lure-delivery
    tactic: initial-access
    techniques:
    - T1566
  - name: Multi-stage URL Redirection
    observables:
    - 'Domain: monday.com'
    - Compromised Joomla websites
    - 'TLD: .vu domains'
    slug: redirect-chain-obfuscation
    tactic: initial-access
    techniques:
    - T1090.003
  - name: AiTM Token Theft via Device Code Flow
    observables:
    - 'URL: microsoft.com/devicelogin'
    - Nine-letter deviceauth codes
    - 'IP: 73.125.13.x (Callback proxy)'
    - 'User-Agent: Microsoft Authentication Broker / OfficeHome'
    slug: aitm-device-code-theft
    tactic: credential-access
    techniques:
    - T1566
    - T1090.003
  - name: Entra ID Rogue Device Registration
    observables:
    - 'IP: 104.37.188.94'
    - 'User-Agent: python-requests/2.34.2'
    - Unauthorized host enrollment into Microsoft Entra ID
    slug: rogue-device-persistence
    tactic: persistence
    techniques:
    - T1098
  - name: Windows Hello for Business Key Binding
    observables:
    - 'User-Agent: Dsreg/10.0 (Windows 10.0.19044.1826)'
    - NGC key binding
    - WHfB passwordless authentication success
    slug: whfb-key-binding
    tactic: persistence
    techniques:
    - T1098
  summary: Threat actors use the Knight Office phishing kit to perform Adversary-in-the-Middle
    (AiTM) attacks against Microsoft 365 accounts via the Device Code flow. After
    harvesting session tokens using residential callback proxies and redirect infrastructure,
    the attackers establish persistence by enrolling rogue devices in Microsoft Entra
    ID and binding Windows Hello for Business (WHfB) keys to the compromised accounts.
series:
  index: 2
  slug: inside-knight-office-a-new-m365-aitm-phishing-kit
  title: Inside Knight Office, a New M365 AiTM Phishing Kit
  total: 2
severity: high
targets:
  analyst:
    name: Tier-2 analyst
    role: analyst
  endpoint:
    category: endpoint
    name: Endpoint telemetry (hb_ surfaces)
    telemetry:
    - endpoint
  hunter:
    agent: true
    name: Hunt agent
  identity:
    category: identity
    name: Identity / sign-in telemetry
    telemetry:
    - identity
  web:
    category: siem
    name: Web server / proxy logs
    telemetry:
    - network
tlp: clear
type: investigation
---


# Knight Office Token Theft and Device Persistence

This hunt identifies the lifecycle of a Knight Office kit attack, focusing on the transition from initial phishing to long-term persistence. It begins by scoping users and hosts interacting with the Microsoft device login endpoint or known kit infrastructure. It then correlates these leads with rare User-Agents on endpoint HTTP traffic and unauthorized device registrations in Entra ID. An agent weighs the evidence to confirm if a successful token theft led to a rogue host enrollment, which survives password resets and MFA changes.

## kit-interaction-lead
<!-- Lead interaction with kit infrastructure -->
Identify hosts and identities interacting with the device-code login flow or known kit management IPs.

```sqlite target=web role=scoping params=(attacker_ips=attacker_ips, lookback_days=lookback_days)
~~~yaml
expected: Internal identities and hostnames visiting the device login page or kit
  management infrastructure. Results scope the subsequent behavioral queries.
reads:
- device_hostname
- actor_user_name
- dst_endpoint_ip
- url_hostname
- url_path
- time
silence: not_evidence_of_absence
source: hb_http_activity
verified: dry-run
verified_at: '2026-09-20'
~~~
SELECT DISTINCT device_hostname, actor_user_name, dst_endpoint_ip, url_hostname, url_path, time FROM hb_http_activity WHERE ((instr(LOWER(url_hostname), 'microsoft.com') > 0 AND instr(LOWER(url_path), 'devicelogin') > 0) OR instr(',' || '{{attacker_ips}}' || ',', ',' || dst_endpoint_ip || ',') > 0) AND time >= datetime('now', '-{{lookback_days}} days')
```

## parallel-investigation
<!-- Correlate traffic and cloud inventory -->
parallel:
- → rare-user-agents-to-microsoft
- → rogue-device-registration
join: → triage-knight-office

## rare-user-agents-to-microsoft
<!-- Rare User-Agents to authentication endpoints -->
Stack-count User-Agents on interaction with login infrastructure to find automated kit tools like python-requests.

```sqlite target=web role=baseline params=(scope_hosts=scope_hosts, lookback_days=lookback_days)
~~~yaml
baseline:
  compare: first_seen
  window: '{{lookback_days}}d'
expected: Rare User-Agents like python-requests or Microsoft Authentication Broker
  associated with a small number of hosts.
prevalence:
  by: device_hostname
  key:
  - user_agent
  - url_hostname
  rare_below: 3
reads:
- user_agent
- url_hostname
- device_hostname
- time
silence: not_evidence_of_absence
source: hb_http_activity
verified: dry-run
verified_at: '2026-09-20'
~~~
SELECT user_agent, url_hostname, device_hostname, COUNT(DISTINCT device_hostname) AS host_count, MIN(time) AS first_seen FROM hb_http_activity WHERE (instr(LOWER(url_hostname), 'microsoft.com') > 0 OR instr(LOWER(url_hostname), 'login') > 0) AND ('{{scope_hosts}}' = '' OR instr(',' || '{{scope_hosts}}' || ',', ',' || device_hostname || ',') > 0) AND time >= datetime('now', '-{{lookback_days}} days') GROUP BY user_agent, url_hostname HAVING host_count <= 3 ORDER BY host_count ASC
```

## rogue-device-registration
<!-- New Entra ID device registration -->
Find newly enrolled cloud devices that may represent the attacker's persistence mechanism.

```sqlite target=endpoint role=detection-candidate params=(lookback_days=lookback_days)
~~~yaml
expected: Newly registered devices in Entra ID. The hostname typically differs from
  the victim's standard machine, identifying the rogue enrollment.
reads:
- hostname
- device_owner
- os_name
- os_version
- device_uid
- provider
- time
silence: not_evidence_of_absence
source: hb_devices
verified: dry-run
verified_at: '2026-09-20'
~~~
SELECT hostname, device_owner, os_name, os_version, device_uid, provider, time FROM hb_devices WHERE provider = 'azure_ad' AND time >= datetime('now', '-{{lookback_days}} days') ORDER BY time DESC
```

## triage-knight-office
<!-- Triage Knight Office indicators -->
```agent target=hunter
cite: required
context:
- kit-interaction-lead
- rare-user-agents-to-microsoft
- rogue-device-registration
max_iterations: 4
objective: Determine if any user who visited the device login flow or kit infrastructure
  also registered a new Azure AD device and utilized a rare User-Agent during authentication.
success_criteria: A verdict citing specific identities, the rare HTTP indicators,
  and the rogue cloud device identifiers.
tools:
- endpoint
- web
```

## route-on-verdict
<!-- Route on Knight Office verdict -->
if~: "the triage verdict is malicious for at least one identity, indicating both suspicious deviceauth interaction and an unauthorized device enrollment" (confidence: high, judge=hunter)
then: → contain-compromised-identity
indeterminate: → analyst-investigation
unavailable: → analyst-investigation (blind_spot: external-token-replay-visibility)
else: → close-out-clean

## contain-compromised-identity
<!-- Revoke sessions and remove device -->
```action target=identity
~~~yaml
approval: required
~~~
Revoke all active M365 refresh tokens and sessions for the affected identities. Remove the rogue device UID identified in the triage step from the Microsoft Entra ID tenant.
```
→ verify-key-persistence

## verify-key-persistence
<!-- Verify Windows Hello persistence -->
```manual target=analyst
Inspect native Entra ID audit logs for the compromised users to identify 'Add registered key to device' events. Confirm if the Dsreg User-Agent was used to bind a WHfB key, as this allows the attacker to regain access after token revocation.
```
→ close-out-clean

## close-out-clean
<!-- Hunt closure -->
```manual target=analyst
Record the identified malicious IPs and User-Agents in the organization's perimeter security controls. Document the efficacy of the rarity-based HTTP triage for future tuning.
```
→ end

## analyst-investigation
<!-- Analyst manual investigation -->
```manual target=analyst
Manually review the cited HTTP interactions and cross-reference with Entra ID sign-in logs. Look for replayed tokens from unusual ASN/IP ranges that match the timing of the kit interaction.
```
→ close-out-clean

Run it

Take this hunt into your environment.

Open it in Huntbase to run every step against your own connections, with Scout weighing the evidence and your analysts in command. Or take the open hunt.md file anywhere that reads the format.

Machine-drafted by huntbase-hunt-generation using hb_google/gemini-3-flash-preview, gated by dry-run, lint, then reviewed by a person.