GNU/Linux >> Tutoriales Linux >  >> Linux

¿Cómo puedo escribir un script bash de Linux que me diga qué computadoras están ENCENDIDAS en mi LAN?

Sugeriría usar el indicador de escaneo de ping de nmap,

$ nmap -sn 192.168.1.60-70

Starting Nmap 4.11 ( http://www.insecure.org/nmap/ ) at 2009-04-09 20:13 BST
Host machine1.home (192.168.1.64) appears to be up.
Host machine2.home (192.168.1.65) appears to be up.
Nmap finished: 11 IP addresses (2 hosts up) scanned in 0.235 seconds

Dicho esto, si quieres escribirlo tú mismo (lo cual es bastante justo), así es como lo haría:

for ip in 192.168.1.{1..10}; do ping -c 1 -t 1 $ip > /dev/null && echo "${ip} is up"; done

..y una explicación de cada bit del comando anterior:

Generando lista de direcciones IP

Puedes usar el {1..10} sintaxis para generar una lista de números, por ejemplo..

$ echo {1..10}
1 2 3 4 5 6 7 8 9 10

(también es útil para cosas como mkdir {dir1,dir2}/{sub1,sub2} - lo que hace dir1 y dir2 , cada uno conteniendo sub1 y sub2 )

Entonces, para generar una lista de direcciones IP, haríamos algo como

$ echo 192.168.1.{1..10}
192.168.1.1 192.168.1.2 [...] 192.168.1.10

Bucles

Para recorrer algo en bash, usa for :

$ for thingy in 1 2 3; do echo $thingy; done
1
2
3

Hacer ping

A continuación, para hacer ping... El comando ping varía un poco con diferentes sistemas operativos, diferentes distribuciones/versiones (estoy usando OS X actualmente)

De forma predeterminada (nuevamente, en la versión OS X de ping ) hará ping hasta que se interrumpa, lo que no funcionará para esto, así que ping -c 1 solo intentará enviar un paquete, que debería ser suficiente para determinar si una máquina está funcionando.

Otro problema es el valor del tiempo de espera, que parece ser de 11 segundos en esta versión de ping. Se cambia usando el -t bandera. Un segundo debería ser suficiente para ver si una máquina en la red local está activa o no.

Entonces, el comando ping que usaremos es...

$ ping -c 1 -t 1 192.168.1.1
PING 192.168.1.1 (192.168.1.1): 56 data bytes

--- 192.168.1.1 ping statistics ---
1 packets transmitted, 0 packets received, 100% packet loss

Comprobando el resultado del ping

A continuación, necesitamos saber si la máquina respondió o no.

Podemos usar el && operador para ejecutar un comando si el primero tiene éxito, por ejemplo:

$ echo && echo "It works"

It works
$ nonexistantcommand && echo "This should not echo"
-bash: nonexistantcommand: command not found

Bien, entonces podemos hacer...

ping -c 1 -t 1 192.168.1.1 &&echo "¡192.168.1.1 está activo!"

La otra forma sería usar el código de salida de ping. El comando ping saldrá con el código de salida 0 (éxito) si funcionó, y un código distinto de cero si falló. En bash obtienes el código de salida de los últimos comandos con la variable $?

Entonces, para verificar si el comando funcionó, haríamos...

ping -c 1 -t 1 192.168.1.1;
if [ $? -eq 0 ]; then
    echo "192.168.1.1 is up";
else 
    echo "ip is down";
fi

Ocultar salida de ping

Lo último, no necesitamos ver el resultado del ping, por lo que podemos redirigir stdout a /dev/null con el > redirección, por ejemplo:

$ ping -c 1 -t 1 192.168.1.1 > /dev/null && echo "IP is up"
IP is up

Y para redirigir stderr (para descartar el ping: sendto: Host is down mensajes), utiliza 2> - por ejemplo:

$ errorcausingcommand
-bash: errorcausingcommand: command not found
$ errorcausingcommand 2> /dev/null
$

El guión

Entonces, para combinar todo eso..

for ip in 192.168.1.{1..10}; do  # for loop and the {} operator
    ping -c 1 -t 1 192.168.1.1 > /dev/null 2> /dev/null  # ping and discard output
    if [ $? -eq 0 ]; then  # check the exit code
        echo "${ip} is up" # display the output
        # you could send this to a log file by using the >>pinglog.txt redirect
    else
        echo "${ip} is down"
    fi
done

O, usando el && método, en una sola línea:

for ip in 192.168.1.{1..10}; do ping -c 1 -t 1 $ip > /dev/null && echo "${ip} is up"; done

Problema

Es lento.. Cada comando ping tarda aproximadamente 1 segundo (ya que configuramos el indicador -t timeout en 1 segundo). Solo puede ejecutar un comando ping a la vez. La forma obvia de evitar esto es usar subprocesos, por lo que puede ejecutar comandos concurrentes, pero eso va más allá de lo que debería usar bash.

"Subprocesos de Python:un primer ejemplo" explica cómo usar el módulo de subprocesos de Python para escribir un ping'er de subprocesos múltiples. Aunque en ese punto, sugeriría una vez más usar nmap -sn ..


En el mundo real, podría usar nmap para conseguir lo que quieres.

nmap -sn 10.1.1.1-255

Esto hará ping a todas las direcciones en el rango 10.1.1.1 a 10.1.1.255 y le permitirá saber cuáles responden.

Por supuesto, si de hecho quiere hacer esto como un ejercicio bash, puede ejecutar ping para cada dirección y analizar la salida, pero esa es otra historia.


Suponiendo que mi red es 10.10.0.0/24, si ejecuto un ping en la dirección de transmisión como

ping -b 10.10.0.255

Obtendré una respuesta de todas las computadoras en esta red que no bloquearon su puerto de ping ICMP.

64 bytes from 10.10.0.6: icmp_seq=1 ttl=64 time=0.000 ms
64 bytes from 10.10.0.12: icmp_seq=1 ttl=64 time=0.000 ms 
64 bytes from 10.10.0.71: icmp_seq=1 ttl=255 time=0.000 ms 

Entonces solo tienes que extraer la cuarta columna, con awk por ejemplo:

ping -b 10.10.0.255 | grep 'bytes from' | awk '{ print $4 }'

10.10.0.12:
10.10.0.6:
10.10.0.71:
10.10.0.95:

Bueno, obtendrá un duplicado y es posible que deba eliminar el ':'.

EDITAR desde comentarios:la opción -c limita el número de pings ya que el script finalizará, también podemos limitarnos a IP únicas

ping -c 5 -b 10.10.0.255 | grep 'bytes from' | awk '{ print $4 }' | sort | uniq

Linux
  1. ¿Cómo agregar un usuario de Unix/linux en un script Bash?

  2. Cómo encontrar qué Shell está utilizando en Linux

  3. ¿Cómo puedo verificar si PostgreSQL está instalado o no a través de un script de Linux?

  4. ¿Cómo puedo saber en Linux qué proceso envió una señal a mi proceso?

  5. ¿Cómo puedo probar mi script Bash en versiones anteriores de Bash?

Cómo escribir un script Bash con ejemplos

Cómo usar una contraseña cifrada en Linux Bash Shell Script

¿Cómo saber qué distribución de Linux está utilizando?

Shell Scripting para principiantes:cómo escribir Bash Scripts en Linux

¿Cómo ejecutar comandos bash de Linux en un script PERL?

Cómo encontrar qué versión de Linux está ejecutando