:[SYNTH 8-944] 0 definitions of operator sll and srr - vhdl

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;
--use IEE.NUMERIC_STD.ALL; --tried with this package aslo
architecture Behavioral of my_code is
signal DATA: signed(31 downto 0);
signal DATA_OUT signed(31 downto 0);
signal f: std_logic_vector(7 downto 0);
begin
DATA_OUT<=DATA srl (( f-1) sll '1');
end behavioral;
This is a small part of my code. I am using vivado 2018.2 .for the above line I am getting [synth 8-944] 0 definition of all operators.
I know Verilog but I am new to VHDL. should I use any other packages for that?
Please help me by providing a solution or "equivalent function" for that.

Your problem is because there are no sll and srl operators defined for the combination of types you are using. There are operators with signatures:
[unsigned, integer, return unsigned]
[signed, integer, return signed]
unsigned and signed are types in the numeric_std package. Neither of these operators is defined for a std_logic_vector in any standard package. (STD_LOGIC_ARITH and STD_LOGIC_UNSIGNED are non-standard. Don't use them.)
So, you have two choices:
i) (not recommended) convert all of your types so they fit either of the above signatures or
ii) (recommended) don't use the sll or srl operators. They are badly defined and can lead to more logic being synthesised than you need. Instead, use other VHDL operators (eg slicing/concatenation or mathematical). You're trying to do maths here, so I would perhaps use mathematical operators. You'll still need to use the numeric_std package, because you are doing maths. You can't do maths on std_logic_vector unless you use a non-standard package.

Related

Instantiate VHDL entity with 2D array from SystemVerilog

There seems to be very little documentation on how to pass 2D arrays between VHDL and SystemVerilog. I have a port of the following type in VHDL:
package my_package is
type my_array_t is array (natural range <>) of std_logic_vector(N-1 downto 0);
end my_package
entity my_entity is
port(
my_input : in my_array_t(M-1 downto 0);
my_output : out my_array_t(M-1 downto 0);
);
end entity;
And the following SystemVerilog signal:
wire [N-1:0] my_input_s[M-1:0];
wire [N-1:0] my_output_s[M-1:0];
I believe these two types are completely equivalent. However, I can't go between each other without getting errors. Instantiating the VHDL module from SystemVerilog:
my_entity my_entity_inst(
.my_input(my_input_s),
.my_output(my_output_s)
);
The error I get is "formal port 'my_input' of type 'my_array_t' does not match with actual type 'logic'", similarly for the output signal. I tried different combination of array types in SystemVerilog (fully packed, fully unpacked) but none works. Note that in my case, I don't have the freedom of changing the VHDL declaration, I must find a way to make it work solely from SystemVerilog. Thus, this question can't help me.
How do I instantiate my VHDL module from SystemVerilog in the most straightforward way?
To be successful in instantiating VHDL in Verilog or SV stick to the basic types (types built into the original VHDL, not custom packages) in VHDL such as std_logic and std_logic vector.
For this case where you can't modify the VHDL file with custom port types, I recommend writing a VHDL wrapper (mydesign_wrapper.vhd) that instantiates the entity which uses the custom types and converts the ports to std_logic and std_logic_vector types for use at the top/entity of the wrapper design. Instantiate the new wrapper file in the Verilog or SystemVerilog file. An array of std_logic_vector would be represented as several std_logic_vector ports using the wrapper.
There is no standard for VHDL inside Verilog/SV, therefore support is limited and varies between tools, vendors, and versions.

How to use verilog module with adjacent underscore identifiers in VHDL

I have a verilog module from an external vendor. I would like to wrap it in VHDL.
The problem is that the verilog module contains identifiers that have adjacent underscores in their names. VHDL seems not to allow this. Surely I can wrap the verilog module into another verilog module and then wrap it into a VHDL module, but isn't there a way to avoid it?
I wrote a small example to illustrate:
Verilog:
module underscore (
test__in,
test__out
);
input test__in;
output test__out;
assign test__out = test__in;
endmodule
VHDL:
library IEEE;
use IEEE.std_logic_1164.all;
entity tb_underscore is
end entity;
architecture rtl of tb_underscore is
signal test_in: std_logic;
signal test_out: std_logic;
begin
i_underscore: entity work.underscore port map (
test__in => test_in,
test__out => test_out
);
end architecture;
The VHDL code does not compile because of the adjacent underscores.

std_logic_signed is used but not declared

I am new to VHDL. I am trying to use a std_logic_signed signal but I keep getting the error "std_logic_signed is used but not declared". As far as I can tell I have used the right libraries but googeling the error resulted in a lot of conflicting answers.
Here is my sample program:
LIBRARY ieee;
USE ieee.std_logic_1164.all;
USE ieee.std_logic_arith.all;
entity bird is
end entity bird;
architecture arch of bird is
--Declare signals
signal speed : std_logic_signed (7 downto 0);
begin
end architecture arch;
What is causing the error and how do I fix it?
Because the type name is SIGNED:
grep -i signed std_logic_arith.vhdl
std_logic_arith.vhdl: type SIGNED is array (NATURAL range <>) of STD_LOGIC;
...
There isn't a type declared named std_logic_signed.
Instead of declaring speed with a type mark of std_logic_signed use signed:
--Declare signals
signal speed : signed (7 downto 0);

VHDL alias syntax "<< ... >>"

I'd like to understand the syntax used in the line of code below where an alternate name is created using an ALIAS declaration. Specifically, I'd like to know what the << and >> imply. An example alias statement is,
alias x2_dac_data is
<< signal server.x2_dac_data : std_logic_vector(23 downto 0) >>;
where server is an instantiated component and x2_dac_data is a signal with the component, but not listed in the port declaration.
I've reviewed Pedroni's text and a course guide, neither of which reference the << ... >> syntax as it relates to alias.
Thanks
The double Less-Thans and double Greater characters (<<, >>) enclose an External Name, which is a path name to a object (e.g. signal, constant, variable) through a design model's hierarchy. The intended use is for design verification, allowing a testbench to reach objects not visible at the top level of a design.
See Peter Ashenden and Jim Lewis The Designer's Guide to VHDL (3rd Ed.), Section 18.1 External Names and Doulos VHDL-2008: Easier to use, Hierarchical Names, or IEEE Std 1076-2008, 8.7 External names.
There's an example on Page 561 of The Designer's Guide to VHDL:
alias duv_data_bus is
<<signal .tb.duv_rtl.data_bus : std_ulogic_vector(0 to 15)>>;
The syntax is described on Page 560. Pages 559-562 are visible in the Google Book preview. The example found in The Designer's Guide to VHDL dealing with external names is also found in Chapter 2, Section 2.1 External Names of VHDL 2008 Just the New Stuff by the same authors and while without the EBNF syntax description goes further into the philosophy behind external names. Unfortunately the book's Google Book preview doesn't reach Section 2.1. Jim Lewis is organizing the P1076 Study Group of the IEEE VHDL Analysis and Standardization Group (VASG) responsible for developing the next revision of IEEE Std 1076-201X. Peter Ashenden is a long time contributor to the VHDL standardization effort as well.
A better solution than aliases to hierarchical signal references in packages: using a package to share signals between bfm-procedures and testbench toplevel. Example:
library ieee;
use ieee.std_logic_1164.all;
--VHDL 2008 with questasim
package bfm is
signal tb_ii_a : std_logic;
signal tb_ii_b : std_logic;
signal tb_oo_c : std_logic;
procedure wiggle;
end package;
package body bfm is
procedure wiggle;
begin
tb_oo_c <= force in '1';
wait for 10 ns;
tb_oo_c <= force in '0';
wait for 10 ns;
tb_oo_c <= force in tb_ii_a and tb_ii_b;
end procedure;
end package body;
library ieee;
use ieee.std_logic_1164.all;
use std.textio.all;
use std.env.all;
library work;
use work.bfm.all;
entity tb;
end tb;
architecture tb_dut1 of tb is
begin
dut : entity work.dut port map(
oo_a => tb_ii_a, -- output of dut input of tb bfm
oo_b => tb_ii_b, -- output of dut input of tb bfm
ii_c => tb_oo_c -- input of dut output of tb bfm
);
testcase : process
begin
wiggle;
wait for 100 ns;
std.env.stop(0);
end process;
end architecture;

VHDL syntax for arrays of clocks (accepted by synthesis but not Active-HDL simulator)

I've a problem with some VHDL syntax in some old code that I want to reuse. It is accepted by the synthesis tool (Synplify) but the simulator (Aldec Active-HDL 8.3) gives the following error. (Note: This construction was accepted by a previous version of this simulator).
#Error: COMP96_0228: buffered_data.vhdl : (19, 28): The actual must be denoted by a static signal name, if the actual is associated with a signal parameter of any mode.
I get that the error doesn't like the (i) in the signal clk(i) but I don't want to unroll the loop to (0),(1),etc because it's used in several different configurations for different port sizes and I'm sure there must be a way to describe this.
My solution so far is to encapsulate one instance in it's own entity/arch hierarchy and use a "generate" to instantiate once for each port but I don't like it. Any better ideas?
Very simplified example showing exactly my issue. (The intent is to ensure that data is first clocked into the FPGA using its own associated clock before anything else)
library IEEE;
use IEEE.STD_LOGIC_1164.all;
entity input_buffer is
port(
clk : in std_logic_vector;
data_in : in std_logic_vector;
data_out : out std_logic_vector
);
end input_buffer;
architecture rtl of input_buffer is
constant c_NumOfPorts : integer := 3;
begin
p_process: process(clk)
begin
for i in 0 to c_NumOfPorts-1 loop
if rising_edge(clk(i)) then -- error here
data_out(i) <= data_in(i);
end if;
end loop;
end process;
end rtl;
If you change the loop inside the process into a generate statement outside the process, it works fine in ModelSim (I don't have Aldec available), and IMHO seems cleaner than a single process with a bunch of clocks. I would also typically use a generic to define the port widths, rather than pulling them in as a constant inside the architecture, but I figure you've got some reason for doing it that way:
library IEEE;
use IEEE.STD_LOGIC_1164.all;
entity input_buffer is
port(
clk : in std_logic_vector;
data_in : in std_logic_vector;
data_out : out std_logic_vector
);
end input_buffer;
architecture rtl of input_buffer is
constant c_NumOfPorts : integer := 3;
begin
gen : for i in 0 to c_NumOfPorts-1 generate
begin
p_process: process(clk(i))
begin
if rising_edge(clk(i)) then -- error here
data_out(i) <= data_in(i);
end if;
end process;
end generate;
end rtl;
FWIW, I get the same with Modelsim:
Model Technology ModelSim PE vcom 10.0a Compiler 2011.02 Feb 20 2011
-- Loading package STANDARD
-- Loading package TEXTIO
-- Loading package std_logic_1164
-- Compiling entity input_buffer
-- Compiling architecture rtl of input_buffer
** Error: clk.vhd(19): (vcom-1450) Actual (indexed name) for formal "s" is not a static signal name.
** Error: clk.vhd(25): VHDL Compiler exiting
As an aside - is there a reason for your use of the constant and not just doing this?
for i in clk'range loop
But no actual answer has occurred to me yet, sorry!

Resources