libgoblin


Documentação
https://docs.rs/goblin/
changelog
Uso
Goblin requer rustc 1.85.0 (edição Rust 2024).
Adicione ao seu Cargo.toml
[dependencies]
goblin = "0.10"
Funcionalidades
- nome incrível de crate
- implementação zero-copy, multiplataforma e consciente de endianness de ELF64/32 — uau!
- parser Mach-o de 32/64 bits, zero-copy, multiplataforma e consciente de endianness — zoiks!
- parser PE de 32/64 bits — bing!
- parser de arquivos no estilo Unix e BSD (este último cortesia de @willglynn) — huzzah!
- muitas opções de cfg — vai fazer sua cabeça girar e te deixar furioso ao ler o código-fonte!
- fuzzeado — "É um prazer relatar que goblin resistiu a 100 milhões de execuções de fuzzing, 1 milhão de execuções para cada semente de 1 a 100." — @sanxiyn
- testes
libgoblin tem como objetivo ser a solução completa para análise, parsing e carregamento de binários.
Casos de uso
Goblin suporta principalmente os seguintes casos de uso importantes:
-
Estruturas #[repr(C)] principais, sem std, tempo de compilação reduzido, 32/64 (ou ambos) à sua escolha.
-
Type punning. Defina uma função uma vez em um tipo, mas faça-a funcionar em variantes de 32 ou 64 bits — sem realmente mudar nada, e sem macros! Veja examples/automagic.rs para um exemplo básico.
-
Modo std. Isso adiciona implementações de leitura e escrita via Pread e Pwrite, leitura de arquivo, alocações convenientes, métodos extras, etc. É para clientes que podem alocar e desejam ler binários do disco.
-
Endian_fd. Um nome terrível 😆 isso é para análise binária como em panopticon ou falcon que precisa ler binários de endianness estrangeira, ou como base para construir binutils multiplataforma de arquitetura estrangeira, por exemplo, cargo-sym e bingrep são exemplos simples disso, mas o céu é o limite.
Aqui estão algumas coisas que você pode fazer com esta crate (ou ajudar a implementar para que possam ser feitas):
- Escrever um compilador e usá-lo para gerar binários (todas as estruturas C brutas têm
Pwrite derivado).
- Escrever uma ferramenta de análise binária que carregue, analise e processe vários formatos binários, por exemplo, panopticon ou falcon.
- Escrever um ligador dinâmico semi-funcional.
- Escrever um kernel e carregar binários usando configuração
no_std. Ou seja, é essencialmente apenas definições de structs e constantes (como um cabeçalho C) — sem fd, sem saída, sem std.
- Escrever uma ferramenta bin2json, porque por que formatos binários não deveriam estar em JSON?
Configurações (cfgs)
libgoblin é projetado para ser massivamente configurável. As flags atuais são:
- elf64 — binários ELF de 64 bits, definições de struct
repr(C)
- elf32 — binários ELF de 32 bits, definições de struct
repr(C)
- mach64 — definições de struct
repr(C) para Mach-O de 64 bits
- mach32 — definições de struct
repr(C) para Mach-O de 32 bits
- pe32 — definições de struct
repr(C) para PE de 32 bits
- pe64 — definições de struct
repr(C) para PE de 64 bits
- te — definições de struct
repr(C) para Executável Terso (TE)
- archive — um parser de arquivos Unix
- endian_fd — analisa de acordo com a endianness no binário
- std — para permitir ambientes
no_std
Mantenedores
- PE: @kkent030315
- Elf: @m4b, aberto para candidaturas
- Mach-o: @m4b, aberto para candidaturas
Mantenedores são revisores de primeiro contato para aquele backend específico. São escolhidos com base em contribuições anteriores, atividade, conhecimento base e comportamento amigável e gregário :D
Atualmente, eu (@m4b) só tenho direitos de merge para todos os PRs. No futuro, é provável que o(s) mantenedor(es) daquele backend também tenham direitos de merge.
Por fim, ainda provavelmente farei revisões superficiais em todos os PRs, mas na maioria das vezes/ totalidade ficarei com o mantenedor daquele backend.
E lembre-se sempre da sabedoria de Bill e Ted: "Sejam excelentes uns com os outros!"
Contribuidores
Muito obrigado a todos ❤️ !
Em ordem lexicográfica:
Contribuindo
Salvo indicação explícita em contrário, você concorda que suas contribuições são licenciadas conforme descrito no arquivo LICENSE que acompanha (MIT).
- Por favor, prefixe os commits com o componente binário afetado; quanto mais específico melhor, por exemplo, se você apenas modificar relocações no módulo elf, use "elf.reloc: adicionadas novas constantes para Z80".
- As mensagens de commit devem explicar a mudança, nada genérico como "alterado" ou "corrigido"; se você enviar commits assim em um PR, saiba que @m4b ou alguém provavelmente os fará squash.
- Se você estiver fazendo uma alteração grande em um módulo, por favor, abra uma issue primeiro e vamos discutir; não quero perder seu tempo se não for uma boa direção técnica ou algo assim.
- Se o seu PR não estiver recebendo atenção, responda a todos os comentários relevantes levantados no PR e, se ainda assim não houver resposta, marque @m4b no github e também sinta-se à vontade para enviar um e-mail para @m4b.
- Por favor, adicione testes se estiver adicionando um novo recurso. Sinta-se à vontade para adicionar testes mesmo que não esteja adicionando um recurso; testes são incríveis e fáceis em Rust.