基于Go语言实现一个并发端口扫描器

Written by

in

文章目录
  • 端口扫描器是网络安全领域常用的工具,它通过对目标主机的端口进行扫描,检测目标设备是否开放某些服务端口(如 HTTP、FTP、SSH 等)。常见的端口扫描场景包括: 安全审计:检测主机是否存在未授权服务 漏洞扫描:识别可能存在漏洞的服务端口 网络诊断:排查服务器是否正常工作 传统的端口扫描使用串行方式,一个端口一个端口地检查,速度非常慢。而 Go 的并发编程可以极大地提升扫描效率。
  • 我们将实现一个并发端口扫描器,具备以下功能: 输入目标主机 IP 和端口范围 使用并发扫描多个端口 输出每个端口的开放状态 使用超时机制控制扫描时间,避免阻塞
  • 优化方向 说明 控制并发数量 使用令牌桶算法(Token Bucket)或 sem 控制并发扫描的 Goroutine 数量 支持输入多个目标 IP 扩展支持一次扫描多个 IP 地址 扫描端口的协议支持 不仅支持 TCP 端口扫描,还可支持 UDP 扫描 日志记录 将扫描结果输出到日志文件,便于后期分析 进度条显示 添加扫描进度显示,提升用户体验 智能端口扫描 根据常见端口列表(如 80、443、21 等)进行扫描
  • 通过本篇案例,你学会了如何用 Go 实现一个并发端口扫描器,掌握了以下关键技术: 使用 Goroutine 实现并发任务处理 利用 sync.WaitGroup 等待所有并发任务完成 使用 net.DialTimeout 进行超时控制,防止阻塞 使用 Channel 收集并传递任务结果 这个并发端口扫描器可以帮助你在网络安全和系统维护中快速诊断目标主机的开放端口。通过优化,您还可以将其扩展成更完整的网络扫描工具。 以上就是基于Go语言实现一个并发端口扫描器的详细内容,更多关于Go并发端口扫描器的资料请关注风君子博客其它相关文章! 您可能感兴趣的文章: GoLand编写 TCP 端口扫描器的详细过程 go语言制作端口扫描器 GO语言实现的端口扫描器分享 go 实现简易端口扫描的示例 Go语言实现的简单网络端口扫描方法
  • 目录
    • 一、实战背景
    • 二、实战目标
    • 三、完整代码实现
      • 1. 扫描器实现(scanner.go)
    • 四、运行方式
      • 执行端口扫描器
        • 输入示例:
        • 输出示例:
    • 五、关键技术点解析
      • 1. 使用 Goroutine 并发扫描端口
        • 2. 使用 sync.WaitGroup 等待所有 Goroutine 完成
          • 3. 使用 net.DialTimeout 设置连接超时
            • 4. 使用 channel 收集扫描结果
              • 5. 缓存扫描结果并打印
              • 六、优化和扩展方向
                • 七、小结

                  端口扫描器是网络安全领域常用的工具,它通过对目标主机的端口进行扫描,检测目标设备是否开放某些服务端口(如 HTTP、FTP、SSH 等)。常见的端口扫描场景包括:

                  • 安全审计:检测主机是否存在未授权服务
                  • 漏洞扫描:识别可能存在漏洞的服务端口
                  • 网络诊断:排查服务器是否正常工作

                  传统的端口扫描使用串行方式,一个端口一个端口地检查,速度非常慢。而 Go 的并发编程可以极大地提升扫描效率。

                  我们将实现一个并发端口扫描器,具备以下功能:

                  1. 输入目标主机 IP 和端口范围
                  2. 使用并发扫描多个端口
                  3. 输出每个端口的开放状态
                  4. 使用超时机制控制扫描时间,避免阻塞

                  package main
                  
                  import (
                      "fmt"
                      "net"
                      "strconv"
                      "sync"
                      "time"
                  )
                  
                  func scanPort(ip string, port int, wg *sync.WaitGroup, resultCh chan<- string) {
                      defer wg.Done()
                  
                      address := fmt.Sprintf("%s:%d", ip, port)
                      conn, err := net.DialTimeout("tcp", address, 1*time.Second) // 设置连接超时时间
                      if err != nil {
                          resultCh <- fmt.Sprintf("端口 %d: 关闭", port)
                          return
                      }
                      conn.Close()
                      resultCh <- fmt.Sprintf("端口 %d: 开放", port)
                  }
                  
                  func main() {
                      var wg sync.WaitGroup
                      resultCh := make(chan string, 100) // 创建带缓冲的 Channel,缓冲区大小为 100
                  
                      fmt.Print("请输入目标 IP 地址: ")
                      var ip string
                      fmt.Scanln(&ip)
                  
                      fmt.Print("请输入端口范围(例如:80 100): ")
                      var startPort, endPort int
                      fmt.Scanln(&startPort, &endPort)
                  
                      // 扫描指定范围的端口
                      for port := startPort; port <= endPort; port++ {
                          wg.Add(1)
                          go scanPort(ip, port, &wg, resultCh)
                      }
                  
                      // 等待所有扫描任务完成并关闭 Channel
                      go func() {
                          wg.Wait()
                          close(resultCh)
                      }()
                  
                      // 打印扫描结果
                      fmt.Println("n扫描结果:")
                      for result := range resultCh {
                          fmt.Println(result)
                      }
                  }
                  

                  go run scanner.go
                  

                  请输入目标 IP 地址: 192.168.1.1
                  请输入端口范围(例如:80 100): 80 90
                  

                  扫描结果:
                  端口 80: 开放
                  端口 81: 关闭
                  端口 82: 关闭
                  端口 83: 关闭
                  端口 84: 开放
                  端口 85: 关闭
                  端口 86: 开放
                  端口 87: 关闭
                  端口 88: 关闭
                  端口 89: 开放
                  端口 90: 关闭
                  

                  每个端口的扫描任务都是由独立的 Goroutine 执行的。这样可以最大化利用 CPU 核心,实现端口扫描的并发化。

                  go scanPort(ip, port, &wg, resultCh)
                  

                  WaitGroup 用来等待所有扫描任务完成,确保在关闭结果通道之前所有扫描任务已经结束。

                  var wg sync.WaitGroup
                  wg.Add(1)
                  

                  DialTimeout 可以在指定的超时时间内完成连接,如果超时则返回错误。我们在这里设置了 1 秒的超时。

                  conn, err := net.DialTimeout("tcp", address, 1*time.Second)
                  

                  通过 Channel 传递每个端口的扫描结果,避免了主线程和 Goroutine 之间的数据竞争问题。

                  resultCh <- fmt.Sprintf("端口 %d: 开放", port)
                  

                  使用带缓冲的 Channel resultCh 存储扫描结果。所有任务完成后,我们关闭通道并打印扫描结果。

                  go func() {
                      wg.Wait()
                      close(resultCh)
                  }()
                  

                  优化方向 说明
                  控制并发数量 使用令牌桶算法(Token Bucket)或 sem 控制并发扫描的 Goroutine 数量
                  支持输入多个目标 IP 扩展支持一次扫描多个 IP 地址
                  扫描端口的协议支持 不仅支持 TCP 端口扫描,还可支持 UDP 扫描
                  日志记录 将扫描结果输出到日志文件,便于后期分析
                  进度条显示 添加扫描进度显示,提升用户体验
                  智能端口扫描 根据常见端口列表(如 80、443、21 等)进行扫描

                  通过本篇案例,你学会了如何用 Go 实现一个并发端口扫描器,掌握了以下关键技术:

                  • 使用 Goroutine 实现并发任务处理
                  • 利用 sync.WaitGroup 等待所有并发任务完成
                  • 使用 net.DialTimeout 进行超时控制,防止阻塞
                  • 使用 Channel 收集并传递任务结果

                  这个并发端口扫描器可以帮助你在网络安全和系统维护中快速诊断目标主机的开放端口。通过优化,您还可以将其扩展成更完整的网络扫描工具。

                  以上就是基于Go语言实现一个并发端口扫描器的详细内容,更多关于Go并发端口扫描器的资料请关注风君子博客其它相关文章!

                  您可能感兴趣的文章:

                  • GoLand编写 TCP 端口扫描器的详细过程
                  • go语言制作端口扫描器
                  • GO语言实现的端口扫描器分享
                  • go 实现简易端口扫描的示例
                  • Go语言实现的简单网络端口扫描方法

                  站内搜索