Jump to content

    
Sign in to follow this  
novartis

IP ядро целочисленного деления от Альтеры

Recommended Posts

Сколько я его не пытался использовать, все какие то заморочки.

Утыкаюсь в ограничение по частоте. Нужно например поделить два числа (64 бит на 32 бит) на частоте 300МГц.

Компилю проект, таймквест репортует - отрицательные слаки. Считаю, вроде тактов 10 не хватает.

В мегавизарде можно выставить latency, ставлю 14 тактов ( запасом).

Компилю проект, таймквест репортует - отрицательные слаки.

Ставлю 24 такта.

Компилю проект, таймквест репортует - отрицательные слаки.

Сколько ему тактов то надо?

 

Зашел с другой стороны. Завел пониженную частоту 30МГц.

Данные с 300мгц перекидываю на частоту 30мгц. Результат с 30мгц перевожу на 300мгц, все это делаю через всякие там защелки-синхронизаторы .

Таймквест весь изнылся, что куча переходов с 30 мгц на 300мгц и обратно. Все надо описывать в sdc. Час на это потратил, устал, уже под ночь было, и так не доделал все.

 

Есть нормальный способ целочисленно поделить в ПЛИС?

 

Сморю сейчас на корки с opencores, может кто что использовал от туда?

Share this post


Link to post
Share on other sites
Сколько я его не пытался использовать, все какие то заморочки.

Утыкаюсь в ограничение по частоте. Нужно например поделить два числа (64 бит на 32 бит) на частоте 300МГц.

Компилю проект, таймквест репортует - отрицательные слаки. Считаю, вроде тактов 10 не хватает.

В мегавизарде можно выставить latency, ставлю 14 тактов ( запасом).

Компилю проект, таймквест репортует - отрицательные слаки.

Ставлю 24 такта.

Компилю проект, таймквест репортует - отрицательные слаки.

Сколько ему тактов то надо?

 

Зашел с другой стороны. Завел пониженную частоту 30МГц.

Данные с 300мгц перекидываю на частоту 30мгц. Результат с 30мгц перевожу на 300мгц, все это делаю через всякие там защелки-синхронизаторы .

Таймквест весь изнылся, что куча переходов с 30 мгц на 300мгц и обратно. Все надо описывать в sdc. Час на это потратил, устал, уже под ночь было, и так не доделал все.

 

Есть нормальный способ целочисленно поделить в ПЛИС?

 

Сморю сейчас на корки с opencores, может кто что использовал от туда?

какая FPGA?

 

Альтера предлагает следующее описание... попробуйте добавить "врукопашную" регистры

divider_tb.v

divider.v

Share this post


Link to post
Share on other sites
В какой версии квартуса работаете? Попробую у себя собрать ради спортивного интереса.

кристалл 10AX115N2F45E1SG.

квартус 16.0.2 Build 222 07/20/2016 SJ Standard Edition

 

Но то же самое было с циклоном 4, квартус не помню, наверно 13.1

 

 

Альтера предлагает следующее описание... попробуйте добавить "врукопашную" регистры

Спасибо, посмотрю

Share this post


Link to post
Share on other sites
Утыкаюсь в ограничение по частоте. Нужно например поделить два числа (64 бит на 32 бит) на частоте 300МГц.

попробуйте латентность сделать 64 или 32 такта, тогда возможно получиться...

Share this post


Link to post
Share on other sites

С мегафункцией целочисленного деления lpm_divide у меня тоже нормальной частоты не вышло. И варьирование latency не дает желаемого эффекта.

Что интересно, altera_fp_functions может делить плавающую точку и там можно указать желаемую частоту или latency. Вот там как нефиг делать 350MHz получилось.

Share this post


Link to post
Share on other sites

попробуйте такое описание

 

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;
--pipelined Radix2 division 
entity DivRadix2 is
   GENERIC(width : Natural := 16);
    Port ( clk      : in  STD_LOGIC;
           Dividend : in  STD_LOGIC_VECTOR ((Width-1) downto 0);
           Divisor  : in  STD_LOGIC_VECTOR ((Width-1) downto 0);
           Quotient : out STD_LOGIC_VECTOR ((Width-1) downto 0);
           Remainder: out STD_LOGIC_VECTOR ((Width-1) downto 0));
end DivRadix2;

architecture Behavioral of DivRadix2 is
  type test_arr    is array(0 to (Width-1)) of std_logic_vector((Width-1) downto 0);
  type partial_arr is array(0 to Width) of std_logic_vector((Width-1) downto 0);
  type divisor_arr is array(0 to Width) of std_logic_vector((Width-1) downto 0);
  type q_arr       is array(0 to Width) of std_logic_vector((Width-1) downto 0);
  
  signal test : test_arr;
  signal p    : partial_arr;
  signal d    : divisor_arr;
  signal q    : q_arr;

  constant zeros     : STD_LOGIC_VECTOR ((Width-2) downto 0) := (others => '0');

begin
  q(Width)       <= (others => '0');
  p(Width)       <= dividend;
  d(Width)       <= divisor;
  remainder   <= p(0);
  quotient    <= q(0);

  testgen: for I in 0 to (Width-1) generate
    test(I) <= zeros(I-1 downto 0) & p(I+1)((Width-1) downto I);
  end generate testgen;
  
  procgen: for I in 0 to (Width-1) generate
    process (clk, p(I+1),test(I), d(I+1), q(I+1))
    begin
      if rising_edge(clk) then 
        q(I) <= q(I+1)((Width-2) downto 0) & "0";
        d(I) <= d(I+1);
        p(I) <= p(I+1);
        if test(I) >= d(I+1) then
          q(I) <= q(I+1)((Width-2) downto 0) & '1';
          p(I) <= (p(I+1)((Width-1) downto I)-test(I)((Width-1)-I downto 0)) & p(I+1)(I-1 downto 0);
        end if;
      end if;
    end process;
  end generate procgen;
end Behavioral;

 

 

Share this post


Link to post
Share on other sites
попробуйте такое описание

 

post-52845-1492756174_thumb.png

 

Попытался поделить 37 на 10, этот модуль выдал 2 и 1.

Еще делил 57 на 10, там результат был 4 (остаток не помню).

 

Что-то не верно он считает. Пока не когда с ним дальше разбираться.

Share this post


Link to post
Share on other sites

У меня тоже есть вопрос по делению, задам тут.

Существует ли какой-нибудь оптимальный способ целочисленного деления на 2^n-1 ?

Или только предложенными выше универсальными делителями?

Share this post


Link to post
Share on other sites
У меня тоже есть вопрос по делению, задам тут.

Существует ли какой-нибудь оптимальный способ целочисленного деления на 2^n-1 ?

Или только предложенными выше универсальными делителями?

 

Если цель - уменьшить разрядность, а результаты потом используются для пост-обработки, то можно делить на 2^n, а уже после полученный результаты домножать на 2^n / 2^n - 1. В общем случае это, конечно, не годится, но вдруг.

Share this post


Link to post
Share on other sites
Существует ли какой-нибудь оптимальный способ целочисленного деления на 2^n-1 ?

Или только предложенными выше универсальными делителями?

Да, такой "оптимальный" способ существует. :biggrin:

 

Чтобы его "найти", нужно вспомнить школьную формулу для суммы геометрической прогрессии:

 

2-n + 2-2n + 2-3n + ... + 2-mn = (1 - 2-mn)/(2n - 1).

 

Из этого следует, что:

 

a*(1 - 2-mn)/(2n - 1) = a/(2n - 1) - a*2-mn/(2n - 1) = a*(2-n + 2-2n + 2-3n + ... + 2-mn),

 

или:

 

a/(2n - 1) = a*(2-n + 2-2n + 2-3n + ... + 2-mn) + a*2-mn/(2n - 1),

 

или:

 

a/(2n - 1) = (a >>> n) + (a >>> 2n) + (a >>> 3n) + ... + (a >>> mn) + a*2-mn/(2n - 1).

 

Из этой формулы видно, что с точностью до слагаемого:

 

Δ = b*2-mn,

 

частное от деления "a" на (2n - 1) равно:

 

b == a/(2n - 1) ≈ (a >>> n) + (a >>> 2n) + (a >>> 3n) + ... + (a >>> mn).

Share this post


Link to post
Share on other sites
В мегавизарде можно выставить latency, ставлю 14 тактов ( запасом).

Компилю проект, таймквест репортует - отрицательные слаки.

Ставлю 24 такта.

Компилю проект, таймквест репортует - отрицательные слаки.

Сколько ему тактов то надо?

 

А в настройких фиттера опция Perform Register Retiming у вас используется?

 

Share this post


Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Sign in to follow this