一、QN格式(Q数据格式)
XQN格式数据,是一个1bit符号位+X bits整数位+N bits小数位的补码数据。可表达的数据的范围是,
比如Q15,指的是X=0,N=15的Q格式数据,加上符号位合计16位数据(等同于Q1.15)。
又比如1Q15,指的是X=1,N=15的Q格式数据,加上符号位合计17位数据(等同于Q2.15)。
Q格式数据也可以用Fix格式数据表示。
对于有符号数,表示为Fix(1+X+N)_N,X表示整数位数,N表示小数位数。
对于无符号数,表示为uFix(X+N)_N,X表示整数位数,N表示小数位数。
举例:
1Q7格式数据(Q2.7)
2Q7格式数据(Q3.7)
二、CORDIC算法中的Q格式
2.1笛卡尔坐标数据的表示
笛卡尔坐标数据使用定点数补码表示,无视总的数据位宽,整数位固定2位,其余为小数位。使用Q数据格式表达为1QN,小数位N=总数据位宽-2。
一般情况下,输入数据X_IN和Y_IN范围为[-1,1]。超范围可能会导致未定义的结果。
最大值和最小值表示如下:
计算平方根时,若设置为无符号小数,X_IN范围时[0,2],Q数据格式为1bit整数位,其余是小数位(没有符号位)
若设置为无符号整数X_IN范围时,Q格式数据位宽全部为整数位。
2.2相位/弧度数据的表示
PHASE_IN和PHASE_OUT使用二进制补码形式的定点数表示,整数位一共3位,其余为小数位。
相位数据格式可使用两种表达形式:Radians和scaled Radians。
选用Radians表达形式时,PHASE_IN范围为[-π,π]。最大值和最小值可以表达如下:
选用scaled Radians表达形式时,PHASE_IN范围为[-1,1]。最大值和最小值可以表达如下:
2.3举例
举例:旋转模式下,从坐标(Xin,Yin)旋转角度Pin,目标坐标的值为(Xout,Yout)。Q 格式数据示例如下:
上图表示的是,从坐标(0.707,0.25)顺时针旋转90°,旋转到坐标(0.25,-0.707)。
举例:向量模式下,坐标(Xin,Yin)旋转到x轴上,得到的横坐标和旋转的角度值。Q 格式数据表示如下:
上图表示的是,从坐标(0.707,0.25)旋转到横坐标(0.75,0),一共旋转的弧度是0.336。
三、映射不同数据格式
假设输入数据与输出数据位宽不一致时,需要进行映射处理。同一个二进制数据,按照不同的XQN格式,其表达的十进制数据是不同的。
如果输出数据宽度比输入数据宽度小,CORDIC算法输出的结果减少了小数部分bits数。当数据输出比输入数据宽度大,那么增加小数部分的bits数。
平方根数据的映射。
无符号数X_IN:00001000
UFix8_7:
UFix8_1:
UFix8_0:
平方根X_OUT输出:00100000,在不同的Q格式下,X_OUT代表的数值:
UFix8_7:
UFix8_1:
UFix8_0:
CORDIC计算平方根的X_IN的取值范围是[0,2)。根据上表,我们发现,如果直接用Ufix8_1和Ufix8_1格式计算X_OUT,计算出来的数值明显错误。那么该如何处理呢?
我们先计输入数据范围在[0,2)的数据为X,输入数据范围在[2,∞)为xalt,输出出数据为Y。
我们先计输入数据X,输出出数据为Y,。范围在[0,2)的输入数据X记为
,其平方根即为
;范围在[2,∞)输入数据X 记为
,其平方根记为
;
当输入数据取值为,数据格式为Ufix8_7,正常按照CORDIC算法处理得出平方根
结果即可。
当输入数据取值为,直接使用CORDIC算法处理得到的数据不正确,需要先对数据进行缩放处理。
缩放处理方式:右移A位,变换成Ufix8_7格式
(A=m-1)。(实际二进制数值不发生任何变化,仅从意义上更改了Q格式小数点位置而已)
根据上面两个公式,我们发现,将X按照不同的取值范围方式进行CORDIC处理,得到的Y值存在的倍数关系。即超过数值2的输入X_IN,经过CORDIC算法计算平方根时,需要乘上
。
再回到刚才的示例:
X_IN:00001000
UFix8_7:
UFix8_1:
UFix8_0:
X_OUT:00100000
UFix8_7:
UFix8_1: (整数位共7位,因此A=7-1=6)
UFix8_0: (整数位共7位,因此A=8-1=7)
这里我们需要知道的是,使用CORDIC算法计算[0,2)之间的数与[2,∞]之间的数,计算平方根时有上面描述的缩放处理的区别。
四、CORDIC IP核 IO用户界面的参数配置
1、功能选择
可选功能包括:
rotate :旋转模式。输入初始坐标和旋转角度,输出目标坐标值
Translate:向量模式。输入初始坐标,将其旋转到横坐标轴,输出旋转弧度和目标横坐标。
Sin and cos:输入角度(弧度),输出cos值和sin值
Sinh and cosh:输入双曲线角度(弧度),输出cosh值和sinh值
Arctan:输入初始坐标(x,y),旋转到横坐标轴,输出atan(y/x)
Arctanh:输入初始坐标,沿着双曲线旋转到横坐标轴,输出atanh(y/x)
Square root:输入一个数值,输出其平方根值
基本上涵盖了CORDIC算法所能计算的全部运算。
当然,也可以通过基本的加减乘除运算简介地实现下面的运算:
2、架构配置
并行架构:或者可以称为流水线架构,每个时钟可以输出新的数据(输入与其对应的输出相差N个时钟的延迟,N等于输出数据宽度)。
串行架构:每N个时钟输出一个新的数据。(N等于输出数据宽度)
3、流水线模式
NONE:CORDIC 实现时不使用流水线
Optimal:CORDIC算法实现时,使用流水线,但是尽可能不多使用查找表资源,相当于自动优化资源和时序。
Maximum:每个加减法运算都使用流水线。比较适合资源充裕时序困难的逻辑
4、数据格式
CORDIC算法提供了三种不同的格式表达输入数据X和Y。
有符号小数:该格式是默认的设置,X和Y按照有符号定点数的补码进行表述,并且整数位宽度为2bits。1位符号位,1位整数位,其余为小数位。
无符号小数:X和Y按照无符号定点数表达。1位整数位,其余为小数位。
无符号整数:X和Y按照无符号整数表达,仅用于计算平方根的时候。
5、相位格式
两种相位格式可供选择:
弧度:相位使用定点数补码表示,整数位为3bits,单位是rad,范围[-π,π]。比如01100000表示3.0rad
归一化弧度:使用定点数补码表示,整数位宽3bits,单位是π rad,范围[-1,1]。比如00100000表示1*πrad;又比如11110000表示-0.5*πrad。
6、输入数据宽度
X_IN/Y_IN/PHASE_IN的数据宽度
7、输出数据宽度
X_OUT/Y_OUT/PHASE_OUT的数据宽度
8、取整模式
提供了三种输出数据的取整模式
Truncate:截断模式,直接舍弃低位
Positive infinity:,正方向四舍五入,等效于matlab的floor(x+0.5)
Pos Neg infinity:正数正方向四舍五入,负数负方向四舍五入,等效于matlab的round(x)
Nearest Even:输出数据取整为最近的整数,0.5向下取整,1.5向上取证
9、迭代次数
设置为0时,迭代次数由IP核自动决定。也可以手动输入迭代次数。
10、精确度
配置CORDIC IP内部计算时的精确度,当设置为0时,IP核自动决定精确度取值。也可以手动输入精确度。
11、粗略旋转
控制CORDIC算法使用的象限,勾选时可以在所有象限中使用;不勾选时只能在第一象限使用。
12、补偿方式
讲解原理的时候,学习过使用CORDIC算法时,会带来模长的拉伸,此处可选择是否乘上补偿因子。
No scale compensation:不乘补偿因子
LUT based:基于查找表保存补偿因子
BRAM:基于BRAM保存补偿因子
Embedded Multiplier:使用DPS进行计算补偿
五、CORDIC IP核的仿真使用
5.1 使用CORDIC IP核计算cos值和sin值
IP核配置截图
按照手册要求、以Q3.13格式输入Q码数据,弧度值分别为
0,
π/6,
π/3,
π/2,
2π/3,
π,
-π/6,
-π/3,
-2π/3,
-π
仿真后结果如下:(注意输出的cos和sin数据为Q2.14格式)
输入角度 | 输入相位 | 输入相位 | 理论cos值 | 理论sin值 | CORDIC IP计算的cos值 | CORDIC IP计算的sin值 | ||
/ | / | / | / | / | 有符号Q2.14码 | 十进制转换,近似值 | 有符号Q2.14码 | 十进制转换,近似值 |
0 | 0 | 0.000000 | 1.000000 | 0.000000 | 16'b01_00_0000_0000_0000 | 0 | 16'b11_11_1111_1111_1111 | 0 |
30° | pi/6 | 0.523599 | 0.866025 | 0.500000 | 16'b00_11_0111_0110_1100 | 0.86597 | 16'b00_10_0000_0000_0000 | 0.5 |
60° | pi/3 | 1.047198 | 0.500000 | 0.866025 | 16'b00_10_0000_0000_0000 | 0.5 | 16'b00_11_0111_0110_1101 | 0.86603 |
90° | pi/2 | 1.570796 | 0.000000 | 1.000000 | 16'b11_11_1111_1111_1100 | 0 | 16'b01_00_0000_0000_0000 | 1 |
120° | pi*2/3 | 2.094395 | -0.500000 | 0.866025 | 16'b11_01_1111_1111_1111 | -0.5 | 16'b00_11_0111_0110_1100 | 0.86597 |
180° | pi | 3.141593 | -1.000000 | 0.000000 | 16'b11_00_0000_0000_0000 | -1 | 16'b00_00_0000_0000_0001 | 0 |
-30° | -pi/6 | -0.523599 | 0.866025 | -0.500000 | 16'b00_11_0111_0100_1110 | 0.86413 | 16'b11_10_0000_0000_0001 | -0.5 |
-60° | -pi/3 | -1.047198 | 0.500000 | -0.866025 | 16'b00_10_0000_0000_0001 | 0.5 | 16'b11_00_1000_1001_0011 | -0.86602 |
-120° | -pi*2/3 | -2.094395 | -0.500000 | -0.866025 | 16'b11_10_0000_0000_0001 | -0.5 | 16'b11_00_1000_1001_0010 | -0.86602 |
-180° | -pi | -3.141593 | -1.000000 | 0.000000 | 16'b10_11_1111_1111_1111 | -1 | 16'b11_11_1111_1111_1111 | 0 |
根据表格可以看出,经过CORDIC IP核计算出来的结果与理论结果非常相近。
5.2 使用CORDIC IP核计算平方根值
IP核配置截图
按照手册要求、输入无符号整数数据,分别为
1 |
4 |
16386 |
4096 |
16384 |
0 |
仿真后结果如下:
输入数值 | 理论的平方根 | CORDIC算法计算的平方根 | ||
十六进制 | 十进制 | / | 十六进制 | 十进制 |
1 | 1 | 1 | 1 | 1 |
4 | 4 | 2 | 2 | 2 |
4002 | 16386 | 128.0078123 | 80 | 128 |
1000 | 4096 | 64 | 40 | 64 |
4000 | 16384 | 128 | 80 | 128 |
0 | 0 | 0 | 0 |
根据表格可以看出,经过CORDIC IP核计算出来的结果与理论结果非常相近。