mirror of
https://github.com/OJ/gobuster.git
synced 2024-11-15 08:45:21 +01:00
more debugging and fix #460
This commit is contained in:
parent
2d84a5b8e3
commit
08f6652cd8
@ -6,3 +6,4 @@
|
||||
.vscode/
|
||||
gobuster
|
||||
.git/
|
||||
mitm*
|
||||
|
2
.gitignore
vendored
2
.gitignore
vendored
@ -20,3 +20,5 @@
|
||||
|
||||
.vscode/
|
||||
gobuster
|
||||
|
||||
mitm*
|
||||
|
@ -104,12 +104,13 @@ func run(c *cli.Context) error {
|
||||
return err
|
||||
}
|
||||
|
||||
plugin, err := gobusterdir.New(&globalOpts, pluginOpts)
|
||||
log := libgobuster.NewLogger(globalOpts.Debug)
|
||||
|
||||
plugin, err := gobusterdir.New(&globalOpts, pluginOpts, log)
|
||||
if err != nil {
|
||||
return fmt.Errorf("error on creating gobusterdir: %w", err)
|
||||
}
|
||||
|
||||
log := libgobuster.NewLogger(globalOpts.Debug)
|
||||
if err := internalcli.Gobuster(c.Context, &globalOpts, plugin, log); err != nil {
|
||||
var wErr *gobusterdir.ErrWildcard
|
||||
if errors.As(err, &wErr) {
|
||||
|
@ -74,7 +74,7 @@ func BenchmarkDirMode(b *testing.B) {
|
||||
for x := 0; x < b.N; x++ {
|
||||
os.Stdout = devnull
|
||||
os.Stderr = devnull
|
||||
plugin, err := gobusterdir.New(&globalopts, pluginopts)
|
||||
plugin, err := gobusterdir.New(&globalopts, pluginopts, log)
|
||||
if err != nil {
|
||||
b.Fatalf("error on creating gobusterdir: %v", err)
|
||||
}
|
||||
|
@ -67,12 +67,13 @@ func run(c *cli.Context) error {
|
||||
return fmt.Errorf("please provide the %s keyword", gobusterfuzz.FuzzKeyword)
|
||||
}
|
||||
|
||||
plugin, err := gobusterfuzz.New(&globalOpts, pluginOpts)
|
||||
log := libgobuster.NewLogger(globalOpts.Debug)
|
||||
|
||||
plugin, err := gobusterfuzz.New(&globalOpts, pluginOpts, log)
|
||||
if err != nil {
|
||||
return fmt.Errorf("error on creating gobusterfuzz: %w", err)
|
||||
}
|
||||
|
||||
log := libgobuster.NewLogger(globalOpts.Debug)
|
||||
if err := internalcli.Gobuster(c.Context, &globalOpts, plugin, log); err != nil {
|
||||
log.Debugf("%#v", err)
|
||||
return fmt.Errorf("error on running gobuster on %s: %w", pluginOpts.URL, err)
|
||||
|
@ -47,12 +47,13 @@ func run(c *cli.Context) error {
|
||||
return err
|
||||
}
|
||||
|
||||
plugin, err := gobustergcs.New(&globalOpts, pluginOpts)
|
||||
log := libgobuster.NewLogger(globalOpts.Debug)
|
||||
|
||||
plugin, err := gobustergcs.New(&globalOpts, pluginOpts, log)
|
||||
if err != nil {
|
||||
return fmt.Errorf("error on creating gobustergcs: %w", err)
|
||||
}
|
||||
|
||||
log := libgobuster.NewLogger(globalOpts.Debug)
|
||||
if err := internalcli.Gobuster(c.Context, &globalOpts, plugin, log); err != nil {
|
||||
log.Debugf("%#v", err)
|
||||
return fmt.Errorf("error on running gobuster: %w", err)
|
||||
|
@ -127,7 +127,7 @@ func writeToFile(f *os.File, output string) error {
|
||||
}
|
||||
|
||||
// Gobuster is the main entry point for the CLI
|
||||
func Gobuster(ctx context.Context, opts *libgobuster.Options, plugin libgobuster.GobusterPlugin, log libgobuster.Logger) error {
|
||||
func Gobuster(ctx context.Context, opts *libgobuster.Options, plugin libgobuster.GobusterPlugin, log *libgobuster.Logger) error {
|
||||
// Sanity checks
|
||||
if opts == nil {
|
||||
return fmt.Errorf("please provide valid options")
|
||||
|
@ -47,12 +47,13 @@ func run(c *cli.Context) error {
|
||||
return err
|
||||
}
|
||||
|
||||
plugin, err := gobusters3.New(&globalOpts, pluginOpts)
|
||||
log := libgobuster.NewLogger(globalOpts.Debug)
|
||||
|
||||
plugin, err := gobusters3.New(&globalOpts, pluginOpts, log)
|
||||
if err != nil {
|
||||
return fmt.Errorf("error on creating gobusters3: %w", err)
|
||||
}
|
||||
|
||||
log := libgobuster.NewLogger(globalOpts.Debug)
|
||||
if err := internalcli.Gobuster(c.Context, &globalOpts, plugin, log); err != nil {
|
||||
log.Debugf("%#v", err)
|
||||
return fmt.Errorf("error on running gobuster: %w", err)
|
||||
|
@ -64,12 +64,13 @@ func run(c *cli.Context) error {
|
||||
return err
|
||||
}
|
||||
|
||||
plugin, err := gobustervhost.New(&globalOpts, pluginOpts)
|
||||
log := libgobuster.NewLogger(globalOpts.Debug)
|
||||
|
||||
plugin, err := gobustervhost.New(&globalOpts, pluginOpts, log)
|
||||
if err != nil {
|
||||
return fmt.Errorf("error on creating gobustervhost: %w", err)
|
||||
}
|
||||
|
||||
log := libgobuster.NewLogger(globalOpts.Debug)
|
||||
if err := internalcli.Gobuster(c.Context, &globalOpts, plugin, log); err != nil {
|
||||
log.Debugf("%#v", err)
|
||||
return fmt.Errorf("error on running gobuster on %s: %w", pluginOpts.URL, err)
|
||||
|
@ -61,7 +61,7 @@ func BenchmarkVhostMode(b *testing.B) {
|
||||
for x := 0; x < b.N; x++ {
|
||||
os.Stdout = devnull
|
||||
os.Stderr = devnull
|
||||
plugin, err := gobustervhost.New(&globalopts, pluginopts)
|
||||
plugin, err := gobustervhost.New(&globalopts, pluginopts, log)
|
||||
if err != nil {
|
||||
b.Fatalf("error on creating gobusterdir: %v", err)
|
||||
}
|
||||
|
@ -51,7 +51,7 @@ type GobusterDir struct {
|
||||
}
|
||||
|
||||
// New creates a new initialized GobusterDir
|
||||
func New(globalopts *libgobuster.Options, opts *OptionsDir) (*GobusterDir, error) {
|
||||
func New(globalopts *libgobuster.Options, opts *OptionsDir, logger *libgobuster.Logger) (*GobusterDir, error) {
|
||||
if globalopts == nil {
|
||||
return nil, fmt.Errorf("please provide valid global options")
|
||||
}
|
||||
@ -86,7 +86,7 @@ func New(globalopts *libgobuster.Options, opts *OptionsDir) (*GobusterDir, error
|
||||
Method: opts.Method,
|
||||
}
|
||||
|
||||
h, err := libgobuster.NewHTTPClient(&httpOpts)
|
||||
h, err := libgobuster.NewHTTPClient(&httpOpts, globalopts.Debug, logger)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
@ -37,7 +37,7 @@ type GobusterFuzz struct {
|
||||
}
|
||||
|
||||
// New creates a new initialized GobusterFuzz
|
||||
func New(globalopts *libgobuster.Options, opts *OptionsFuzz) (*GobusterFuzz, error) {
|
||||
func New(globalopts *libgobuster.Options, opts *OptionsFuzz, logger *libgobuster.Logger) (*GobusterFuzz, error) {
|
||||
if globalopts == nil {
|
||||
return nil, fmt.Errorf("please provide valid global options")
|
||||
}
|
||||
@ -72,7 +72,7 @@ func New(globalopts *libgobuster.Options, opts *OptionsFuzz) (*GobusterFuzz, err
|
||||
Method: opts.Method,
|
||||
}
|
||||
|
||||
h, err := libgobuster.NewHTTPClient(&httpOpts)
|
||||
h, err := libgobuster.NewHTTPClient(&httpOpts, globalopts.Debug, logger)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
@ -99,6 +99,12 @@ func (d *GobusterFuzz) ProcessWord(ctx context.Context, word string, progress *l
|
||||
if len(d.options.Headers) > 0 {
|
||||
requestOptions.ModifiedHeaders = make([]libgobuster.HTTPHeader, len(d.options.Headers))
|
||||
for i := range d.options.Headers {
|
||||
// Host header can't be set via Headers, needs to be a separate field
|
||||
if d.options.Headers[i].Name == "Host" {
|
||||
requestOptions.Host = strings.ReplaceAll(d.options.Headers[i].Value, FuzzKeyword, word)
|
||||
continue
|
||||
}
|
||||
|
||||
requestOptions.ModifiedHeaders[i] = libgobuster.HTTPHeader{
|
||||
Name: strings.ReplaceAll(d.options.Headers[i].Name, FuzzKeyword, word),
|
||||
Value: strings.ReplaceAll(d.options.Headers[i].Value, FuzzKeyword, word),
|
||||
|
@ -27,7 +27,7 @@ type GobusterGCS struct {
|
||||
}
|
||||
|
||||
// New creates a new initialized GobusterGCS
|
||||
func New(globalopts *libgobuster.Options, opts *OptionsGCS) (*GobusterGCS, error) {
|
||||
func New(globalopts *libgobuster.Options, opts *OptionsGCS, logger *libgobuster.Logger) (*GobusterGCS, error) {
|
||||
if globalopts == nil {
|
||||
return nil, fmt.Errorf("please provide valid global options")
|
||||
}
|
||||
@ -57,7 +57,7 @@ func New(globalopts *libgobuster.Options, opts *OptionsGCS) (*GobusterGCS, error
|
||||
FollowRedirect: true,
|
||||
}
|
||||
|
||||
h, err := libgobuster.NewHTTPClient(&httpOpts)
|
||||
h, err := libgobuster.NewHTTPClient(&httpOpts, globalopts.Debug, logger)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
@ -27,7 +27,7 @@ type GobusterS3 struct {
|
||||
}
|
||||
|
||||
// New creates a new initialized GobusterS3
|
||||
func New(globalopts *libgobuster.Options, opts *OptionsS3) (*GobusterS3, error) {
|
||||
func New(globalopts *libgobuster.Options, opts *OptionsS3, logger *libgobuster.Logger) (*GobusterS3, error) {
|
||||
if globalopts == nil {
|
||||
return nil, fmt.Errorf("please provide valid global options")
|
||||
}
|
||||
@ -57,7 +57,7 @@ func New(globalopts *libgobuster.Options, opts *OptionsS3) (*GobusterS3, error)
|
||||
FollowRedirect: true,
|
||||
}
|
||||
|
||||
h, err := libgobuster.NewHTTPClient(&httpOpts)
|
||||
h, err := libgobuster.NewHTTPClient(&httpOpts, globalopts.Debug, logger)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
@ -31,7 +31,7 @@ type GobusterVhost struct {
|
||||
}
|
||||
|
||||
// New creates a new initialized GobusterDir
|
||||
func New(globalopts *libgobuster.Options, opts *OptionsVhost) (*GobusterVhost, error) {
|
||||
func New(globalopts *libgobuster.Options, opts *OptionsVhost, logger *libgobuster.Logger) (*GobusterVhost, error) {
|
||||
if globalopts == nil {
|
||||
return nil, fmt.Errorf("please provide valid global options")
|
||||
}
|
||||
@ -66,7 +66,7 @@ func New(globalopts *libgobuster.Options, opts *OptionsVhost) (*GobusterVhost, e
|
||||
Method: opts.Method,
|
||||
}
|
||||
|
||||
h, err := libgobuster.NewHTTPClient(&httpOpts)
|
||||
h, err := libgobuster.NewHTTPClient(&httpOpts, globalopts.Debug, logger)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
@ -7,6 +7,7 @@ import (
|
||||
"fmt"
|
||||
"io"
|
||||
"net/http"
|
||||
"net/http/httputil"
|
||||
"net/url"
|
||||
"strings"
|
||||
)
|
||||
@ -29,6 +30,8 @@ type HTTPClient struct {
|
||||
cookies string
|
||||
method string
|
||||
host string
|
||||
debug bool
|
||||
logger *Logger
|
||||
}
|
||||
|
||||
// RequestOptions is used to pass options to a single individual request
|
||||
@ -42,7 +45,7 @@ type RequestOptions struct {
|
||||
}
|
||||
|
||||
// NewHTTPClient returns a new HTTPClient
|
||||
func NewHTTPClient(opt *HTTPOptions) (*HTTPClient, error) {
|
||||
func NewHTTPClient(opt *HTTPOptions, debug bool, logger *Logger) (*HTTPClient, error) {
|
||||
var proxyURLFunc func(*http.Request) (*url.URL, error)
|
||||
var client HTTPClient
|
||||
proxyURLFunc = http.ProxyFromEnvironment
|
||||
@ -104,6 +107,8 @@ func NewHTTPClient(opt *HTTPOptions) (*HTTPClient, error) {
|
||||
break
|
||||
}
|
||||
}
|
||||
client.debug = debug
|
||||
client.logger = logger
|
||||
return &client, nil
|
||||
}
|
||||
|
||||
@ -171,6 +176,11 @@ func (client *HTTPClient) makeRequest(ctx context.Context, fullURL string, opts
|
||||
// currently only relevant on fuzzing
|
||||
if len(opts.ModifiedHeaders) > 0 {
|
||||
for _, h := range opts.ModifiedHeaders {
|
||||
// empty headers are not valid
|
||||
if h.Name == "" {
|
||||
continue
|
||||
}
|
||||
|
||||
if client.noCanonicalizeHeaders {
|
||||
// https://stackoverflow.com/questions/26351716/how-to-keep-key-case-sensitive-in-request-header-using-golang
|
||||
req.Header[h.Name] = []string{h.Value}
|
||||
@ -195,6 +205,14 @@ func (client *HTTPClient) makeRequest(ctx context.Context, fullURL string, opts
|
||||
req.SetBasicAuth(client.username, client.password)
|
||||
}
|
||||
|
||||
if client.debug {
|
||||
dump, err := httputil.DumpRequestOut(req, false)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
client.logger.Debugf("%s", dump)
|
||||
}
|
||||
|
||||
resp, err := client.client.Do(req)
|
||||
if err != nil {
|
||||
var ue *url.Error
|
||||
|
@ -51,7 +51,8 @@ func TestRequest(t *testing.T) {
|
||||
h := httpServerT(t, ret)
|
||||
defer h.Close()
|
||||
var o HTTPOptions
|
||||
c, err := NewHTTPClient(&o)
|
||||
log := NewLogger(false)
|
||||
c, err := NewHTTPClient(&o, false, log)
|
||||
if err != nil {
|
||||
t.Fatalf("Got Error: %v", err)
|
||||
}
|
||||
@ -78,7 +79,8 @@ func BenchmarkRequestWithoutBody(b *testing.B) {
|
||||
h := httpServerB(b, r)
|
||||
defer h.Close()
|
||||
var o HTTPOptions
|
||||
c, err := NewHTTPClient(&o)
|
||||
log := NewLogger(false)
|
||||
c, err := NewHTTPClient(&o, false, log)
|
||||
if err != nil {
|
||||
b.Fatalf("Got Error: %v", err)
|
||||
}
|
||||
@ -98,7 +100,8 @@ func BenchmarkRequestWitBody(b *testing.B) {
|
||||
h := httpServerB(b, r)
|
||||
defer h.Close()
|
||||
var o HTTPOptions
|
||||
c, err := NewHTTPClient(&o)
|
||||
log := NewLogger(false)
|
||||
c, err := NewHTTPClient(&o, false, log)
|
||||
if err != nil {
|
||||
b.Fatalf("Got Error: %v", err)
|
||||
}
|
||||
@ -118,8 +121,9 @@ func BenchmarkNewHTTPClient(b *testing.B) {
|
||||
h := httpServerB(b, r)
|
||||
defer h.Close()
|
||||
var o HTTPOptions
|
||||
log := NewLogger(false)
|
||||
for x := 0; x < b.N; x++ {
|
||||
_, err := NewHTTPClient(&o)
|
||||
_, err := NewHTTPClient(&o, false, log)
|
||||
if err != nil {
|
||||
b.Fatalf("Got Error: %v", err)
|
||||
}
|
||||
|
@ -25,13 +25,13 @@ type ResultToStringFunc func(*Gobuster, *Result) (*string, error)
|
||||
// Gobuster is the main object when creating a new run
|
||||
type Gobuster struct {
|
||||
Opts *Options
|
||||
Logger Logger
|
||||
Logger *Logger
|
||||
plugin GobusterPlugin
|
||||
Progress *Progress
|
||||
}
|
||||
|
||||
// NewGobuster returns a new Gobuster object
|
||||
func NewGobuster(opts *Options, plugin GobusterPlugin, logger Logger) (*Gobuster, error) {
|
||||
func NewGobuster(opts *Options, plugin GobusterPlugin, logger *Logger) (*Gobuster, error) {
|
||||
var g Gobuster
|
||||
g.Opts = opts
|
||||
g.plugin = plugin
|
||||
|
@ -16,8 +16,8 @@ type Logger struct {
|
||||
debug bool
|
||||
}
|
||||
|
||||
func NewLogger(debug bool) Logger {
|
||||
return Logger{
|
||||
func NewLogger(debug bool) *Logger {
|
||||
return &Logger{
|
||||
log: log.New(os.Stdout, "", 0),
|
||||
errorLog: log.New(os.Stderr, color.New(color.FgRed).Sprint("[ERROR] "), 0),
|
||||
debugLog: log.New(os.Stderr, color.New(color.FgBlue).Sprint("[DEBUG] "), 0),
|
||||
|
Loading…
Reference in New Issue
Block a user