Skip to content

Commit

Permalink
vpi: add 'quickstart'
Browse files Browse the repository at this point in the history
  • Loading branch information
umarcor committed May 3, 2020
1 parent a7bbd9e commit 00b6b1e
Show file tree
Hide file tree
Showing 7 changed files with 152 additions and 3 deletions.
6 changes: 4 additions & 2 deletions .github/workflows/test.yml
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@ jobs:
vhpidirect/arrays/intvector,
vhpidirect/arrays/logicvector,
vhpidirect/arrays/matrices,
vpi/quickstart,
]
runs-on: ubuntu-latest
env:
Expand Down Expand Up @@ -73,11 +74,12 @@ jobs:
vhpidirect/quickstart/package,
vhpidirect/quickstart/sharedvar,
vhpidirect/shared/shlib,
#vhpidirect/shared/dlopen, ! dlfcn.h is not available on win
#vhpidirect/shared/shghdl, ! dlfcn.h is not available on win
#vhpidirect/shared/dlopen, ! dlfcn.h is not available on win
#vhpidirect/shared/shghdl, ! dlfcn.h is not available on win
vhpidirect/arrays/intvector,
vhpidirect/arrays/logicvector,
vhpidirect/arrays/matrices,
vpi/quickstart,
]
runs-on: windows-latest
env:
Expand Down
18 changes: 17 additions & 1 deletion doc/vpi/examples/index.rst
Original file line number Diff line number Diff line change
@@ -1,4 +1,20 @@
.. program:: ghdl
.. _COSIM:VPI:Examples:

Examples
########

TBC
A very brief description of how to use VPI is that ``vpi_user.h`` provides dozens of functions to scan/navigate the hierarchy
of the elaborated hardware design, and it allows to set callbacks for specific events/signals.

.. NOTE::
Since VHDL sources are agnostic to the usage of VPI modules, most of the examples in this section reuse the same VHDL
sources. Readers should focus on the differences between the provided C files.

.. ATTENTION::
On Windows, the directory containing ``libghdlvpi.dll`` needs to be added to the ``PATH``. This can be achieved with
:option:`--vpi-library-dir`, :option:`--vpi-library-dir-unix` or ``$(cd $(dirname $(which ghdl))/../lib; pwd)``.

.. toctree::

quickstart
17 changes: 17 additions & 0 deletions doc/vpi/examples/quickstart.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
.. program:: ghdl
.. _COSIM:VPI:Examples:quickstart:

Quick Start
###########

.. _COSIM:VPI:Examples:quickstart:hello:

:cosimtree:`hello <vpi/quickstart/vpi_hello.c>`
***********************************************

This is the most minimal example, where a single callback is registered at the beginning of the simulation. The callback just
prints ``Hello!``. Then, the simulation is executed as usual.

VPI allows to register callbacks at multiple events and to optionally delay their execution after the event is triggered.
The list of available callback reasons is defined in :ghdlsrc:`vpi_user.h <grt/vpi_user.h>`. The structure type that is used
and required to register a callback, ``s_cb_data``, is also defined in the same header file.
26 changes: 26 additions & 0 deletions vpi/ent.vhd
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;

entity ent is
generic (
G_WIDTH : natural := 4
);
port (
A : in std_logic_vector(G_WIDTH-1 downto 0);
B : in std_logic_vector(G_WIDTH-1 downto 0);
C : in std_logic;
Q : out std_logic_vector(G_WIDTH downto 0)
);
end entity;

architecture arch of ent is

signal c_in : unsigned(0 downto 0);

begin

c_in <= to_unsigned(1,1) when C='1' else to_unsigned(0,1);
Q <= std_logic_vector(unsigned('0' & A) + unsigned(B) + c_in);

end architecture;
25 changes: 25 additions & 0 deletions vpi/quickstart/run.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
#!/usr/bin/env sh

set -e

cd $(dirname "$0")

echo "> Analyze ent.vhd and tb.vhd"
ghdl -a ../ent.vhd ../tb.vhd

echo "> Elaborate tb"
ghdl -e -o tb tb

echo "> Compile vpi_hello.c"
ghdl --vpi-compile gcc -c vpi_hello.c -o vpi.o

echo "> Link vpi.o"
ghdl --vpi-link gcc vpi.o -o vpi.vpi

if [ "$OS" = "Windows_NT" ]; then
# Need to put the directory containing libghdlvpi.dll in the path.
PATH=$PATH:`ghdl --vpi-library-dir-unix`
fi

echo "> Execute tb"
./tb --vpi=./vpi.vpi
22 changes: 22 additions & 0 deletions vpi/quickstart/vpi_hello.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
#include <vpi_user.h>
#include <stdio.h>

PLI_INT32 cb_hello(){
printf("Hello!\n");
return 0;
}

void entry_point_cb() {
s_cb_data cb;

cb.reason = cbStartOfSimulation;
cb.cb_rtn = &cb_hello;
cb.user_data = NULL;

if (vpi_register_cb(&cb) == NULL) {
vpi_printf ("cannot register cbStartOfSimulation call back\n");
}
}

// List of entry points called when the plugin is loaded
void (*vlog_startup_routines[]) () = {entry_point_cb, 0};
41 changes: 41 additions & 0 deletions vpi/tb.vhd
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;

entity tb is
generic (
G_WIDTH : natural := 4;
G_INST : natural := 4
);
end tb;

architecture arch of tb is

signal a, b : std_logic_vector(G_INST*G_WIDTH-1 downto 0);
signal c : std_logic_vector(G_INST downto 0);

begin

i_ent: for x in 0 to G_INST-1 generate
signal q: std_logic_vector(G_WIDTH downto 0);
begin
w_ent: entity work.ent
port map (
A => a((x+1)*G_WIDTH-1 downto x*G_WIDTH),
B => b((x+1)*G_WIDTH-1 downto x*G_WIDTH),
C => c(x),
Q => q
);
c(x+1) <= q(q'left);
end generate;

process
begin
a <= std_logic_vector(to_unsigned(2, a'length));
b <= std_logic_vector(to_unsigned(13, b'length));
c(0) <= '0';
wait for 10 ns;
wait;
end process;

end architecture;

0 comments on commit 00b6b1e

Please sign in to comment.