mirror of
https://github.com/bettercap/bettercap
synced 2025-08-19 13:09:49 -07:00
new: wifi.show.filter, wifi.show.limit, wifi.show.sort and wifi.show.sort_by parameters to control wifi.show
This commit is contained in:
parent
28f8586abb
commit
573cb17735
6 changed files with 164 additions and 52 deletions
|
@ -40,6 +40,7 @@ type WiFiModule struct {
|
||||||
writes *sync.WaitGroup
|
writes *sync.WaitGroup
|
||||||
reads *sync.WaitGroup
|
reads *sync.WaitGroup
|
||||||
chanLock *sync.Mutex
|
chanLock *sync.Mutex
|
||||||
|
selector *ViewSelector
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewWiFiModule(s *session.Session) *WiFiModule {
|
func NewWiFiModule(s *session.Session) *WiFiModule {
|
||||||
|
@ -143,9 +144,12 @@ func NewWiFiModule(s *session.Session) *WiFiModule {
|
||||||
w.AddHandler(session.NewModuleHandler("wifi.show", "",
|
w.AddHandler(session.NewModuleHandler("wifi.show", "",
|
||||||
"Show current wireless stations list (default sorting by essid).",
|
"Show current wireless stations list (default sorting by essid).",
|
||||||
func(args []string) error {
|
func(args []string) error {
|
||||||
return w.Show("rssi")
|
return w.Show()
|
||||||
}))
|
}))
|
||||||
|
|
||||||
|
w.selector = ViewSelectorFor(&w.SessionModule, "wifi.show",
|
||||||
|
[]string{"rssi", "bssid", "essid", "channel", "encryption", "seen", "sent", "rcvd"}, "rssi")
|
||||||
|
|
||||||
w.AddHandler(session.NewModuleHandler("wifi.recon.channel", `wifi\.recon\.channel[\s]+([0-9]+(?:[, ]+[0-9]+)*|clear)`,
|
w.AddHandler(session.NewModuleHandler("wifi.recon.channel", `wifi\.recon\.channel[\s]+([0-9]+(?:[, ]+[0-9]+)*|clear)`,
|
||||||
"WiFi channels (comma separated) or 'clear' for channel hopping.",
|
"WiFi channels (comma separated) or 'clear' for channel hopping.",
|
||||||
func(args []string) error {
|
func(args []string) error {
|
||||||
|
|
|
@ -1,46 +0,0 @@
|
||||||
package modules
|
|
||||||
|
|
||||||
import (
|
|
||||||
"github.com/bettercap/bettercap/network"
|
|
||||||
)
|
|
||||||
|
|
||||||
type ByRSSISorter []*network.Station
|
|
||||||
|
|
||||||
func (a ByRSSISorter) Len() int { return len(a) }
|
|
||||||
func (a ByRSSISorter) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
|
|
||||||
func (a ByRSSISorter) Less(i, j int) bool {
|
|
||||||
if a[i].RSSI == a[j].RSSI {
|
|
||||||
return a[i].HwAddress < a[j].HwAddress
|
|
||||||
}
|
|
||||||
return a[i].RSSI > a[j].RSSI
|
|
||||||
}
|
|
||||||
|
|
||||||
type ByChannelSorter []*network.Station
|
|
||||||
|
|
||||||
func (a ByChannelSorter) Len() int { return len(a) }
|
|
||||||
func (a ByChannelSorter) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
|
|
||||||
func (a ByChannelSorter) Less(i, j int) bool {
|
|
||||||
if a[i].Frequency == a[j].Frequency {
|
|
||||||
return a[i].HwAddress < a[j].HwAddress
|
|
||||||
}
|
|
||||||
return a[i].Frequency < a[j].Frequency
|
|
||||||
}
|
|
||||||
|
|
||||||
type ByEssidSorter []*network.Station
|
|
||||||
|
|
||||||
func (a ByEssidSorter) Len() int { return len(a) }
|
|
||||||
func (a ByEssidSorter) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
|
|
||||||
func (a ByEssidSorter) Less(i, j int) bool {
|
|
||||||
if a[i].ESSID() == a[j].ESSID() {
|
|
||||||
return a[i].HwAddress < a[j].HwAddress
|
|
||||||
}
|
|
||||||
return a[i].ESSID() < a[j].ESSID()
|
|
||||||
}
|
|
||||||
|
|
||||||
type ByWiFiSeenSorter []*network.Station
|
|
||||||
|
|
||||||
func (a ByWiFiSeenSorter) Len() int { return len(a) }
|
|
||||||
func (a ByWiFiSeenSorter) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
|
|
||||||
func (a ByWiFiSeenSorter) Less(i, j int) bool {
|
|
||||||
return a[i].LastSeen.After(a[j].LastSeen)
|
|
||||||
}
|
|
|
@ -110,30 +110,88 @@ func (w *WiFiModule) getRow(station *network.Station) ([]string, bool) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (w *WiFiModule) Show(by string) error {
|
func (w *WiFiModule) doFilter(station *network.Station) bool {
|
||||||
var stations []*network.Station
|
if w.selector.Expression == nil {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
return w.selector.Expression.MatchString(station.BSSID()) ||
|
||||||
|
w.selector.Expression.MatchString(station.ESSID()) ||
|
||||||
|
w.selector.Expression.MatchString(station.Alias) ||
|
||||||
|
w.selector.Expression.MatchString(station.Vendor) ||
|
||||||
|
w.selector.Expression.MatchString(station.Encryption)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (w *WiFiModule) doSelection() (err error, stations []*network.Station) {
|
||||||
|
if err = w.selector.Update(); err != nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
apSelected := w.isApSelected()
|
apSelected := w.isApSelected()
|
||||||
if apSelected {
|
if apSelected {
|
||||||
if ap, found := w.Session.WiFi.Get(w.ap.HwAddress); found {
|
if ap, found := w.Session.WiFi.Get(w.ap.HwAddress); found {
|
||||||
stations = ap.Clients()
|
stations = ap.Clients()
|
||||||
} else {
|
} else {
|
||||||
return fmt.Errorf("Could not find station %s", w.ap.HwAddress)
|
err = fmt.Errorf("Could not find station %s", w.ap.HwAddress)
|
||||||
|
return
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
stations = w.Session.WiFi.Stations()
|
stations = w.Session.WiFi.Stations()
|
||||||
}
|
}
|
||||||
switch by {
|
|
||||||
|
filtered := []*network.Station{}
|
||||||
|
for _, station := range stations {
|
||||||
|
if w.doFilter(station) {
|
||||||
|
filtered = append(filtered, station)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
stations = filtered
|
||||||
|
|
||||||
|
// "encryption"}, "rssi"
|
||||||
|
switch w.selector.SortBy {
|
||||||
case "seen":
|
case "seen":
|
||||||
sort.Sort(ByWiFiSeenSorter(stations))
|
sort.Sort(ByWiFiSeenSorter(stations))
|
||||||
case "essid":
|
case "essid":
|
||||||
sort.Sort(ByEssidSorter(stations))
|
sort.Sort(ByEssidSorter(stations))
|
||||||
|
case "bssid":
|
||||||
|
sort.Sort(ByBssidSorter(stations))
|
||||||
case "channel":
|
case "channel":
|
||||||
sort.Sort(ByChannelSorter(stations))
|
sort.Sort(ByChannelSorter(stations))
|
||||||
|
case "sent":
|
||||||
|
sort.Sort(ByWiFiSentSorter(stations))
|
||||||
|
case "rcvd":
|
||||||
|
sort.Sort(ByWiFiRcvdSorter(stations))
|
||||||
|
case "rssi":
|
||||||
default:
|
default:
|
||||||
sort.Sort(ByRSSISorter(stations))
|
sort.Sort(ByRSSISorter(stations))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// default is asc
|
||||||
|
if w.selector.Sort == "desc" {
|
||||||
|
// from https://github.com/golang/go/wiki/SliceTricks
|
||||||
|
for i := len(stations)/2 - 1; i >= 0; i-- {
|
||||||
|
opp := len(stations) - 1 - i
|
||||||
|
stations[i], stations[opp] = stations[opp], stations[i]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if w.selector.Limit > 0 {
|
||||||
|
limit := w.selector.Limit
|
||||||
|
max := len(stations)
|
||||||
|
if limit > max {
|
||||||
|
limit = max
|
||||||
|
}
|
||||||
|
stations = stations[0:limit]
|
||||||
|
}
|
||||||
|
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
func (w *WiFiModule) Show() (err error) {
|
||||||
|
var stations []*network.Station
|
||||||
|
if err, stations = w.doSelection(); err != nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
rows := make([][]string, 0)
|
rows := make([][]string, 0)
|
||||||
for _, s := range stations {
|
for _, s := range stations {
|
||||||
if row, include := w.getRow(s); include {
|
if row, include := w.getRow(s); include {
|
||||||
|
@ -143,7 +201,7 @@ func (w *WiFiModule) Show(by string) error {
|
||||||
nrows := len(rows)
|
nrows := len(rows)
|
||||||
|
|
||||||
columns := []string{"RSSI", "BSSID", "SSID" /* "Vendor", */, "Encryption", "Channel", "Clients", "Sent", "Recvd", "Last Seen"}
|
columns := []string{"RSSI", "BSSID", "SSID" /* "Vendor", */, "Encryption", "Channel", "Clients", "Sent", "Recvd", "Last Seen"}
|
||||||
if apSelected {
|
if w.isApSelected() {
|
||||||
// these are clients
|
// these are clients
|
||||||
columns = []string{"RSSI", "MAC" /* "Vendor", */, "Channel", "Sent", "Received", "Last Seen"}
|
columns = []string{"RSSI", "MAC" /* "Vendor", */, "Channel", "Sent", "Received", "Last Seen"}
|
||||||
|
|
||||||
|
|
96
modules/wifi_show_sort.go
Normal file
96
modules/wifi_show_sort.go
Normal file
|
@ -0,0 +1,96 @@
|
||||||
|
package modules
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/bettercap/bettercap/network"
|
||||||
|
"github.com/bettercap/bettercap/packets"
|
||||||
|
"github.com/bettercap/bettercap/session"
|
||||||
|
)
|
||||||
|
|
||||||
|
type ByRSSISorter []*network.Station
|
||||||
|
|
||||||
|
func (a ByRSSISorter) Len() int { return len(a) }
|
||||||
|
func (a ByRSSISorter) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
|
||||||
|
func (a ByRSSISorter) Less(i, j int) bool {
|
||||||
|
return a[i].RSSI < a[j].RSSI
|
||||||
|
}
|
||||||
|
|
||||||
|
type ByChannelSorter []*network.Station
|
||||||
|
|
||||||
|
func (a ByChannelSorter) Len() int { return len(a) }
|
||||||
|
func (a ByChannelSorter) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
|
||||||
|
func (a ByChannelSorter) Less(i, j int) bool {
|
||||||
|
return a[i].Frequency < a[j].Frequency
|
||||||
|
}
|
||||||
|
|
||||||
|
type ByBssidSorter []*network.Station
|
||||||
|
|
||||||
|
func (a ByBssidSorter) Len() int { return len(a) }
|
||||||
|
func (a ByBssidSorter) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
|
||||||
|
func (a ByBssidSorter) Less(i, j int) bool {
|
||||||
|
return a[i].BSSID() < a[j].BSSID()
|
||||||
|
}
|
||||||
|
|
||||||
|
type ByEssidSorter []*network.Station
|
||||||
|
|
||||||
|
func (a ByEssidSorter) Len() int { return len(a) }
|
||||||
|
func (a ByEssidSorter) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
|
||||||
|
func (a ByEssidSorter) Less(i, j int) bool {
|
||||||
|
if a[i].ESSID() == a[j].ESSID() {
|
||||||
|
return a[i].HwAddress < a[j].HwAddress
|
||||||
|
}
|
||||||
|
return a[i].ESSID() < a[j].ESSID()
|
||||||
|
}
|
||||||
|
|
||||||
|
type ByWiFiSeenSorter []*network.Station
|
||||||
|
|
||||||
|
func (a ByWiFiSeenSorter) Len() int { return len(a) }
|
||||||
|
func (a ByWiFiSeenSorter) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
|
||||||
|
func (a ByWiFiSeenSorter) Less(i, j int) bool {
|
||||||
|
return a[i].LastSeen.Before(a[j].LastSeen)
|
||||||
|
}
|
||||||
|
|
||||||
|
type ByWiFiSentSorter []*network.Station
|
||||||
|
|
||||||
|
func (a ByWiFiSentSorter) Len() int { return len(a) }
|
||||||
|
func (a ByWiFiSentSorter) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
|
||||||
|
func (a ByWiFiSentSorter) Less(i, j int) bool {
|
||||||
|
session.I.Queue.Lock()
|
||||||
|
defer session.I.Queue.Unlock()
|
||||||
|
|
||||||
|
var found bool = false
|
||||||
|
var aTraffic *packets.Traffic = nil
|
||||||
|
var bTraffic *packets.Traffic = nil
|
||||||
|
|
||||||
|
if aTraffic, found = session.I.Queue.Traffic[a[i].IpAddress]; !found {
|
||||||
|
aTraffic = &packets.Traffic{}
|
||||||
|
}
|
||||||
|
|
||||||
|
if bTraffic, found = session.I.Queue.Traffic[a[j].IpAddress]; !found {
|
||||||
|
bTraffic = &packets.Traffic{}
|
||||||
|
}
|
||||||
|
|
||||||
|
return bTraffic.Sent > aTraffic.Sent
|
||||||
|
}
|
||||||
|
|
||||||
|
type ByWiFiRcvdSorter []*network.Station
|
||||||
|
|
||||||
|
func (a ByWiFiRcvdSorter) Len() int { return len(a) }
|
||||||
|
func (a ByWiFiRcvdSorter) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
|
||||||
|
func (a ByWiFiRcvdSorter) Less(i, j int) bool {
|
||||||
|
session.I.Queue.Lock()
|
||||||
|
defer session.I.Queue.Unlock()
|
||||||
|
|
||||||
|
var found bool = false
|
||||||
|
var aTraffic *packets.Traffic = nil
|
||||||
|
var bTraffic *packets.Traffic = nil
|
||||||
|
|
||||||
|
if aTraffic, found = session.I.Queue.Traffic[a[i].IpAddress]; !found {
|
||||||
|
aTraffic = &packets.Traffic{}
|
||||||
|
}
|
||||||
|
|
||||||
|
if bTraffic, found = session.I.Queue.Traffic[a[j].IpAddress]; !found {
|
||||||
|
bTraffic = &packets.Traffic{}
|
||||||
|
}
|
||||||
|
|
||||||
|
return bTraffic.Received > aTraffic.Received
|
||||||
|
}
|
Loading…
Add table
Add a link
Reference in a new issue