using procedures

M

Michel Bieleveld

Guest
I am confused howto make use of procedures. It was my understanding
that i could use wait statements within the body of procedure. Yet my
vhdl code is not being synthesized. Can someone help me with this ? or
give good online reference/tutorial concerning procedures ?

With regards,

Michel Bieleveld.

architecture RTL of ax88796 is
..

Procedure AX_write (AX_reg : in std_logic_vector(9 downto 0);
AX_data : in
std_logic_vector(15 downto 0)) is
begin
Write_ax_loop : loop
..
wait until CLK'EVENT and CLK = '1';
exit Write_ax_loop when nRST = '0';
..
end loop;
end AX_Write;

COMB_PROC: process (CState,Div2ms)
begin
..
AX_Write(reg_dcr,init_dcr);
..
end process;
end RTL;
 
Michel Bieleveld a écrit:
I am confused howto make use of procedures. It was my understanding
that i could use wait statements within the body of procedure. Yet my
vhdl code is not being synthesized. Can someone help me with this ? or
give good online reference/tutorial concerning procedures ?
You cannot call a procedure with wait statements from within a process
with a sensitivity list.


--
____ _ __ ___
| _ \_)/ _|/ _ \ Adresse de retour invalide: retirez le -
| | | | | (_| |_| | Invalid return address: remove the -
|_| |_|_|\__|\___/
 
Hmm since i was planning on calling the procedure within my
statemachine I think I have a problem. What I want is to make a
macro?/procedure to easily write values to a registe, do you have any
suggestions to solve my problem ?

How do people generally solve this problem , synchronizing the main
state machine with a write register state machine ?



On Thu, 12 Aug 2004 14:21:12 +0200, Nicolas Matringe
<nicolasmatringe001@numeri-cable.fr> wrote:

Michel Bieleveld a écrit:
I am confused howto make use of procedures. It was my understanding
that i could use wait statements within the body of procedure. Yet my
vhdl code is not being synthesized. Can someone help me with this ? or
give good online reference/tutorial concerning procedures ?

You cannot call a procedure with wait statements from within a process
with a sensitivity list.
 
Michel Bieleveld a écrit:
Hmm since i was planning on calling the procedure within my
statemachine I think I have a problem. What I want is to make a
macro?/procedure to easily write values to a registe, do you have any
suggestions to solve my problem ?

How do people generally solve this problem , synchronizing the main
state machine with a write register state machine ?
I never use procedures in synthesizable code.
Synchronization of state machines is usually done with signals...
I don't understand what you're trying to do so I can't help you any further
--
____ _ __ ___
| _ \_)/ _|/ _ \ Adresse de retour invalide: retirez le -
| | | | | (_| |_| | Invalid return address: remove the -
|_| |_|_|\__|\___/
 
Michel Bieleveld wrote:

I am confused howto make use of procedures. It was my understanding
that i could use wait statements within the body of procedure.
Waits are not allowed for synthesis. See:
http://groups.google.com/groups?q=vhdl+synthesis+procedure+lapenta

-- Mike Treseler
 
Michel Bieleveld wrote:

I am trying to improve my coding, what i have till so far is working
nicely. BUT since i need to initialize around 10 registers this would
mean i have to write down 10 * 2 states (like Boot4/Boot5 and
Boot6/Boot7). So now i am confused how to make the code more compact,
and more elegant. ( Like using a procedure)
The code looks a tad scary ... 2 asynchronous state machines that send
information back and forth will often give interesting results in the
field. How about giving us the original problem you're trying to solve to
see if we can help you with it?

Regards,

Pieter Hulshoff
 
"Michel Bieleveld" <thechatter@hotmail.com> wrote in message
news:hkpnh0dm4sgdrgaqk4i6muu6ageimv30am@4ax.com...
Yes I thought the code looked scary too ;) Although i *think* the
state machines are well synchronized. However I would love to see some
clean code.

So here is my problem:

I am communicating with another chip. To setup the other chip I need
to make a reset signal of 20ms and then set some registers.

For the communication I need to make a /IOWR pin low for 60ns and high
for at least 100ns. My result were the two main processes listed in my
previous post.

I have no idea to make it more beautiful and would love to hear some
suggestions of how my betters are doing this :)

With regards,

Michel.


On Thu, 12 Aug 2004 21:31:04 +0200, Pieter Hulshoff
phulshof@xs4all.nl> wrote:

Michel Bieleveld wrote:

I am trying to improve my coding, what i have till so far is working
nicely. BUT since i need to initialize around 10 registers this would
mean i have to write down 10 * 2 states (like Boot4/Boot5 and
Boot6/Boot7). So now i am confused how to make the code more compact,
and more elegant. ( Like using a procedure)

The code looks a tad scary ... 2 asynchronous state machines that send
information back and forth will often give interesting results in the
field. How about giving us the original problem you're trying to solve to
see if we can help you with it?

Regards,

Pieter Hulshoff
What I usually do is to use 2 state machines; one FSM takes care of
transferring the data to the external chip, the other (higher level) FSM
takes of what data should be sent. Both communiciate with each other with
signals. The interface to the lower level FSM is for example

data:std_logic_vector(7 downto 0);
start_write:std_logic;
write_done:std_logic;

The first FSM waits for 'start_write' to become '1' and starts the transfer.
When it's done, it sets 'write_done' to '1' and waits for 'start_write' to
become '0' again and sets 'write_done' to '0'. This is a two way handshake.
The higher level FSM just controls these signals.
In this way almostly duplicate logic in states is removed, and has some
analogy of procedures in a procedural language like C.
Depending on some factors, a full two way handshake is not neccessary, and
the control signals can be only one clock pulse wide.

To save even further on states, you can put all the initialisation data in a
big vector and use a counter to select the proper subvector.

Hope this helps,

Jeroen
 
Michel Bieleveld wrote:
I am communicating with another chip. To setup the other chip I need
to make a reset signal of 20ms and then set some registers.

For the communication I need to make a /IOWR pin low for 60ns and high
for at least 100ns. My result were the two main processes listed in my
previous post.
Do you have any clock available to your design to synchronize things, and to
measure time with? What frequency is said clock running at?

I agree with Jeroen that it would be good to have one process that
communicates, and one that controls the information that needs to be
communicated. Both should be clocked. I know there are people out there
that have managed to get asynchronous designs working, but it's a
complicated design practice. :)

Regards,

Pieter Hulshoff
 
Yes this helps and this is what I already made. I was thinking of
using arrays to store the init data instead of one large vector. What
do you think is better ?


On Fri, 13 Aug 2004 01:23:29 +0200, "Jeroen" <jayjay.1974@xs4all.nl>
wrote:

"Michel Bieleveld" <thechatter@hotmail.com> wrote in message
news:hkpnh0dm4sgdrgaqk4i6muu6ageimv30am@4ax.com...
Yes I thought the code looked scary too ;) Although i *think* the
state machines are well synchronized. However I would love to see some
clean code.

So here is my problem:

I am communicating with another chip. To setup the other chip I need
to make a reset signal of 20ms and then set some registers.

For the communication I need to make a /IOWR pin low for 60ns and high
for at least 100ns. My result were the two main processes listed in my
previous post.

I have no idea to make it more beautiful and would love to hear some
suggestions of how my betters are doing this :)

With regards,

Michel.


On Thu, 12 Aug 2004 21:31:04 +0200, Pieter Hulshoff
phulshof@xs4all.nl> wrote:

Michel Bieleveld wrote:

I am trying to improve my coding, what i have till so far is working
nicely. BUT since i need to initialize around 10 registers this would
mean i have to write down 10 * 2 states (like Boot4/Boot5 and
Boot6/Boot7). So now i am confused how to make the code more compact,
and more elegant. ( Like using a procedure)

The code looks a tad scary ... 2 asynchronous state machines that send
information back and forth will often give interesting results in the
field. How about giving us the original problem you're trying to solve to
see if we can help you with it?

Regards,

Pieter Hulshoff


What I usually do is to use 2 state machines; one FSM takes care of
transferring the data to the external chip, the other (higher level) FSM
takes of what data should be sent. Both communiciate with each other with
signals. The interface to the lower level FSM is for example

data:std_logic_vector(7 downto 0);
start_write:std_logic;
write_done:std_logic;

The first FSM waits for 'start_write' to become '1' and starts the transfer.
When it's done, it sets 'write_done' to '1' and waits for 'start_write' to
become '0' again and sets 'write_done' to '0'. This is a two way handshake.
The higher level FSM just controls these signals.
In this way almostly duplicate logic in states is removed, and has some
analogy of procedures in a procedural language like C.
Depending on some factors, a full two way handshake is not neccessary, and
the control signals can be only one clock pulse wide.

To save even further on states, you can put all the initialisation data in a
big vector and use a counter to select the proper subvector.

Hope this helps,

Jeroen
 
Yes I have a clock available and processes that i use to synchronize
the state machines, like (in short):

If Reset then CState <= Boot1;
If Clk get high then Cstate <= NState;

The frequency that i am targetting for at the moment is 80 MHz, I
don`t know if it will be reasonable but I hope it is. That is why i
wait 5 clocks (states) for the 60ns to let /IOWR low, and then 100ns ,
8 clocks(states) to make /IOWR high.

I agree about the asynchronous, so that is why i think i solved the
problem by using one combinatorial process, and one synchronizing
process for a state machine. This way it seems too me to garantee
synchronized state machines.

How can i reduce the very long sequence of when => in the following
code ?

I appreciate the help I get from all of you :)

With regards,

Michel.


WRITE_AX: process(CStateW,AX_Write)
begin
case CStateW is
when Write0 =>
nIOWR <= '1';
if (AX_Write='1') then
AX_Write_Ready<= '0';
NStateW <= Write1;
else
AX_Write_Ready<= '1';
end if;
when Write1 =>
nIOWR <= '0';
AX_Write_Ready<= '0';
NStateW <= Write2;
when Write2 =>
nIOWR <= '0';
AX_Write_Ready<= '0';
NstateW <= Write3;
when Write3 =>
nIOWR <= '0';
AX_Write_Ready<= '0';
NstateW <= Write4;
when Write4 =>
nIOWR <= '0';
AX_Write_Ready<= '0';
NstateW <= Write5;
when Write5 =>
nIOWR <= '0';
AX_Write_Ready<= '0';
NStateW <= Write6;
when Write6 =>
AX_Write_Ready<= '0';
nIOWR <= '1';
NstateW <= Write7;
when Write7 =>
AX_Write_Ready<= '0';
nIOWR <= '1';
NstateW <= Write8;
when Write8 =>
AX_Write_Ready<= '0';
nIOWR <= '1';
NStateW <= Write9;
when Write9 =>
AX_Write_Ready<= '0';
nIOWR <= '1';
NstateW <= Write10;
when Write10 =>
AX_Write_Ready<= '0';
nIOWR <= '1';
NStateW <= Write11;
when Write11 =>
AX_Write_Ready<= '0';
nIOWR <= '1';
NstateW <= Write12;
when Write12 =>
AX_Write_Ready <= '0';
nIOWR <= '1';
NStateW <= Write13;
when Write13 =>
AX_Write_Ready<= '0';
nIOWR <= '1';
NStateW <= Write0;
end case;
end process;


On Fri, 13 Aug 2004 07:40:16 +0200, Pieter Hulshoff
<phulshof@xs4all.nl> wrote:

Michel Bieleveld wrote:
I am communicating with another chip. To setup the other chip I need
to make a reset signal of 20ms and then set some registers.

For the communication I need to make a /IOWR pin low for 60ns and high
for at least 100ns. My result were the two main processes listed in my
previous post.

Do you have any clock available to your design to synchronize things, and to
measure time with? What frequency is said clock running at?

I agree with Jeroen that it would be good to have one process that
communicates, and one that controls the information that needs to be
communicated. Both should be clocked. I know there are people out there
that have managed to get asynchronous designs working, but it's a
complicated design practice. :)

Regards,

Pieter Hulshoff
 
"Michel Bieleveld" <thechatter@hotmail.com> schreef in bericht
news:eek:hmoh0pomdh23jr04btg60ke0bfa16pb2i@4ax.com...
Yes I have a clock available and processes that i use to synchronize
the state machines, like (in short):

If Reset then CState <= Boot1;
If Clk get high then Cstate <= NState;

The frequency that i am targetting for at the moment is 80 MHz, I
don`t know if it will be reasonable but I hope it is. That is why i
wait 5 clocks (states) for the 60ns to let /IOWR low, and then 100ns ,
8 clocks(states) to make /IOWR high.

I agree about the asynchronous, so that is why i think i solved the
problem by using one combinatorial process, and one synchronizing
process for a state machine. This way it seems too me to garantee
synchronized state machines.

How can i reduce the very long sequence of when => in the following
code ?

I appreciate the help I get from all of you :)

With regards,

Michel.
Best way is to use a counter or shiftregister; and use default assignments
for the outputs. That will make the state machine look much tidier. By using
a counter you can change the timing without messing with the states.
 
Jeroen wrote:

Best way is to use a counter or shiftregister; and use default assignments
for the outputs. That will make the state machine look much tidier. By
using a counter you can change the timing without messing with the states.
I agree with Jeroen. There is no reason to limit yourself to
a single process variable. Updating a counter or shifter variable can
be a single line of code replacing a large case statement.
A single-process controller will be a bit tidier than two processes.
Sometimes a couple of booleans is cleaner than a type enumeration.
Try it and see.

-- Mike Treseler
 
"Michel Bieleveld" <thechatter@hotmail.com> wrote in message
news:tajrh0tjiu69ncs282htg91ophl8pbkj81@4ax.com...
By the way one more question, does anyone know if I need to specify
every output signal that i want to use in every state. Or does the
xilinx compiler maintain the state of the signals between different
states as long as I don`t change them.

E.g.

when State1 =
a <= '1';
when State2 =

Is the value of a in State2 guaranteed '1' or does the compiler
interpret this as a don`t care for a in state2. If so is there
somewhere an option to turn this don`t care interpretation off ?

Michel.
This has to do with VHDL, not the synthesizer. A signal will retain its
value if it's not reassigned a value when the process is iterated again. The
synthesizer will either infer a latch or flipflop, depending if your process
is clocked or not.

I suggest that you better read an (online) VHDL tutorial; there are plenty
and these very basic VHDL issues are covered in there.

Jeroen
 

Welcome to EDABoard.com

Sponsor

Back
Top