Dynamic Frequency Selection (DFS) is a regulatory requirement for wireless devices operating in certain 5GHz frequency bands. It ensures that these devices do not interfere with radar systems by dynamically switching channels when radar signals are detected. Sometimes it happens even there is no radar operating in the area. In this articles we shall guide you through creating a script to automatically restart your 5GHz radio of Dual Band Openwrt Router using a DFS channel upon radar detection.
Introduction to DFS
DFS is crucial for maintaining the integrity of radar operations and ensuring that wireless networks comply with regulatory standards. When a radar signal is detected on a DFS channel, the wireless device must vacate the channel and switch to another one. This process can cause temporary disruptions in the network, but it is necessary to prevent interference with radar systems.
The Challenge
In some cases, the automatic channel switching might not work as expected, or the device might not switch to the desired channel. To address this, we can create a script that monitors the current channel and frequency of the 5GHz radio and restarts it if necessary.
Step-by-Step Explanation of the Script:
1. Configuration Section
RADIO="radio1" MAX_RESTARTS=2 RESTART_INTERVAL=3600 # 1 hour in seconds LOG_FILE="/tmp/check_radio_channel.log" MAX_LOG_SIZE=10240 # 10 KB
- RADIO: Specifies the radio interface to monitor (e.g.,
radio1
). - MAX_RESTARTS: Maximum number of restarts allowed within the specified interval.
- RESTART_INTERVAL: Time interval (in seconds) within which the maximum restarts are counted.
- LOG_FILE: Path to the log file.
- MAX_LOG_SIZE: Maximum size of the log file before it gets truncated.
2. Function Definitions
- get_current_channel: Retrieves the current channel setting of the specified radio.
get_current_channel() { uci get wireless.$RADIO.channel }
- get_current_frequency: Retrieves the current operating frequency of the specified radio.
get_current_frequency() { iwinfo $RADIO info | grep 'Channel:' | awk '{print $4}' }
- restart_radio: Restarts the specified radio interface.
restart_radio() { wifi down $RADIO && wifi up $RADIO }
- truncate_log: Truncates the log file if it exceeds the specified maximum size.
truncate_log() { if [ -f $LOG_FILE ]; then log_size=$(wc -c < "$LOG_FILE") if [ "$log_size" -ge "$MAX_LOG_SIZE" ]; then : > $LOG_FILE echo "Log file truncated" > $LOG_FILE fi fi }
3. Main Script Execution
- Truncate Log: Ensures the log file does not exceed the maximum size.
truncate_log
- Get Current Channel and Frequency: Retrieves the current channel and frequency.
current_channel=$(get_current_channel) current_frequency=$(get_current_frequency)
- Check if Channel is Set to Auto: If the channel is set to “auto”, the script exits without taking any action.
if [ "$current_channel" = "auto" ]; then echo "$(date '+%Y-%m-%d %H:%M:%S') - Channel is set to auto, no action taken" >> $LOG_FILE exit 0 fi
- Initialize Restart Count and Time: Initializes variables to keep track of the restart count and the last restart time.
restart_count=0 last_restart_time=0
- Get Current Time: Retrieves the current time in seconds since the epoch.
current_time=$(date +%s)
- Check Channel and Frequency Mismatch: If the current channel does not match the current frequency, the script checks if a restart is needed.
if [ "$current_channel" != "$current_frequency" ]; then if [ $((current_time - last_restart_time)) -le $RESTART_INTERVAL ]; then if [ $restart_count -lt $MAX_RESTARTS ]; then restart_radio restart_count=$((restart_count + 1)) last_restart_time=$current_time else echo "$(date '+%Y-%m-%d %H:%M:%S') - Maximum restarts reached within an hour" >> $LOG_FILE fi else restart_radio restart_count=1 last_restart_time=$current_time fi fi
Full Script
Here is the complete script with all the explained sections combined:
#!/bin/sh # Configuration RADIO="radio1" MAX_RESTARTS=2 RESTART_INTERVAL=3600 # 1 hour in seconds LOG_FILE="/tmp/check_radio_channel.log" MAX_LOG_SIZE=10240 # 10 KB # Function to get the current channel of the specified radio get_current_channel() { uci get wireless.$RADIO.channel } # Function to get the current frequency of the specified radio get_current_frequency() { iwinfo $RADIO info | grep 'Channel:' | awk '{print $4}' } # Function to restart the radio restart_radio() { # Restart the radio wifi down $RADIO && wifi up $RADIO } # Function to truncate the log file if it exceeds the maximum size truncate_log() { if [ -f $LOG_FILE ]; then log_size=$(wc -c < "$LOG_FILE") if [ "$log_size" -ge "$MAX_LOG_SIZE" ]; then : > $LOG_FILE echo "Log file truncated" > $LOG_FILE fi fi } # Truncate log if necessary truncate_log # Get current channel and frequency current_channel=$(get_current_channel) current_frequency=$(get_current_frequency) # Check if the channel is set to auto if [ "$current_channel" = "auto" ]; then echo "$(date '+%Y-%m-%d %H:%M:%S') - Channel is set to auto, no action taken" >> $LOG_FILE exit 0 fi # Initialize restart count and time restart_count=0 last_restart_time=0 # Get current time current_time=$(date +%s) # Check if the current channel is not the same as the current frequency if [ "$current_channel" != "$current_frequency" ]; then # Check if the restart count is less than the maximum allowed restarts within an hour if [ $((current_time - last_restart_time)) -le $RESTART_INTERVAL ]; then if [ $restart_count -lt $MAX_RESTARTS ]; then restart_radio restart_count=$((restart_count + 1)) last_restart_time=$current_time else echo "$(date '+%Y-%m-%d %H:%M:%S') - Maximum restarts reached within an hour" >> $LOG_FILE fi else # Reset the restart count if more than an hour has passed restart_radio restart_count=1 last_restart_time=$current_time fi fi
How to use this script:
Step 1: Downloading WinSCP
- Visit the Official Website: Go to the WinSCP download page.
- Download the Installer: Click on the download link to get the latest version of WinSCP. Save the installer to an easily accessible location, such as your desktop or Downloads folder.
Step 2: Installing WinSCP
- Run the Installer: Double-click the downloaded installer file to start the installation process.
- Follow the Installation Wizard:
- Language Selection: Choose your preferred language.
- License Agreement: Review and accept the license agreement.
- Setup Type: Select “Typical installation” for a standard setup.
- User Interface Style: Choose between the Commander interface (similar to Total Commander) or the Explorer interface (similar to Windows Explorer).
- Complete the Installation: Click “Install” and wait for the installation to finish. You may need to restart your computer or Windows File Explorer.
Step 3: Connecting to Your Router Using WinSCP
- Open WinSCP: Launch WinSCP from your Start menu or desktop shortcut.
- Create a New Session:
- File Protocol: Select
SCP
orSFTP
. - Hostname: Enter the IP address of your router (e.g.,
192.168.1.1
). - Port Number: Use
22
for SSH. - Username: Enter
root
or the appropriate username for your router. - Password: Enter your router’s password.
- File Protocol: Select
- Login: Click “Login” to connect to your router. You may need to accept the host key if prompted.
Step 4: Creating a File in a Given Directory
- Navigate to the Directory: Use the WinSCP interface to navigate to the directory where you want to create the file.
- Open Terminal: Click on the “Commands” menu and select “Open Terminal”.
- Create the File: In the terminal, use the
touch
command to create a new file. For example:
touch /etc/check_radio_channel.sh
- Copy Script: Open the newly created file by write click and choose edit. Copy and paste the script in it and save.
Step 5: Making the Script Executable
- Open Terminal in WinSCP: If not already open, use the “Commands” menu to open the terminal.
- Change Permissions: Use the
chmod
command to make the script executable:
chmod +x /root/check_radio_channel.sh
Step 6: Setting Up the Cron Job Using LuCI Web Interface
- Access LuCI: Open your web browser and navigate to your router’s LuCI web interface (usually
http://192.168.1.1
). - Login: Enter your username and password to log in.
- Navigate to System > Scheduled Tasks: This is where you can manage cron jobs.
- Add a Cron Job: Enter the cron job details to run your script at the desired intervals. For example, to run the script every minute, add:
* * * * * /etc/check_radio_channel.sh >> /tmp/check_radio_channel.log 2>&1
- Save: Click “Save” to save the cron job.
- Navigate to System > Startup: Look for
cron
Initscript and tap on Restart.
Step 7: Checking logs
- Script is saving logs to
/tmp/check_radio_channel.log
file - Navigate to
/tmp
direcotry using Winscp and opencheck_radio_channel.log
file.