Skip to content

Instantly share code, notes, and snippets.

@geekman
Created December 30, 2015 08:35
Show Gist options
  • Star 2 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save geekman/e506fe45b55a8f5a9885 to your computer and use it in GitHub Desktop.
Save geekman/e506fe45b55a8f5a9885 to your computer and use it in GitHub Desktop.
32c3CTF 2015 bruteforce tool for "config.bin"
/*
* bruteforce-cfg1.go
* to bruteforce CFG1 encryption passwords for 32c3CTF "config.bin"
*
* @zxcvgm
*/
package main
import (
brutedict "github.com/dieyushi/golang-brutedict"
"crypto/aes"
"crypto/md5"
"io/ioutil"
"encoding/binary"
"bytes"
"sync"
"fmt"
"os"
)
func main() {
file, err := os.Open(os.Args[1])
if err != nil {
fmt.Println(err)
return
}
defer file.Close()
file.Seek(4 + 4 + 8 + 7 + 1 + 2, os.SEEK_SET)
// padding size. not used in the end
var padding uint16
binary.Read(file, binary.BigEndian, &padding)
data_hash := make([]byte, 16)
file.Seek(4, os.SEEK_CUR)
file.Read(data_hash)
// read header to compute checksum
headerBytes := make([]byte, 0x30)
file.ReadAt(headerBytes, 0)
for i := 8; i < 16; i++ {
headerBytes[i] = 0
}
fmt.Printf("hdr hash = %x\n", md5.Sum(headerBytes))
// header is 0x30 bytes
file.Seek(0x30, os.SEEK_SET)
src, err := ioutil.ReadAll(file)
fmt.Printf("data hash = %x\n", data_hash)
try_pwds := make(chan string, 2048)
var wg sync.WaitGroup
for i := 0; i < 4; i++ {
wg.Add(1)
go func() {
for pwd := range try_pwds {
//fmt.Printf("trying %s\n", pwd)
cksum := decryptHash(pwd, src)
if bytes.Equal(data_hash, cksum[:]) {
fmt.Printf("found password! %s\n", pwd)
os.Exit(0)
}
}
wg.Done()
}()
}
// generate passwords here
try_pwds <- "dummy"
// password len is hardcoded here
bd := brutedict.New(true, true, true, 5, 5)
defer bd.Close()
for {
id := bd.Id()
if id != "" {
try_pwds <- id
} else {
break
}
}
close(try_pwds)
wg.Wait()
//cksum := decryptHash("dummy", src)
//fmt.Printf("computed cksum %x\n", cksum)
//fmt.Printf("matches? %s\n", bytes.Equal(data_hash, cksum[:]))
}
// decrypt and hash at the same time
func decryptHash(keyStr string, data []byte)[]byte {
key := make([]byte, 32)
dst := make([]byte, aes.BlockSize)
copy(key, keyStr)
//fmt.Printf("key: %x\n", key)
c, err := aes.NewCipher(key)
if err != nil {
fmt.Println(err)
return nil
}
hash := md5.New()
n := 0
l := len(data)
for n < l {
c.Decrypt(dst, data[n:n+aes.BlockSize])
//fmt.Printf("offset %d\n", n)
//fmt.Printf("dec %x\n", dst)
hash.Write(dst)
n += aes.BlockSize
}
return hash.Sum(nil)
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment