cloudflare/cloudflared · error

did not receive ICMP echo reply

Error message

did not receive ICMP echo reply

What it means

In icmpSendEcho, when IcmpSendEcho returns 0 replies and the reply buffer does NOT carry a parseable non-success IP status, cloudflared wraps the raw API error as 'did not receive ICMP echo reply'. It means no ICMPv4 reply arrived (or none could be attributed) within icmpRequestTimeoutMs.

Source

Thrown at ingress/icmp_windows.go:393

	if err != nil {
		return nil, err
	}
	replyCount, _, err := IcmpSendEcho_proc.Call(
		ip.handle,
		uintptr(inAddr),
		uintptr(unsafe.Pointer(&echo.Data[0])),
		uintptr(dataSize),
		noIPHeaderOption,
		uintptr(unsafe.Pointer(&replyBuf[0])),
		replySize,
		icmpRequestTimeoutMs,
	)
	if replyCount == 0 {
		// status is returned in 5th to 8th byte of reply buffer
		if status, parseErr := unmarshalIPStatus(replyBuf[4:8]); parseErr == nil && status != success {
			return nil, errors.Wrapf(err, "received ip status: %s", status)
		}
		return nil, errors.Wrap(err, "did not receive ICMP echo reply")
	} else if replyCount > 1 {
		ip.logger.Warn().Msgf("Received %d ICMP echo replies, only sending 1 back", replyCount)
	}
	return newEchoV4Resp(replyBuf)
}

// Third definition of https://docs.microsoft.com/en-us/windows/win32/api/inaddr/ns-inaddr-in_addr#syntax is address in uint32
func inAddrV4(ip netip.Addr) (uint32, error) {
	if !ip.Is4() {
		return 0, fmt.Errorf("%s is not IPv4", ip)
	}
	v4 := ip.As4()
	return endian.Uint32(v4[:]), nil
}

type echoResp interface {
	status() ipStatus
	rtt() uint32

View on GitHub (pinned to 2253eeeb25)

Solutions

  1. Treat as a timeout: retry or increase the effective timeout budget in the probing layer.
  2. Confirm the target actually responds to ICMP with the OS ping tool.
  3. Check for firewall rules silently dropping ICMP echo on the path.
  4. Verify network path stability (packet loss) between the Windows host and the destination.
Defensive patterns

Strategy: retry

Try / catch

// Go: treat as timeout and retry with a budget
resp, err := proxy.Request(ctx, dst, echo)
if err != nil && strings.Contains(err.Error(), "did not receive ICMP echo reply") {
	select {
	case <-ctx.Done():
		// give up within caller's deadline
	case <-time.After(retryDelay):
		resp, err = proxy.Request(ctx, dst, echo)
	}
}

Prevention

When it happens

Trigger: IcmpSendEcho returns replyCount == 0 with either a successful/unknown status byte pattern — typically a pure timeout where no echo response was received before icmpRequestTimeoutMs elapsed.

Common situations: Pinging hosts that silently drop ICMP (common for public endpoints), congested links exceeding the fixed request timeout, or firewalls dropping echo requests without an ICMP unreachable response.

Understand the failure class

Background: Request timed out: what client-side request timeouts mean across libraries (Request timed out, TIMED_OUT, APITimeoutError) — this error's family across 39 libraries.

Related errors


AI-assisted analysis of cloudflare/cloudflared@2253eeeb25 (2026-09-06). Data as JSON: /api/errors/95fa08da2dd8bf82. Report an issue: GitHub.