How SpeedtestService Measures Server Latency and Bandwidth in v2rayN

SpeedtestService measures server latency through raw TCP handshakes and ICMP-like pings routed through local SOCKS5 proxies, then calculates bandwidth by downloading test files via the same proxy tunnel, storing all metrics through ProfileExManager for UI display.

The SpeedtestService class in the open-source v2rayN client (2dust/v2rayN) provides comprehensive network performance testing for V2Ray/Xray server configurations. Located in v2rayN/ServiceLib/Services/SpeedtestService.cs, this service orchestrates concurrent latency and bandwidth measurements while managing proxy lifecycle and UI updates through injected callbacks.

Architecture and Core Components

According to the 2dust/v2rayN source code, the service operates through an injected update callback (_updateFunc) that streams SpeedTestResult objects to the UI in real-time. It supports cancellation via ExitLoop() and uses semaphores to manage concurrent test execution safely. All results persist through ProfileExManager.Instance, which stores delay and speed metrics for each server profile using SetTestDelay and SetTestSpeed methods.

Measuring Server Latency (Ping)

The service implements two distinct latency measurement paths depending on whether you need rapid screening or accurate proxy-path latency.

TCP Handshake Latency Measurement

For rapid latency assessment without establishing a full proxy tunnel, the RunTcpingAsync method calls GetTcpingTime at v2rayN/ServiceLib/Services/SpeedtestService.cs (lines 323-352). This function opens a raw TCP socket directly to the server's address and port, measuring the elapsed milliseconds between ConnectAsync initiation and successful connection completion. The implementation enforces a 5-second timeout, providing a quick "handshake" latency ideal for fast server screening.

Real Ping via SOCKS5 Proxy

For accurate latency through the actual encrypted path, RunRealPingAsync launches a temporary local SOCKS5 listener using the server's configuration. It invokes ConnectionHandler.GetRealPingTime with the configurable test URL specified in _config.SpeedTestItem.SpeedPingTestUrl, sending ICMP-like probes through the established proxy tunnel. This measures true round-trip time from the client through the V2Ray/Xray server to the target destination, with results stored via ProfileExManager.Instance.SetTestDelay.

Measuring Bandwidth (Speed Test)

Bandwidth measurement occurs only after successful latency verification when the blSpeedTest parameter is true.

Download-Based Throughput Calculation

The DoSpeedTest method (located in SpeedtestService.cs) creates a WebProxy instance pointing to the local SOCKS5 listener for the target server configuration. It calls DownloadService.DownloadDataAsync, which utilizes DownloaderHelper.Instance.DownloadDataAsync4Speed to fetch the test file configured in _config.SpeedTestItem.SpeedTestUrl.

The download helper executes the HTTP GET request through the proxy tunnel and returns the measured speed as a formatted string (e.g., "12.34"). The service parses this to a decimal value and persists it via ProfileExManager.Instance.SetTestSpeed, providing realistic throughput data for the specific server configuration.

Practical Implementation Example

The following example demonstrates initializing the service and executing a comprehensive speed test:

// Load configuration and define UI callback
var config = Config.Load();
Func<SpeedTestResult, Task> updateFunc = async result =>
{
    Console.WriteLine($"Server {result.IndexId}: {result.Delay}ms delay, {result.Speed}MB/s");
};

// Initialize service with configuration and callback
var speedtest = new SpeedtestService(config, updateFunc);

// Execute full speed test (latency + bandwidth)
await speedtest.RunLoop(ESpeedActionType.Speedtest, selectedProfileItems);

To cancel an ongoing test programmatically:

speedtest.ExitLoop(); // Signals cancellation via exit-loop key

Summary

  • Dual latency modes: TCP handshake for quick checks (GetTcpingTime) and full proxy ping for path-accurate measurements (ConnectionHandler.GetRealPingTime).
  • Bandwidth measurement: Downloads test files through SOCKS5 proxies using DownloadService.DownloadDataAsync and DownloaderHelper.Instance.DownloadDataAsync4Speed.
  • Data persistence: All metrics store through ProfileExManager.Instance using SetTestDelay and SetTestSpeed methods.
  • Concurrency control: Semaphores manage parallel tests while ExitLoop() provides thread-safe cancellation support.
  • Configuration-driven: Test URLs are configurable via _config.SpeedTestItem.SpeedPingTestUrl (latency) and _config.SpeedTestItem.SpeedTestUrl (bandwidth).

Frequently Asked Questions

What is the difference between TCP ping and Real ping in v2rayN SpeedtestService?

TCP ping (GetTcpingTime) measures raw TCP connection latency to the server endpoint without proxy overhead, suitable for quick server screening. Real ping routes ICMP-like probes through the established SOCKS5 proxy tunnel via ConnectionHandler.GetRealPingTime, measuring true round-trip time through the encrypted forwarding path.

Where does SpeedtestService store latency and speed test results?

Results persist through ProfileExManager.Instance.SetTestDelay for latency values and ProfileExManager.Instance.SetTestSpeed for bandwidth values. This manager makes metrics available for UI display, server sorting, and selection algorithms throughout the v2rayN application.

How does the bandwidth test avoid interfering with system proxy settings?

The service creates isolated WebProxy instances pointing to temporary local SOCKS5 listeners created specifically for each server test. This ensures bandwidth measurement occurs through dedicated proxy tunnels without modifying system-wide proxy configurations or affecting other applications.

Can I customize the test URLs used by SpeedtestService?

Yes. Configure _config.SpeedTestItem.SpeedPingTestUrl for latency test targets and _config.SpeedTestItem.SpeedTestUrl for bandwidth test files in the v2rayN configuration settings. These URLs determine the destination endpoints used when measuring latency and download speed.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →