FPGA利用IP核计算反正切的方法

来源:互联网 发布:五毒风湿骨刺丹,淘宝网 编辑:程序博客网 时间:2024/05/16 09:44

(毕竟新手,请各位不吝赐教)

因为FPGA计算反正切可以用IP核进行,但是IP核需要输入二进制小数,一般我们得到的数都是十进制数,所以要先进行一些处理:


1:把十进制数变成浮点数


2:进行浮点数除法,除以相对应的位数最大值以便得到小数,比如说8位的就除以255。


3:进行反正切运算


4:如果需要转换为角度需要把浮点数转换为定点数之后乘以255.


以下为程序:

module float_3(CLK,data_in_1,data_in_2,data_out_1,data_out_2,data_dividend_1,data_dividend_2,data_divisor,cnt,CE_1,CE_2,nRESET,phase_out    ); input CLK,nRESET;input [31:0]data_in_1,data_in_2;output [31:0]data_out_1,data_out_2,data_dividend_1,data_dividend_2,data_divisor,phase_out;output reg [7:0]cnt;output reg CE_1,CE_2;always@(posedge CLK or negedge nRESET)beginif(!nRESET)begincnt <= 8'd0;CE_1 <= 8'd0;CE_2 <= 8'd0;endelsebeginif(cnt == 8'd15)beginCE_1 <= 8'd1;cnt <= cnt + 8'd1;                 // 计算浮点数时的延时endelse if(cnt == 8'd50)beginCE_2 <= 8'd1;cnt <= cnt + 8'd1;                 // 计算反正切时的延时endelsecnt <= cnt + 8'd1;endendjkjlk A1(.clk(CLK),.a(data_in_1),.result(data_dividend_1)    //第一个数转化为浮点数的IP核);  jkjlk A2(.clk(CLK),.a(32'd255),.result(data_divisor)    //255转换为浮点数的IP核);jkjlk A3(.clk(CLK),.a(data_in_2),.result(data_dividend_2)// 第二个数转换为浮点数的IP核);divided A4(        .clk(CLK),         .ce(CE_1),         .a(data_dividend_1),         .b(data_divisor),         .result(data_out_1)// 第一个数转换为小数0-1之间);divided A5(       .clk(CLK),        .ce(CE_1),        .a(data_dividend_2),        .b(data_divisor),        .result(data_out_2)// 第二个数转换为0-1之间的小数 );angle A6(.clk(CLK), .ce(CE_2),.x_in(data_out_1), .y_in(data_out_2), .phase_out(phase_out)       //反正切运算);endmodule


仿真结果如图所示:


以上:输入两个数都为48. 输出的结果为45°


好吧... 还是有问题

修补1:2017年5月17日

因为反正切核的输入要求是定点数,所以上述使用的整形就可以,小数就有些许问题,所以要把结果转化成定点数再进行反正切运算。

代码如下:

`timescale 1ns / 1ps//////////////////////////////////////////////////////////////////////////////////// Company: // Engineer: // // Create Date:    10:39:15 05/15/2017 // Design Name: // Module Name:    float_1 // Project Name: // Target Devices: // Tool versions: // Description: //// Dependencies: //// Revision: // Revision 0.01 - File Created// Additional Comments: ////////////////////////////////////////////////////////////////////////////////////module float_3(CLK,data_in_1,data_in_2,data_out_1,data_out_2,data_dividend_1,data_dividend_2,angle_in_1,angle_in_2,data_divisor,cnt,CE_1,CE_2,CE_3,nRESET,phase_out    ); input CLK,nRESET;input [31:0]data_in_1,data_in_2;output [31:0]data_out_1,data_out_2,data_dividend_1,data_dividend_2,data_divisor,phase_out,angle_in_1,angle_in_2;output reg [7:0]cnt;output reg CE_1,CE_2,CE_3;always@(posedge CLK or negedge nRESET)beginif(!nRESET)begincnt <= 8'd0;CE_1 <= 8'd0;CE_2 <= 8'd0;CE_3 <= 8'd0;endelsebeginif(cnt == 8'd15)beginCE_1 <= 8'd1;cnt <= cnt + 8'd1;endelse if(cnt == 8'd55)beginCE_2 <= 8'd1;cnt <= cnt + 8'd1;endelse if(cnt == 8'd45)beginCE_3 <= 8'd1;cnt <= cnt + 8'd1;endelsecnt <= cnt + 8'd1;endendjkjlk A1(.clk(CLK),.a(data_in_1),.result(data_dividend_1));  jkjlk A2(.clk(CLK),.a(32'd255),.result(data_divisor));jkjlk A3(.clk(CLK),.a(data_in_2),.result(data_dividend_2));divided A4(       .clk(CLK),        .ce(CE_1),        .a(data_dividend_1),        .b(data_divisor),        .result(data_out_1));divided A5(       .clk(CLK),        .ce(CE_1),        .a(data_dividend_2),        .b(data_divisor),        .result(data_out_2));fixed B1(.clk(CLK),.a(data_out_1),.result(angle_in_1),.ce(CE_3));fixed B2(.clk(CLK),.a(data_out_2),.result(angle_in_2),.ce(CE_3));angle A6(.clk(CLK), .ce(CE_2),.x_in(angle_in_1), .y_in(angle_in_2), .phase_out(phase_out));endmodule


仿真结果:


原创粉丝点击