go-ping / ping

ICMP Ping library for Go
MIT License
1.31k stars 344 forks source link

Pings not being returned after a certain number of IP addresses #201

Closed cycloss closed 1 year ago

cycloss commented 2 years ago

I'm building a utility to keep track of network nodes with this library, but after a certain number of IP addresses tested, pings stop being returned. My application is containerised using docker, and it works for about 20 IP addresses in sequence, but after around that number, pings stop being returned for further IP addresses. The strange thing is that IP addresses which are reported as not responding, can be pinged from outside the container on my development machine, but not from inside the container.

My latency testing function (called sequentially for different ips) looks like this:

func getLatency(ipAddress string, msLatencyTrigger int) (*time.Duration, error) {
    pinger, err := ping.NewPinger(ipAddress)
    pinger.SetPrivileged(true)
    if err != nil {
        return nil, err
    }
    pinger.Count = 10
    pinger.Timeout = time.Second * 5
    var averagePing *time.Duration
    pinger.OnFinish = func(stats *ping.Statistics) {
        if stats.PacketsRecv == 0 {
            averagePing = nil
        } else {
            averagePing = &stats.AvgRtt
        }
    }

    err = pinger.Run()
    return averagePing, err
}

Am I missing something critical here about the library? Or is this not a library problem?

stanimirivanovde commented 2 years ago

Look at the issue I just posted as it might be related: https://github.com/go-ping/ping/issues/209.

First you're asking ping to do 10 pings (count = 10) but the timeout is 5 seconds with default interval of 1 second which means you'll only get 5 pings at the most and probably get the 5th one truncated. The timeout kills the entire ping operation. So I'd say you want the timeout to be at least one second larger than the count * interval.

As to why the ping doesn't return the correct results - make sure you can ping the hosts inside the container using the regular Linux command. The way docker default networking is set can prevent the containers from reaching out to your outside network. You might need play with your host and docker firewalls.