车载毫米波雷达的角分辨率是雷达的一项重要性能指标,为了正确的解算目标的角度(目标的方向角,俯仰角)信息,雷达往往在出厂之前需要将不同信号通道(TX===>RX)在面对相对零度角目标时,回波信号幅度与初始相位保持一致。
雷达幅相标定往往需要在暗室(室内墙壁贴满了吸波材料,防止反射干扰)的环境下进行,角反(模拟点目标)相对雷达为零角度,然后进行幅相标定,获得标定参数存储至雷达内非易失性存储器。
目录
幅相标定的定义
幅相标定的原因
幅相标定的过程
幅相标定的定义
标定与校准两个过程区别并不大,下面是两个过程的不同定义:
- 通过测量标准器的偏差来补偿仪器系统误差,从而改善仪器或系统准确度(精度)的操作。标定一般用于较高精度的仪器。
-
依据相关校准规范,通过实验确定计量器具示值的活动。通常采用与精度较高的标准器比对测量得到被计量器具相对标准器的误差,从而得到被计量器具示值的修正值。校准主要用于非强制检定的计量器具。
可以看出,校准过程是使用精度更高的仪器将计量值逼近准确值,而标定的含义是用实际的环境测量偏差,进行弥补系统误差,最常用的过程就是零点标定(Adjustment zero valid)。幅相标定是对数据处理端(对雷达接收到的各通道的回波数据进行校准处理)来校准毫米波雷达的各个通道,使其幅度相位在面对零度目标时具备一致性。经过标定之后,雷达内部会存储标定参数,在之后的雷达探测的信号处理流程之前,先将采样得到的回波数据根据通道号与对应的参数相乘,如下面的matlab代码所示。
load('amp_calib.mat');%获得幅度标定参数
load('phase_calib.mat'); %获得相位标定参数
sAmp=amp_calib(1:16);
sPhase=phase_calib(1:16);
commonCfg.numSamp = numPT;
commonCfg.numAnt = numANT;
commonCfg.numChirp = numChirp;
calib_Ap = (sAmp.*exp(1j * sPhase)).';%获得个通道标定参数
calib_Ap = repmat(reshape(repmat(calib_Ap, commonCfg.numSamp, 1), [commonCfg.numSamp, 1, commonCfg.numAnt]), 1, commonCfg.numChirp, 1);%形成与Radar Data Cube结构相同的标定参数
ADCBufCalib=ADCBuf.*calib_Ap;%数据相乘
幅相标定的原因
毫米波雷达一般都是MIMO的工作方式,具体到车载雷达,引起各通道之间的偏差原因,主要有以下两个方面:
- 不同的发送和接收天线本身就不可能在同一位置,再加上不同天线之间的耦合,雷达天线罩对不同位置上天线的不同影响,不同通道布线是的线长,线径,线距这些无法统一客观原因都会引起各通道之间的偏差。
- 芯片内部不同通道,不同芯片引起的工艺差,以及级联情况下的各芯片之间的工艺差,外围相关的阻容的偏差,这些不同使我们必须每个板卡都独立获取标定参数。
幅相标定的过程
幅相标定的过程如下:
- 获得单chirp的AD数据,本例中的数据为16通道(4发4收)的回波AD数据如下,每个通道512个点。
- 针对各通道数据进行512*1000个点的FFT(512个AD数据后补零,模拟一千次采样的数据),对结果进行abs运算获得各频点能量值(由于输入信号为实信号,所以结果是共轭对称的,取前一半结果即可)。
- 排除直流分量的影响,从abs结果的2000点之后的数组中获得16个通道的最大能量频点以及频点下标。
- 理论上这个时候16个通道最大能量的频点下标应该是一致的(反应目标的距离信息),如果不一样,可以以第一通道为标准,获得频点下标差(频率标定参数)从而进行频率标定,将原始数据使用频率标定参数进行校准之后,再次进行FFT和abs求个频点能量的操作,最终获得16个通道最大能量频点下标一致的能量数据。
- 用16个通道最大能量数据,以第一个通道为标准,将其余通道与第一通道的能量值做差,即可得幅度标定参数。
- 根据第四步骤获得的16通道统一的最大能量频点下标,获取对应的FFT数据,获得对应的相位角之后,以第一通道为标准,将其余通道与第一通道的相位值做差,即可得相位标定参数。
下面是对应的Matlab实现代码,din为512*16的回波信号AD采样数据,calibCfg为标定参数配置,定义如下:
- ptRange:采样点数。
- numAnt:通道数。
- ptTimes:采样次数。
输出的三个参数分别是:
- calibAmp:幅度标定参数。
- calibFreq:频率标定参数。
- calibPhase:相位标定参数。
function [calibAmp, calibFreq, calibPhase] = simpleCalib(din, calibCfg)
% size(din) = NUM_SAMP * NUM_ANT
ptRange= calibCfg.ptRange;
numAnt = calibCfg.numAnt;
ptTimes= calibCfg.ptTimes;
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% original time domain data
figure(fig); fig=fig+1;
for k=1:numAntplot(real(din(:, k))+1024*(k-1)); hold on;
end
hold off;
title('time domain data');
legend('1','2','3','4','5','6','7','8','9','10','11','12');
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
dfft = fft(din, ptTimes * ptRange, 1);
dabs = abs(dfft(1:ptTimes * ptRange/2,:));
figure(fig); fig=fig+1;
for k=1:numAntplot(dabs(:, k)); hold on;
end
hold off;
title('freq domain before calib');
legend('1','2','3','4','5','6','7','8','9','10','11','12');
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% get calib freq & apply data
for k=1:numAnt[max_val(k), max_f(k)] = max(dabs(ptTimes*2+1:end,k));max_f(k)=max_f(k)+ptTimes*2;calibFreq(k) = (max_f(1) - max_f(k)) / ptTimes;
end
for k=1:numAntdin_calibFreq(:, k) = din(:, k) .* exp(1j * 2 * pi * calibFreq(k) * [0:ptRange-1]/ptRange).';
enddfft = fft(din_calibFreq, ptTimes * ptRange, 1);
dabs = abs(dfft);
figure(fig); fig=fig+1;
for k=1:numAntplot(dabs(:, k)); hold on;
end
hold off;
title('freq domain after calib freq');
legend('1','2','3','4','5','6','7','8','9','10','11','12');
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% get calib amp & apply data
dtmp = dabs(max_f(1),:);
for k=1:numAntcalibAmp(k) = dtmp(1) / dtmp(k);
endfor k=1:numAntdin_calibFreqAmp(:, k) = din_calibFreq(:, k) * calibAmp(k);
end
dfft = fft(din_calibFreqAmp, ptTimes * ptRange, 1);
dabs = abs(dfft);
figure(fig); fig=fig+1;
for k=1:numAntplot(dabs(:, k)); hold on;
end
hold off;
title('freq domain after calib amp');
legend('1','2','3','4','5','6','7','8','9','10','11','12');
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% get calib phase & apply data
dtmp = angle(dfft(max_f(1),:));
for k=1:numAntcalibPhase(k) = dtmp(1) - dtmp(k);
endfor k=1:numAntdin_calibFreqAmpPhase(:, k) = din_calibFreqAmp(:, k) * exp(1j * calibPhase(k));
end
dfft = fft(din_calibFreqAmpPhase, ptTimes * ptRange, 1);
dabs = abs(dfft);
figure(fig); fig=fig+1;
subplot(2,1,1);
for k=1:numAntplot(dabs(:, k)); hold on;
end
hold off;
title('freq domain after calib phase');
legend('1','2','3','4','5','6','7','8','9','10','11','12');subplot(2,1,2);
for k=1:numAntplot(angle(dfft(:,k))); hold on;
end
hold off;
title('freq domain after calib phase');
legend('1','2','3','4','5','6','7','8','9','10','11','12');
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% printFile(1, 'real', [calibCfg.savePath, 'calib_freq.txt'], 1, 2, 15, 2, 15, calibFreq);
% printFile(1, 'real', [calibCfg.savePath, 'calib_amp.txt'], 1, 2, 15, 2, 15, calibAmp);
% printFile(1, 'real', [calibCfg.savePath, 'calib_phase.txt'], 1, 2, 15, 2, 15, calibPhase);
amp_calib = calibAmp.';
freq_calib = calibFreq.';
phase_calib = calibPhase.';
save('amp_calib.mat', 'amp_calib');
save('freq_calib.mat', 'freq_calib');
save('phase_calib.mat', 'phase_calib');end
十六宿舍 原创作品,转载必须标注原文链接。
©2023 Yang Li. All rights reserved.
欢迎关注 『十六宿舍』,大家喜欢的话,给个👍,更多关于嵌入式相关技术的内容持续更新中。