Skip to content

Commit

Permalink
优化并发逻辑,扫描速度增加;增加扫描Druidun默认口令、swagger未授权访问漏洞
Browse files Browse the repository at this point in the history
  • Loading branch information
selinuxG committed Aug 4, 2023
1 parent e5422c1 commit eddb6b4
Show file tree
Hide file tree
Showing 28 changed files with 193 additions and 76 deletions.
10 changes: 6 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,7 @@
| 11 | 主机操作系统识别 || 基于ttl |
| 12 | 组件识别 || 目前常用200+ |
| 13 | 自动扫描弱口令 || rdp、ssh、redis、mysql、oracle、es、telnet、pgsql等 |
| 14 | web自动扫描xss || 仅验证反射型 |
| 14 | web自动扫描xss || |



Expand All @@ -92,7 +92,7 @@
| 13 | 识别目录浏览 || |
| 14 | 识别敏感信息泄露 || |
| 15 | 识别文件下载 || |
| 16 | xss扫描 || 仅验证反射型 |
| 16 | xss扫描 || |
| 17 | 组件识别 || 目前常用200+ |

## 子域名扫描现阶段支持功能
Expand All @@ -108,12 +108,14 @@
# 常用启动参数
```
golin web (通过web方式启动,仅支持等保功能)
golin port -i 192.168.1.1/24 (扫描c段端口以及弱口令)
golin port -i 192.168.1.1/24 (扫描c段端口并扫描弱口令、xss、poc漏洞)
golin port -i 192.168.1.1/24 -c 1000 -t 1(仅扫描c段端口并设置并发数为1000,端口连接超时为1秒)
golin port -i 192.168.1.1/24 --noping --nocrack --random(扫描c段端口但不探测存活不扫描弱口令,并且打乱主机顺序扫描)
golin port -i 192.168.1.1/24 --noxss(扫描c段端口但禁用扫描xss)
golin port -i 192.168.1.1/24 --nopoc(扫描c段端口但禁用扫描poc)
golin dirsearch -u https://test.com -f 字典.txt --code 200,404 (扫描状态码为200以及404的web目录)
golin domain -u baidu.com --api (扫描子域名,并且调用fofa、RapidDNS的API)
golin [linux、mysql、oracle、sqlserver、redis、windows...] (按照3级等保要求核查各项安全配置)
golin [linux、mysql、oracle、sqlserver、redis、windows...] (按照3级等保要求核查各项安全配置生成html形式报告)
golin update (检查是否可更新)
```

Expand Down
1 change: 0 additions & 1 deletion dirscan/StatusCode.go
Original file line number Diff line number Diff line change
Expand Up @@ -103,7 +103,6 @@ func isStatusCodeOk(URL string) {
}

for k, v := range ContentType {
//fmt.Println(contype, k, v)
if strings.Contains(contype, k) {
yesurl.info = append(yesurl.info, v)
}
Expand Down
2 changes: 1 addition & 1 deletion global/percent.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ var (
)

// Percent 输出进度条
func Percent(mu *sync.Mutex, succeCount, countall int) {
func Percent(mu *sync.Mutex, succeCount, countall uint32) {
percent := (float64(succeCount) / float64(countall)) * 100.00

spinChar := rotateSpinner(mu)
Expand Down
6 changes: 3 additions & 3 deletions global/version.go
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
package global

const (
Version = "v3.3.2" //当前版本号
Releasenotes = "增加识别主机来源局域网/互联网,增加识别CVE-2022-22947漏洞检测,NPS内网穿透默认口令扫描,增加识别web组件数量,优化扫描进度条输出" //版本说明
RepoUrl = "https://api.github.com/repos/selinuxg/Golin/releases/latest" //仓库最新版本
Version = "v3.3.3" //当前版本号
Releasenotes = "优化并发逻辑,扫描速度增加;增加扫描Druidun默认口令、swagger未授权访问漏洞" //版本说明
RepoUrl = "https://api.github.com/repos/selinuxg/Golin/releases/latest" //仓库最新版本
)
34 changes: 34 additions & 0 deletions poc/AuthDruidun.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
package poc

import (
"io"
"net/http"
"strings"
)

func AuthDruidun(url string) {
url += "/druid/index.html"
req, _ := http.NewRequest("GET", url, nil)
resp, err := newRequest(req)
if err != nil {
return
}
defer resp.Body.Close()

if resp.StatusCode == 200 {
bodyBytes, err2 := io.ReadAll(resp.Body)
if err2 != nil {
return
}
bodyString := string(bodyBytes)
if strings.Contains(bodyString, "Druid Stat Index") &&
strings.Contains(bodyString, "DruidVersion") &&
strings.Contains(bodyString, "DruidDrivers") {
flags := Flagcve{
url: url,
cve: "Druid未授权访问",
}
echoFlag(flags)
}
}
}
63 changes: 63 additions & 0 deletions poc/AuthSwagger.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
package poc

import (
"io"
"net/http"
"strings"
)

func AuthSwagger(url string) {

paths := []string{
"/swagger/ui/index",
"/swagger-ui.html",
"/api/swagger-ui.html",
"/service/swagger-ui.html",
"/web/swagger-ui.html",
"/swagger/swagger-ui.html",
"/actuator/swagger-ui.html",
"/libs/swagger-ui.html",
"/template/swagger-ui.html",
"/api_docs",
"/api/docs/",
"/api/index.html",
"/swagger/v1/swagger.yaml",
"/swagger/v1/swagger.json",
"/swagger.yaml",
"/swagger.json",
"/api-docs/swagger.yaml",
"/api-docs/swagger.json",
}

for _, path := range paths {
req, _ := http.NewRequest("GET", url+path, nil)
resp, err := newRequest(req)

if err != nil {
continue
}
defer resp.Body.Close()

if resp.StatusCode == 200 {
bodyBytes, err2 := io.ReadAll(resp.Body)
if err2 != nil {
continue
}
bodyString := string(bodyBytes)

if strings.Contains(bodyString, "Swagger UI") ||
strings.Contains(bodyString, "swagger-ui.min.js") ||
strings.Contains(bodyString, "swagger:") ||
strings.Contains(bodyString, "Swagger 2.0") ||
strings.Contains(bodyString, "\"swagger\":") {
flags := Flagcve{
url: url + path,
cve: "swagger未授权访问",
}
echoFlag(flags)
//break
}
}
}

}
2 changes: 1 addition & 1 deletion poc/Spring-CVE-2022-22947.go
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ func CVE_2022_22947(url, cmd string) {
flags := Flagcve{
url: url,
cve: "CVE_2022_22947",
flag: flag,
flag: "执行命令结果:" + flag,
}
echoFlag(flags)
}
Expand Down
11 changes: 10 additions & 1 deletion poc/client.go
Original file line number Diff line number Diff line change
@@ -1,14 +1,23 @@
package poc

import (
"crypto/tls"
"net/http"
"time"
)

func newRequest(req *http.Request) (*http.Response, error) {

transport := &http.Transport{
TLSClientConfig: &tls.Config{
InsecureSkipVerify: true,
}}

client := &http.Client{
Timeout: time.Second * 3,
Transport: transport,
Timeout: time.Second * 3,
}

resp, err := client.Do(req)
return resp, err
}
4 changes: 2 additions & 2 deletions poc/nps-default-password.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,8 @@ import (
"net/http"
)

// npc_default_passwd nps默认账号密码admin/123
func nps_default_passwd(url string) {
// NPS_default_passwd nps默认账号密码admin/123
func NPS_default_passwd(url string) {
url += "/login/verify"
var data = []byte(`username=admin&password=123`)
req, err := http.NewRequest("POST", url, bytes.NewBuffer(data))
Expand Down
13 changes: 11 additions & 2 deletions poc/run.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,12 +18,21 @@ func CheckPoc(url, app string) {
url = url[:len(url)-1]
}

functions := []func(string){
AuthDruidun, //Druid未授权访问
AuthSwagger, //swagger未授权访问
}
for _, function := range functions {
function(url)
}

//以下是基于特征扫描
app = strings.ToLower(app)
switch {
case strings.Contains(app, "spring"):
CVE_2022_22947(url, "pwd") //任意执行命令
case strings.Contains(app, "nps"):
nps_default_passwd(url) //默认用户密码
NPS_default_passwd(url) //默认用户密码
}

}
Expand All @@ -32,7 +41,7 @@ func echoFlag(flag Flagcve) {
fmt.Printf("\033[2K\r") // 擦除整行
fmt.Printf("\r| %-2s | %-15s | %-15s |%s\n",
fmt.Sprintf("%s", color.RedString("%s", "✓")),
fmt.Sprintf("%s", color.RedString("发现漏洞_%s", flag.cve)),
fmt.Sprintf("%s", color.RedString("漏洞:%s", flag.cve)),
fmt.Sprintf("%s", color.RedString(flag.url)),
fmt.Sprintf("%s", color.RedString(flag.flag)),
)
Expand Down
27 changes: 19 additions & 8 deletions port/Protocol/web.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,13 +16,14 @@ import (
)

type webinfo struct {
url string
title string
app string
statuscode int
ContentType string
xss string
server string
url string //web地址
title string //网站标题
app string //识别到的组件
statuscode int //状态码
ContentType string //ContentType
xss string //是否存在xss漏洞
server string //ContentType中的server
risk string //通过title与ContentType确认是否存在风险
}

func IsWeb(host, port string, timeout int, xss, Poc bool) string {
Expand Down Expand Up @@ -81,8 +82,14 @@ func IsWeb(host, port string, timeout int, xss, Poc bool) string {
//poc扫描
if Poc {
go poc.CheckPoc(info.url, info.app)
}

// 基于title确认是否url是目录浏览
var risk []string
if strings.Contains(strings.ToLower(info.title), "index of") {
risk = append(risk, "目录浏览漏洞")
}
info.risk = strings.Join(risk, ",")

info.server = resp.Header.Get("Server")

Expand Down Expand Up @@ -134,8 +141,12 @@ func CheckApp(body string, head map[string][]string, cookies []*http.Cookie) str
func chekwebinfo(info webinfo) string {
output := fmt.Sprintf("%-23s ", info.url)

if info.risk != "" {
output += color.RedString("%s", fmt.Sprintf("[%s]", info.risk))
}

if info.xss != "" {
output += color.RedString("%s", fmt.Sprintf(" XSS:「%s」", info.xss))
output += color.RedString("%s", fmt.Sprintf(" [XSS漏洞:%s]", info.xss))
}

if info.app != "" {
Expand Down
2 changes: 1 addition & 1 deletion port/Protocol/web_RuleDatas.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ var RuleDatas = []RuleData{
{"织梦内容管理系统", "body", "(织梦内容管理系统)"},
{"宝塔", "body", "(app.bt.cn/static/app.png|安全入口校验失败|<title>入口校验失败</title>|href=\"http://www.bt.cn/bbs|恭喜, 站点创建成功!)"},
{"启明防火墙", "body", "(/cgi-bin/webui?op=get_product_model)"},
{"数据库ElasticSearch」(未授权)", "body", `(?s)"name"\s*:\s*"[^"]*".*?"cluster_name"\s*:\s*"[^"]*".*?"cluster_uuid"\s*:\s*"[^"]*".*?"number"\s*:\s*"[^"]*"`},
{"数据库|ElasticSearch[存在未授权漏洞]", "body", `(?s)"name"\s*:\s*"[^"]*".*?"cluster_name"\s*:\s*"[^"]*".*?"cluster_uuid"\s*:\s*"[^"]*".*?"number"\s*:\s*"[^"]*"`},
{"AList", "body", "(由 AList 驱动|alist_pic.js)"},
{"数据库「MongoDB」", "body", `(MongoDB)`},
{"ZABBIX-监控系统", "body", "(Zabbix SIA|<title>omni: Zabbix</title>|images/general/zabbix.ico|Zabbix SIA|zabbix-server: Zabbix)"},
Expand Down
3 changes: 2 additions & 1 deletion port/crack/ftp.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,11 @@ import (
"context"
"fmt"
"github.com/jlaffaye/ftp"
"sync"
"time"
)

func ftpcon(ctx context.Context, cancel context.CancelFunc, ip, user, passwd string, port, timeout int) {
func ftpcon(ctx context.Context, cancel context.CancelFunc, ip, user, passwd string, port, timeout int, ch <-chan struct{}, wg *sync.WaitGroup) {
defer func() {
wg.Done()
<-ch
Expand Down
3 changes: 2 additions & 1 deletion port/crack/mysql.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,10 @@ import (
"gorm.io/driver/mysql"
"gorm.io/gorm"
"gorm.io/gorm/logger"
"sync"
)

func mySql(ctx context.Context, cancel context.CancelFunc, ip, user, passwd string, port, timeout int) {
func mySql(ctx context.Context, cancel context.CancelFunc, ip, user, passwd string, port, timeout int, ch <-chan struct{}, wg *sync.WaitGroup) {
defer func() {
wg.Done()
<-ch
Expand Down
3 changes: 2 additions & 1 deletion port/crack/oracle.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,11 @@ import (
"database/sql"
"fmt"
_ "github.com/sijms/go-ora/v2"
"sync"
"time"
)

func oraclecon(ctx context.Context, cancel context.CancelFunc, ip, user, passwd string, port, timeout int) {
func oraclecon(ctx context.Context, cancel context.CancelFunc, ip, user, passwd string, port, timeout int, ch <-chan struct{}, wg *sync.WaitGroup) {
defer func() {
wg.Done()
<-ch
Expand Down
8 changes: 3 additions & 5 deletions port/crack/pgsql.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,13 +6,11 @@ import (
"gorm.io/driver/postgres"
"gorm.io/gorm"
"gorm.io/gorm/logger"
"sync"
)

func pgsql(ctx context.Context, cancel context.CancelFunc, ip, user, passwd string, port, timeout int) {
defer func() {
wg.Done()
<-ch
}()
func pgsql(ctx context.Context, cancel context.CancelFunc, ip, user, passwd string, port, timeout int, ch <-chan struct{}, wg *sync.WaitGroup) {
defer done(ch, wg)
select {
case <-ctx.Done():
return
Expand Down
7 changes: 2 additions & 5 deletions port/crack/rdp.go
Original file line number Diff line number Diff line change
Expand Up @@ -32,11 +32,8 @@ type Client struct {
vnc *rfb.RFB
}

func rdpcon(ctx context.Context, cancel context.CancelFunc, ip, user, passwd string, port, timeout int) {
defer func() {
wg.Done()
<-ch
}()
func rdpcon(ctx context.Context, cancel context.CancelFunc, ip, user, passwd string, port, timeout int, ch <-chan struct{}, wg *sync.WaitGroup) {
defer done(ch, wg)
select {
case <-ctx.Done():
return
Expand Down
3 changes: 2 additions & 1 deletion port/crack/redis.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,12 +4,13 @@ import (
"context"
"fmt"
"github.com/go-redis/redis/v8"
"sync"
"time"
)

var ctx = context.Background()

func rediscon(ctx context.Context, cancel context.CancelFunc, ip, user, passwd string, port, timeout int) {
func rediscon(ctx context.Context, cancel context.CancelFunc, ip, user, passwd string, port, timeout int, ch <-chan struct{}, wg *sync.WaitGroup) {
defer func() {
wg.Done()
<-ch
Expand Down
Loading

0 comments on commit eddb6b4

Please sign in to comment.