ledcontrol

This commit is contained in:
Miguel Fuertes committed 2025-10-03 16:40:21 +02:00
1 parent 519cefb5d8
commit 30804ea4f5
13 files changed
+235 -108

No files matched your search

+1
View File
@@ -21,6 +21,7 @@ CONFIG_PACKAGE_kmod-tun=y
CONFIG_PACKAGE_kmod-udptunnel4=y CONFIG_PACKAGE_kmod-udptunnel4=y
CONFIG_PACKAGE_kmod-udptunnel6=y CONFIG_PACKAGE_kmod-udptunnel6=y
CONFIG_PACKAGE_kmod-wireguard=y CONFIG_PACKAGE_kmod-wireguard=y
CONFIG_PACKAGE_ledcontrol=y
CONFIG_PACKAGE_libattr=y CONFIG_PACKAGE_libattr=y
CONFIG_PACKAGE_libdbus=y CONFIG_PACKAGE_libdbus=y
CONFIG_PACKAGE_libexpat=y CONFIG_PACKAGE_libexpat=y
+20
View File
@@ -0,0 +1,20 @@
#!/bin/sh -e
# Usage: generate-gpt.sh <OUTFILE>
OUTFILE="$1"
TMPDIR="$(mktemp -d)"
IMG="${TMPDIR}/gpt.img"
SECTOR_SIZE=512
SECTORS_TOTAL=7634944
truncate -s $((SECTORS_TOTAL*SECTOR_SIZE)) "${IMG}"
sfdisk "${IMG}" < gpt.table
{
dd if="${IMG}" bs=${SECTOR_SIZE} count=34 status=none
dd if="${IMG}" bs=${SECTOR_SIZE} skip=$((SECTORS_TOTAL - 33)) count=33 status=none
} > "${OUTFILE}"
echo "Wrote: ${OUTFILE}"
rm -rf "${TMPDIR}"
+18
View File
@@ -0,0 +1,18 @@
label: gpt
unit: sectors
sector-size: 512
p1 : start= 4096, size= 2, type=57B90A16-22C9-E33B-8F5D-0E81686A68CB, name="fsc"
p2 : start= 4098, size= 3072, type=638FF8E2-22C9-E33B-8F5D-0E81686A68CB, name="fsg"
p3 : start= 7170, size= 131072, type=EBD0A0A2-B9E5-4433-87C0-68B6B72699C7, name="modem"
p4 : start= 138242, size= 3072, type=EBBEADAF-22C9-E33B-8F5D-0E81686A68CB, name="modemst1"
p5 : start= 141314, size= 3072, type=0A288B1F-22C9-E33B-8F5D-0E81686A68CB, name="modemst2"
p6 : start= 144386, size= 65536, type=6C95E238-E343-4BA8-B489-8681ED22AD0B, name="persist"
p7 : start= 209922, size= 32, type=303E6AC3-AF15-4C54-9E9B-D9A8FBECF401, name="sec"
p8 : start= 209954, size= 1024, type=E1A6A689-0C8D-4CC6-B4E8-55A4320FBD8A, name="hyp"
p9 : start= 210978, size= 1024, type=098DF793-D712-413D-9D4E-89D711772228, name="rpm"
p10: start= 212002, size= 1024, type=DEA0BA2C-CBDD-4805-B4F9-F428251C3E98, name="sbl1"
p11: start= 213026, size= 2048, type=A053AA7F-40B8-4B1C-BA08-2F68AC71A4F4, name="tz"
p12: start= 215074, size= 2048, type=400FFDCD-22E0-47E7-9A23-F16ED9382388, name="aboot"
p13: start= 217122, size= 131072, type=20117F86-E985-4357-B9EE-374BC1D8487D, name="boot"
p14: start= 348194, type=0FC63DAF-8483-4772-8E79-3D69D8477DE4, name="rootfs"
+4 -6
View File
@@ -2,11 +2,9 @@
ifeq ($(SUBTARGET),msm8916) ifeq ($(SUBTARGET),msm8916)
define Build/generate-gpt-ext4 define Build/generate-gpt
$(TOPDIR)/target/linux/$(BOARD)/image/generate_gpt.sh \ chmod +x $(TOPDIR)/target/linux/$(BOARD)/image/generate_gpt.sh
"$(dir $@)" \ $(TOPDIR)/target/linux/$(BOARD)/image/generate_gpt.sh $@
$(TOPDIR)/target/linux/$(BOARD)/image/gpt-ext4.table \
"$(notdir $@)"
endef endef
define Build/install-flasher define Build/install-flasher
@@ -28,7 +26,7 @@ define Device/yiming-uz801v3
DEVICE_PACKAGES := uz801-tweaks wpad-basic-wolfssl msm-firmware-dumper rmtfs rootfs-resizer msm8916-usb-gadget DEVICE_PACKAGES := uz801-tweaks wpad-basic-wolfssl msm-firmware-dumper rmtfs rootfs-resizer msm8916-usb-gadget
IMAGE/system.img := append-rootfs | append-metadata | sparse-img IMAGE/system.img := append-rootfs | append-metadata | sparse-img
ARTIFACTS := gpt_both0.bin flash.sh ARTIFACTS := gpt_both0.bin flash.sh
ARTIFACT/gpt_both0.bin := generate-gpt-ext4 ARTIFACT/gpt_both0.bin := generate-gpt
ARTIFACT/flash.sh := install-flasher ARTIFACT/flash.sh := install-flasher
endef endef
TARGET_DEVICES += yiming-uz801v3 TARGET_DEVICES += yiming-uz801v3
+37
View File
@@ -0,0 +1,37 @@
include $(TOPDIR)/rules.mk
PKG_NAME:=ledcontrol
PKG_VERSION:=1.0
PKG_RELEASE:=1
PKG_LICENSE:=GPL-2.0
include $(INCLUDE_DIR)/package.mk
define Package/ledcontrol
SECTION:=utils
CATEGORY:=Utilities
TITLE:=Simple LED control utility
DEPENDS:=
endef
define Package/ledcontrol/description
Simple utility to control device LEDs via sysfs
Usage: ledcontrol <color> <on|off|blink|blink_fast>
Includes hotplug scripts for WiFi and modem LED management
endef
define Build/Compile
endef
define Package/ledcontrol/install
$(INSTALL_DIR) $(1)/usr/sbin
$(INSTALL_BIN) ./files/ledcontrol $(1)/usr/sbin/
$(INSTALL_DIR) $(1)/etc/hotplug.d/ieee80211
$(INSTALL_DATA) ./files/etc/hotplug.d/ieee80211/99-wifi-led $(1)/etc/hotplug.d/ieee80211/
$(INSTALL_DIR) $(1)/etc/hotplug.d/iface
$(INSTALL_DATA) ./files/etc/hotplug.d/iface/99-modem-led $(1)/etc/hotplug.d/iface/
endef
$(eval $(call BuildPackage,ledcontrol))
+14
View File
@@ -0,0 +1,14 @@
#!/bin/sh
# /etc/hotplug.d/iface/99-modem-led
# Modem LED control based on interface status
case "$ACTION:$INTERFACE" in
ifup:modem)
ledcontrol green on
logger -t modem-led "Modem UP - Green LED ON"
;;
ifdown:modem)
ledcontrol green off
logger -t modem-led "Modem DOWN - Green LED OFF"
;;
esac
@@ -1,22 +1,23 @@
#!/bin/sh #!/bin/sh
# /etc/hotplug.d/ieee80211/99-wifi-led # /etc/hotplug.d/ieee80211/99-wifi-led
# WiFi LED control based on phy0 status
case "$ACTION" in case "$ACTION" in
add) add)
if [ "$DEVICENAME" = "phy0" ]; then if [ "$DEVICENAME" = "phy0" ]; then
sleep 5 sleep 5
if ip link show phy0-ap0 2>/dev/null >/dev/null; then if ip link show phy0-ap0 2>/dev/null >/dev/null; then
echo 1 > /sys/class/leds/blue:wan/brightness ledcontrol blue on
logger -t wifi-led "phy0-ap0 exists, blue LED ON" logger -t wifi-led "phy0-ap0 exists, blue LED ON"
else else
echo 0 > /sys/class/leds/blue:wan/brightness ledcontrol blue off
logger -t wifi-led "phy0-ap0 missing, blue LED OFF" logger -t wifi-led "phy0-ap0 missing, blue LED OFF"
fi fi
fi fi
;; ;;
remove) remove)
if [ "$DEVICENAME" = "phy0" ]; then if [ "$DEVICENAME" = "phy0" ]; then
echo 0 > /sys/class/leds/blue:wan/brightness ledcontrol blue off
logger -t wifi-led "phy0 removed, blue LED OFF" logger -t wifi-led "phy0 removed, blue LED OFF"
fi fi
;; ;;
+87
View File
@@ -0,0 +1,87 @@
#!/bin/sh
# LED Control Utility for OpenWrt
# Usage: ledcontrol <color> <on|off|blink|blink_fast>
set -e
COLOR="$1"
ACTION="$2"
# LED base path
LED_BASE="/sys/class/leds"
# Find LED by color
find_led() {
local color="$1"
local led_path
# Search for LED containing the color in name
led_path=$(find "$LED_BASE" -maxdepth 1 -type l -iname "*:${color}:*" 2>/dev/null | head -n 1)
if [ -z "$led_path" ]; then
# Try without colons
led_path=$(find "$LED_BASE" -maxdepth 1 -type l -iname "*${color}*" 2>/dev/null | head -n 1)
fi
if [ -z "$led_path" ]; then
logger -t ledcontrol "LED color '$color' not found"
echo "[!] LED color '$color' not found" >&2
echo "[*] Available LEDs:" >&2
ls -1 "$LED_BASE" | sed 's/^/ /' >&2
return 1
fi
echo "$led_path"
}
# Set LED state
set_led() {
local led_path="$1"
local action="$2"
case "$action" in
on)
echo none > "$led_path/trigger"
echo 1 > "$led_path/brightness"
;;
off)
echo none > "$led_path/trigger"
echo 0 > "$led_path/brightness"
;;
blink)
echo timer > "$led_path/trigger"
echo 500 > "$led_path/delay_on"
echo 500 > "$led_path/delay_off"
;;
blink_fast)
echo timer > "$led_path/trigger"
echo 100 > "$led_path/delay_on"
echo 100 > "$led_path/delay_off"
;;
*)
logger -t ledcontrol "Invalid action: $action"
echo "[!] Invalid action: $action" >&2
echo "[*] Valid actions: on, off, blink, blink_fast" >&2
return 1
;;
esac
}
# Main
if [ -z "$COLOR" ] || [ -z "$ACTION" ]; then
echo "Usage: ledcontrol <color> <on|off|blink|blink_fast>" >&2
echo "" >&2
echo "Available LEDs:" >&2
ls -1 "$LED_BASE" 2>/dev/null | sed 's/^/ /' >&2
exit 1
fi
LED_PATH=$(find_led "$COLOR") || exit 1
LED_NAME=$(basename "$LED_PATH")
if set_led "$LED_PATH" "$ACTION"; then
logger -t ledcontrol "LED '$LED_NAME' set to '$ACTION'"
echo "[+] LED '$COLOR' set to '$ACTION'"
else
exit 1
fi
@@ -1,8 +1,5 @@
#!/bin/sh #!/bin/sh
# One-shot Qualcomm firmware dumper: mount partitions read-only, # One-shot Qualcomm firmware dumper with LED feedback
# copy relevant blobs into /lib/firmware, set a marker to avoid
# re-running, and trigger a reboot. Accepts optional 'MCFG_PATH'
# env var to override the MCFG relative path within modem/persist.
set -e set -e
DEFAULT_MARKER="/lib/firmware/DUMPED" DEFAULT_MARKER="/lib/firmware/DUMPED"
@@ -12,63 +9,61 @@ MARKER="${MSM_DUMPER_FLAG_FILE:-$DEFAULT_MARKER}"
[ -f "$MARKER" ] && exit 0 [ -f "$MARKER" ] && exit 0
log() { logger -t msm-fw-dumper "$*"; } log() { logger -t msm-fw-dumper "$*"; }
led() { command -v ledcontrol >/dev/null 2>&1 && ledcontrol "$@" || true; }
MNT="/tmp/mnt/msmfw" MNT="/tmp/mnt/msmfw"
FW="/lib/firmware" FW="/lib/firmware"
MCFG_REL="${MCFG_PATH:-$DEFAULT_MCFG_PATH}" MCFG_REL="${MCFG_PATH:-$DEFAULT_MCFG_PATH}"
log "start (marker not present)" log "starting firmware dump"
led blue blink
# Prepare mount points and target # Prepare mount points and target
mkdir -p "$MNT/modem" "$MNT/persist" "$FW/wlan/prima" mkdir -p "$MNT/modem" "$MNT/persist" "$FW/wlan/prima"
# Mount partitions read-only (adjust device nodes if needed) # Mount partitions read-only
mount -t vfat -o ro,nosuid,nodev,noexec,iocharset=iso8859-1,codepage=437 /dev/mmcblk0p3 "$MNT/modem" 2>/dev/null || log "WARN: modem mount failed" mount -t vfat -o ro,nosuid,nodev,noexec,iocharset=iso8859-1,codepage=437 /dev/mmcblk0p3 "$MNT/modem" 2>/dev/null || log "WARN: modem mount failed"
mount -t ext4 -o ro,nosuid,nodev,noexec /dev/mmcblk0p6 "$MNT/persist" 2>/dev/null || log "WARN: persist mount failed" mount -t ext4 -o ro,nosuid,nodev,noexec /dev/mmcblk0p6 "$MNT/persist" 2>/dev/null || log "WARN: persist mount failed"
# Copy if exists! # Copy helper
copy_if() { copy_if() {
src="$1"; dst="$2" [ -f "$1" ] && cp -af "$1" "$2" && log "copied $(basename "$1")"
if [ -f "$src" ]; then
cp -af "$src" "$dst" && log "copied $(basename "$src")" || return $?
fi
return 0
} }
# Modem/Wi-Fi core blobs (MDT + fragments + MBA if present) # Modem/Wi-Fi core blobs
for p in "$MNT/modem"/image/wcnss.mdt "$MNT/modem"/image/wcnss.b* \ for p in "$MNT/modem"/image/wcnss.{mdt,b*} \
"$MNT/modem"/image/modem.mdt "$MNT/modem"/image/modem.b* \ "$MNT/modem"/image/modem.{mdt,b*} \
"$MNT/modem"/image/mba.mbn "$MNT/modem"/image/mba.mbn
do do
[ -f "$p" ] && cp -af "$p" "$FW/" copy_if "$p" "$FW/"
done done
# Wi‑Fi NV/configs required by wcn36xx (place under wlan/prima) # Wi‑Fi NV/configs
copy_if "$MNT/persist/WCNSS_qcom_wlan_nv.bin" "$FW/wlan/prima/WCNSS_qcom_wlan_nv.bin" copy_if "$MNT/persist/WCNSS_qcom_wlan_nv.bin" "$FW/wlan/prima/WCNSS_qcom_wlan_nv.bin"
copy_if "$MNT/modem/image/wlan/prima/WCNSS_qcom_wlan_nv.bin" "$FW/wlan/prima/WCNSS_qcom_wlan_nv.bin" copy_if "$MNT/modem/image/wlan/prima/WCNSS_qcom_wlan_nv.bin" "$FW/wlan/prima/WCNSS_qcom_wlan_nv.bin"
copy_if "$MNT/modem/image/wlan/prima/WCNSS_cfg.dat" "$FW/wlan/prima/WCNSS_cfg.dat" copy_if "$MNT/modem/image/wlan/prima/WCNSS_cfg.dat" "$FW/wlan/prima/WCNSS_cfg.dat"
copy_if "$MNT/modem/image/wlan/prima/WCNSS_qcom_cfg.ini" "$FW/wlan/prima/WCNSS_qcom_cfg.ini" copy_if "$MNT/modem/image/wlan/prima/WCNSS_qcom_cfg.ini" "$FW/wlan/prima/WCNSS_qcom_cfg.ini"
# MCFG handling: # MCFG handling
if [ -f "$MNT/modem/$MCFG_REL/mcfg_sw.mbn" ]; then if [ -f "$MNT/modem/$MCFG_REL/mcfg_sw.mbn" ]; then
cp -af "$MNT/modem/$MCFG_REL/mcfg_sw.mbn" "$FW/MCFG_SW.MBN" && log "MCFG from modem:$MCFG_REL" cp -af "$MNT/modem/$MCFG_REL/mcfg_sw.mbn" "$FW/MCFG_SW.MBN" && log "MCFG from modem:$MCFG_REL"
else else
log "WARN: MCFG 'MCFG_PATH=$MCFG_REL' not found in modem" log "WARN: MCFG '$MCFG_REL' not found"
fi fi
# Honoring any user copied MCFG to /lib/firmware # User override support
[ -f "$FW/mcfg_sw.mbn" ] && ln -sf "$FW/mcfg_sw.mbn" "$FW/MCFG_SW.MBN" 2>/dev/null || true [ -f "$FW/mcfg_sw.mbn" ] && ln -sf "$FW/mcfg_sw.mbn" "$FW/MCFG_SW.MBN" 2>/dev/null || true
sync sync
# Unmount and cleanup # Cleanup
umount "$MNT/modem" 2>/dev/null || true umount "$MNT/modem" "$MNT/persist" 2>/dev/null || true
umount "$MNT/persist" 2>/dev/null || true
rmdir "$MNT/persist" "$MNT/modem" 2>/dev/null || true rmdir "$MNT/persist" "$MNT/modem" 2>/dev/null || true
# Set marker and reboot once # Mark done
touch "$MARKER" touch "$MARKER"
log "done, rebooting" log "firmware dump complete, rebooting"
( sleep 2; reboot ) & led green on
( sleep 2; led green blink; sleep 1; reboot ) &
exit 0 exit 0
@@ -1,74 +1,50 @@
#!/bin/sh /etc/rc.common #!/bin/sh /etc/rc.common
# Early ext4 rootfs resizer with flag and logs (OpenWrt rc.common) # Early ext4 rootfs resizer with LED feedback
START=01 START=01
STOP=00
NAME=rootfs-resizer NAME=rootfs-resizer
FLAG="/etc/rootfs-resizer.done" FLAG="/RESIZED"
log() { logger -t rootfs-resizer "$*"; } log() { logger -t rootfs-resizer "$*"; }
led() { command -v ledcontrol >/dev/null 2>&1 && ledcontrol "$@" || true; }
get_rootdev() { get_rootdev() {
local dev local dev="$(awk '$2=="/"{print $1; exit}' /proc/mounts)"
dev="$(findmnt -n -o SOURCE / 2>/dev/null || awk '$2=="/"{print $1; exit}' /proc/mounts)"
[ -n "$dev" ] || dev="$(sed -n 's/.*\broot=\([^ ]*\).*/\1/p' /proc/cmdline)"
[ "$dev" = "/dev/root" ] && dev="$(sed -n 's/.*\broot=\([^ ]*\).*/\1/p' /proc/cmdline)" [ "$dev" = "/dev/root" ] && dev="$(sed -n 's/.*\broot=\([^ ]*\).*/\1/p' /proc/cmdline)"
case "$dev" in
LABEL=*|UUID=*|PARTUUID=*|PARTLABEL=*)
dev="$(blkid -l -t "$dev" -o device 2>/dev/null || true)"
;;
esac
echo "$dev" echo "$dev"
} }
start() { start() {
if [ -f "$FLAG" ]; then [ -f "$FLAG" ] && { log "already resized, skipping"; return 0; }
log "flag present, skipping resize"
return 0
fi
log "starting early rootfs resize" log "starting rootfs resize"
led blue blink
local dev rc out local dev="$(get_rootdev)"
dev="$(get_rootdev)" [ -z "$dev" ] || [ ! -b "$dev" ] && {
if [ -z "$dev" ] || [ ! -b "$dev" ]; then log "ERROR: invalid root device";
log "could not resolve a valid root block device; aborting" led red blink_fast;
return 0 return 1;
fi }
log "root device resolved: $dev"
# Remount root read-only before metadata changes/checks log "resizing $dev"
log "remounting / read-only"
mount -o ro,remount / 2>/dev/null || log "WARN: remount ro failed (continuing)"
# Clear resize_inode like the working script (safe to ignore errors if not present) # Prepare filesystem
log "clearing resize_inode feature if present" mount -o ro,remount / 2>/dev/null
out="$(tune2fs -O^resize_inode "$dev" 2>&1)"; rc=$? tune2fs -O^resize_inode "$dev" >/dev/null 2>&1
echo "$out" | logger -t rootfs-resizer e2fsck -yDf "$dev" >/dev/null 2>&1
[ $rc -ne 0 ] && log "tune2fs exited rc=$rc (continuing)" mount -o rw,remount / 2>/dev/null
# Run fsck (note: generally discouraged on mounted FS; we remounted ro) # Resize
log "running e2fsck -yDf on $dev" if resize2fs "$dev" 2>&1 | logger -t rootfs-resizer; then
out="$(e2fsck -yDf "$dev" 2>&1)"; rc=$? log "resize successful"
echo "$out" | logger -t rootfs-resizer led green on
[ $rc -ne 0 ] && log "e2fsck exited rc=$rc (continuing)"
# Back to read-write for online resize
log "remounting / read-write"
mount -o rw,remount / 2>/dev/null || log "WARN: remount rw failed (continuing)"
log "invoking resize2fs (online) on $dev"
out="$(resize2fs "$dev" 2>&1)"; rc=$?
echo "$out" | logger -t rootfs-resizer
if [ $rc -eq 0 ]; then
log "resize2fs succeeded on $dev"
touch "$FLAG" touch "$FLAG"
sync sync
log "flag created at $FLAG; syncing and rebooting" ( sleep 2; led green blink; sleep 1; reboot -f ) &
( sleep 1; reboot -f ) &
else else
log "resize2fs failed rc=$rc; leaving system as-is" log "ERROR: resize failed"
led red blink_fast
return 1
fi fi
} }
-7
View File
@@ -29,13 +29,6 @@ endef
define Package/$(PKG_NAME)/install define Package/$(PKG_NAME)/install
$(INSTALL_DIR) $(1)/etc/uci-defaults $(INSTALL_DIR) $(1)/etc/uci-defaults
$(INSTALL_BIN) ./files/uci_defaults $(1)/etc/uci-defaults/99-default-config $(INSTALL_BIN) ./files/uci_defaults $(1)/etc/uci-defaults/99-default-config
$(INSTALL_DIR) $(1)/etc/hotplug.d/ieee80211
$(INSTALL_BIN) ./files/wifi-led.hotplug $(1)/etc/hotplug.d/ieee80211/99-wifi-led
$(INSTALL_DIR) $(1)/etc/hotplug.d/iface
$(INSTALL_BIN) ./files/modem-led.hotplug $(1)/etc/hotplug.d/iface/99-modem-led
endef endef
$(eval $(call BuildPackage,$(PKG_NAME))) $(eval $(call BuildPackage,$(PKG_NAME)))
@@ -1,13 +0,0 @@
#!/bin/sh
# /etc/hotplug.d/iface/99-modem-led
case "$ACTION:$INTERFACE" in
ifup:modem)
echo 1 > /sys/class/leds/green:wlan/brightness
logger -t smart-leds "Modem UP - Green LED ON"
;;
ifdown:modem)
echo 0 > /sys/class/leds/green:wlan/brightness
logger -t smart-leds "Modem DOWN - Green LED OFF"
;;
esac
+2 -2
View File
@@ -20,8 +20,8 @@ Modern version of OpenWrt working on UZ801v3:
- Wireguard Installed - Wireguard Installed
- `hotplug.d` scripts to manage leds, only on/off if iface, no blinking: - `hotplug.d` scripts to manage leds, only on/off if iface, no blinking:
- On default Linux Kernel `dts`, leds are swapped! - On default Linux Kernel `dts`, leds are swapped!
- Wifi Led: [packages/uz801-tweaks/files/wifi-led.hotplug](packages/uz801-tweaks/files/wifi-led.hotplug) - Wifi Led: [packages/ledcontrol/files/99-modem-led](packages/ledcontrol/files/99-modem-led)
- Modem Led: [packages/uz801-tweaks/files/modem-led.hotplug](packages/uz801-tweaks/files/modem-led.hotplug) - Modem Led: [packages/ledcontrol/files/99-wifi-led](packages/ledcontrol/files/99-wifi-led)
- Firmware is dumped on first boot from modem/persist partition: - Firmware is dumped on first boot from modem/persist partition:
- Uses the binaries/firmware from the own device. - Uses the binaries/firmware from the own device.
- __This might imply that a port for other devices would be easier... but I have not tested it as I only have this device.___ - __This might imply that a port for other devices would be easier... but I have not tested it as I only have this device.___