misc update, 初步可用

This commit is contained in:
M09Ic 2022-09-23 11:20:41 +08:00
parent 637eb21377
commit ea3ea58dd2
4 changed files with 65 additions and 45 deletions

View File

@ -15,7 +15,6 @@ func NewBaseline(u *fasthttp.URI, resp *fasthttp.Response) *baseline {
UrlString: u.String(), UrlString: u.String(),
Status: resp.StatusCode(), Status: resp.StatusCode(),
IsValid: true, IsValid: true,
Body: make([]byte, 20480),
} }
bl.Body = resp.Body() bl.Body = resp.Body()
@ -31,9 +30,8 @@ func NewInvalidBaseline(u *fasthttp.URI, resp *fasthttp.Response) *baseline {
bl := &baseline{ bl := &baseline{
Url: u, Url: u,
UrlString: u.String(), UrlString: u.String(),
//BodyLength: resp.ContentLength, Status: resp.StatusCode(),
Status: resp.StatusCode(), IsValid: false,
IsValid: false,
} }
bl.RedirectURL = string(resp.Header.Peek("Location")) bl.RedirectURL = string(resp.Header.Peek("Location"))
@ -95,7 +93,7 @@ func (bl *baseline) FuzzyEqual(other *baseline) bool {
func (bl *baseline) String() string { func (bl *baseline) String() string {
var line strings.Builder var line strings.Builder
line.WriteString("[+] ") //line.WriteString("[+] ")
line.WriteString(bl.UrlString) line.WriteString(bl.UrlString)
line.WriteString(fmt.Sprintf(" - %d - %d ", bl.Status, bl.BodyLength)) line.WriteString(fmt.Sprintf(" - %d - %d ", bl.Status, bl.BodyLength))
if bl.RedirectURL != "" { if bl.RedirectURL != "" {
@ -104,7 +102,11 @@ func (bl *baseline) String() string {
} }
line.WriteString(bl.Frameworks.ToString()) line.WriteString(bl.Frameworks.ToString())
//line.WriteString(bl.Extracteds) //line.WriteString(bl.Extracteds)
line.WriteString("\n") //line.WriteString("\n")
if bl.Err != nil {
line.WriteString("err: ")
line.WriteString(bl.Err.Error())
}
return line.String() return line.String()
} }

View File

@ -30,19 +30,21 @@ func NewPool(ctx context.Context, config *pkg.Config, outputCh chan *baseline) (
worder: words.NewWorder(config.Wordlist), worder: words.NewWorder(config.Wordlist),
outputCh: outputCh, outputCh: outputCh,
tempCh: make(chan *baseline, config.Thread), tempCh: make(chan *baseline, config.Thread),
wg: &sync.WaitGroup{}, wg: sync.WaitGroup{},
initwg: sync.WaitGroup{},
checkPeriod: 100, checkPeriod: 100,
errPeriod: 10, errPeriod: 10,
//reqCount: 1,
} }
switch config.Mod { switch config.Mod {
case pkg.PathSpray: case pkg.PathSpray:
pool.genReq = func(s string) (*fasthttp.Request, error) { pool.genReq = func(s string) (*fasthttp.Request, error) {
return pool.BuildPathRequest(s) return pool.buildPathRequest(s)
} }
case pkg.HostSpray: case pkg.HostSpray:
pool.genReq = func(s string) (*fasthttp.Request, error) { pool.genReq = func(s string) (*fasthttp.Request, error) {
return pool.BuildHostRequest(s) return pool.buildHostRequest(s)
} }
} }
@ -55,12 +57,11 @@ func NewPool(ctx context.Context, config *pkg.Config, outputCh chan *baseline) (
} }
var bl *baseline var bl *baseline
resp, err := pool.client.Do(pctx, req) resp, reqerr := pool.client.Do(pctx, req)
if err != nil { if reqerr != nil && reqerr != fasthttp.ErrBodyTooLarge {
//logs.Log.Debugf("%s request error, %s", strurl, err.Error()) //logs.Log.Debugf("%s request error, %s", strurl, err.Error())
pool.errorCount++ pool.errorCount++
bl = &baseline{Err: err} bl = &baseline{UrlString: pool.BaseURL + unit.path, Err: reqerr}
} else { } else {
defer fasthttp.ReleaseResponse(resp) defer fasthttp.ReleaseResponse(resp)
defer fasthttp.ReleaseRequest(req) defer fasthttp.ReleaseRequest(req)
@ -71,22 +72,32 @@ func NewPool(ctx context.Context, config *pkg.Config, outputCh chan *baseline) (
} else { } else {
bl = NewInvalidBaseline(req.URI(), resp) bl = NewInvalidBaseline(req.URI(), resp)
} }
bl.Err = reqerr
} }
switch unit.source { switch unit.source {
case CheckSource: case CheckSource:
if pool.baseline == nil { logs.Log.Debugf("check: " + bl.String())
if pool.base == nil {
//初次check覆盖baseline //初次check覆盖baseline
pool.baseline = bl pool.base = bl
pool.initwg.Done()
} else if bl.Err != nil { } else if bl.Err != nil {
logs.Log.Warn("maybe ip banned by waf") logs.Log.Warn("maybe ip banned by waf")
} else if !pool.baseline.Equal(bl) { } else if !pool.base.Equal(bl) {
logs.Log.Warn("maybe trigger risk control") logs.Log.Warn("maybe trigger risk control")
} }
case WordSource: case WordSource:
// 异步进行性能消耗较大的深度对比 // 异步进行性能消耗较大的深度对比
pool.reqCount++
pool.tempCh <- bl pool.tempCh <- bl
if pool.reqCount%pool.checkPeriod == 0 {
go pool.check()
} else if pool.reqCount%pool.errPeriod == 0 {
go pool.check()
}
} }
//todo connectivity check //todo connectivity check
pool.bar.Done() pool.bar.Done()
@ -108,7 +119,7 @@ type Pool struct {
ctx context.Context ctx context.Context
cancel context.CancelFunc cancel context.CancelFunc
//baseReq *http.Request //baseReq *http.Request
baseline *baseline base *baseline
outputCh chan *baseline outputCh chan *baseline
tempCh chan *baseline tempCh chan *baseline
reqCount int reqCount int
@ -116,18 +127,16 @@ type Pool struct {
failedCount int failedCount int
checkPeriod int checkPeriod int
errPeriod int errPeriod int
analyzeDone bool
genReq func(s string) (*fasthttp.Request, error) genReq func(s string) (*fasthttp.Request, error)
//wordlist []string worder *words.Worder
worder *words.Worder wg sync.WaitGroup
wg *sync.WaitGroup initwg sync.WaitGroup
} }
func (p *Pool) check() { func (p *Pool) check() {
var wg sync.WaitGroup p.wg.Add(1)
wg.Add(1)
_ = p.pool.Invoke(newUnit(pkg.RandPath(), CheckSource)) _ = p.pool.Invoke(newUnit(pkg.RandPath(), CheckSource))
//}
wg.Wait()
if p.failedCount > breakThreshold { if p.failedCount > breakThreshold {
p.cancel() p.cancel()
@ -135,20 +144,21 @@ func (p *Pool) check() {
} }
func (p *Pool) Init() error { func (p *Pool) Init() error {
p.initwg.Add(1)
p.check() p.check()
p.initwg.Wait()
// todo 分析baseline // todo 分析baseline
// 检测基本访问能力 // 检测基本访问能力
if p.baseline != nil && p.baseline.Err != nil { if p.base != nil && p.base.Err != nil {
p.cancel() p.cancel()
return p.baseline.Err return p.base.Err
} }
p.baseline.Collect() p.base.Collect()
if p.base.RedirectURL != "" {
if p.baseline.RedirectURL != "" {
CheckRedirect = func(redirectURL string) bool { CheckRedirect = func(redirectURL string) bool {
if redirectURL == p.baseline.RedirectURL { if redirectURL == p.base.RedirectURL {
// 相同的RedirectURL将被认为是无效数据 // 相同的RedirectURL将被认为是无效数据
return false return false
} else { } else {
@ -170,13 +180,7 @@ Loop:
if !ok { if !ok {
break Loop break Loop
} }
p.reqCount++
p.wg.Add(1) p.wg.Add(1)
if p.reqCount%p.checkPeriod == 0 {
go p.check()
} else if p.reqCount%p.errPeriod == 0 {
go p.check()
}
_ = p.pool.Invoke(newUnit(u, WordSource)) _ = p.pool.Invoke(newUnit(u, WordSource))
case <-time.NewTimer(time.Duration(p.DeadlineTime) * time.Second).C: case <-time.NewTimer(time.Duration(p.DeadlineTime) * time.Second).C:
break Loop break Loop
@ -186,8 +190,8 @@ Loop:
break Loop break Loop
} }
} }
p.bar.Close()
p.wg.Wait() p.Close()
} }
func (p *Pool) PreCompare(resp *fasthttp.Response) error { func (p *Pool) PreCompare(resp *fasthttp.Response) error {
@ -212,7 +216,7 @@ func (p *Pool) RunWithWord(words []string) {
func (p *Pool) Comparing() { func (p *Pool) Comparing() {
for bl := range p.tempCh { for bl := range p.tempCh {
if p.baseline.Equal(bl) { if p.base.Equal(bl) {
// 如果是同一个包则设置为无效包 // 如果是同一个包则设置为无效包
bl.IsValid = false bl.IsValid = false
p.outputCh <- bl p.outputCh <- bl
@ -220,7 +224,7 @@ func (p *Pool) Comparing() {
} }
bl.Collect() bl.Collect()
if p.EnableFuzzy && p.baseline.FuzzyEqual(bl) { if p.EnableFuzzy && p.base.FuzzyEqual(bl) {
bl.IsValid = false bl.IsValid = false
p.outputCh <- bl p.outputCh <- bl
continue continue
@ -228,15 +232,25 @@ func (p *Pool) Comparing() {
p.outputCh <- bl p.outputCh <- bl
} }
}
func (p *Pool) BuildPathRequest(path string) (*fasthttp.Request, error) { p.analyzeDone = true
}
func (p *Pool) Close() {
p.wg.Wait()
p.bar.Close()
close(p.tempCh)
for !p.analyzeDone {
time.Sleep(time.Duration(100) * time.Millisecond)
}
}
func (p *Pool) buildPathRequest(path string) (*fasthttp.Request, error) {
req := fasthttp.AcquireRequest() req := fasthttp.AcquireRequest()
req.SetRequestURI(p.BaseURL + path) req.SetRequestURI(p.BaseURL + path)
return req, nil return req, nil
} }
func (p *Pool) BuildHostRequest(host string) (*fasthttp.Request, error) { func (p *Pool) buildHostRequest(host string) (*fasthttp.Request, error) {
req := fasthttp.AcquireRequest() req := fasthttp.AcquireRequest()
req.SetRequestURI(p.BaseURL) req.SetRequestURI(p.BaseURL)
req.SetHost(host) req.SetHost(host)

View File

@ -161,7 +161,7 @@ func (r *Runner) Outputting() {
select { select {
case bl := <-r.OutputCh: case bl := <-r.OutputCh:
if bl.IsValid { if bl.IsValid {
logs.Log.Console(bl.String()) logs.Log.Console("[+] " + bl.String() + "\n")
} else { } else {
logs.Log.Debug(bl.String()) logs.Log.Debug(bl.String())
} }

View File

@ -8,6 +8,10 @@ import (
"time" "time"
) )
var (
DefaultMaxBodySize = 1024 * 100 // 100k
)
func NewClient(thread int, timeout int) *Client { func NewClient(thread int, timeout int) *Client {
//tr := &http.Transport{ //tr := &http.Transport{
// //Proxy: Proxy, // //Proxy: Proxy,
@ -31,7 +35,7 @@ func NewClient(thread int, timeout int) *Client {
MaxConnWaitTimeout: time.Duration(timeout) * time.Second, MaxConnWaitTimeout: time.Duration(timeout) * time.Second,
ReadTimeout: time.Duration(timeout) * time.Second, ReadTimeout: time.Duration(timeout) * time.Second,
WriteTimeout: time.Duration(timeout) * time.Second, WriteTimeout: time.Duration(timeout) * time.Second,
MaxResponseBodySize: 20480, MaxResponseBodySize: DefaultMaxBodySize,
}, },
timeout: time.Duration(timeout) * time.Second, timeout: time.Duration(timeout) * time.Second,
} }