Octave 是 GNU Radio 的最流行的分析工具,因此 GNU Radio 軟件包也包含它自身的一組腳本用於讀取和語法分析輸出。本文介紹如何使用 Octave 分析 GNU Radio 產生的數據, 並解決"error: 'read_complex_binary' undefined"這類錯誤信息!
1. 安裝Octave
在 Ubuntu 下使用如下命令安裝 Octave
$ sudo apt-get install octave
為了可以使用 GNURadio 的 Octave 腳本,你必須將 gnuradio 的路徑添加了 Octave 的路徑變量中。可以通過配置~/.octaverc文件完成。將gnuradio的路徑命令添加到 .octaverc 文件中.具體方法為:
1) 打開新終端(Ctrl + Alt + t)
$ gedit .octaverc
2) 在.octaverc文件中輸入如下, 根據gnuradio所在路徑與版本自行修改, 然后保存退出即可.
addpath("/home/hao/software/gnuradio-3.7.5.1/gr-utils/octave")
如果不執行上面的步驟, 在調用函數 read_complex_binary() 則會產生error: error: 'read_complex_binary' undefined near line 1 column 3
從語法上分析 GNU Radio 的數據輸出,最便捷的方法便是使用 GNU Radio 提供的腳本。如上安裝指導所示,確保把 GNU Radio 的腳本的路徑已經添加到 Octave 的路徑中。這便可幫助讀取那些被使用 gr.file_sink (大小、文件名) 頃倒到磁盤的數據。
下 面的方法函數是基於參數 size 的用在 gr.file_sink() 內的,它把文件名作為第一個參數、第二個參數是可選項,它表示了從文件中要讀取的數量。
1 read_complex_binary(): gr.sizeof_gr_complex 2 read_float_binary(): gr.sizeof_float 3 read_int_binary(): gr.sizeof_int 4 read_short_binary(): gr.sizeof_short 5 read_char_binary(): gr.sizeof_char
比如:在 Python 腳本中,使用 gr.file_sink(gr.sizeof_gr_complex, "capture.dat") 獲取了 64 位的復合數據如下:
c = read_complex_binary('capture.dat');
從 USRP 直接能獲取的數據是以 32 位復合數據形式存儲的,而不是 64 位復合型 (gr.sizeof_gr_complex)。為了能讀取此數據,首先,使用 read_short_binary() 然后將其分離進入 - a two dimensional vector 如下:
1 d = read_short_binary(data); 2 c = split_vect(d, 2);
2. 安裝gnuplot
使用 Octave 來繪制數據,最簡便的方法是使用 gnuplot。在 Ubuntu 上鍵入如下命令:
$ sudo apt-get install gnuplot gnuplot-doc
在時間軸上的 I 和 Q,可如下分別地繪制各個元素:
plot([real(c), imag(c)])
如下可生成一個 I/Q 曲線(x 表示 I, y 表示 Q):
plot(c)
3. 舉例說明
例子背景: LTE下行數據鏈路中, 每個幀1ms, 每個幀包含10個子幀, 每個子幀包含14個 OFDM 符號, 在3M帶寬條件下, 其時頻資源格為14 * 180的 std::vector <std::vector<gr_complex> > 類型. 在發端2天線, 收端2天線的LTE MOMI-OFDM無線通信系統中, 進行信道估計和插值后得到插值后的信道估計值, 或稱信道特征矩陣. 其類型也為 std::vector <std::vector<gr_complex> > 使用如下C++程序, 將信道特征矩陣存入本地文件, 2×2 MIMO 可以得到4個信道特征矩陣(s00, s01, s10, s11):
1 for (int i = 0; i < d_channel_estimate_s00.size(); ++i) 2 { 3 dump_array("s00.dat", &d_channel_estimate_s00[i][0], d_channel_estimate_s00[i].size()); 4 } 5 for (int i = 0; i < d_channel_estimate_s01.size(); ++i) 6 { 7 dump_array("s01.dat", &d_channel_estimate_s01[i][0], d_channel_estimate_s01[i].size()); 8 } 9 for (int i = 0; i < d_channel_estimate_s10.size(); ++i) 10 { 11 dump_array("s10.dat", &d_channel_estimate_s10[i][0], d_channel_estimate_s10[i].size()); 12 } 13 for (int i = 0; i < d_channel_estimate_s11.size(); ++i) 14 { 15 dump_array("s11.dat", &d_channel_estimate_s11[i][0], d_channel_estimate_s11[i].size()); 16 }
其中dump_array()函數的定義如下:
1 template <typename T> 2 static void dump_array(const char* filename, T* arr, int len) 3 { 4 std::string sname = filename; 5 FILE* f = fopen(sname.c_str(), "ab+");//"ab+"是可讀可寫追加方式的打開一個二進制文件 6 fwrite(arr, sizeof(T), len, f);//fwrite(buffer, size, count, fp);//從buffer地址讀size*count個字節寫到f文件中. 7 fclose(f); 8 }
如果數據為 std::vector<gr_complex> 類型, 可以這樣調用dump_array()函數
1 dump_array("fd_user_data_subf_1tx1rx_before.dat", &fd_user_data[0], fd_user_data.size());
使用 Octave 對這4個信道特征矩陣(s00, s01, s10, s11)進行分析, 代碼如下(文件名為test.m):
1 a = read_complex_binary('s00.dat', 10000); 2 plot(abs(a), 'b+'); 3 title("00"); 4 figure; 5 6 b = read_complex_binary('s01.dat', 10000); 7 plot(abs(b), 'ro'); 8 title("01"); 9 figure; 10 11 c = read_complex_binary('s10.dat', 10000); 12 plot(abs(c), 'g-'); 13 title("10"); 14 figure; 15 16 d = read_complex_binary('s11.dat', 10000); 17 plot(abs(d), 'bo'); 18 title("11");
運行程序:
$ octave octave:1> test
注意: 如果沒有把 gnuradio 的腳本的路徑已經添加到 Octave 的路徑中, 將會有如下提示錯誤
error: 'read_complex_binary' undefined near line 1 column 3
4. 使用Octave畫星座圖:
以QPSK調制為例, 用前面所述的dump_array()函數, 將接收端均衡前后的數據存到文件里, 然后使用Octave處理數據, 程序如下:(文件名: plot_scatter.m)
1 a = read_complex_binary('before.dat', 10000); 2 a1 = real(a); 3 a2 = imag(a); 4 scatter(a1, a2); 5 title("Before Equalization"); 6 figure; 7 8 b = read_complex_binary('after.dat', 10000); 9 b1 = real(b); 10 b2 = imag(b); 11 scatter(b1, b2); 12 title("After Equalization");
運行結果如下, 左圖為均衡前, 又圖為均衡后
用Python作為Octave和Matlab之外的另一個選擇
很有可能你已經安裝了一些Python的科學分析包,例如SciPy和NumPy (特別是Matplotlib)。利用這些工具,你可以使用Python來繪制或者分析數據。
本文地址:
http://www.cnblogs.com/moon1992/p/5717706.html
參考連接: