Skip to content

Instantly share code, notes, and snippets.

@nasirhm
Created October 19, 2024 09:59
Show Gist options
  • Save nasirhm/435e81e414461a97729e9b5d21861b1b to your computer and use it in GitHub Desktop.
Save nasirhm/435e81e414461a97729e9b5d21861b1b to your computer and use it in GitHub Desktop.
// $ go mod init
// $ go mod tidy
// --
// It'll install the x86 ASM package.
// It traverses the directory for subdirectories and all the files.
// It determines the sections (it only decodes the executable section) and the assembly of each file into a CSV.
package main
import (
"debug/elf"
"encoding/csv"
"fmt"
"log"
"os"
"path/filepath"
"strings"
"golang.org/x/arch/x86/x86asm"
)
func main() {
if len(os.Args) < 2 {
fmt.Println("Usage: go run main.go <directory>")
os.Exit(1)
}
dir := os.Args[1]
csvFile, err := os.Create("disassembly.csv")
if err != nil {
log.Fatalf("Error creating CSV file: %v", err)
}
defer csvFile.Close()
writer := csv.NewWriter(csvFile)
defer writer.Flush()
writer.Write([]string{"Filename", "Section", "Assembly"})
err = filepath.Walk(dir, func(path string, info os.FileInfo, err error) error {
if err != nil {
return err
}
if !info.IsDir() && filepath.Ext(path) == ".o" { // Process only ELF files
err = processELF(path, writer)
if err != nil {
return err
}
}
return nil
})
if err != nil {
log.Fatalf("Error walking directory: %v", err)
}
}
func processELF(filename string, writer *csv.Writer) error {
f, err := elf.Open(filename)
if err != nil {
return fmt.Errorf("error opening ELF file %s: %v", filename, err)
}
defer f.Close()
var combinedAssemblyOutput string
for _, section := range f.Sections {
// check if the section is executable
if section.Flags&elf.SHF_EXECINSTR != 0 {
combinedAssemblyOutput += fmt.Sprintf("Section: %s\n", section.Name)
data, err := section.Data()
if err != nil {
return fmt.Errorf("error reading section %s in %s: %v", section.Name, filename, err)
}
for i := 0; i < len(data); {
inst, err := x86asm.Decode(data[i:], 64)
if err != nil {
return fmt.Errorf("error decoding instruction in %s: %v", filename, err)
}
combinedAssemblyOutput += fmt.Sprintf("%#x: %s\n", section.Addr+uint64(i), inst.String())
i += inst.Len
}
combinedAssemblyOutput = strings.ReplaceAll(combinedAssemblyOutput, "\n", " ")
writer.Write([]string{filename, section.Name, combinedAssemblyOutput})
}
}
return nil
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment