
Esta é uma prova de conceito para abusar do filtro clean do git contra IDEs e Sublime.
Este é um problema documentado (conhecido), mas encontrei isso durante minha pesquisa e é bastante útil para RT/PT.
Resumo: A diretiva filter.<name>.clean em .git/config aponta para um script e .gitattributes vincula esse filtro a um arquivo rastreado. Sempre que o git renderiza um git diff real desse arquivo, ele executa o conteúdo da worktree pelo comando clean primeiro, então o git executa cegamente qualquer caminho que especificarmos ali.
Agora é aqui que fica interessante. Nossos editores executam git diff automaticamente no momento em que você clica em um arquivo alterado para preencher o painel de SCM (Gerenciamento de Controle de Código-Fonte) e as anotações de margem. Apenas abrir a pasta não é suficiente, mas visualizar a alteração é, e isso é algo bem natural quando você chega em um repositório.
Essa é a mesma ideia do core.fsmonitor, só que em uma diretiva diferente, e não é fsmonitor, então quem procura por isso não vai ver. A técnica se encaixa em engajamentos de RT e cenários de assume-breach com qualquer C2 ou o nosso XRayC2 para obter um callback que contorna as defesas de rede tradicionais. (É claro, e-mails de phishing são necessários para enganar o usuário final, mas abrir uma pasta em um IDE e clicar em um arquivo parece uma operação razoável.)
Prova de conceito. O git clone não carrega o .git/config, então envie a pasta com o .git/ intacto. Configuração em .git/config:
[filter "poc"]
clean = ./icons/clean.sh
smudge = cat
.gitattributes:
sample.txt filter=poc
sample.txt está commitado, mas é enviado modificado na working tree. No momento em que o git faz diff nele, o filtro clean é acionado. O clean.sh abre a Calculadora e passa o conteúdo adiante inalterado, para que a working tree nunca seja corrompida:
#!/bin/sh
pgrep -x Calculator >/dev/null 2>&1 || open -a Calculator 2>/dev/null
exec cat
Abra a pasta no seu editor, clique em sample.txt para visualizar a alteração, e uma calculadora aparece. (Saia da Calculadora para executá-lo novamente.) Este POC é específico para macOS; modifique-o para o seu ambiente.
Testado no Cursor (git CLI) e no Sublime Text (libgit2).
O filtro clean é executado apenas em um git diff completo, não no git status, então ele dispara quando o editor renderiza a alteração, não apenas ao abrir a pasta. Curiosamente, o Sublime o aciona dentro do processo via libgit2, o pai do payload é o próprio sublime_text, sem nenhum binário git na cadeia, portanto isso não se limita a ferramentas que fazem chamadas externas ao git.
https://github.com/user-attachments/assets/31ea495f-1ed8-44f8-bef3-8c6366a0eece
Assim como o fsmonitor, isso é controlado pelo prompt "confiar nesta pasta?" do editor. A maioria dos desenvolvedores mantém ~/Downloads e pastas de nível superior semelhantes como confiáveis, e o Cursor vem com a confiança de workspace desativada por padrão, então o PoC roda silenciosamente. Se um repositório estiver localizado fora desses caminhos confiáveis, o IDE perguntará "confiar neste publicador?" antes de ler .git/config.
Documentação do Git: core.fsmonitor e filter.* em https://git-scm.com/docs/gitattributes.