ver trabajos segundo programa proceso plano enviar ejecutar ejecuciones correr comandos comando bash ssh background-process pid

bash - trabajos - ver ejecuciones en segundo plano linux



¿Cómo elimino una sesión ssh en segundo plano/desconectada? (10)

Estoy usando la sinergia del programa junto con un túnel ssh

Funciona, solo tengo que abrir una consola y escribir estos dos comandos:

ssh -f -N -L localhost:12345:otherHost:12345 otherUser@OtherHost synergyc localhost

porque im lazy hice un Bash-Script que se ejecuta con un solo clic sobre un ícono:

#!/bin/bash ssh -f -N -L localhost:12345:otherHost:12345 otherUser@OtherHost synergyc localhost

el Bash-Script anterior también funciona, pero ahora también quiero matar la sinergia y el túnel ssh mediante un clic de ratón, así que tengo que guardar los PID de sinergia y ssh en el archivo para matarlos más tarde:

#!/bin/bash mkdir -p /tmp/synergyPIDs || exit 1 rm -f /tmp/synergyPIDs/ssh || exit 1 rm -f /tmp/synergyPIDs/synergy || exit 1 [ ! -e /tmp/synergyPIDs/ssh ] || exit 1 [ ! -e /tmp/synergyPIDs/synergy ] || exit 1 ssh -f -N -L localhost:12345:otherHost:12345 otherUser@OtherHost echo $! > /tmp/synergyPIDs/ssh synergyc localhost echo $! > /tmp/synergyPIDs/synergy

Pero los archivos de este script están vacíos.

¿Cómo obtengo los PID de ssh y la sinergia?
(Intento evitar las combinaciones de ps aux | grep ... | awk ... | sed ... , tiene que haber una manera más fácil).


Acabo de encontrar este hilo y quería mencionar la utilidad de Linux "pidof":

$ pidof init 1


Basado en la muy buena respuesta de @ghoti, aquí hay una secuencia de comandos más simple (para probar) que utiliza los sockets de control SSH sin la necesidad de configuración adicional:

#!/bin/bash if ssh -fN -MS /tmp/mysocket -L localhost:12345:otherHost:12345 otherUser@otherHost; then synergyc localhost ssh -S /tmp/mysocket -O exit otherHost fi

synergyc solo se iniciará si el túnel se ha establecido con éxito, que se cerrará tan pronto como vuelva la synergyc . Aunque la solución carece de informes de errores adecuados.


Con todo respeto a los usuarios de pgrep , pkill , ps | awk ps | awk , etc, hay una manera mucho mejor.

Considere que si confía en ps -aux | grep ... ps -aux | grep ... para encontrar un proceso, corre el riesgo de una colisión. Puede tener un caso de uso donde sea poco probable, pero como regla general, no es el camino a seguir.

SSH proporciona un mecanismo para administrar y controlar procesos en segundo plano. Pero como tantas otras cosas SSH, es una característica "avanzada", y muchas personas (al parecer, de las otras respuestas aquí) desconocen su existencia.

En mi propio caso de uso, tengo una estación de trabajo en casa en la que quiero dejar un túnel que se conecta a un proxy HTTP en la red interna de mi oficina, y otro que me da acceso rápido a las interfaces de administración en servidores compartidos . Así es como puedes crear los túneles básicos, iniciados desde casa:

$ ssh -fNT -L8888:proxyhost:8888 -R22222:localhost:22 officefirewall $ ssh -fNT -L4431:www1:443 -L4432:www2:443 colocatedserver

Esto causa que ssh se encienda en sí mismo, dejando los túneles abiertos. Pero si el túnel se va, estoy atascado, y si quiero encontrarlo, tengo que analizar mi lista de procesos y en casa tengo el ssh "correcto" (en caso de que accidentalmente haya lanzado varios que se vean) similar).

En cambio, si quiero administrar conexiones múltiples, utilizo la opción de configuración ControlMaster de SSH, junto con la opción de línea de comandos -O para control. Por ejemplo, con lo siguiente en mi archivo ~/.ssh/config ,

host officefirewall colocatedserver ControlMaster auto ControlPath ~/.ssh/cm_sockets/%r@%h:%p

los comandos ssh de arriba, cuando se ejecutan, dejarán spoor en ~/.ssh/cm_sockets/ que puede proporcionar acceso para el control, por ejemplo:

$ ssh -O check officefirewall Master running (pid=23980) $ ssh -O exit officefirewall Exit request sent. $ ssh -O check officefirewall Control socket connect(/home/ghoti/.ssh/cm_socket/[email protected]:22): No such file or directory

Y en este punto, el túnel (y el control de la sesión SSH) se ha ido, sin la necesidad de usar un martillo ( kill , killall , pkill , etc.).

Devolviendo esto a tu caso de uso ...

Está estableciendo el túnel a través del cual desea que syngergyc converse con syngergys en el puerto TCP 12345. Para eso, haría algo como lo siguiente.

Agregue una entrada a su archivo ~/.ssh/config :

Host otherHosttunnel HostName otherHost User otherUser LocalForward 12345 otherHost:12345 RequestTTY no ExitOnForwardFailure yes ControlMaster auto ControlPath ~/.ssh/cm_sockets/%r@%h:%p

Tenga en cuenta que la opción de línea de comando -L se maneja con la palabra clave LocalForward , y las líneas Control {Master, Path} se incluyen para asegurarse de tener el control una vez que se establece el túnel.

Entonces, puedes modificar tu script bash a algo como esto:

#!/bin/bash if ! ssh -f -N otherHosttunnel; then echo "ERROR: couldn''t start tunnel." >&2 exit 1 else synergyc localhost ssh -O exit otherHosttunnel fi

La opción -f recorre el túnel, dejando un socket en su ControlPath para cerrar el túnel más tarde. Si el ssh falla (que puede deberse a un error de red o ExitOnForwardFailure ), no hay necesidad de salir del túnel, pero si no falló ( else ), se inicia synergyc y luego el túnel se cierra después de que sale.

También es posible que desee ver si la opción SSH LocalCommand podría utilizarse para iniciar synergyc directamente desde su archivo de configuración ssh.


Este es más un caso especial para Synergyc (y la mayoría de los otros programas que intentan demonizarse a sí mismos). ¡Usando $! funcionaría, excepto que synergyc hace un syscall de clonación () durante la ejecución que le dará un nuevo PID distinto al que bash pensó que tenía. Si quieres evitar esto para poder usar $ !, entonces puedes decirle a synergyc que se quede en el forground y luego lo fondo.

synergyc -f -n mydesktop remoteip & synergypid=$!

synergyc también hace algunas otras cosas como autorestart que es posible que desee desactivar si está tratando de administrarlo.


Otra opción es usar pgrep para encontrar el PID del proceso ssh más nuevo

ssh -fNTL 8073:localhost:873 otherUser@OtherHost tunnelPID=$(pgrep -n -x ssh) synergyc localhost kill -HUP $tunnelPID


Puede soltar el -f , que lo hace ejecutarlo en segundo plano, luego ejecutarlo con eval y forzarlo al fondo usted mismo.

A continuación, puede agarrar el pid . Asegúrese de poner el & dentro de la declaración de eval .

eval "ssh -N -L localhost:12345:otherHost:12345 otherUser@OtherHost & " tunnelpid=$!


Puede usar lsof para mostrar el pid del proceso que escucha el puerto 12345 en localhost:

lsof -t -i @localhost:12345 -sTCP:listen

Ejemplos:

PID=$(lsof -t -i @localhost:12345 -sTCP:listen) lsof -t -i @localhost:12345 -sTCP:listen >/dev/null && echo "Port in use"


Puedes buscar el procedimiento ssh que está vinculado a tu puerto local, usando esta línea:

netstat -tpln | grep 127/.0/.0/.1:12345 | awk ''{print $7}'' | sed ''s#/.*##''

Devuelve el PID del proceso utilizando el puerto 12345 / TCP en localhost. Por lo tanto, no tiene que filtrar todos los resultados ssh de ps .

Si solo necesita comprobar, si ese puerto está vinculado, use:

netstat -tln | grep 127/.0/.0/.1:12345 >/dev/null 2>&1

Devuelve 1 si no está vinculado o 0 si alguien está escuchando este puerto.


así que no quiero agregar un & al final de los comandos ya que la conexión morirá si la consola wintow está cerrada ... así que terminé con un ps-grep-awk-sed-combo

ssh -f -N -L localhost:12345:otherHost:12345 otherUser@otherHost echo `ps aux | grep -F ''ssh -f -N -L localhost'' | grep -v -F ''grep'' | awk ''{ print $2 }''` > /tmp/synergyPIDs/ssh synergyc localhost echo `ps aux | grep -F ''synergyc localhost'' | grep -v -F ''grep'' | awk ''{ print $2 }''` > /tmp/synergyPIDs/synergy

(Podrías integrar grep en awk, pero ahora soy demasiado flojo)


Resumen rápido: no funcionará.

¡Mi primera idea es que debe iniciar los procesos en segundo plano para obtener sus PID con $! .

Un patrón como

some_program & some_pid=$! wait $some_pid

podría hacer lo que necesites ... excepto que entonces ssh no estará en primer plano para pedir más frases de contraseña.

Bueno, entonces, es posible que necesites algo diferente después de todo. ssh -f probablemente genere un nuevo proceso que tu caparazón nunca podrá saber al invocarlo de todos modos. Idealmente, ssh en sí mismo ofrecería una forma de escribir su PID en algún archivo.