Update to 2.9.5.5

Signed-off-by: Jeroen Oudshoorn <oudshoorn.jeroen@gmail.com>
This commit is contained in:
Jeroen Oudshoorn
2026-03-25 19:25:43 +01:00
parent 01c6ab856d
commit aad8c01f65
13 changed files with 5021 additions and 677 deletions

11
.idea/deployment.xml generated
View File

@@ -1,6 +1,15 @@
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<project version="4"> <project version="4">
<component name="PublishConfigData" filePermissions="493" folderPermissions="493" remoteFilesAllowedToDisappearOnAutoupload="false" confirmBeforeUploading="false"> <component name="PublishConfigData" serverName="pwnagotchi" filePermissions="493" folderPermissions="493" remoteFilesAllowedToDisappearOnAutoupload="false" confirmBeforeUploading="false">
<option name="confirmBeforeUploading" value="false" /> <option name="confirmBeforeUploading" value="false" />
<serverData>
<paths name="pwnagotchi">
<serverdata>
<mappings>
<mapping deploy="/home/pi/.pwn/lib/python3.13" local="$PROJECT_DIR$" web="/" />
</mappings>
</serverdata>
</paths>
</serverData>
</component> </component>
</project> </project>

2
.idea/misc.xml generated
View File

@@ -3,7 +3,7 @@
<component name="Black"> <component name="Black">
<option name="sdkName" value="Python 3.11 (pwnagotchi)" /> <option name="sdkName" value="Python 3.11 (pwnagotchi)" />
</component> </component>
<component name="ProjectRootManager" version="2" project-jdk-name="Python 3.13" project-jdk-type="Python SDK" /> <component name="ProjectRootManager" version="2" project-jdk-name="Python 3.14 (pwnagotchi)" project-jdk-type="Python SDK" />
<component name="PythonCompatibilityInspectionAdvertiser"> <component name="PythonCompatibilityInspectionAdvertiser">
<option name="version" value="3" /> <option name="version" value="3" />
</component> </component>

2
.idea/pwnagotchi.iml generated
View File

@@ -5,7 +5,7 @@
<excludeFolder url="file://$MODULE_DIR$/.venv" /> <excludeFolder url="file://$MODULE_DIR$/.venv" />
<excludeFolder url="file://$MODULE_DIR$/venv" /> <excludeFolder url="file://$MODULE_DIR$/venv" />
</content> </content>
<orderEntry type="jdk" jdkName="Python 3.13" jdkType="Python SDK" /> <orderEntry type="jdk" jdkName="Python 3.14 (pwnagotchi)" jdkType="Python SDK" />
<orderEntry type="sourceFolder" forTests="false" /> <orderEntry type="sourceFolder" forTests="false" />
</component> </component>
<component name="PyDocumentationSettings"> <component name="PyDocumentationSettings">

2
.idea/sshConfigs.xml generated
View File

@@ -2,7 +2,7 @@
<project version="4"> <project version="4">
<component name="SshConfigs"> <component name="SshConfigs">
<configs> <configs>
<sshConfig authType="PASSWORD" connectionConfig="{&quot;serverAliveInterval&quot;:300}" id="8b69df7d-cec5-421f-8edf-53ed6233f6b6" port="22" customName="pwnagotchi" nameFormat="CUSTOM" useOpenSSHConfig="true"> <sshConfig authType="PASSWORD" connectionConfig="{&quot;hostKeyVerifier&quot;:{&quot;hashKnownHosts&quot;:true},&quot;serverAliveInterval&quot;:300}" host="pwnagotchi.local" id="8b69df7d-cec5-421f-8edf-53ed6233f6b6" port="22" customName="pwnagotchi" nameFormat="CUSTOM" username="pi" useOpenSSHConfig="true">
<option name="customName" value="pwnagotchi" /> <option name="customName" value="pwnagotchi" />
</sshConfig> </sshConfig>
</configs> </configs>

4
.idea/webServers.xml generated
View File

@@ -3,9 +3,9 @@
<component name="WebServers"> <component name="WebServers">
<option name="servers"> <option name="servers">
<webServer id="cf2a1148-a103-4472-a782-7debdc6dabf9" name="pwnagotchi"> <webServer id="cf2a1148-a103-4472-a782-7debdc6dabf9" name="pwnagotchi">
<fileTransfer accessType="SFTP" port="22" sshConfigId="8b69df7d-cec5-421f-8edf-53ed6233f6b6" sshConfig="pwnagotchi"> <fileTransfer accessType="SFTP" host="pwnagotchi.local" port="22" sshConfigId="8b69df7d-cec5-421f-8edf-53ed6233f6b6" sshConfig="pwnagotchi">
<advancedOptions> <advancedOptions>
<advancedOptions dataProtectionLevel="Private" passiveMode="true" shareSSLContext="true" /> <advancedOptions dataProtectionLevel="Private" passiveMode="true" shareSSLContext="true" isUseSudo="true" />
</advancedOptions> </advancedOptions>
</fileTransfer> </fileTransfer>
</webServer> </webServer>

View File

@@ -1 +1 @@
__version__ = '2.9.5.4' __version__ = '2.9.5.5'

View File

@@ -6,11 +6,9 @@ import sys
import tomlkit import tomlkit
import requests import requests
import os import os
import re
import pwnagotchi import pwnagotchi
from pwnagotchi import utils from pwnagotchi import utils
from pwnagotchi.google import cmd as google_cmd
from pwnagotchi.plugins import cmd as plugins_cmd from pwnagotchi.plugins import cmd as plugins_cmd
from pwnagotchi import log from pwnagotchi import log
from pwnagotchi import fs from pwnagotchi import fs
@@ -104,9 +102,6 @@ def pwnagotchi_cli():
# Add parsers from plugins_cmd # Add parsers from plugins_cmd
plugins_cmd.add_parsers(subparsers) plugins_cmd.add_parsers(subparsers)
# Add parsers from google_cmd
google_cmd.add_parsers(subparsers)
parser = argparse.ArgumentParser(prog="pwnagotchi") parser = argparse.ArgumentParser(prog="pwnagotchi")
# pwnagotchi --help # pwnagotchi --help
parser.add_argument('-C', '--config', action='store', dest='config', default='/etc/pwnagotchi/default.toml', parser.add_argument('-C', '--config', action='store', dest='config', default='/etc/pwnagotchi/default.toml',
@@ -130,9 +125,7 @@ def pwnagotchi_cli():
parser.add_argument('--print-config', dest="print_config", action="store_true", default=False, parser.add_argument('--print-config', dest="print_config", action="store_true", default=False,
help="Print the configuration.") help="Print the configuration.")
# Jayofelony added these
parser.add_argument('--wizard', dest="wizard", action="store_true", default=False,
help="Interactive installation of your personal configuration.")
parser.add_argument('--check-update', dest="check_update", action="store_true", default=False, parser.add_argument('--check-update', dest="check_update", action="store_true", default=False,
help="Check for updates on Pwnagotchi. And tells current version.") help="Check for updates on Pwnagotchi. And tells current version.")
parser.add_argument('--donate', dest="donate", action="store_true", default=False, parser.add_argument('--donate', dest="donate", action="store_true", default=False,
@@ -147,133 +140,11 @@ def pwnagotchi_cli():
log.setup_logging(args, config) log.setup_logging(args, config)
rc = plugins_cmd.handle_cmd(args, config) rc = plugins_cmd.handle_cmd(args, config)
sys.exit(rc) sys.exit(rc)
if google_cmd.used_google_cmd(args):
config = utils.load_config(args)
log.setup_logging(args, config)
rc = google_cmd.handle_cmd(args)
sys.exit(rc)
if args.version: if args.version:
print(pwnagotchi.__version__) print(pwnagotchi.__version__)
sys.exit(0) sys.exit(0)
if args.wizard:
def is_valid_hostname(hostname):
if len(hostname) > 255:
return False
if hostname[-1] == ".":
hostname = hostname[:-1] # strip exactly one dot from the right, if present
allowed = re.compile("(?!-)[A-Z\d-]{1,63}(?<!-)$", re.IGNORECASE)
return all(allowed.match(x) for x in hostname.split("."))
pwn_restore = input("Do you want to restore the previous configuration?\n\n"
"[Y/N]: ")
if pwn_restore in ('y', 'yes'):
os.system("cp -f /etc/pwnagotchi/config.toml.bak /etc/pwnagotchi/config.toml")
print("Your previous configuration is restored, and I will restart in 5 seconds.")
time.sleep(5)
os.system("service pwnagotchi restart")
else:
pwn_check = input("This will create a new configuration file and overwrite your current backup, are you sure?\n\n"
"[Y/N]: ")
if pwn_check.lower() in ('y', 'yes'):
os.system("mv -f /etc/pwnagotchi/config.toml /etc/pwnagotchi/config.toml.bak")
with open("/etc/pwnagotchi/config.toml", "a+") as f:
f.write("# Do not edit this file if you do not know what you are doing!!!\n\n")
# Set pwnagotchi name
print("Welcome to the interactive installation of your personal Pwnagotchi configuration!\n"
"My name is Jayofelony, how may I call you?\n\n")
pwn_name = input("Pwnagotchi name (no spaces): ")
if pwn_name == "":
pwn_name = "Pwnagotchi"
print("I shall go by Pwnagotchi from now on!")
pwn_name = (f"[main]\n"
f"name = \"{pwn_name}\"\n")
f.write(pwn_name)
else:
if is_valid_hostname(pwn_name):
print(f"I shall go by {pwn_name} from now on!")
pwn_name = (f"[main]\n"
f"name = \"{pwn_name}\"\n")
f.write(pwn_name)
else:
print("You have chosen an invalid name. Please start over.")
exit()
pwn_whitelist = input("How many networks do you want to whitelist? "
"We will also ask a MAC for each network?\n"
"Each SSID and BSSID count as 1 network. \n\n"
"Be sure to use digits as your answer.\n\n"
"Amount of networks: ")
if int(pwn_whitelist) > 0:
f.write("whitelist = [\n")
for x in range(int(pwn_whitelist)):
ssid = input("SSID (Name): ")
bssid = input("BSSID (MAC): ")
f.write(f"\t\"{ssid}\",\n")
if bssid != "":
f.write(f"\t\"{bssid}\",\n")
f.write("]\n")
# set bluetooth tether
pwn_bluetooth = input("Do you want to enable BT-Tether?\n\n"
"[Y/N] ")
if pwn_bluetooth.lower() in ('y', 'yes'):
f.write("[main.plugins.bt-tether]\n"
"enabled = true\n\n")
pwn_bluetooth_phone_name = input("What name uses your phone, check settings?\n\n")
if pwn_bluetooth_phone_name != "":
f.write(f"phone-name = \"{pwn_bluetooth_phone_name}\"\n")
pwn_bluetooth_device = input("What device do you use? android or ios?\n\n"
"Device: ")
if pwn_bluetooth_device != "":
if pwn_bluetooth_device != "android" and pwn_bluetooth_device != "ios":
print("You have chosen an invalid device. Please start over.")
exit()
f.write(f"phone = \"{pwn_bluetooth_device.lower()}\"\n")
if pwn_bluetooth_device == "android":
f.write("ip = \"192.168.44.44\"\n")
elif pwn_bluetooth_device == "ios":
f.write("ip = \"172.20.10.6\"\n")
pwn_bluetooth_mac = input("What is the bluetooth MAC of your device?\n\n"
"MAC: ")
if pwn_bluetooth_mac != "":
f.write(f"mac = \"{pwn_bluetooth_mac}\"\n")
# set up display settings
pwn_display_enabled = input("Do you want to enable a display?\n\n"
"[Y/N]: ")
if pwn_display_enabled.lower() in ('y', 'yes'):
f.write("[ui.display]\n"
"enabled = true\n")
pwn_display_type = input("What display do you use?\n\n"
"Be sure to check for the correct display type @ \n"
"https://github.com/jayofelony/pwnagotchi/blob/master/pwnagotchi/utils.py#L240-L501\n\n"
"Display type: ")
if pwn_display_type != "":
f.write(f"type = \"{pwn_display_type}\"\n")
pwn_display_invert = input("Do you want to invert the display colors?\n"
"N = Black background\n"
"Y = White background\n\n"
"[Y/N]: ")
if pwn_display_invert.lower() in ('y', 'yes'):
f.write("[ui]\n"
"invert = true\n")
f.close()
if pwn_bluetooth.lower() in ('y', 'yes'):
if pwn_bluetooth_device.lower == "android":
print("To visit the webui when connected with your phone, visit: http://192.168.44.44:8080\n"
"Be sure to run `sudo bluetoothctl` to set-up the bluetooth connection for the first time. And read the wiki step 4.\n"
"Your configuration is done, and I will restart in 5 seconds.")
elif pwn_bluetooth_device.lower == "ios":
print("To visit the webui when connected with your phone, visit: http://172.20.10.6:8080\n"
"Your configuration is done, and I will restart in 5 seconds.")
else:
print("Your configuration is done, and I will restart in 5 seconds.")
time.sleep(5)
os.system("service pwnagotchi restart")
else:
print("Ok, doing nothing.")
sys.exit(0)
if args.donate: if args.donate:
print("Donations can be made @ \n " print("Donations can be made @ \n "
"https://github.com/sponsors/jayofelony \n\n" "https://github.com/sponsors/jayofelony \n\n"

View File

@@ -30,22 +30,16 @@ enabled = true
enabled = false enabled = false
interval = "daily" # or "hourly", or a number (minutes) interval = "daily" # or "hourly", or a number (minutes)
max_tries = 0 max_tries = 0
backup_location = "/home/pi/" backup_location = "/etc/pwnagotchi/"
files = [ files = [
"/root/settings.yaml",
"/root/client_secrets.json",
"/root/.api-report.json", "/root/.api-report.json",
"/root/.ssh", "/root/.ssh",
"/root/.bashrc", "/root/.bashrc",
"/root/.profile", "/root/.profile",
"/home/pi/handshakes",
"/root/peers",
"/etc/pwnagotchi/", "/etc/pwnagotchi/",
"/usr/local/share/pwnagotchi/custom-plugins", "/root/peers",
"/etc/ssh/", "/etc/ssh/",
"/home/pi/.bashrc", "/root/.auto-backup"
"/home/pi/.profile",
"/home/pi/.wpa_sec_uploads"
] ]
exclude = [ "/etc/pwnagotchi/logs/*"] exclude = [ "/etc/pwnagotchi/logs/*"]
commands = [ "tar cf {backup_file} {files}"] commands = [ "tar cf {backup_file} {files}"]
@@ -58,12 +52,12 @@ token = "" # Create a personal access token (classic) with scope set to public_r
[main.plugins.bt-tether] [main.plugins.bt-tether]
enabled = false enabled = false
phone-name = "" # name as shown on the phone i.e. "Pwnagotchi's Phone" auto_reconnect = true # Auto reconnect on disconnect (default: true)
mac = "" show_on_screen = true # Master switch: show status on display
phone = "" # android or ios show_mini_status = true # Show mini status indicator (C/N/P/D)
ip = "" # optional, default : 192.168.44.2 if android or 172.20.10.2 if ios mini_status_position = [110, 0] # Position for mini status
gateway = "" #optional, default : 192.168.44.1 if android or 172.20.10.2 if ios show_detailed_status = true # Show detailed status line with IP
dns = "8.8.8.8 1.1.1.1" # optional, default (google): "8.8.8.8 1.1.1.1". Consider using anonymous DNS like OpenNic :-) detailed_status_position = [0, 82] # Position for detailed status line
[main.plugins.fix_services] [main.plugins.fix_services]
enabled = true enabled = true
@@ -71,12 +65,6 @@ enabled = true
[main.plugins.cache] [main.plugins.cache]
enabled = true enabled = true
[main.plugins.gdrivesync]
enabled = false
backupfiles = [""]
backup_folder = "PwnagotchiBackups"
interval = 1
[main.plugins.gpio_buttons] [main.plugins.gpio_buttons]
enabled = false enabled = false
@@ -85,9 +73,6 @@ enabled = false
speed = 19200 speed = 19200
device = "/dev/ttyUSB0" # for GPSD: "localhost:2947" device = "/dev/ttyUSB0" # for GPSD: "localhost:2947"
[main.plugins.gps_listener]
enabled = false
[main.plugins.grid] [main.plugins.grid]
enabled = true enabled = true
report = true report = true
@@ -126,7 +111,7 @@ key = ""
[main.plugins.session-stats] [main.plugins.session-stats]
enabled = false enabled = false
save_directory = "/var/tmp/pwnagotchi/sessions/" save_directory = "/etc/pwnagotchi/sessions/"
[main.plugins.ups_hat_c] [main.plugins.ups_hat_c]
enabled = false enabled = false
@@ -243,7 +228,7 @@ rotation = 180
type = "waveshare_4" type = "waveshare_4"
[bettercap] [bettercap]
handshakes = "/home/pi/handshakes" handshakes = "/etc/pwnagotchi/handshakes"
silence = [ silence = [
"ble.device.new", "ble.device.new",
"ble.device.lost", "ble.device.lost",

View File

@@ -72,7 +72,7 @@ def check(version, repo, native=True, token=""):
def make_path_for(name): def make_path_for(name):
path = os.path.join("/home/pi/", name) path = os.path.join("/opt/", name)
if os.path.exists(path): if os.path.exists(path):
logging.debug("[update] deleting %s" % path) logging.debug("[update] deleting %s" % path)
shutil.rmtree(path, ignore_errors=True, onerror=None) shutil.rmtree(path, ignore_errors=True, onerror=None)
@@ -155,7 +155,7 @@ def install(display, update):
try: try:
# Activate the virtual environment and install the package # Activate the virtual environment and install the package
subprocess.run( subprocess.run(
["bash", "-c", f"source /home/pi/.pwn/bin/activate && pip install {source_path}"], ["bash", "-c", f"source /opt/.pwn/bin/activate && pip install {source_path}"],
check=True check=True
) )

File diff suppressed because it is too large Load Diff

View File

@@ -1,233 +0,0 @@
import json
import logging
import os
import subprocess
import threading
import pwnagotchi.plugins as plugins
import pwnagotchi.ui.fonts as fonts
from pwnagotchi.ui.components import LabeledValue
from pwnagotchi.ui.view import BLACK
"""
# Android
# Termux:API : https://f-droid.org/en/packages/com.termux.api/
# Termux : https://f-droid.org/en/packages/com.termux/
pkg install termux-api socat bc
-----
#!/data/data/com.termux/files/usr/bin/bash
# Server details
SERVER_IP="192.168.44.44" # IP of the socat receiver
SERVER_PORT="5000" # UDP port to send data to
# Function to calculate checksum
calculate_checksum() {
local sentence="$1"
local checksum=0
# Loop through each character in the sentence
for ((i = 0; i < ${#sentence}; i++)); do
checksum=$((checksum ^ $(printf '%d' "'${sentence:i:1}")))
done
# Return checksum in hexadecimal
printf "%02X" $checksum
}
# Infinite loop to send GPS data
while true; do
# Get location data
LOCATION=$(termux-location -p gps)
# Extract latitude, longitude, altitude, speed, and bearing
LATITUDE=$(echo "$LOCATION" | jq '.latitude')
LONGITUDE=$(echo "$LOCATION" | jq '.longitude')
ALTITUDE=$(echo "$LOCATION" | jq '.altitude')
SPEED=$(echo "$LOCATION" | jq '.speed') # Speed in meters per second
BEARING=$(echo "$LOCATION" | jq '.bearing')
# Convert speed from meters per second to knots and km/h
SPEED_KNOTS=$(echo "$SPEED" | awk '{printf "%.1f", $1 * 1.943844}')
SPEED_KMH=$(echo "$SPEED" | awk '{printf "%.1f", $1 * 3.6}')
# Format latitude and longitude for NMEA
LAT_DEGREES=$(printf "%.0f" "${LATITUDE%.*}")
LAT_MINUTES=$(echo "(${LATITUDE#${LAT_DEGREES}} * 60)" | bc -l)
LAT_DIRECTION=$(if (( $(echo "$LATITUDE >= 0" | bc -l) )); then echo "N"; else echo "S"; fi)
LON_DEGREES=$(printf "%.0f" "${LONGITUDE%.*}")
LON_MINUTES=$(echo "(${LONGITUDE#${LON_DEGREES}} * 60)" | bc -l)
LON_DIRECTION=$(if (( $(echo "$LONGITUDE >= 0" | bc -l) )); then echo "E"; else echo "W"; fi)
# Format the NMEA GGA sentence
RAW_NMEA_GGA="GPGGA,123519,$(printf "%02d%07.4f" ${LAT_DEGREES#-} $LAT_MINUTES),$LAT_DIRECTION,$(printf "%03d%07.4f" ${LON_DEGREES#-} $LON_MINUTES),$LON_DIRECTION,1,08,0.9,$(printf "%.1f" $ALTITUDE),M,46.9,M,,"
CHECKSUM=$(calculate_checksum "$RAW_NMEA_GGA")
NMEA_GGA="\$${RAW_NMEA_GGA}*${CHECKSUM}"
# Format the VTG sentence
RAW_NMEA_VTG="GPVTG,$(printf "%.1f" $BEARING),T,,M,$(printf "%.1f" $SPEED_KNOTS),N,$(printf "%.1f" $SPEED_KMH),K"
CHECKSUM_VTG=$(calculate_checksum "$RAW_NMEA_VTG")
NMEA_VTG="\$${RAW_NMEA_VTG}*${CHECKSUM_VTG}"
# Send data via UDP
echo "$NMEA_GGA"
echo "$NMEA_GGA" | socat - UDP:$SERVER_IP:$SERVER_PORT
#echo "$NMEA_VTG"
#echo "$NMEA_VTG" | socat - UDP:$SERVER_IP:$SERVER_PORT
sleep 1
done
-----
# Pwnagotchi
main.plugins.gps_listener.enabled = true
# packages
sudo apt-get install socat
"""
class GPS(plugins.Plugin):
__author__ = 'https://github.com/krishenriksen'
__version__ = "1.0.0"
__license__ = "GPL3"
__description__ = "Receive GPS coordinates via termux-location and save whenever an handshake is captured."
def __init__(self):
self.listen_ip = self.get_ip_address('bnep0')
self.listen_port = "5000"
self.write_virtual_serial = "/dev/ttyUSB1"
self.read_virtual_serial = "/dev/ttyUSB0"
self.baud_rate = "19200"
self.socat_process = None
self.stop_event = threading.Event()
self.status_lock = threading.Lock()
self.status = '-'
self.socat_thread = threading.Thread(target=self.run_socat)
def get_ip_address(self, interface):
try:
result = subprocess.run(
["ip", "addr", "show", interface],
capture_output=True,
text=True,
check=True
)
for line in result.stdout.split('\n'):
if 'inet ' in line:
ip_address = line.strip().split()[1].split('/')[0]
return ip_address
except subprocess.CalledProcessError:
logging.warning(f"Could not get IP address for interface {interface}")
return None
def set_status(self, status):
with self.status_lock:
self.status = status
def get_status(self):
with self.status_lock:
return self.status
def on_loaded(self):
logging.info("GPS Listener plugin loaded")
self.cleanup_virtual_serial_ports()
self.create_virtual_serial_ports()
self.socat_thread.start()
def cleanup_virtual_serial_ports(self):
if os.path.exists(self.write_virtual_serial):
logging.info(f"Removing old {self.write_virtual_serial}")
os.remove(self.write_virtual_serial)
if os.path.exists(self.read_virtual_serial):
logging.info(f"Removing old {self.read_virtual_serial}")
os.remove(self.read_virtual_serial)
def create_virtual_serial_ports(self):
self.socat_process = subprocess.Popen(
["socat", "-d", "-d", f"pty,link={self.write_virtual_serial},mode=777",
f"pty,link={self.read_virtual_serial},mode=777"],
stdout=subprocess.PIPE,
stderr=subprocess.PIPE,
)
def run_socat(self):
while not self.stop_event.is_set():
self.socat_process = subprocess.Popen(
["socat", f"UDP-RECVFROM:{self.listen_port},reuseaddr,bind={self.listen_ip}", "-"],
stdout=subprocess.PIPE,
stderr=subprocess.PIPE,
text=True
)
self.set_status('C')
with open(self.write_virtual_serial, 'w') as serial_port:
for line in self.socat_process.stdout:
if self.stop_event.is_set():
break
serial_port.write(line)
serial_port.flush() # Ensure the data is written immediately
self.status = 'C'
self.socat_process.wait()
if self.stop_event.is_set():
break
self.set_status('-')
def cleanup(self):
if self.socat_process:
self.socat_process.terminate()
self.socat_process.wait() # Ensure the process is reaped
self.stop_event.set()
self.socat_thread.join()
self.cleanup_virtual_serial_ports()
def on_ready(self, agent):
if os.path.exists(self.read_virtual_serial):
logging.info(
f"enabling bettercap's gps module for {self.read_virtual_serial}"
)
try:
agent.run("gps off")
except Exception:
logging.info(f"bettercap gps module was already off")
pass
agent.run(f"set gps.device {self.read_virtual_serial}")
agent.run(f"set gps.baudrate {self.baud_rate}")
agent.run("gps on")
logging.info(f"bettercap gps module enabled on {self.read_virtual_serial}")
else:
self.set_status('NF')
logging.warning("no GPS detected")
def on_handshake(self, agent, filename, access_point, client_station):
info = agent.session()
coordinates = info["gps"]
gps_filename = filename.replace(".pcap", ".gps.json")
if coordinates and all([
# avoid 0.000... measurements
coordinates["Latitude"], coordinates["Longitude"]
]):
self.set_status('S')
logging.info(f"saving GPS to {gps_filename} ({coordinates})")
with open(gps_filename, "w+t") as fp:
json.dump(coordinates, fp)
else:
logging.warning("not saving GPS. Couldn't find location.")
def on_ui_setup(self, ui):
with ui._lock:
ui.add_element('gps', LabeledValue(color=BLACK, label='GPS', value='-', position=(ui.width() / 2 - 47, 0), label_font=fonts.Bold, text_font=fonts.Medium))
def on_unload(self, ui):
self.cleanup()
with ui._lock:
ui.remove_element('gps')
def on_ui_update(self, ui):
ui.set('gps', self.get_status())

View File

@@ -18,10 +18,10 @@ class ohcapi(plugins.Plugin):
self.ready = False self.ready = False
self.lock = Lock() self.lock = Lock()
try: try:
self.report = StatusFile('/root/handshakes/.ohc_uploads', data_format='json') self.report = StatusFile('/etc/pwnagotchi/handshakes/.ohc_uploads', data_format='json')
except JSONDecodeError: except JSONDecodeError:
os.remove('/root/.ohc_newapi_uploads') os.remove('/root/.ohc_newapi_uploads')
self.report = StatusFile('/root/handshakes/.ohc_uploads', data_format='json') self.report = StatusFile('/etc/pwnagotchi/handshakes/.ohc_uploads', data_format='json')
self.skip = list() self.skip = list()
self.last_run = 0 # Track last time periodic tasks were run self.last_run = 0 # Track last time periodic tasks were run
self.internet_active = False # Track whether internet is currently available self.internet_active = False # Track whether internet is currently available

View File

@@ -34,7 +34,7 @@ class WpaSec(plugins.Plugin):
self._init_db() self._init_db()
def _init_db(self): def _init_db(self):
db_conn = sqlite3.connect('/home/pi/.wpa_sec_db') db_conn = sqlite3.connect('/etc/pwnagotchi/.wpa_sec_db')
db_conn.execute('pragma journal_mode=wal') db_conn.execute('pragma journal_mode=wal')
with db_conn: with db_conn:
db_conn.execute(''' db_conn.execute('''
@@ -72,7 +72,7 @@ class WpaSec(plugins.Plugin):
if not remove_whitelisted([filename], config['main']['whitelist']): if not remove_whitelisted([filename], config['main']['whitelist']):
return return
db_conn = sqlite3.connect('/home/pi/.wpa_sec_db') db_conn = sqlite3.connect('/etc/pwnagotchi/.wpa_sec_db')
with db_conn: with db_conn:
db_conn.execute(''' db_conn.execute('''
INSERT INTO handshakes (path, status) INSERT INTO handshakes (path, status)
@@ -93,7 +93,7 @@ class WpaSec(plugins.Plugin):
display = agent.view() display = agent.view()
try: try:
db_conn = sqlite3.connect('/home/pi/.wpa_sec_db') db_conn = sqlite3.connect('/etc/pwnagotchi/.wpa_sec_db')
cursor = db_conn.cursor() cursor = db_conn.cursor()
cursor.execute('SELECT path FROM handshakes WHERE status = ?', (self.Status.TOUPLOAD.value,)) cursor.execute('SELECT path FROM handshakes WHERE status = ?', (self.Status.TOUPLOAD.value,))
@@ -264,7 +264,7 @@ class WpaSec(plugins.Plugin):
def on_ui_update(self, ui): def on_ui_update(self, ui):
if 'show_pwd' in self.options and self.options['show_pwd'] and 'download_results' in self.options and self.options['download_results']: if 'show_pwd' in self.options and self.options['show_pwd'] and 'download_results' in self.options and self.options['download_results']:
file_path = '/home/pi/handshakes/wpa-sec.cracked.potfile' file_path = '/etc/pwnagotchi/handshakes/wpa-sec.cracked.potfile'
try: try:
with open(file_path, 'r') as file: with open(file_path, 'r') as file:
# Read all lines and extract the required fields # Read all lines and extract the required fields