[SOLVED]How to use physical buttons to "ifup a interface"?

My question is simple, is there any way to "ifup a interface" triggered with "push a button"?

I got a TP-Link WDR4300 working as a managed switch with 5 VLANs / interfaces declared at /etc/config/network file, only one of them has an IP address, this interface called admin is to access to router to manage it by ssh and web interface, the rest of them, are only a L2 interfaces with their own MAC addresses (VLAN Software or 802.1q).

My target is to be able to "ifup" the admin interface when I push button WPS for example (it's the only physical button that I got available), which packages (and / or other things) that I need to this purpose?

Thanks in advance, regards.

EDIT: I've been reading about the physical buttons actions at the OpenWrt's Wiki, but I don't have understood to make my purpose possible by myself.

What part do you need help with in https://openwrt.org/docs/guide-user/hardware/hardware.button ?

3 Likes

Well, I've been reading that doc that you've linked and the only physical buttons available in this device are "reset button" and "wi-fi button" (the last is a switch button with 2 positions).

I need to know how to bring up a X interface with a "pressed" action linked to the reset button, but my main problem is that I don't know how to make a simple script to accomplish this.

Please, can you help me?

did you even try the minimal script in the preliminary scripts chapter ?

Try editing /etc/rc.button/wps, but first set the correct logical interface name.

#!/bin/sh

if [ "$ACTION" = "released" ] && [ "$BUTTON" = "wps" ]; then
        if [ "$SEEN" -lt 2 ] ; then
                ifup lan
        else
                ifdown lan
        fi
fi

If you press and hold the WPS/reset button for less than 2 seconds, the interface will go up.
If you hold it longer, it will go down.

4 Likes
opkg update
opkg install kmod-button-hotplug

mkdir -p /etc/hotplug.d/button
 
cat << "EOF" > /etc/hotplug.d/button/buttons
logger "the button was ${BUTTON} and the action was ${ACTION}"
EOF

Now press the button you want to use, then run `logread`.

Jan 1 00:01:15 OpenWrt user.notice root: BTN_1
Jan 1 00:01:15 OpenWrt user.notice root: pressed
Jan 1 00:01:16 OpenWrt user.notice root: BTN_1
Jan 1 00:01:16 OpenWrt user.notice root: released



uci add system button
uci set system.@button[-1].button="BTN_1"
uci set system.@button[-1].action="released"
uci set system.@button[-1].handler="ifup admin_interface"
uci set system.@button[-1].min="5"
uci set system.@button[-1].max="10"
uci commit system

uci add system button
uci set system.@button[-1].button="wps"
uci set system.@button[-1].action="released"
uci set system.@button[-1].handler="/root/admin-on"
uci set system.@button[-1].min="0"
uci set system.@button[-1].max="3"
uci commit system
 
cat << "EOF" > /root/admin-on
#!/bin/sh
[ "${BUTTON}" = "BTN_1" ] && [ "${ACTION}" = "pressed" ] 
        ifup admin_interface
EOF
chmod u+x /root/admin-on
```
2 Likes

Thank you for your help guys, I will take a look to your scripts and try to adapt to my "interface and button names"

Hi again mates @frollic @ncompact @pavelgl :

After reading more about how to attach functions to a push button and take a look to your fantastic scripts, I've to say that I don't have be able to accomplish my objective, well, my device uses gpio buttons (sorry for don't say it before), and there are only two physical buttons, reset and rfkill (or wifi like you prefer), the firs is used for "reset" and "wps" functions in original firmware but only for reset in OpenWrt, and the second button (rfkill) is a switch with 2 positions.

About the rfkill button, I prefer to use it in place of reset button, using the method described at wiki:

opkg update
opkg install kmod-button-hotplug
 
mkdir -p /etc/hotplug.d/button
 
cat << "EOF" > /etc/hotplug.d/button/buttons
logger "the button was ${BUTTON} and the action was ${ACTION}"
EOF

The logread shows the next:

Tue May 16 10:34:34 2023 user.notice root: the button was rfkill and the action was pressed
Tue May 16 10:34:36 2023 user.notice root: the button was rfkill and the action was released

That was to use the switch one time in each position, the pressed action when I change the position from off to on, and the released action when I change from on to off.

I've to say that I'm using the device as a managed switch, because of that, I'm not using the Wi-Fi, this is why I prefer use this button instead of the reset button, is there any way to adapt your scripts to make use of the rfkill (switch) button?


P.S.: Like the Wiki indicates, to see which buttons are available:

find /sys/firmware/devicetree/base/keys -mindepth 1 -type d | while read -r f; do printf '%s: %s\n' $(basename $f) $(hexdump -s2 -e '2/1 "%02x""\n"' $f/linux,code); done
wifi: 00f7
reset: 0198

P.S.2: I show you the rfkill script associated to wifi button:

#!/bin/sh

[ "${ACTION}" = "released" -o -n "${TYPE}" ] || exit 0
 
. /lib/functions.sh

rfkill_state=0

wifi_rfkill_set() {
          uci set wireless.$1.disabled=$rfkill_state
}

wifi_rfkill_check() {
         local disabled
         config_get disabled $1 disabled
         [ "$disabled" = "1" ] || rfkill_state=1
}

config_load wireless
case "${TYPE}" in
"switch")
        [ "${ACTION}" = "released" ] && rfkill_state=1
        ;;
*)
        config_foreach wifi_rfkill_check wifi-device
        ;;
esac
config_foreach wifi_rfkill_set wifi-device
uci commit wireless
wifi up

return 0

Finally!!!, I got the button working as I want, if I "turn on" (pressed) the rfkill button the admin interface brings up, and if I "turn off" (released) the rfkill button, the admin interface brings down.

I've edited the rfkill script located at "/etc/rc.button" with this:

#!/bin/sh

if [ "$ACTION" = "pressed" ] && [ "$BUTTON" = "rfkill" ]; then
           ifup admin
fi

if [ "$ACTION" = "released" ] && [ "$BUTTON" = "rfkill" ]; then              
           ifdown admin
fi

Thank you so much guys for help to this newbie, this community is incredible.

2 Likes

Great Job solving your own problem :smile: . You could simplify it like this:

#!/bin/sh
if [ "$BUTTON" = "rfkill" ]; then
  case "$ACTION" in
    pressed) ifup admin;;
    released) ifdown admin;;
  esac
fi
1 Like

Thank you for your recommendation, I'll take a look later, my skills scripting are "practically nil", all your recommendations are so helpful, to resolve problems and learn.

1 Like

This topic was automatically closed 10 days after the last reply. New replies are no longer allowed.