Suspicious Request

ID

suspicious_request

Severity

low

Resource

Network

Tags

dropper

Description

This detector aims to detect code performing requests to suspicious resources or sites.

Rationale

Suspicious requests may involve unusual patterns, unusual destinations, or non-standard ports:

  • Often, Malware establishes a communication channel with a remote command and control server controlled by attackers. In these cases, it’s common to find hardcoded C2 IPs or hostnames in the source code.

  • It may also attempt to exfiltrate data by generating network requests to them.

  • It may read the cloud instance metadata service (IMDS) — the link-local endpoints 169.254.169.254, fd00:ec2::254, 100.100.100.200 or metadata.google.internal — to steal instance credentials or perform environment reconnaissance, often as the payload of a Server-Side Request Forgery (SSRF) chain.

  • Frequently it also involves attempts to download additional malware payloads or updates. Malicious software may request files from external servers to enhance its capabilities or change its behavior.

    Nowadays, many attacks are related to malicious file distributions from GitHub Raw files or Discord/ Telegram attachments.

This is a common feature that could be broadly found among malicious code. However, we can enumerate some popular variants using this technique:

  • 3CX Supply Chain Attack unfolded in March 2023 as a significant supply chain security breach. The assailants successfully infiltrated applications by incorporating a compromised library file, leading to the subsequent download of an encrypted file housing Command & Control information.

    The affected software ran a downloader, SUDDENICON, which in turn received additional command and control (C2) servers from encrypted icon files hosted on GitHub. The decrypted C2 server was used to download a third stage identified as ICONICSTEALER, a dataminer that steals browser information.

Configuration

The detector has the following configurable parameters:

  • sources, that indicates the source kinds to check. Available values are:

    • cloud_metadata

    • github_raw_link

    • dangerous_file_extension

    • discord_attachment_link

    • discord_webhook_link

    • github_raw_link

    • hardcoded_ip

    • ip_leakage

    • telegram_attachment_link

    • tor_resource

    • snippet_hosting

  • file_hosting

  • sinks, that indicates the sink to check. Available values are:

    • insecure_transport

  • neutralizations, that indicates the neutralization kinds to check. By default, this is empty. No neutralizers are considered for potential malicious code.

Destination provenance

The destination a flow reaches is read and recorded on the finding, and the severity is lowered — never the finding removed — when the destination is one the package can account for:

  • own-declared-domain — the destination’s registrable domain (eTLD+1) is named by the package’s own metadata (homepage, repository, issue tracker, author address) in at least downgrade_min_declared_fields independent fields. Gated: it does not apply when the registry recorded the declared repository as not served, when a typosquatting or dependency-confusion finding is present, or when the flow is inside a file an installation script executes. Matching is on the exact registrable domain, so api.example.com.attacker.net never answers to a declared example.com.

  • operator-supplied-messaging-token — the destination is a chat platform (Telegram, Slack, Discord) reached without a bot token in the URL, so the channel belongs to whoever installed the package rather than to whoever published it. A URL carrying the token keeps full severity: that channel shipped with the package.

  • first-party-provider — the destination is a listed first-party service (url.providers.yml). This replaced an outright suppression: the finding used to disappear, which took it out of evidence_correlation (it fires on detector ids, not on severity), hid any collector placed behind a listed host, and left no way to notice the list was wrong. It now drops downgrade_provider_steps levels — two by default, which on the info < low < high < critical ladder puts a critical finding at low: below the conviction gate, still in the report, still correlatable.

  • oauth-token-exchange — the request carries grant_type and goes to a listed token endpoint, which is a client renewing its own credentials (RFC 6749 §4). The field is the discriminator, not the host: a stolen refresh token would be replayed at the very same endpoint, and an exfiltrator has no reason to send grant_type.

A credential whose name belongs to a different listed provider than the destination keeps full severity, whatever the host: shipping one vendor’s key to another vendor is key siphoning with the destination as cover. A name no provider claims says nothing about ownership and does not block the downgrade.

The reason travels on the finding as DOWNGRADE_REASON, alongside DECLARED_DOMAIN / DECLARED_DOMAIN_FIELDS or PROVIDER.

The first-party destinations a package may legitimately reach are listed in url.providers.yml, which is versioned and can be replaced out of band. Loopback and private addresses are still dropped outright — data that does not travel cannot be exfiltrated — and are recognized in any spelling; cloud instance metadata (169.254.169.254) is deliberately never treated as local.

© 2026 Xygeni. All rights reserved