Skip to content
Heist/ feed
Back to feed
Unrated

Malicious code in hardhat-bits (npm)

Type: advisorySources: OSV

--- _-= Per source details. Do not edit below this line.=-_ ## Source: amazon-inspector (4e10f22980d33eea7649312f6b2b0a94637e5b4da400f7d585c58b6902a77944) The package is published as hardhat-bits but its README, LICENSE, docs/, and lib/* files are copied verbatim from the pino logger project, providing cover for an inserted file at lib/config.js. index.js performs `const config = require('./lib/config')` at the top level, so the file executes unconditionally when the module is required. lib/config.js is a single-line, ~4.47 MB obfuscator.io output: a 26,130-entry shuffled string array with a rotating decoder, hex-escaped member access, RC4-style key-schedule string decoding, control-flow flattening, and a self-defending IIFE. The exported `middleware` in index.js is a no-op `(_req, _res, next) => next()`, so the obfuscated module serves no documented purpose in the public API. The combination of name/branding mismatch (hardhat tooling name, pino content), a stub public API, and a multi-megabyte obfuscated blob auto-executed on import matches the trojan-loader shape used by npm supply-chain malware; any installer that requires hardhat-bits runs attacker-controlled code hidden behind the obfuscation.

Products
hardhat-bits
Affected versions
2.21.0
Fixed versions
Not specified
CVEs
Not specified
Confirmed fixed CVEs
Not specified
Updated in this feed
28 Oct 2026, 08:58 UTC · Revision 1

Source evidence

Malicious code in hardhat-bits (npm)

core-osv · Original source

Published 8 Oct 2026, 03:39 UTC

--- _-= Per source details. Do not edit below this line.=-_ ## Source: amazon-inspector (4e10f22980d33eea7649312f6b2b0a94637e5b4da400f7d585c58b6902a77944) The package is published as hardhat-bits but its README, LICENSE, docs/, and lib/* files are copied verbatim from the pino logger project, providing cover for an inserted file at lib/config.js. index.js performs `const config = require('./lib/config')` at the top level, so the file executes unconditionally when the module is required. lib/config.js is a single-line, ~4.47 MB obfuscator.io output: a 26,130-entry shuffled string array with a rotating decoder, hex-escaped member access, RC4-style key-schedule string decoding, control-flow flattening, and a self-defending IIFE. The exported `middleware` in index.js is a no-op `(_req, _res, next) => next()`, so the obfuscated module serves no documented purpose in the public API. The combination of name/branding mismatch (hardhat tooling name, pino content), a stub public API, and a multi-megabyte obfuscated blob auto-executed on import matches the trojan-loader shape used by npm supply-chain malware; any installer that requires hardhat-bits runs attacker-controlled code hidden behind the obfuscation.

osv:MAL-2026-17658

hardhat-bits

Fixed versions: Not specified

Complete source record
{
  "id": "be9cdd8413ee63d3fe749a484abf71a63395a3e8a69c207125d753b9fc964fb5",
  "url": "https://osv.dev/vulnerability/MAL-2026-17658",
  "method": "structured",
  "payload": {
    "kind": "advisory",
    "title": "Malicious code in hardhat-bits (npm)",
    "summary": "--- _-= Per source details. Do not edit below this line.=-_ ## Source: amazon-inspector (4e10f22980d33eea7649312f6b2b0a94637e5b4da400f7d585c58b6902a77944) The package is published as hardhat-bits but its README, LICENSE, docs/, and lib/* files are copied verbatim from the pino logger project, providing cover for an inserted file at lib/config.js. index.js performs `const config = require('./lib/config')` at the top level, so the file executes unconditionally when the module is required. lib/config.js is a single-line, ~4.47 MB obfuscator.io output: a 26,130-entry shuffled string array with a rotating decoder, hex-escaped member access, RC4-style key-schedule string decoding, control-flow flattening, and a self-defending IIFE. The exported `middleware` in index.js is a no-op `(_req, _res, next) => next()`, so the obfuscated module serves no documented purpose in the public API. The combination of name/branding mismatch (hardhat tooling name, pino content), a stub public API, and a multi-megabyte obfuscated blob auto-executed on import matches the trojan-loader shape used by npm supply-chain malware; any installer that requires hardhat-bits runs attacker-controlled code hidden behind the obfuscation.",
    "evidence": "osv:MAL-2026-17658",
    "products": [
      {
        "name": {
          "value": "hardhat-bits",
          "evidence": "/affected/0/package/name"
        },
        "prerequisites": [],
        "fixed_versions": [],
        "affected_versions": [
          {
            "value": "2.21.0",
            "evidence": "/affected/0/versions"
          }
        ]
      }
    ],
    "severity": "unknown",
    "structured": {
      "id": "MAL-2026-17658",
      "aliases": [
        "MAL-2026-17658"
      ],
      "affected": [
        {
          "package": {
            "name": "hardhat-bits",
            "purl": "pkg:npm/hardhat-bits",
            "ecosystem": "npm"
          },
          "versions": [
            "2.21.0"
          ],
          "database_specific": {
            "cwes": [
              {
                "name": "Embedded Malicious Code",
                "cweId": "CWE-506",
                "description": "The product contains code that appears to be malicious in nature."
              }
            ],
            "source": "https://github.com/ossf/malicious-packages/blob/main/osv/malicious/npm/hardhat-bits/MAL-2026-17658.json",
            "indicators": {
              "evidence_files": [
                {
                  "path": "index.js",
                  "tlsh": "0421149124d560ce9938dac0f6306115acdbc677260752b3bdfc97c927860080161fba",
                  "sha256": "4e6c4e61a7019ab0affe9c2d20e36701b330ec357be205930355bac1464f9316"
                },
                {
                  "path": "lib/config.js",
                  "tlsh": "5e265fec9591c037d6dd1b53bf0929e8e17ea8aa95ccb587853cbda829bc00fc560cd4",
                  "sha256": "34cba8ace8486e69dbb70bcedc0f5e2a72b70735afb21071f4ba2a7b6c8f3153"
                },
                {
                  "path": "package.json",
                  "tlsh": "0d017620deb88e2301ed25425c2a4643b6618c175528fc2932dba12c0f9d5ff02ff21e",
                  "sha256": "2587db067c5c545cc5025470b1043f7ced5a1aa547dc57876076576e9fb40d09"
                }
              ],
              "package_integrity": [
                {
                  "hashes": {
                    "sha1": "12b0e1e77b1386de9d31e6415c29de95c8fff0e7",
                    "sha512_sri": "sha512-owxGBrkFMQg0h3xXsv53Eg8UNKeO5q6aFQ/CPn9yZRIBL5ggLcHajRsYJMLI22DjSsP5Amh7C7xTMnNel+4l2Q=="
                  },
                  "filename": "hardhat-bits-2.21.0.tgz"
                }
              ]
            }
          }
        }
      ],
      "modified": "2026-10-08T04:00:05.136932807Z",
      "provider": "osv",
      "references": [
        "https://www.npmjs.com/package/hardhat-bits/v/2.21.0"
      ],
      "provider_metadata": {
        "malicious-packages-origins": [
          {
            "id": "IN-MAL-2026-021121",
            "sha256": "4e10f22980d33eea7649312f6b2b0a94637e5b4da400f7d585c58b6902a77944",
            "source": "amazon-inspector",
            "versions": [
              "2.21.0"
            ],
            "import_time": "2026-10-08T03:50:29.289732007Z",
            "modified_time": "2026-10-08T03:39:07Z"
          }
        ]
      }
    },
    "related_cves": [],
    "security_relevant": true,
    "severity_evidence": null
  },
  "source_id": "core-osv",
  "document_id": 98434,
  "published_at": "2026-10-08T03:39:07+00:00"
}