GNU Radio 中OFDM Tunnel 详解以及相关OFDM模块介绍

测试USRP发送接收的时候完整的程序在benchmark_tx.py 和 benchmark_rx.py里面。其中调用了很多外面的分支如transmit_path.py.exe和 ofdm.py等。

在USRP发送端,执行的是benchmark_tx.py程序,在该程序里定义了发送数据包的相关参数,包括USRP发送频率、增益、天线、时钟源等,通过调用send_pkt函数来发送数据包。在程序中调用transmit_path和uhd_transmitter函数,它们分别定义在transmit_path.py和uhd_interface.py模块。调用ofdm_mod函数进行OFDM调制,然后将生成的基带调制信号传送给uhd_transmitter函数,即USRP射频模块,每成功发送一个数据包,屏幕上会输出一个‘.’。

在USRP接收端,执行的是benchmark_rx.py程序,在该程序中定义了接收数据包的相关参数,包括USRP接收频率、增益、天线、时钟源等,定义了rx_callback函数,当接收到数据包就会触发该函数,每调用一次rx_callback函数,变量n_rcvd加1;再通过CRC检验收到的数据包,如果无误则变量n_right加1。在程序中调用receive_path和uhd_receiver函数,它们分别定义在receive_path.py和uhd_interface.py模块。调用ofdm_demod函数进行相应的OFDM解调,数据包接收成功后,会显示接收端接收情况,在屏幕上输出当前数据包的编号(pktno)、已接收到的数据包的数量(n_rcvd)和其中正确的数据包的数量(n_right)。

 

 

 

 

(在gnuradio3.4中确实有文中的例子,而且也在相应的目录下,在gnuradio3.7.1中,基于GMSK的是在/usr/local/share/gnuradio/examples/digital/narrowband目录下,基于OFDM的是在/usr/local/share/gnuradio/examples/digital/ofdm目录下,本文讲的应该是在3.4下的,但看了3.7的感觉大同小异)

OFDM Tunnel是GNU Radio中很经典的例子。Tunnel有两个,一个是基于GMSK 调 制 的 (gnuradio-examples\python\digital) , 另 一 个 基 于 OFDM 调 制 的 (gnuradio-examples\python\ofdm)。它们都由物理层和MAC层构成,提供一个虚 拟的Ethernet接口,使得基于IP的各种应用程序都可以加载在这个tunnel 上面, 它的主要作用是负责数据的传输。我们主要研究后者。因为MIMO/OFDM 在当前最 新一代的通信系统中,几乎是必选的两个关键技术,因此很多做物理层研发的GNU Radio用户都会从这两个例子开始着手。

 系统框图和MAC帧的构成

 下图是Tunnel的系统框图。Tunnel的物理层由发射机,接收机和一个载波侦 听(sensing probe)三部分构成,完成由信息比特到基带波形之间的转换,以 及通过能量检测判断当前信道是否空闲。MAC 层是一个基于CSMA的简单的MAC。 MAC 层与PHY 层之间传递的是一个在IP包的基础上加了一些包头和包尾的数据 包。

了解了Tunnel的系统框图,我们来看一下MAC帧的结构和数据打包过程。图2 说明了一个IP数据包是如何打包成MAC数据包的。

 首先,IP包被加上了4字节的校验比特,算法是CRC32。然后数据部分,加上 CRC比特和尾比特(X55),都被白化处理,使得数据具有随机均匀分布的特性。 最后,加上一个4字节的包头。包头包含两个信息:白化参数4 比特和数据包长 度12比特。包头采用了重复发送的方法,以增加可靠性。到此,一个完整的MAC 数据包就包装完成了。

OFDM Tunnel 发射部分解读

下面以ofdm tunnel为例来解读一下物理层。Ofdm tunnel的代码除了在 gnuradio-examples\python\ofdm 目 录 下 以 外 , 还 有 一 些 在 gnuradiocore\src\python\gnuradio\blks2impl目录下。

先来看发射机,如图3所示。在transmit_path.py中,语句 self.connect(self.ofdm_tx,self.amp,self)

 说明其中包含两个模块,ofdm_tx是一个ofdm_mod类,amp是一个乘法器。 进入ofdm_mod类看一下,其代码在文件ofdm.py中。Ofdm_mod中,数据包首

 先经过一个send_pkt函数,完成MAC包的打包过程。 send_pkt(self,payload='',eof=False)

 然后MAC包被放进一个队列 self._pkt_input.msgq().insert_tail(msg)

 后面的ofdm_mapper_bcv模块从队列中取出数据包,根据OFDM调制的参数映 射成一个个OFDM symbol,再送到后续模块,添加preamble,IFFT变换,添加cyclic prefix,最后调整一下幅度,发送出去。这里想特别提一下的是,在ofdm_mapper 之后是流图的形式,在这之前是通过一个message queue与MAC层联系在一起。这 种连接方式使得“异步的”MAC层数据(而且数据包长不定),跟与系统时钟“同 步的”物理层连接在一起。这种连接方式是一个很好的例子,值得参考。

 OFDM Tunnel 接收部分解读

 接收机部分如图4所示。receive_path.py包含了ofdm_demod和probe两个模 块。Ofdm_demod显然就是ofdm接收机部分。而probe是一个信号检测模块,当usrp 收到的信号幅度大于门限时,就认为无线信道已经被其他用户占用。Ofdm_demod类的代码在文件ofdm.py中,主要分成同步模块(ofdm_receiver),解调模块 (ofdm_frame_sink),和MAC帧拆包部分。与发射部分类似,物理层与MAC层也是 通过一个队列self._rcvd_pktq连接在一起的。Ofdm_receiver部分比较复杂,是 用python写的,完成了帧同步,频偏估计,频偏纠正,FFT的功能。ofdm_frame_sink是一个C写成的模块,完成了从调制符号到比特的解映射过程。

下面就详细介绍一下接收解调框图中各个模块的具体作用。

 1)OFDM Receiver 部分。Filter(gr_fft_filter_ccc.cc)模块完成对 USRP 接收信号的匹配滤波功能;sync(gr_ofdm_sync_pn.py)模块的主要功能是完成 接收符号的窗口匹配,匹配成功时发送匹配成功标志给 sampler 模块;Nco (gr_frequency_modulator_fc.cc)模块完成细频偏纠正功能,相当于锁相环 PLL;Sig_mix(gr_multiply_cc.cc)模块对接收到的 OFDM 符号进行处理(将输 入符号相乘后输出),然后送给 sampler 模块;sampler(gr_ofdm_sampler.cc)

模块根据 sync 模块的匹配标志信号寻找 preamble,将 preamble 和 data 分离, 并给出二者的边界标志,然后把每个帧前面的循环前缀(Cycle Prefix)去除, 最后将 OFDM 符号送给 fft 模块,同时发送帧时序信号(Frame timing signal) 给 Frame acquisition 模块;fft(gr_fft_vcc.cc)模块对接收到的数据进行 fft 变换后输出给 Frame acquisition 模块(当查看 gr_fft_vcc.cc 时,你会发 现 该 模 块 并 没 有 做 实 际 的 fft 变 换 , 而 真 正 的 fft 和 ifft 变 换 在 gr_fft_vcc_fftw.cc 中进行);Frame acquisition(gr_ofdm_frame_acquisition)模块接收来自 FFT 的星座映射点向量,使用已知的 pn 码和接收到的 pn 码序列进 行比较得到信道增益,然后使用的到的增益修正其后的数据帧,进行相关和均衡。

 2)ofdm_frame_sink(解调)模块。该模块接收 OFDM 符号,把他们接映射 成 0、1 比特流数据,再将这些比特流打包发送到接收消息序列,完成从调制的 OFDM 信号到实际发送比特数据的解映射过程。

 3)MAC 帧拆包部分。主要功能是对解映射后的数据(还是帧结构的)进行帧 拆包,最终获得实际的有用数据信息。

 开发和调试方法

 整个ofdm tunnel 的物理层还是比较简单的。它模仿了802.11 的物理层, 在不定长的burst 前面添加一个定长的preamble,依靠这个preamble 完成时间 同步和频率同步。但它没有信道编码,因此抗噪声性能较差。

 gnuradio-examples\python\ofdm 目录下,除了tunnel 调用的函数外,还

 有许多其他的函数。这些函数都是程序的开发过程中需要用到的,它们教会了我 们如何一步步的进行程序开发。特别是对于利用GNU Radio 做物理层研发的人来 说,是很好的参考。下面简单说明一下。

 ofdm_mod_demod_test.py——用于物理层收发模块的仿真测试。

 benchmark_ofdm.py——加上MAC 层以后,做收发的仿真测试。

 benchmark_ofdm_tx.py,benchmark_ofdm_rx.py——加上USRP 之后,做单 向收发的测试。分别测试了连续的数据包传输,和不连续的突发数据包传输。

 当单向传输没有问题之后,就可以实验双向的传输了:tunnel.py。

 另外,还有一些matlab程序,帮助调试程序。当我们把log标志设为True时, 就会产生很多.dat文件。这些文件把各个block的输出都记录下来:同步之前, 频率同步之后,FFT之后,解映射之后等等。然后用Matlab程序一一检查,就可 以发现究竟哪一步出了问题。

 总结这个例子的开发方法,要创建一个自定义的无线连接程序,

 第一步:用Matlab写一个物理层收发程序,设计各个功能模块,确定参数等。

 第二步:用GNU Radio写一个不包括USRP 的收发程序,与Matlab程序一致, 方便把GNU Radio中的数据导入Matlab 中调试。

 第三步:当物理层没有问题之后,再添加MAC层。

 第四步:加入USRP。先调试单向通信,再调试双向的。


 

GNURadio默认提供的OFDM调制解调模块见下面的列表。

  1. OFDM Carrier Allocator / OFDM载波分配器
    • 由复数值创建频域的OFDM符号,添加导频。
    • 该块将复杂的标量调制符号流转换为向量,该向量是OFDM发射机中的IFFT的输入。 它还支持将导频符号放置在载波上的可能性。
    • 可以自由分配载波,如果未分配载波,则将其设置为零。 这允许进行OFDMA样式的载波分配。
  2. OFDM Channel Estimation /  OFDM信道估计
    • Estimate channel and coarse frequency offset for OFDM from preambles
    • 输入:OFDM符号(在频域中)。 期望前一个(或两个)符号是同步符号,其用于估计粗略频率偏移和初始均衡器抽头(这些符号从流中移除)。 以下n_data_symbols通过未修改传递(实际均衡必须在其他地方完成)。 输出:数据符号,没有同步符号。 通过的第一个数据符号有两个标签:'ofdm_sync_carr_offset'(整数),粗略频率偏移量作为载波数量,'ofdm_sync_eq_taps'(复矢量)。 附加到同步符号的任何标记都附加到第一个数据符号。 所有其他标记按预期传播。
  3. OFDM Cyclic Prefixer / OFDM循环前缀
    • Adds a cyclic prefix and performs pulse shaping on OFDM symbols.
    • 输入:OFDM符号(在时域中,即在IFFT之后)。 可选地,可以处理整个帧。 在这种情况下,必须指定len_tag_key,其保存标记的密钥,该密钥表示帧中有多少OFDM符号。 输出:(标量)复数符号流,包括循环前缀和脉冲整形。 注意:如果处理完整帧,并且rolloff_len大于零,则最后的OFDM符号后面跟着脉冲整形的延迟线。
    • 脉冲形状是时域中的升余弦.
  4. OFDM Demod / OFDM解调
  5. OFDM Frame Acquisition / OFDM帧采集
    • take a vector of complex constellation points in from an FFT and performs a correlation and equalization.
  6. OFDM Frame Equalizer / OFDM帧均衡器
    • OFDM frame equalizer.
    • 在标记的OFDM帧上执行一维或二维的均衡。
    • 这样做有两件事:首先,它消除了粗略的载波偏移。 如果在具有键'ofdm_sync_carr_offset'的第一项上找到标签,则将其解释为载波数量的粗略频率偏移。 接下来,它在标记的OFDM帧上执行一维或二维的均衡。 实际的均衡是由块外的ofdm_frame_equalizer对象完成的。
  7. OFDM Insert Preamble / OFDM插入前同步码
    • insert "pre-modulated" preamble symbols before each payload.
  8. OFDM Mod / OFDM调制
  9. OFDM Receiver / OFDM接收机
  10. OFDM Sampler / OFDM 采样器
  11. OFDM Serializer / OFDM 序列化
    • Serializes complex modulations symbols from OFDM sub-carriers.
  12. OFDM Sync PN /
  13. Schmidl & Cox OFDM synch.
  14. OFDM Transmitter / OFDM 发射机

 

下图是ofdm_loopback.grc,实现了一个简单的OFDM回环。

更详细的示例可以参见/usr/local/share/gnuradio/examples/digital/ofdm/里的其它框图。

---------------------  
作者:天一涯  
来源:CSDN  
原文:https://blog.csdn.net/yuan1164345228/article/details/17584045  
版权声明:本文为博主原创文章,转载请附上博文链接!

  • 4
    点赞
  • 33
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
OFDM(正交频分复用)是一种用于无线通信系统的调制技术,它将高速数据流分成多个低速子载波进行传输,以提高系统的传输效率和抗干扰能力。GNURadio是一个开源的软件无线电开发平台,可以用于设计和实现各种无线通信系统。 在GNURadio实现OFDM系统,可以按照以下步骤进行: 1. 随机生成数据:首先,使用随机数生成器生成需要传输的数据。 2. 数据打包:将生成的数据按照一定的规则进行打包,例如每96个数据打包成一个packet。 3. 添加CRC校验:为了保证数据的完整性,可以使用CRC(循环冗余校验)算法为每个packet添加校验码。 4. 数据重组:将打包后的数据按照一定的规则进行重组,例如将8bit的数据拆分成2bit的数据,以便进行QPSK调制。 5. 星座映射:对重组后的数据进行星座映射,即将数据映射到复平面上的不同点,以便进行调制。 6. OFDM载波映射:将映射后的数据进行OFDM调制,即将数据分配到不同的子载波上。 7. IFFT变换:对每个子载波进行IFFT(逆快速傅里叶变换),将频域信号转换为时域信号。 8. 添加循环前缀:为了抵消多径传播引起的符号间干扰,可以在每个OFDM符号前添加循环前缀。 9. OFDM信号生成:将经过循环前缀处理的时域信号组合起来,生成最终的OFDM信号。 以上是一个标准的OFDM发射端的流程,其包括数据生成、打包、校验、重组、映射、调制、IFFT变换和循环前缀处理等步骤。通过GNURadio可以方便地实现这些步骤,并生成OFDM信号。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值