← Back to Feed CACHED · 2026-05-17 09:42:19 · cache_key CVE-2025-29912
CVE-2023-7163 · CWE-20 · Disclosed 2023-12-28

A security issue exists in D-Link D-View 8 v2

ASSESSED — NOISGATE V0.5
Vendor
Reassessed
Verdict:
01 · The Real Story

This is a fake badge at the loading dock, not a master key to the whole building

CVE-2023-7163 affects D-Link D-View 8 v2.0.2.89 and earlier and breaks trust between the Core server and Probe servers. An unauthenticated actor who can reach the probe/core service can register rogue probes with probe-online, pollute the probe inventory, and—if they know a real probeId—race legitimate probes with request_task calls to grab queued tasks that may contain SNMP, WMI, or SSH credentials.

The vendor's CRITICAL 10.0 score overshoots real enterprise risk. This is not unauthenticated code execution on the D-View core itself; the nasty outcomes depend on reaching an internal management channel, and the most damaging path also needs knowledge of a legitimate probe ID plus pending tasks worth stealing. Still, it deserves HIGH because D-View is a network-management control plane: if an attacker is on that segment, this flaw can expose device credentials and disrupt discovery and operations without needing D-View credentials.

"Critical on paper, but in practice this is an internal management-plane hijack, not an internet-scale one-shot RCE."
02 · The Attack Path

4 steps from start to impact.

STEP 01

Reach the Core probe service on TCP 17500

The attacker first needs network access to the D-View Core service used by probes. Tenable's PoC targets the Core on port 17500, which D-View documentation and the PoC both identify as the default Core listening port for probe communication.
Conditions required:
  • Network path to the D-View Core host
  • Probe/Core service reachable on TCP 17500
  • Target is running D-View 8 <= 2.0.2.89
Where this breaks in practice:
  • This traffic usually lives on a management VLAN, server segment, or VPN-only path rather than the public internet
  • D-View is a niche enterprise NMS, so the exposed population is much smaller than commodity edge software
  • Firewall ACLs often already restrict which subnets may talk to management infrastructure
Detection/coverage: ASM and port scans can find reachable 17500/tcp; asset discovery can identify D-View with Tenable plugin 183521, but that is product detection, not a definitive vulnerable-version check.
STEP 02

Register a rogue probe with Tenable's dview8_probe_server.py

The unauthenticated attacker sends a probe-online task to the Core and claims an arbitrary probeId. Because the Core does not strongly authenticate the probe on this path, the bogus probe is accepted and added to inventory, poisoning the DView8_Probe collection and UI state.
Conditions required:
  • Unauthenticated access to the Core probe channel
  • Ability to send probe protocol messages
Where this breaks in practice:
  • IP allowlists or strict east-west firewall policy can stop this cold
  • Environments using only a local probe have less operational surface than multi-probe enterprise deployments
Detection/coverage: Watch for new or duplicate probe registrations, sudden growth in probe inventory, and Core-side logs or MongoDB changes involving unexpected probeId values.
STEP 03

Race a legitimate probe for queued tasks

To steal interesting data, the attacker uses request_task calls more frequently than the real probe and asks for a known legitimate probeId. Tenable notes real probes poll every 10 seconds; the attacker can poll faster and capture tasks before the legitimate probe consumes them.
Conditions required:
  • Knowledge of a valid legitimate probeId
  • A legitimate probe exists and is active
  • Queued tasks are present in DView8_Task
Where this breaks in practice:
  • Learning probeId is easier on the same LAN because the ID format embeds the probe MAC address
  • If no discovery, CLI, or credential-bearing tasks are pending, impact drops sharply
  • This is a race; the attacker needs timing and persistence, not just one packet
Detection/coverage: Look for repeated request_task activity from non-probe IPs, especially faster-than-normal polling intervals and multiple task fetch attempts for the same probeId.
STEP 04

Exfiltrate credentials or break probe-driven operations

Captured tasks can expose SNMP, WMI, or SSH credentials used by D-View discovery and CLI features. Because a stolen task is marked consumed, the legitimate probe may never execute it, producing discovery failures, operational blind spots, or other denial-of-service side effects.
Conditions required:
  • Queued tasks contain credentials or operational jobs
  • Admins are using discovery or CLI features, or scheduled jobs are running
Where this breaks in practice:
  • Impact is mostly limited to what D-View orchestrates; this is not arbitrary code execution on the Core
  • Some credentials may be low-value or scoped to network management only
  • Downstream device controls and credential hygiene can reduce blast radius after theft
Detection/coverage: Correlate missing or failed discovery jobs, unexpected CLI task failures, and downstream authentication attempts using service credentials shortly after anomalous probe traffic.
03 · Intelligence Metadata

The supporting signals.

In-the-wild statusNo confirmed active exploitation found in the browsed sources. CISA's KEV catalog does not list this CVE, and I found no public GreyNoise campaign write-up tied to it.
Proof-of-concept availabilityPublic PoC exists. Tenable's advisory includes working example usage of dview8_probe_server.py for both rogue probe registration and task theft.
EPSS3.444% from the supplied intel. Percentile was not provided in the prompt and was not directly retrievable from the browsed official EPSS pages.
KEV statusNot KEV-listed as of the current review against CISA's Known Exploited Vulnerabilities Catalog.
CVSS vector reality checkVendor/CNA scored it 10.0 with CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:C/C:H/I:H/A:H; NVD shows 9.8 with unchanged scope. In practice, the real-world path behaves more like an internal management-channel abuse case than a universal internet-edge critical.
Affected versionsD-Link D-View 8 <= 2.0.2.89 per NVD and Tenable.
Fixed version statusNo explicit vendor advisory for this CVE was found in the browsed sources. D-Link download pages show later builds such as 2.0.3.88 and newer current releases, but I did not find an authoritative statement tying this CVE to a specific fixed build.
Exposure / scanning dataNo reliable public indexed exposure count found. I did not find a browsed Shodan/Censys/GreyNoise source with counts for this service. *Inference:* exposure is likely narrower than the CVSS suggests because D-View is a niche NMS and the vulnerable channel is the default Core port 17500 used for probe communication.
Disclosure2023-12-28 published by Tenable; NVD enrichment followed on 2024-01-04.
Reporter / product contextTenable Research reported it. D-View 8 is marketed as a Windows/Linux network management platform for up to 5,000 nodes with multiple probes in enterprise deployments, which increases internal blast radius once the management plane is reachable.
04 · The Call

noisgate verdict.

Final Verdict
DOWNGRADED to HIGH (7.3/10)

The decisive downward pressure is attacker position: this flaw matters only after an attacker can reach D-View's probe/core channel, which is usually an internal management path rather than a true internet-edge service. It still lands in HIGH because the unauthenticated protocol trust failure can expose network-management credentials and disrupt a control-plane system defenders rely on.

HIGH Technical exploit path and impact mechanics from Tenable research
MEDIUM Typical enterprise exposure assumptions for D-View Core/Probe traffic
LOW Exact vendor-fixed version for this specific CVE

Why this verdict

  • Reachability is the whole game: the vulnerable service is the Core/Probe channel on 17500/tcp, which is normally on an internal management network, VPN, or tightly filtered server segment—not a mass-exposed internet edge.
  • The best impact path has extra prerequisites: stealing useful tasks requires a valid probeId, and Tenable specifically notes learning that ID is easier for an attacker on the same LAN because it embeds the probe MAC address.
  • Operational context gates the payoff: credential exposure only happens when queued tasks actually carry secrets such as SNMP, WMI, or SSH credentials; if no such jobs are pending, the attacker mostly gets inventory pollution and task disruption.
  • The product population is limited: D-View 8 is a specialized NMS, not a ubiquitous browser, VPN, or web framework, so reachable victim counts are inherently lower.
  • Public exploit material exists: Tenable published a usable PoC, which keeps this above MEDIUM because exploitation on a reachable management segment is straightforward once prerequisites are met.

Why not higher?

This is not direct unauthenticated code execution on the D-View Core host, and the most damaging outcomes are conditional rather than automatic. There is also no KEV listing or solid public evidence of broad in-the-wild exploitation, so treating it as a top-tier emergency like an internet-edge RCE would over-prioritize noise.

Why not lower?

The flaw is still unauthenticated on the affected channel, public PoC exists, and D-View can queue high-value management credentials inside tasks. On networks where an adversary reaches the management plane, this becomes a clean credential-theft and operational-disruption primitive against a high-trust system.

05 · Compensating Control

What to do — in priority order.

  1. Restrict Core/Probe traffic — Allow 17500/tcp only between the D-View Core and the exact approved probe IPs or subnets, and deploy that control within 30 days. This directly cuts off the unauthenticated protocol path the PoC abuses.
  2. Move D-View onto a dedicated management segment — Place the Core and probes on a dedicated management VLAN or VPN-only enclave with no broad workstation access, and complete that isolation within 30 days. The biggest severity reducer here is attacker position, so shrinking who can even talk to the service matters more than generic hardening.
  3. Inventory and validate all probe IDs — Baseline expected probe hosts, names, MAC-derived probeId patterns, and last-seen IPs, then alert on new or duplicate probes within 30 days. This catches the rogue-registration side of the attack even when no patch status is clear.
  4. Monitor task-fetch cadence — Alert when non-probe IPs request tasks or when a probe ID is polled faster than the normal cadence Tenable described, and put that detection in place within 30 days. Frequent request_task races are one of the clearest behavioral signs of exploitation.
  5. Reduce credential value inside D-View — Replace broad shared SNMP/WMI/SSH accounts with scoped, rotated, least-privilege credentials and remove stale entries within 30 days. Even if the attacker wins the race for a task, lower-value credentials mean lower blast radius.
What doesn't work
  • Turning on MFA for the D-View web UI does not fix this path, because the vulnerable channel is the unauthenticated Core/Probe protocol, not an interactive web login.
  • A WAF is usually irrelevant here, because the attack targets the probe/core service on 17500/tcp, not just the browser-facing application surface.
  • Relying only on EDR is weak coverage: the exploit is mostly protocol abuse and credential interception over an allowed management channel, so there may be little obvious endpoint exploit telemetry to catch early.
06 · Verification

Crowdsourced verification payload.

Run this on the target D-View host or on a management endpoint with local read access to that host's package/registry metadata. Invoke it as python3 check_dview8_cve_2023_7163.py on Linux or py check_dview8_cve_2023_7163.py on Windows; no admin rights are usually needed for local package queries and uninstall-registry reads, but elevated rights may help if your environment restricts them.

noisgate-verify.py
PYTHONREAD-ONLYSAFE
#!/usr/bin/env python3
# check_dview8_cve_2023_7163.py
# Detect likely exposure to CVE-2023-7163 on D-Link D-View 8.
# Exit codes: 0=PATCHED, 1=VULNERABLE, 2=UNKNOWN, 3=ERROR

import os
import platform
import re
import subprocess
import sys

THRESHOLD = "2.0.2.89"
NAME_PATTERNS = ["d-view 8", "dview 8", "d-link d-view 8", "dlink d-view 8"]


def normalize_version(v):
    nums = [int(x) for x in re.findall(r"\d+", v or "")]
    if not nums:
        return None
    return nums


def compare_versions(a, b):
    va = normalize_version(a)
    vb = normalize_version(b)
    if va is None or vb is None:
        return None
    maxlen = max(len(va), len(vb))
    va += [0] * (maxlen - len(va))
    vb += [0] * (maxlen - len(vb))
    if va < vb:
        return -1
    if va > vb:
        return 1
    return 0


def looks_like_target(name):
    n = (name or "").strip().lower()
    return any(p in n for p in NAME_PATTERNS)


def query_windows_registry():
    try:
        import winreg
    except Exception:
        return []

    results = []
    hives = [winreg.HKEY_LOCAL_MACHINE, winreg.HKEY_CURRENT_USER]
    paths = [
        r"SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall",
        r"SOFTWARE\WOW6432Node\Microsoft\Windows\CurrentVersion\Uninstall",
    ]

    for hive in hives:
        for path in paths:
            try:
                key = winreg.OpenKey(hive, path)
            except OSError:
                continue
            try:
                count = winreg.QueryInfoKey(key)[0]
                for i in range(count):
                    try:
                        subname = winreg.EnumKey(key, i)
                        subkey = winreg.OpenKey(key, subname)
                        display_name = None
                        display_version = None
                        try:
                            display_name = winreg.QueryValueEx(subkey, "DisplayName")[0]
                        except OSError:
                            pass
                        try:
                            display_version = winreg.QueryValueEx(subkey, "DisplayVersion")[0]
                        except OSError:
                            pass
                        if looks_like_target(display_name):
                            results.append((display_name, display_version, "registry"))
                    except OSError:
                        continue
            finally:
                try:
                    winreg.CloseKey(key)
                except Exception:
                    pass
    return results


def run_cmd(cmd):
    try:
        cp = subprocess.run(cmd, stdout=subprocess.PIPE, stderr=subprocess.PIPE, text=True, check=False)
        return cp.returncode, cp.stdout, cp.stderr
    except Exception as e:
        return 127, "", str(e)


def query_linux_packages():
    results = []

    rc, out, _ = run_cmd(["dpkg-query", "-W", "-f=${Package}\t${Version}\n"])
    if rc == 0:
        for line in out.splitlines():
            parts = line.split("\t", 1)
            if len(parts) != 2:
                continue
            pkg, ver = parts
            if looks_like_target(pkg) or "dview" in pkg.lower() or "d-view" in pkg.lower():
                results.append((pkg, ver, "dpkg"))

    rc, out, _ = run_cmd(["rpm", "-qa", "--qf", "%{NAME}\t%{VERSION}-%{RELEASE}\n"])
    if rc == 0:
        for line in out.splitlines():
            parts = line.split("\t", 1)
            if len(parts) != 2:
                continue
            pkg, ver = parts
            if looks_like_target(pkg) or "dview" in pkg.lower() or "d-view" in pkg.lower():
                results.append((pkg, ver, "rpm"))

    return results


def dedupe(results):
    seen = set()
    clean = []
    for item in results:
        if item not in seen:
            seen.add(item)
            clean.append(item)
    return clean


def choose_best(results):
    versionish = []
    for name, ver, source in results:
        if normalize_version(ver):
            versionish.append((name, ver, source))
    return versionish[0] if versionish else None


def main():
    system = platform.system().lower()
    findings = []

    if "windows" in system:
        findings.extend(query_windows_registry())
    else:
        findings.extend(query_linux_packages())

    findings = dedupe(findings)
    best = choose_best(findings)

    if not findings:
        print("UNKNOWN: D-Link D-View 8 not found via local registry/package metadata")
        sys.exit(2)

    if best is None:
        printable = "; ".join([f"{n} [{s}] version={v}" for n, v, s in findings])
        print(f"UNKNOWN: D-Link D-View 8 found but version not parseable: {printable}")
        sys.exit(2)

    name, ver, source = best
    cmpv = compare_versions(ver, THRESHOLD)
    if cmpv is None:
        print(f"UNKNOWN: unable to compare version '{ver}' from {source}")
        sys.exit(2)

    if cmpv <= 0:
        print(f"VULNERABLE: {name} version {ver} from {source} is <= {THRESHOLD}")
        sys.exit(1)
    else:
        print(f"PATCHED: {name} version {ver} from {source} is > {THRESHOLD}")
        sys.exit(0)


if __name__ == "__main__":
    try:
        main()
    except Exception as e:
        print(f"UNKNOWN: error during detection: {e}")
        sys.exit(3)
07 · Bottom Line

If you remember one thing.

TL;DR
Monday morning, treat every D-View 8 host at version 2.0.2.89 or earlier as a HIGH priority management-plane containment problem, not a generic internet-fire drill. Per the noisgate mitigation SLA, restrict 17500/tcp to approved probe IPs, isolate Core/Probe traffic onto a dedicated management segment, and alert on rogue probe registrations within 30 days; then, per the noisgate remediation SLA, validate whether you can move to a non-affected current D-View build or retire/replace the platform if you cannot establish authoritative patch status, and complete that remediation within 180 days.

Sources

  1. Tenable Research Advisory TRA-2023-43
  2. NVD CVE-2023-7163
  3. D-Link D-View 8 product site
  4. D-Link D-View 8 manual (port and architecture reference)
  5. D-Link Japan D-View 8 download page
  6. CISA Known Exploited Vulnerabilities Catalog
  7. FIRST EPSS overview
  8. Tenable Nessus D-View 8 detection plugin 183521
Peer Review

What defenders are saying.

Submit a review attribution: handle + country only
0 flags selected · stored anonymously
Validation Results

Crowdsourced verification outputs.

Results submitted by users who ran the verification payload against their environment.