Пример #1
0
        public static string ConstructCommandLine(int packetSize, int timeout, string address, bool ipv4, int ttl = 0, PingFragmentOptions fragmentOption = PingFragmentOptions.Default)
        {
            var sb = new StringBuilder();

            sb.Append("-c 1"); // Just send a single ping ("count = 1")

            //if timeout is zero then some ping implementations can stuck infinitely if endpoint is unreachable
            if (timeout == 0)
            {
                timeout = 1;
            }

            // Pass timeout argument to ping utility
            // BusyBox, Linux: ping and ping6 requires -W flag which accepts timeout in SECONDS.
            // FreeBSD: ping requires -W flag which accepts timeout in MILLISECONDS;
            // ping6 requires -x which accepts timeout in MILLISECONDS
            // OSX: ping requires -W flag which accepts timeout in MILLISECONDS; ping6 doesn't support timeout
            if (OperatingSystem.IsFreeBSD())
            {
                if (ipv4)
                {
                    sb.Append(" -W ");
                }
                else
                {
                    sb.Append(" -x ");
                }
            }
            else if (OperatingSystem.IsMacOS())
            {
                if (ipv4)
                {
                    sb.Append(" -W ");
                }
                else
                {
                    goto skipped_timeout;
                }
            }
            else
            {
                sb.Append(" -W ");
                const int millisInSecond = 1000;
                timeout = Math.DivRem(timeout, millisInSecond, out int remainder);
                if (remainder != 0)
                {
                    timeout += 1;
                }
            }
            sb.Append(timeout);

skipped_timeout:

            // The command-line flags for "Do-not-fragment" and "TTL" are not standard.
            // In fact, they are different even between ping and ping6 on the same machine.

            // The ping utility is not flexible enough to specify an exact payload.
            // But we can at least send the right number of bytes.

            if (ttl > 0)
            {
                if (OperatingSystem.IsFreeBSD() || OperatingSystem.IsMacOS())
                {
                    // OSX and FreeBSD use -h to set hop limit for IPv6 and -m ttl for IPv4
                    if (ipv4)
                    {
                        sb.Append(" -m ");
                    }
                    else
                    {
                        sb.Append(" -h ");
                    }
                }
                else
                {
                    // Linux uses -t ttl for both IPv4 & IPv6
                    sb.Append(" -t ");
                }

                sb.Append(ttl);
            }

            if (fragmentOption != PingFragmentOptions.Default)
            {
                if (OperatingSystem.IsFreeBSD() || OperatingSystem.IsMacOS())
                {
                    // The bit is off by default on OSX & FreeBSD
                    if (fragmentOption == PingFragmentOptions.Dont)
                    {
                        sb.Append(" -D ");
                    }
                }
                else if (!s_isBusybox.Value)  // busybox implementation does not support fragmentation option.
                {
                    // Linux has three state option with default to use PMTU.
                    // When explicit option is used we set it explicitly to one or the other.
                    if (fragmentOption == PingFragmentOptions.Do)
                    {
                        sb.Append(" -M do ");
                    }
                    else
                    {
                        sb.Append(" -M dont ");
                    }
                }
            }

            // ping and ping6 do not report timing information unless at least 16 bytes are sent.
            if (packetSize < 16)
            {
                packetSize = 16;
            }

            sb.Append(" -s ");
            sb.Append(packetSize);

            sb.Append(' ');
            sb.Append(address);

            return(sb.ToString());
        }
Пример #2
0
        public static string ConstructCommandLine(int packetSize, string address, bool ipv4, int ttl = 0, PingFragmentOptions fragmentOption = PingFragmentOptions.Default)
        {
            StringBuilder sb = new StringBuilder();

            sb.Append("-c 1"); // Just send a single ping ("count = 1")

            // The command-line flags for "Do-not-fragment" and "TTL" are not standard.
            // In fact, they are different even between ping and ping6 on the same machine.

            // The ping utility is not flexible enough to specify an exact payload.
            // But we can at least send the right number of bytes.

            if (ttl > 0)
            {
                if (s_isBSD)
                {
                    // OSX and FreeBSD use -h to set hop limit for IPv6 and -m ttl for IPv4
                    if (ipv4)
                    {
                        sb.Append(" -m ");
                    }
                    else
                    {
                        sb.Append(" -h ");
                    }
                }
                else
                {
                    // Linux uses -t ttl for both IPv4 & IPv6
                    sb.Append(" -t ");
                }

                sb.Append(ttl);
            }

            if (fragmentOption != PingFragmentOptions.Default)
            {
                if (s_isBSD)
                {
                    // The bit is off by default on OSX & FreeBSD
                    if (fragmentOption == PingFragmentOptions.Dont)
                    {
                        sb.Append(" -D ");
                    }
                }
                else if (!s_isBusybox.Value)  // busybox implementation does not support fragmentation option.
                {
                    // Linux has three state option with default to use PMTU.
                    // When explicit option is used we set it explicitly to one or the other.
                    if (fragmentOption == PingFragmentOptions.Do)
                    {
                        sb.Append(" -M do ");
                    }
                    else
                    {
                        sb.Append(" -M dont ");
                    }
                }
            }

            // ping and ping6 do not report timing information unless at least 16 bytes are sent.
            if (packetSize < 16)
            {
                packetSize = 16;
            }

            sb.Append(" -s ");
            sb.Append(packetSize);

            sb.Append(' ');
            sb.Append(address);

            return(sb.ToString());
        }