Forum Discussion

Altera_Forum's avatar
Altera_Forum
Icon for Honored Contributor rankHonored Contributor
13 years ago

Problem! Binary Divisor: Error (10028): Can't resolve multiple constant drivers

Hi! I'm trying to make a binary divisor of 4 bits in VHDL.

The process i'm using to get the quotient is to compare and substract.

So, what I want to do is to subtract certain binary number with other witin an If within a process by calling my substractor (SumadorRestador). I tried it but it wasn't possible...

So now, I'm searching to way to get that substraction that is inside the Process 2.

By now im trying to do the substraction before the process, but somehow I know that is impossible because there is no available data to get the result i want to get.

(A,B,C,D)R --> The result of the substraction

(A,B,C,D) --> The "important" number of each state

(A,B,C,D)_1 --> The result of the ifs of the actual number.

Can anyone help me, please?

Or tell me another way to create a binary divisor? :/

Thanks in advance!

Code:

-----

Library IEEE;

use ieee.std_logic_1164.all;

entity Div is

port (Dividendo, Divisor: in std_logic_vector(3 downto 0);

RST, CLK: in std_logic;

Cociente, Residuo: out std_logic_vector(3 downto 0));

end entity Div;

architecture NICE of DIV is

component SumadorRestador is

port( A,B: in std_logic_vector(7 downto 0);

Se: std_logic;

S: out std_logic_vector(7 downto 0));

end component SumadorRestador;

type EDOS is (IDLE, RES_1, RES_2, RES_3, RES_4);

signal EDO, EDOF: EDOS;

signal Cdividendo: std_logic_vector(7 downto 0);

signal A,B,C,D: std_logic_vector(3 downto 0);

signal A_1,B_1,C_1,D_1: std_logic_vector(3 downto 0);

signal RA, RB, RC,RD: std_logic_vector(7 downto 0);

signal Coci: std_logic_vector(3 downto 0);

signal Ini: std_logic;

signal AC, BC, CC,DC: std_logic_vector(3 downto 0);

begin

Cdividendo <= "0000" & Dividendo(3 downto 0);

Ini <= RST;

F0: SumadorRestador port map ("0000"& A, "0000" & Divisor, '1', RA);

F1: SumadorRestador port map ("0000"& B, "0000" & Divisor, '1', RB);

F2: SumadorRestador port map ("0000"& C, "0000" & Divisor, '1', RC);

F3: SumadorRestador port map ("0000"& D, "0000" & Divisor, '1', RD);

p1: process(CLK,RST)

begin

if RST = '0' then

EDO <= RES_1;

elsif CLK'event and CLK='1' then

EDO <= EDOF;

end if;

end process;

p2: process (EDO, RST, A, B, C, D)

begin

case EDO is

when IDLE => if Ini = '0' then

EDO <= RES_1;

else

EDO <= IDLE;

end if;

when RES_1 => if A > Divisor or A = Divisor then

A_1 <= RA(3 downto 0); HERE SHOULD BE THE RESULT OF THE FIRST SUBSTRACTION

Coci(3) <= '1';

EDO <= RES_2;

else

A_1 <= A;

Coci(3) <= '0';

EDO <= RES_2;

end if;

when RES_2 => if B > Divisor or B = Divisor then

B_1 <= RB(3 downto 0); HERE SHOULD BE THE RESULT OF THE SECOND SUBSTRACTION

Coci(2) <= '1';

EDO <= RES_3;

else

B_1 <= B;

Coci(2) <= '0';

EDO <= RES_3;

end if;

when RES_3 =>

if C > Divisor or C = Divisor then

C_1 <= RC(3 downto 0); HERE SHOULD BE THE RESULT OF THE THIRD SUBSTRACTION

Coci(1) <= '1';

EDO <= RES_3;

else

C_1 <= C;

Coci(1) <= '0';

EDO <= RES_3;

end if;

when RES_4 =>

if D > Divisor or D = Divisor then

D_1 <= RD(3 downto 0); HERE SHOULD BE THE RESULT OF THE FOURTH SUBSTRACTION

Coci(0) <= '1';

Residuo <= D_1(3 downto 0);

EDO <= IDLE;

else

D_1 <= D;

Coci(0) <= '0';

Residuo <= D_1(3 downto 0);

EDO <= IDLE;

end if;

when others => null;

end case;

end process;

p3: process (EDO)

begin

case EDO is

when IDLE => Cociente <= Coci;

when RES_1 => A <= CDividendo (6 downto 3);

when RES_2 => B <= A_1(2 downto 0) & CDividendo(2);

when RES_3 => C <= B_1(2 downto 0) & CDividendo(1);

when RES_4 => D <= C_1(2 downto 0) & CDividendo(0);

end case;

end process;

end architecture NICE;

10 Replies

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    May be this approach is similar like yours.

    a-You create a register, call it "resto" for example, with 2N bits. ( N = 4 in this case ).

    b-Fill the 4 MSb bits of that register with '0'.

    c-Fill the 4 LSb bits with the dividendo.

    d-Substract the "4 MSb bits of resto" - divisor.

    e-If the substraction is greater or equal than "0000" fill the 4 MSb of "resto" with the result of the substraction.

    If the result of substraction is negativo don't change "resto".

    f-Shift "resto" one position to the left.

    g-Repete the procedure from step 'd' until you entered all the bits of the original dividendo.

    I hope you understand me.
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Whats the problems specifically? are they problems in simululation? you have missed lots of signals out of sensitivity lists, so the simulation will not match the hardware.

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    --- Quote Start ---

    May be this approach is similar like yours.

    a-You create a register, call it "resto" for example, with 2N bits. ( N = 4 in this case ).

    b-Fill the 4 MSb bits of that register with '0'.

    c-Fill the 4 LSb bits with the dividendo.

    d-Substract the "4 MSb bits of resto" - divisor.

    e-If the substraction is greater or equal than "0000" fill the 4 MSb of "resto" with the result of the substraction.

    If the result of substraction is negativo don't change "resto".

    f-Shift "resto" one position to the left.

    g-Repete the procedure from step 'd' until you entered all the bits of the original dividendo.

    I hope you understand me.

    --- Quote End ---

    Shouldn't that be controlled by a clock?
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Which signals are missing on my sensitivity list?

    My doubt is: can I do substraction with another component inside a process?
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Of course. That algorithm is controlled by state machine so you need a clock.

    What tricky says is correct. If you forget signals from sensivity list ( all the signals that are inputs to the process ), the code will be synthetized anyway. But the simulation show inferred latches, because the ommited signals.

    Why do you make a substraction with a component? If you define a vector as unsigned you can do simply:

    c <= a - b;
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Ok! I've turned my inputs into unsigned, but now i have another problem...

    Error (10327): VHDL error at DIV.vhd(60): can't determine definition of operator "">"" -- found 0 possible definitions

    It is almost done! Please help me :)

    Here's my code again:

    ---

    p2: process (EDO, A, B, C, D, Ini, Dividendo, Divisor)

    begin

    case EDO is

    when IDLE => if Ini = '0' then

    EDO <= RES_1;

    else

    EDO <= IDLE;

    end if;

    when RES_1 => if A > Divisor or A = Divisor then

    A_1 <= A - Dividendo;

    Coci(3) <= '1';

    EDO <= RES_2;

    else

    A_1 <= A;

    Coci(3) <= '0';

    EDO <= RES_2;

    end if;

    when RES_2 => if B > Divisor or B = Divisor then

    B_1 <= B - Dividendo ;

    Coci(2) <= '1';

    EDO <= RES_3;

    else

    B_1 <= B;

    Coci(2) <= '0';

    EDO <= RES_3;

    end if;

    when RES_3 =>

    if C > Divisor or C = Divisor then

    C_1 <= C - Dividendo;

    Coci(1) <= '1';

    EDO <= RES_3;

    else

    C_1 <= C;

    Coci(1) <= '0';

    EDO <= RES_3;

    end if;

    when RES_4 =>

    if D > Divisor or D = Divisor then

    D_1 <= D - Dividendo;

    Coci(0) <= '1';

    EDO <= IDLE;

    else

    D_1 <= D;

    Coci(0) <= '0';

    EDO <= IDLE;

    end if;

    when others => null;

    end case;

    end process;
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    I'm done :(

    According to me theres no more signals of sensitivit to add.

    Please help!

    It stil shows these errors:

    Error (10028): Can't resolve multiple constant drivers for net "EDO.IDLE" at DIV.vhd(50)

    Error (10029): Constant driver at DIV.vhd(40)

    Error (10028): Can't resolve multiple constant drivers for net "EDO.RES_1" at DIV.vhd(50)

    Error (10028): Can't resolve multiple constant drivers for net "EDO.RES_2" at DIV.vhd(50)

    Error (10028): Can't resolve multiple constant drivers for net "EDO.RES_3" at DIV.vhd(50)

    Error (10028): Can't resolve multiple constant drivers for net "EDO.RES_4" at DIV.vhd(50)

    Error: Can't elaborate top-level user hierarchy

    Error: Quartus II Analysis & Synthesis was unsuccessful. 7 errors, 20 warnings

    Error: Peak virtual memory: 226 megabytes

    Error: Processing ended: Sat Nov 03 19:18:09 2012

    Error: Elapsed time: 00:00:00

    Error: Total CPU time (on all processors): 00:00:01

    The code again:

    ----

    entity Div is

    port (Dividen: unsigned(3 downto 0);

    Divisor: unsigned(3 downto 0);

    RST, CLK: in std_logic;

    Cociente, Residuo: out std_logic_vector(3 downto 0));

    end entity Div;

    architecture NICE of DIV is

    component SumadorRestador is

    port( A,B: in std_logic_vector(7 downto 0);

    Se: std_logic;

    S: out std_logic_vector(7 downto 0));

    end component SumadorRestador;

    type EDOS is (IDLE, RES_1, RES_2, RES_3, RES_4);

    signal EDO, EDOF: EDOS;

    signal A,B,C,D: unsigned(3 downto 0);

    signal A_1,B_1,C_1,D_1: unsigned(7 downto 0);

    signal Coci: std_logic_vector(3 downto 0);

    signal Ini: std_logic;

    signal Dividendo: unsigned(7 downto 0);

    begin

    Dividendo <= "0000" & Dividen;

    Ini <= RST;

    p1: process(CLK,RST)

    begin

    if RST = '0' then

    EDO <= IDLE;

    elsif CLK'event and CLK='1' then

    EDO <= EDOF;

    end if;

    end process;

    p2: process (EDO, A, B, C, D, Ini, Dividendo, Divisor)

    begin

    case EDO is

    when IDLE => if Ini = '0' then

    EDO <= RES_1;

    else

    EDO <= IDLE;

    end if;

    when RES_1 => if (A > Divisor) or A = Divisor then

    A_1 <= "0000" & A - Dividendo;

    Coci(3) <= '1';

    EDO <= RES_2;

    else

    A_1 <= "0000" & A;

    Coci(3) <= '0';

    EDO <= RES_2;

    end if;

    when RES_2 => if B > Divisor or B = Divisor then

    B_1 <= "0000" & B - Dividendo ;

    Coci(2) <= '1';

    EDO <= RES_3;

    else

    B_1 <= "0000" & B;

    Coci(2) <= '0';

    EDO <= RES_3;

    end if;

    when RES_3 =>

    if C > Divisor or C = Divisor then

    C_1 <="0000" & C - Dividendo;

    Coci(1) <= '1';

    EDO <= RES_3;

    else

    C_1 <= "0000" & C;

    Coci(1) <= '0';

    EDO <= RES_3;

    end if;

    when RES_4 =>

    if D > Divisor or D = Divisor then

    D_1 <= "0000" & D - Dividendo;

    Coci(0) <= '1';

    EDO <= IDLE;

    else

    D_1 <= "0000" & D;

    Coci(0) <= '0';

    EDO <= IDLE;

    end if;

    when others => null;

    end case;

    end process;

    p3: process (EDO)

    begin

    case EDO is

    when IDLE => Cociente <= Coci;

    when RES_1 => A <= Dividendo (6 downto 3);

    when RES_2 => B <= A_1(2 downto 0) & Dividendo(2);

    when RES_3 => C <= B_1(2 downto 0) & Dividendo(1);

    when RES_4 => D <= C_1(2 downto 0) & Dividendo(0);

    end case;

    end process;

    end architecture NICE;
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    you assign a value to EDO in one process, but you change EDO in another process too. Remember that VHDL is not a programming language, it's a HDL ( hardware description language ). You are defining hardware. Assign a value to a register in 2 diferents process is like conect the output of 2 gates in parallel.

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Ohhh maaaan!!

    Thanks a lot!!

    I'm such a clueless person! I only had to change the "EDO" used in process 2 to "EDOF".

    Uffff!!!

    I just hope it works. :) :) :) I'll check it out on school with the DE2. Now I just have to put the inputs and outputs to 7-segments displays.

    Thaaanks man!