打印

cordic算法verilog实现(复杂版)

[复制链接]
1878|2
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
xjsxjtu|  楼主 | 2012-10-17 20:43 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
 module cordic (clk,rst_n,ena,phase_in,sin_out,cos_out,eps);

parameter DATA_WIDTH=8;
parameter PIPELINE=8;
input     clk;
input     rst_n;
input     ena;
input  [DATA_WIDTH-1:0]         phase_in;

output [DATA_WIDTH-1:0]  sin_out;   
output [DATA_WIDTH-1:0]  cos_out;
output [DATA_WIDTH-1:0]  eps;

reg    [DATA_WIDTH-1:0]  sin_out;
reg    [DATA_WIDTH-1:0]  cos_out;
reg    [DATA_WIDTH-1:0]  eps;

reg    [DATA_WIDTH-1:0]  phase_in_reg;

reg        [DATA_WIDTH-1:0]     x0,y0,z0;
reg        [DATA_WIDTH-1:0]  x1,y1,z1;
reg        [DATA_WIDTH-1:0]  x2,y2,z2;
reg        [DATA_WIDTH-1:0]  x3,y3,z3;
reg        [DATA_WIDTH-1:0]  x4,y4,z4;
reg        [DATA_WIDTH-1:0]  x5,y5,z5;
reg        [DATA_WIDTH-1:0]  x6,y6,z6;
reg        [DATA_WIDTH-1:0]  x7,y7,z7;

reg        [1:0]   quadrant[PIPELINE:0];

integer i;

//get real quadrant and map to first_n quadrant

always@(posedge clk or negedge rst_n)
begin
        if(!rst_n)
               phase_in_reg<=8'b0000_0000;
        else
               if(ena)
                       begin
                               case(phase_in[7:6])
                                      2'b00:phase_in_reg<=phase_in;
                                      2'b01:phase_in_reg<=phase_in-8'h40;  //-pi/2
                                      2'b10:phase_in_reg<=phase_in-8'h80;  //-pi
                                      2'b11:phase_in_reg<=phase_in-8'hc0;  //-3pi/2
                                      default:;
                                endcase
                        end
end

always@(posedge clk or negedge rst_n)
begin
        if(!rst_n)
               begin
                       x0<=8'b0000_0000;
                       y0<=8'b0000_0000;
                       z0<=8'b0000_0000;
               end
         else
               if(ena)
                       begin
                               x0<=8'h4D;  //define aggregate constant Xi=1/P=1/1.6467=0.60725 (Xi=2^7*P+8'h4D)
                               y0<=8'h00;
                               z0<=phase_in_reg;
                       end
end

//level 1
always@(posedge clk or negedge rst_n)
begin
        if(!rst_n)
               begin
                       x1<=8'b0000_0000;
                       y1<=8'b0000_0000;
                       z1<=8'b0000_0000;
               end
         else
                if(ena)
                       if(z0[7]==1'b0)
                               begin
                                      x1<=x0-y0;
                                      y1<=y0+x0;
                                      z1<=z0-8'h20;  //45deg
                               end
               else
                       begin
                                      x1<=x0+y0;
                                      y1<=y0-x0;
                                      z1<=z0+8'h20;  //45deg  
               end      
end

//level 2
always@(posedge clk or negedge rst_n)
begin
        if(!rst_n)
               begin
                       x2<=8'b0000_0000;
                       y2<=8'b0000_0000;
                       z2<=8'b0000_0000;
               end
         else
                if(ena)
                       if(z1[7]==1'b0)
                               begin
                                      x2<=x1-{y1[DATA_WIDTH-1],y1[DATA_WIDTH-1:1]};
                                      y2<=y1+{x1[DATA_WIDTH-1],x1[DATA_WIDTH-1:1]};
                                      z2<=z1-8'h12;  //26deg
                               end
                        else
                               begin
                                      x2<=x1+{y1[DATA_WIDTH-1],y1[DATA_WIDTH-1:1]};
                                      y2<=y1-{x1[DATA_WIDTH-1],x1[DATA_WIDTH-1:1]};
                                      z2<=z1+8'h12;
                               end
end

//level 3   
always@(posedge clk or negedge rst_n)
begin
        if(!rst_n)
               begin
                       x3<=8'b0000_0000;
                       y3<=8'b0000_0000;
                       z3<=8'b0000_0000;
                end
         else
                if(ena)
                       if(z2[7]==1'b0)
                               begin
                                      x3<=x2-{{2{y2[DATA_WIDTH-1]}},y2[DATA_WIDTH-1:2]};
                                      y3<=y2+{{2{x2[DATA_WIDTH-1]}},x2[DATA_WIDTH-1:2]};
                                      z3<=z2-8'h09;  //14deg
                               end
                        else
                               begin
                                      x3<=x2+{{2{y2[DATA_WIDTH-1]}},y2[DATA_WIDTH-1:2]};
                                      y3<=y2-{{2{x2[DATA_WIDTH-1]}},x2[DATA_WIDTH-1:2]};
                                      z3<=z2+8'h09;
                               end
end

//level 4
always@(posedge clk or negedge rst_n)
begin
        if(!rst_n)
               begin
                       x4<=8'b0000_0000;
                       y4<=8'b0000_0000;
                       z4<=8'b0000_0000;
               end
         else
                if(ena)
                       if(z3[7]==1'b0)
                               begin
                                      x4<=x3-{{3{y3[DATA_WIDTH-1]}},y3[DATA_WIDTH-1:3]};
                                      y4<=y3+{{3{x3[DATA_WIDTH-1]}},x3[DATA_WIDTH-1:3]};
                                      z4<=z3-8'h04;  //7deg
                               end
                        else
                               begin
                                      x4<=x3+{{3{y3[DATA_WIDTH-1]}},y3[DATA_WIDTH-1:3]};
                                      y4<=y3-{{3{x3[DATA_WIDTH-1]}},x3[DATA_WIDTH-1:3]};
                                      z4<=z3+8'h04;
                               end
end

//level 5
always@(posedge clk or negedge rst_n)
begin
        if(!rst_n)
               begin
                       x5<=8'b0000_0000;
                       y5<=8'b0000_0000;
                       z5<=8'b0000_0000;
               end
         else
                if(ena)
                       if(z4[7]==1'b0)
                               begin
                                      x5<=x4-{{4{y4[DATA_WIDTH-1]}},y4[DATA_WIDTH-1:4]};
                                      y5<=y4+{{4{x4[DATA_WIDTH-1]}},x4[DATA_WIDTH-1:4]};
                                      z5<=z4-8'h02;  //4deg
                               end
                        else
                               begin
                                      x5<=x4+{{4{y4[DATA_WIDTH-1]}},y4[DATA_WIDTH-1:4]};
                                      y5<=y4-{{4{x4[DATA_WIDTH-1]}},x4[DATA_WIDTH-1:4]};
                                      z5<=z4+8'h02;
                               end
end

//level 6
always@(posedge clk or negedge rst_n)
begin
        if(!rst_n)
               begin
                       x6<=8'b0000_0000;
                       y6<=8'b0000_0000;
                       z6<=8'b0000_0000;
               end
         else
                if(ena)
                       if(z5[7]==1'b0)
                               begin
                                      x6<=x5-{{5{y5[DATA_WIDTH-1]}},y5[DATA_WIDTH-1:5]};
                                      y6<=y5+{{5{x5[DATA_WIDTH-1]}},x5[DATA_WIDTH-1:5]};
        z6<=z5-8'h01;  //2deg
                               end
                        else
                              begin
                                      x6<=x5+{{5{y5[DATA_WIDTH-1]}},y5[DATA_WIDTH-1:5]};
                                      y6<=y5-{{5{x5[DATA_WIDTH-1]}},x5[DATA_WIDTH-1:5]};
                                      z6<=z5+8'h01;
                               end
end

always@(posedge clk or negedge rst_n)
begin
        if(!rst_n)
            for(i=0;i<=PIPELINE;i=i+1)
                       quadrant[i]<=2'b00;
        else
               if(ena)
                       begin
                         for(i=0;i<PIPELINE;i=i+1)
                            quadrant[i+1]<= quadrant[i];
                            quadrant[0]<=phase_in[7:6];
                        end
end

always@(posedge clk or negedge rst_n)
begin
     if(!rst_n)
         begin
           sin_out<=8'b0000_0000;
           cos_out<=8'b0000_0000;
eps<=8'b0000_0000;
         end
     else
        if(ena)
           case(quadrant[7])
             2'b00:begin
                sin_out<=y6;
                cos_out<=x6;
                eps<=z6;
             end
              2'b01:begin
                 sin_out<=x6;
                 cos_out<=~(y6)+ 1'b1;
                 eps<=z6;
             end
            2'b10:begin
                 sin_out<=~(y6)+ 1'b1;
                 cos_out<=~(x6)+ 1'b1;
                 eps<=z6;
            end
            2'b11:begin
                 sin_out<=~(x6)+ 1'b1;
                 cos_out<=y6;
                 eps<=z6;
            end
         encase
end
endmodule

相关帖子

沙发
zhoumingzr| | 2012-10-29 19:26 | 只看该作者
带走了- -

使用特权

评论回复
板凳
GoldSunMonkey| | 2012-10-29 23:00 | 只看该作者
:lol谢谢分享啊。

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

328

主题

1073

帖子

2

粉丝