Skip to content

Instantly share code, notes, and snippets.

@VeggieVampire
Created January 15, 2023 07:39
Show Gist options
  • Save VeggieVampire/c7954358e30c0be5800bace3e5097494 to your computer and use it in GitHub Desktop.
Save VeggieVampire/c7954358e30c0be5800bace3e5097494 to your computer and use it in GitHub Desktop.
import subprocess
import os
import time
import sys
os.system("pkill rtl_fm")
FM_frequency = "103.3e6" #desired FM station
#FM_frequency = sys.argv[1] + "e6"
modulation_mode = "wbfm" #wideband FM
sample_rate = "200000" #lowpass/resample
output_rate = "44100"
gain = "20"
while True:
#rtl_fm commands
new_frequency = input("Enter a new frequency (in MHz): ")
if FM_frequency != new_frequency + "e6":
os.system("pkill rtl_fm")
FM_frequency = new_frequency + "e6"
command = "rtl_fm -A lut -E deemp -f {} -M {} -s {} -r {} - | ffmpeg -nostats -loglevel quiet -r 200k -f s16le -ar {} -ac 1 -i - -f wav - | aplay -q -t wav > /dev/null 2>&1".format(FM_frequency, modulation_mode, sample_rate, output_rate, output_rate)
time.sleep(3)
#Some times it take a few secs to start the SDR. using this loop to help
print ("playing:" + FM_frequency, "MHz")
subprocess.Popen(command, shell=True,
stdout=subprocess.DEVNULL,
stderr=subprocess.STDOUT)
@VeggieVampire
Copy link
Author

The script you provided uses the subprocess.Popen() method to run the command, this method starts the command as a separate process and allows the script to continue running while the command is executing in the background.

It uses the os.system("pkill rtl_fm") command to kill any existing rtl_fm processes before starting a new one.

It uses the input() function to prompt the user to enter a new frequency and assigns the new frequency to the FM_frequency variable, then it compares the current frequency with the entered one, if they are different it kills the rtl_fm process and assigns the new frequency to the FM_frequency variable.

It uses the time.sleep(3) command to wait for 3 seconds before starting the SDR, this is to help with some timing issues that might occur when starting the SDR.

It also uses the subprocess.Popen.stdout=subprocess.DEVNULL, stderr=subprocess.STDOUT to redirect the output of the command to /dev/null so no output will be displayed on the screen.

this command is a pipeline of 3 different commands:

rtl_fm -A lut -E deemp -f {} -M {} -s {} -r {} - : This command is used to receive the FM signal using an RTL-SDR device.
-A lut : This option sets the automatic gain control algorithm to use a look-up table.
-E deemp : This option enables the de-emphasis filter that is used to remove the pre-emphasis that is applied to FM signals.
-f {} : This option sets the center frequency of the RTL-SDR device. The frequency value is passed as an argument to the command and it is stored in the variable FM_frequency.
-M {} : This option sets the modulation mode of the RTL-SDR device. The value is passed as an argument to the command and it is stored in the variable modulation_mode.
-s {} : This option sets the sample rate of the RTL-SDR device. The value is passed as an argument to the command and it is stored in the variable sample_rate.
-r {} : This option sets the output sample rate of the RTL-SDR device. The value is passed as an argument to the command and it is stored in the variable output_rate.

  • : This option tells the rtl_fm command to output the received data to the standard output (stdout) so it can be piped to the next command in the pipeline.
    ffmpeg -nostats -loglevel quiet -r 200k -f s16le -ar {} -ac 1 -i - -f wav - : This command is used to process the received data and convert it to a WAV file.
    -nostats -loglevel quiet : These options are used to prevent ffmpeg from displaying any output on the console.

-r 200k : This option sets the input data rate to 200 kbps

  • -f s16le : This option sets the input format to signed 16-bit little-endian samples
  • -ar {} : This option sets the audio sample rate of the output, the value is passed as an argument to the command and it is stored in the variable output_rate.
  • -ac 1 : This option sets the number of audio channels to 1 (mono)
  • -i - : This option tells ffmpeg to read the input from the standard input (stdin), which is where the data is coming from the previous command in the pipeline.
  • -f wav - : This option tells ffmpeg to output the processed data in WAV format to the standard output (stdout) so it can be piped to the next command in the pipeline.

aplay -q -t wav : This command is used to play the WAV file.
-q : This option tells aplay to operate in quiet mode, so it will not display any output on the console.
-t wav : This option tells aplay to assume the input file is in WAV format.

/dev/null 2>&1 : This redirect the output of the command to /dev/null so no output will be displayed on the screen.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment