# Quartus 2 VHDL Clock Frequency Divider: can't determine definition of operator “+”

I'm extremely new to VHDL and trying to make some easy projects such that I learn the basics and syntax. I use Quartus 2 at home and ISE 10.1 at the school computer. I wrote exactly the same code in both of them where the code is:

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

entity freq_divider is port(

clk: in std_logic;
clkdividedby2,clkdividedby4,clkdividedby8: out std_logic
);

end freq_divider;

architecture karakter of freq_divider is

signal count4 : std_logic := '0'; --In this line, count4 is initialized as 0.
signal count8 : std_logic_vector (1 downto 0) := "00"; -- Count 8 is initialized as 0.
signal clkdividedby2_temp,clkdividedby4_temp,clkdividedby8_temp : std_logic :='0';

begin

process(clk)

begin
if(rising_edge(clk)) then

clkdividedby2_temp<= not clkdividedby2_temp;
count4 <= count4 + '1';
count8 <= count8 + "01";

if(count4 = '1') then -- = Tests for equality, not ==
clkdividedby4_temp<= not clkdividedby4_temp;
count4<='0';
end if;

if(count8 = "11") then
clkdividedby8_temp<= not clkdividedby8_temp;
count8<="00";
end if;

end if;
end process;

clkdividedby2<=clkdividedby2_temp;
clkdividedby4<=clkdividedby4_temp;
clkdividedby8<=clkdividedby8_temp;

end karakter;


This synthesized perfectly on ISE 10.1 in school, but in Quartus 2, I get the error:

Can't determine definition of operator ""+"" -- found 0 possible definitions

I have no idea why this is happening. I wrote all the libraries and stuff, and it is still not working.

You are trying to perform addition on std_logic and std_logic_vector -- that makes no sense in VHDL, because these types do not hold numerical values.

If you want addition to work, you need to use either

• a type that has well-defined overflow semantics, so it is clear what should happen if two '1' values meet in an addition, or
• a type that is a pure numerical value and does not have a representation attached.

For a counter that is only compared against a fixed value, but never read, I'd go with the latter, change the type to natural and give it a range constraint, and leave it up to the compiler to select an internal representation.

• But why it makes sense in ISE, but not Quartus ? I used my code in school in ISE 10.1 and it worked, in quartus 2 it did not. – Deniz Yildirim Jun 22 '16 at 20:29
• My initial guess is that they are trying to be "helpful". – Simon Richter Jun 22 '16 at 20:35
• well, I defined count4 and count8 as integers and now the code is working perfectly, but the thing is, compiler uses two 32 bits numbers when a single bit and two bits are necessary for count4 and count8 respectively. Isnt it a waste of memory or will it reduce the number of bits used in the optimization ? – Deniz Yildirim Jun 22 '16 at 20:39
• In VHDL, you can limit allowed values using the range keyword. If you limit to 0 to 3, you would get the desired behaviour, but also an error in simulation because you assign the value 4 for a short time, even if you immediately overwrite it later (because <= assignments are not performed until the end of the block). – Simon Richter Jun 23 '16 at 13:03

Addition for type std_logic_vector is supported in the IEEE package numeric_std_unsigned as well as the Synopsys package std_logic_unsigned.

What isn't supported is addition for type std_logic, where addition would be equivalent to "and". Replace count4 <= count4 + '1'; with count4 <= not count4; or just use clkdividedby2_temp.

You could likewise show the temp flipflops as part of same std_logic_vectors by making count4 length 2 and count8 length 3 and assigning the MSB's to clkdividedby4 and clkdividedby8 as well as renaming clkdividedby2_temp count2.

You could also use use a single 3 bit counter:

library ieee;
use ieee.std_logic_1164.all;
-- use ieee.numeric_std.all;
use ieee.std_logic_unsigned.all;
-- OR use ieee.numeric_std_unsigned.all;

entity freq_divider is
port (
clk:            in  std_logic;
clkdividedby2,
clkdividedby4,
clkdividedby8:  out std_logic
);
end entity freq_divider;

architecture foo of freq_divider is
signal count : std_logic_vector (2 downto 0) := (others => '0');
begin
process (clk)
begin
if rising_edge(clk) then
count <= count + 1;
end if;
end process;

clkdividedby2 <= count(0);
clkdividedby4 <= count(1);
clkdividedby8 <= count(2);

end architecture;


and with a small testbench:

library ieee;
use ieee.std_logic_1164.all;

entity freq_divider_tb is
end entity;

architecture foo of freq_divider_tb is
signal clk:             std_logic := '0';
signal clkdividedby2:   std_logic;
signal clkdividedby4:   std_logic;
signal clkdividedby8:    std_logic;
begin
DUT:
entity work.freq_divider
port map (
clk => clk,
clkdividedby2 => clkdividedby2,
clkdividedby4 => clkdividedby4,
clkdividedby8 => clkdividedby8
);
CLOCK:
process
begin
wait for 5 ns;
clk <= not clk;
if now > 160 ns then
wait;
end if;
end process;
end architecture;


You would get:

while saving some flip flops by modeling hardware.

• There is very little difference between your code and mine. I tried to write count4<=count4+1 in my code but mine is still not working and giving the same error. I did not understand how count<= count + '1' means and operation but count<=count +1 does not ? I also tried your code with count<=count+"001" and it is working as well. Im confused – Deniz Yildirim Jun 23 '16 at 14:54
• Oh I got you I guess. For single bits, we cant make the things work by count<=count + '1'; . I still dont get why it means and though ? But it is safe to say count4<=count4 +"01" if it was a std_logic_vector of size 2 right ? – Deniz Yildirim Jun 23 '16 at 14:57