
在电子领域里面,这个射频应该是最难的部分了,那ADI早就出了这种集成的收发器,还做了教育套件:ADALM-PLUTO 是一个用于学习 SDR / RF / 无线通信的 Active Learning Module,强调它既适合教学,也适合工程师拿来做原型验证。
PlutoSDR 能在 325 MHz–3.8 GHz 的任意频段,以 ≤20 MHz 的信道带宽, 完成 I/Q 数字调制信号的发射与接收。

核心

使用的是93
在后面可以看到在早期的版本,可以通过更改boot进行所谓的超频。

然后集成器件是真的器件少,在上面就看到做一个阻抗匹配
在视频里面我说没有寄存器,那是我不对,是我没有找到地方:

在这里完整的寄存器手册,100多页
https://www.analog.com/en/lp/001/integrated-rf-agile-transceiver-design-resources.html
然后插入硬件会模拟一个小U盘:

会有一个网页的界面

会自动打印一些信息
说说超频这个事情,其实ADI的官方社区也把这个加进来了。

早期的一些 PlutoSDR 设备使用AD9364芯片,该芯片与量产版本使用的AD9363芯片几乎完全相同。如果拥有基于 AD9364 的 PlutoSDR 设备,只需使用 U-Boot 的fw_printenv和fw_setenv命令即可快速获得该设备更大的调谐范围(70-6000 MHz)和更大的带宽(56MHz)。
AD9363(Pluto 默认):LO 频率 325–3800 MHz,带宽 20 MHz,2Rx2Tx
AD9364:70–6000 MHz,带宽 56 MHz,1Rx1Tx
AD9361:70–6000 MHz,带宽 56 MHz,2Rx2Tx
然后它说,通过 fw_setenv 写入某些 name/value 对,Pluto 可以用“兼容模式”去启用更大的调谐范围/带宽(尤其针对早期硬件或特定版本)。
本质是在启动时加载的 硬件描述/驱动配置 发生变化,让上层软件“认为”硬件是另一款 AD936x,从而放开一些参数边界。
文档在后面给了非常关键的一点(很多人忽略):
mode 1r1t:1Rx1Tx 时,最大数据率可以到 61.44 MSPS
mode 2r2t:2Rx2Tx 时,最大数据率会降到 30.72 MSPS

USB/FPGA/内部数据通路的吞吐是有限的。通道翻倍,要么采样率减半,要么就会丢数据。
所以“解锁更大带宽/频段”这件事,不能只看 RF 芯片能力,还要看:数据链路带宽(USB2.0 极限很快就到顶),FPGA 接口与内部缓冲,主机侧 iio/gr 的吞吐能力。
其实很简单,但是只能是原版和早期的Pluto,个人爱好者的不行。
ssh root@192.168.2.1
fw_setenv attr_name ad9363
fw_setenv compatible ad9363
reboot
这是回退命令
https://wiki.analog.com/university/tools/pluto/users/customizing

自带晶振有点差,可以换好的
TCXO(温度补偿晶体振荡器) 。换了之后,频率稳定性从25 ppm提高到了0.5 ppm,PlutoSDR可以做广泛的定位接收机了。
https://wiki.analog.com/university/tools/pluto/users/customizing

然后这个是结构,非常的简单,就两个芯片

在买的时候可以确定一下到底是什么型号
下面的B版本,引出来另外一路TX和RX

B
https://s-taka.org/plutosdr-tcxo-upgrade/
https://www.rtl-sdr.com/adalm-pluto-sdr-hack-tune-70-mhz-to-6-ghz-and-gqrx-install/
PlutoSDR 基于 AD9363,支持 325 MHz – 3.8 GHz 的 RF 频率范围,并且可达到 最高 61.44 MSPS 的采样率,能够进行 RF 模拟信号的生成与采集。 “325 MHz – 3.8 GHz” 决定你能覆盖哪些无线频段(UHF、ISM 2.4G、部分 3.5G 等)。
“61.44 MSPS” 决定在基带侧能开的“采样时钟上限”(进而影响可实现的信道带宽、滤波器抽取/插值倍率等)。
因为对于开发者来说,现在硬件硬件不用想了,都有了,但是要详细的理解整个RF链条,这样才可以做到会玩。
它指的是:
发射或接收信号的中心频率
不是采样率、不是带宽。
例如,可以把中心频率设在:
433 MHz(ISM)
915 MHz
2.4 GHz(Wi-Fi / ISM)
3.5 GHz(LTE / 5G 子 6G 的一部分)

但不能设在:
100 MHz(低于 325 MHz)
5.8 GHz(高于 3.8 GHz)
这是很多刚接触 SDR 时最容易混淆的地方:
参数 | 含义 |
|---|---|
325 MHz–3.8 GHz | 射频中心频率(LO) |
61.44 MSPS | 基带 I/Q 采样率 |
PlutoSDR 是 零中频(Direct Conversion)架构:
RF(几 GHz)
↓ 下变频
I/Q 基带(0 ~ B/2)
↓ ADC
数字 I/Q

所以:
GHz → 只是模拟射频世界
MSPS → 数字基带世界
这是最核心、也是最容易被误解的参数。
PlutoSDR 不是“直接采 GHz 波形”,而是:把 RF 信号下变频到 基带 I/Q,然后对 I 和 Q 分别采样
所以:

对于复数采样(I/Q):

所以:61.44 MSPS→ 实用信道带宽 ≈ 40–50 MHz;和 AD9363 官方指标 ≤20 MHz 是一致的(留余量给滤波、EVM、ACLR)
PlutoSDR 本质上是一个“≤20 MHz 信道宽度”的 SDR
错误理解 | 正确理解 |
|---|---|
“61.44 MSPS 可以采 3 GHz 信号” | 只能采 下变频后的基带 |
“采样率越高,RF 频率越高” | RF 频率由 LO 决定 |
“MSPS = RF 带宽” | MSPS ≈ 2×基带带宽 |
它是一个“完整收发器”
数字 I/Q
→ 插值滤波
→ DAC
→ 上变频(LO)
→ RF 输出
可以生成 QPSK / QAM / OFDM,当作信号源、调制源、干扰源
RF 输入
→ 下变频(LO)
→ ADC
→ 数字 I/Q
做频谱分析,解调信号,录 IQ 数据离线处理等
pyadi-iio快速控制 Pluto、收发 IQ、做通信/频谱分析。依赖:libiio + pyadi-iio
python -m pip install pyadi-iio numpy scipy matplotlib
Windows 还需要先装 ADI 的 libiio/驱动;Linux 通常更顺。
import adi
import numpy as np
import matplotlib.pyplot as plt
# 连接 Pluto(走 IP)
sdr = adi.Pluto("ip:192.168.2.1")
# ---------- 基本配置 ----------
sdr.rx_lo = int(2.4e9) # 接收中心频率(Hz)
sdr.sample_rate = int(2.5e6) # 基带采样率(Hz)
sdr.rx_rf_bandwidth = int(2.0e6) # 模拟/数字滤波带宽(Hz,通常略小于采样率)
sdr.rx_hardwaregain_chan0 = 20 # 接收增益(dB),也可用自动增益(AGC)
# 采样点数(一次 read 返回的长度)
sdr.rx_buffer_size = 2**15
# ---------- 采集 IQ ----------
iq = sdr.rx() # complex64 数组
iq = iq - np.mean(iq) # 去直流(零中频常见 DC 偏置)
# ---------- 快速频谱 ----------
fs = sdr.sample_rate
N = len(iq)
w = np.hanning(N)
X = np.fft.fftshift(np.fft.fft(iq * w))
freq = np.fft.fftshift(np.fft.fftfreq(N, d=1/fs))
psd = 20*np.log10(np.abs(X) / np.max(np.abs(X)) + 1e-12)
plt.figure()
plt.plot(freq/1e6, psd)
plt.xlabel("Frequency (MHz) relative to LO")
plt.ylabel("Magnitude (dB, normalized)")
plt.grid(True)
plt.title("Pluto RX Spectrum")
plt.show()
rx_lo:RF 中心频率(把要看的频段搬到 0Hz 附近)
sample_rate:基带 I/Q 采样率(决定最大可观察带宽)
rx_rf_bandwidth:前端滤波器带宽(过大容易进噪声/干扰,过小会削信号)
rx_hardwaregain_chan0:增益(过大饱和,过小噪声底上升)
上面 FFT 是“快看”。要测噪声底、比较滤波配置,用 Welch:
import adi
import numpy as np
import matplotlib.pyplot as plt
from scipy.signal import welch
sdr = adi.Pluto("ip:192.168.2.1")
sdr.rx_lo = int(915e6)
sdr.sample_rate = int(2.0e6)
sdr.rx_rf_bandwidth = int(1.5e6)
sdr.rx_hardwaregain_chan0 = 10
sdr.rx_buffer_size = 2**16
# 多帧叠加更稳
frames = []
for _ in range(10):
x = sdr.rx()
x = x - np.mean(x)
frames.append(x)
x = np.concatenate(frames)
fs = sdr.sample_rate
f, Pxx = welch(x, fs=fs, window="hann", nperseg=4096, noverlap=2048,
return_onesided=False, scaling="density")
f = np.fft.fftshift(f)
Pxx = np.fft.fftshift(Pxx)
# PSD 单位: (V^2/Hz) 的相对量。转 dBFS/Hz 需要幅度标定(后面我解释怎么标)
Pxx_db = 10*np.log10(Pxx + 1e-20)
plt.figure()
plt.plot(f/1e6, Pxx_db)
plt.xlabel("Frequency (MHz) relative to LO")
plt.ylabel("PSD (dB, relative/Hz)")
plt.grid(True)
plt.title("Welch PSD (relative)")
plt.show()

Pluto 的 rx() 返回的是归一化数字码流(不是伏特)。要做绝对 dBm/Hz,需要:已知输入功率(用信号源喂入)或用已知参考(校准转换系数)。
https://www.analog.com/media/en/technical-documentation/data-sheets/ad9363.pdf