行为到结构转换问题VHDL

时间:2014-02-26 16:19:33

标签: vhdl hdl modelsim intel-fpga

我在行为类型中设计了Rabin Miller算法的素性测试。我用函数来创建我的模块。不幸的是,当我尝试通过Quartus的Altera Kit合成它时,我发现这个函数没有合成。在这里,我将编写我的整个程序,我真的需要你帮助给我至少一些提示,将它改为结构,因为它是我的高级设计项目。这是我的计划:

 library ieee;
 use ieee.std_logic_1164.all;
 use ieee.numeric_std.all;

 entity PrimeTest is
 port( N: in integer;
 Test1 : out std_logic);
 end PrimeTest;  

  Architecture Behavior1 of PrimeTest is


  function integer_binary (b1:std_logic_vector(31 downto 0)) return integer is
  variable a: integer:=0;
  variable i: integer;
   begin
    i:=0;

     while (i<32) loop
if b1(i) = '1' then
a:=a+2**i; 
end if;
i:=i+1;   
end loop;
     return a;
    end integer_binary;

       function integer_binary1 (b1:std_logic) return integer is
        variable a: integer;

       begin
if b1 = '1' then
a:= 1; 
else
  a:=0;
end if;
     return a;
     end integer_binary1;

     function binary1 (int1:integer) return std_logic_vector is
     variable int2: integer;
     variable a:std_logic_vector(31 downto 0);
  variable i: integer;

   begin
   int2:=int1;
  i:=0;
 while (i<32) loop    
  if (int2 mod 2 = 0) then
    a(i):='0';
  else
    a(i):='1';
  end if;
  i:=i+1;
    int2:=int2/2;
  end loop;
  return a;
  end binary1;

 function mul_mod (x1,y1,m1: std_logic_vector (31 downto 0)) return std_logic_vector is
variable p1: std_logic_vector (31 downto 0);
variable k: integer;
variable n: integer;
variable i: integer;
 variable j: std_logic_vector (31 downto 0);
 begin
n:=32;
i:=31;
p1:="00000000000000000000000000000000";
while(i>=0) loop

  p1:=binary1((integer_binary(p1))*2);

j:=binary1((integer_binary(y1))*((integer_binary1 (x1(i)))));

p1:=binary1((integer_binary(p1))+((integer_binary (j))));

if (p1 >= m1) then
  p1:=binary1(((integer_binary(p1))-(integer_binary (m1))));
end if;

    if (p1 >= m1) then
  p1:=binary1(((integer_binary(p1))-(integer_binary (m1))));
end if;
i:=i-1; 

end loop;
return p1;
end mul_mod;



 FUNCTION modexp3 (exp_m,exp_n: integer; 
                      exp_e: std_logic_vector(31 downto 0)) return integer is 
                 variable s:integer; 
                  variable result: integer:=1;
                        begin
    S := exp_m;

   L1: for I in 0 to 31 loop

    I2:    if (exp_e(I) = '1') then
        result := integer_binary(mul_mod(binary1(result),binary1(s),binary1(exp_n)));
       S := integer_binary(mul_mod(binary1(s),binary1(s),binary1(exp_n)));
   else
       S := integer_binary(mul_mod(binary1(s),binary1(s),binary1(exp_n)));
   end if I2;

    end loop L1 ;
    return result; 
  end modexp3;


 FUNCTION park1 (in_seed1,max1: integer) return integer is 
                 variable hi:integer;
                 variable lo:integer; 
                  variable out_seed:integer;
                  variable test:integer;
                  variable random1: integer;
                   variable rejected: integer;
                   variable a:integer:=16807;
                  variable m:integer:=2147483647;
                  variable q: integer:=127773;
                  variable r: integer:=2836;
                  variable seed:integer;

                        begin
                          seed:=in_seed1;

              for en in 0 to 1 loop
                if (en = 0) then
                  hi:=in_seed1 / q;
                 else
                  hi:=out_seed / q;
               end if;

lo:=in_seed1 mod q;
test:=((a*lo) - (r*hi));

if test > 0 then
Out_seed:= test;

else
Out_seed:= test + m;

    end if;
  end loop;
 random1:=out_seed mod max1;
 if random1 = 0 then
   seed:=(seed-1)**2;
   random1:= park1(seed,max1);
 end if;
    return random1; 
  end park1;

-- Primality Test Function
Function IS_Prime(number: integer) return STD_Logic is
Variable d: integer;
Variable d_binary: std_logic_vector(31 downto 0);
Variable s_1: integer :=0;
Variable iteration: integer :=1;
Variable x: integer;
Variable a: integer;
variable two:std_logic_vector(31 downto 0):="00000000000000000000000000000010";
Variable fake: integer;


Begin
d:= number -1; 
if ( number < 2) then
Return '0';
end if;  
if ( number = 2) then
Return '1';
end if;
if ( number /= 2 and number mod 2 = 0) then
 return '0';
end if;
while ( d mod 2 = 0 ) loop 
d:=d/2;
s_1:=s_1+1;
end loop;
d_binary:=binary1(d);
ii_loop: for ii in 0 to iteration-1 loop
a:=park1((ii+(s_1*100000))+number,(number-2));
x:=modexp3 (a,number,d_binary);
z4: if ((x /= 1) and (x /= number -1)) then 
 R_LOOP:         for r in 0 to s_1-1 loop
        fake:=0;
        x:=modexp3(x,number,two);
            z0: if (x = number -1) then
                fake:=1;
                 exit R_LOOP when fake = 1;
            end if z0;
            z1: if (x = 1) then 
                    return '0';
                end if z1;
    end loop R_LOOP;

        z2: if (fake/=1) then
            return '0'; 
        end if z2;

end if z4;
end loop ii_loop;
return '1';
End IS_Prime;
Begin

Test1 <= IS_Prime(N);


end Behavior1;

我是VHDL的新手,这让我很困惑,因为我的项目没有进展。请,我需要该程序为结构类型(端口映射)。

1 个答案:

答案 0 :(得分:1)

你要求提供一些提示,所以我只想写一些看到你的代码时想到的东西,希望它会有所帮助。

  • 使用功能没有问题;它们是组织设计的好方法。它们是可合成的,只要您在函数体中使用的语句也是可合成的。
  • 不要重新发明轮子。您编写的大多数函数已在标准库中预定义。在实施之前做一些研究,并尝试思考它是否是一个共同的子程序,对大多数设计师有用。如果是这种情况,可能会有一个现成的解决方案,特别是如果它涉及类型转换或数学。
  • 正如Brian Drummond所说,尽量避免while循环,因为编译器难以猜测迭代总数。具有恒定限制的for循环在合成器上更容易。并且忘记具有可变范围的嵌套循环。
  • Jerry Coffin也说得对,他说在硬件和软件中实现算法的方式可能会有些混乱。大多数时候,在编写任何代码之前绘制硬件图有助于解决问题。很多时候,它至少表明设计人员并不十分了解在硬件中实现算法需要做些什么。
  • 您想要从软件过渡到硬件。其中很大一部分是决定你需要立即做什么(在一个时钟周期内),以及你想要按顺序做什么(分布在几个时钟周期内)。因此,假设您有一些使用循环计算某些内容的行为(非可合成)代码,并且您希望在硬件中进行此计算。
    • 如果需要在syngle时钟周期中计算它,编译器将为所有循环迭代复制硬件,这可能是巨大的。
    • 如果您可以在几个时钟周期内进行计算,最好的办法是为此计算设计一个有限状态机(FSM)。再次,在编写代码之前绘制一个图表,这将对您的情况有所帮助。

希望这有助于指明你正确的方向。