Intel® Quartus® Prime Software
Intel® Quartus® Prime Design Software, Design Entry, Synthesis, Simulation, Verification, Timing Analysis, System Design (Platform Designer, formerly Qsys)
16556 Discussions

UART and MODELSIM ALTERA (code attached)

Altera_Forum
Honored Contributor II
5,074 Views

Hi dears.  

 

 

I am trying to use a (slightly) modified version of the UART explained in a tutorial I've found, after reading some theory about. 

 

 

There is one UART entity which has two components - TX and RX, which in turn, operate with 9600bps in transmition and reception of bytes. 

 

 

The UART has two serial ports and two "parallel" ports for doing serial<->parallel conversion. 

 

 

The simulation results (for RX) can be visualized here: http://puu.sh/6tnpq/db6251b4ec.png 

 

 

My doubt: I am writing one byte 11111111 in the parallel_tx sign and I expect it to be passed to UART_RXD (not occurring in simulation). 

 

 

All the right sided signals are included in the sensitive list of all process as taught me here (the original code had not). 

 

I can't see any syntax erro on the codes (I had not noted any appointment in the comments where I took it from (Toni Axe, youtube)). 

 

note: I see that the RX and TX codes are written just with one process, with IFs operating as states (not using switch as I usually do). 

 

Any help will be appreciated (I created this post after 3 days trying to do it "by my self" in my DE2).  

 

thanks. 

 

PS: I am using 20000 ps clock period.
0 Kudos
29 Replies
Altera_Forum
Honored Contributor II
2,150 Views

Well, for a start, the RX.vhd has code in parrellel to the clock - this is bad practice, it should be in it's own asynchronous process. 

This async code contains a counter - with asynchronous counters you're just putting the code into an infinite loop - as soon as the counter increments, it will increment again over and over in 0 time, hence you will lock up the simulator. If you insist on doing a counter in an asynchronous process, you should produce a count_next signal and then register it in another process. 

 

You have an almost identical problem in tx.vhd. 

 

Inside a synchronous process, you only need to have the clock and any asynchronous resets in the sensitivity list. A sensitivity list tells the process which signals should cause a re-evaluation of the process. So for a synchronous process, the outputs can only change on a clock edge, so its not worth having other signals in there as nothing will change when they change.
0 Kudos
Altera_Forum
Honored Contributor II
2,150 Views

Hi friends, I have just a theoretical doubt about rx uart and I would appreciate if any help. 

 

The system clock, provided for the board is 50Mhz, and I was needing a 115200bps UART.  

 

I made a mod entity that outputs 1 tick every 13 ticks from the system clock including a 16 oversampling, based on this claculations: 

 

16 is my choice for the number of oversampling for RX bits. 

115200bps is the uart baud rate. 

50Mhz is the system clock. 

 

50Mhz/(16*115200) = 27,126736111 what I assumed to be 27. 

 

So, if 50Mhz system clock has 20 ps in each cicle, after 27*20ps = 540 ps the mod entity would be generate one tick. 

 

As soon as the start bit is detected, I am interested in sampling the middle of this bit, so, at 13ª cicle or 540ps/2 = 270 ps after this start bit is being detected. 

 

All this explanation is to justify why I made the mod count from 0 to 12 to outputs one tick, for detecting the middle of start bit and after I wait two ticks of 0 to 12, I take the sample for data bits and stop bits. 

 

It gives me a conversion from 50Mhz to 1/540ps = 1.851 Hz, what I think it is close to the1.8432Hz needed to 115200bps. 

 

I attached the begin and the end of simulation. 

 

Are that correct? 

 

Thank you very much.
0 Kudos
Altera_Forum
Honored Contributor II
2,150 Views

Hi,  

 

I have a very simple issue, could some one give me a help with that please? 

 

I made a counter from 0 to 12 to aproximate a counting from 0 to 12,5 need to make a 115200 bps rx uart. 

 

This counting should begin when the rx receives the start bit '0', and reset when the stop bit' 1' is achieved. 

 

So, the RX controls the reset of the MOD counter. I made this way to avoid the pulse going over the length of the bit for the next bytes, due to the error 0,5 in counting. 

 

the only signal I need help in the code is in rx_uart.vhd.vhd , signal en_mod_reset: std_logic:='1';  

when it is '1', the mod_27_uart.vhd do not count. When it is '0', it starts to count. 

 

It works in the first byte received, but after it goes '1' forever. 

 

I know it is about semantic, but I cant see what is my falt in the code. 

 

Thanks.
0 Kudos
Altera_Forum
Honored Contributor II
2,150 Views

according to the code you posted, en_mod_reset doesnt connect to anything...

0 Kudos
Altera_Forum
Honored Contributor II
2,150 Views

 

--- Quote Start ---  

according to the code you posted, en_mod_reset doesnt connect to anything... 

--- Quote End ---  

 

 

Sorry I did not make it clear enough. 

 

 

Assume that en_mod, associated to the signal en_mod_reset in uart_rx, is connected to the reset in the mod_27. 

 

 

Both of them are connected to the 50MHz clock and were simulated. The circuit is working normally if I connect the reset of the mod_27 to the reset of the whole system. 

 

 

But i need the mod_27 reseted if no start bit in uart_rx is detected. So uart_rx controls the mod_27 reset trhough the en_mod_pin. 

 

 

uart_rx(en_mod) -> mod_27(reset) 

 

 

Thank you for your help.
0 Kudos
Altera_Forum
Honored Contributor II
2,150 Views

In resume, why the en_mod is not changing again to '0' in uart_rx when the start bit is detected ? 

 

case state_reg is 

when idle => 

if (rx = '0') then 

state_next <= start; 

en_mod_reset <= '0'; -- mod 27 set, counting. 

s_next <= (others => '0'); 

end if; 

 

Thanks.
0 Kudos
Altera_Forum
Honored Contributor II
2,150 Views

I'll try to model like others signal in the code. I mean like flip-flops.  

 

If not work maybe putting the '0' or '1' directly in the output pin to try to avoid this issue.
0 Kudos
Altera_Forum
Honored Contributor II
2,150 Views

In your code, you have connected en_mod to en_mod_reset inside a process, so according to your code it will only change the value when state_reg, s_reg, n_reg, b_reg, s_tick, rx change. You should move the assignment outside of the process.

0 Kudos
Altera_Forum
Honored Contributor II
2,150 Views

God, You told me it a lot and I again forgot to put what is needed inside the sensitive list. I made this correction and 

I made the n_mod as a flipflop model like the others signals. It works now, thank you very much Tricky. Code attached.
0 Kudos
Altera_Forum
Honored Contributor II
2,153 Views

Hi Tricky. 

 

All the simulations went well. I attached all the code in the case someone wants try it too: 

 

UART.vhd is the main. 

FIFO_mf.vhd is the FIFO mega function, 16 bytes. 

rx_uart.vhd is the rx 115200 bps. 

mod_27_uart.vhd is the modulator from 50MHz (DE2-70) to 1.84KHz (UART). 

 

I have a altera board DE2-70 which I will load the code (UART.vhd is the main) after compilation. 

 

UART.vhd will give me this in/outputs: 

 

ENTITY UART IS  

PORT 

rst : IN STD_LOGIC; -- whole system reset. 

serial_rx : IN STD_LOGIC; -- the data being received serially. 

clock_50MHz : IN STD_LOGIC; -- whole system clock. 

rd : IN STD_LOGIC; -- FIFO outputs the first byte saved from UART when it is '1'. 

full : OUT STD_LOGIC; -- when FIFO is full. 

empty : OUT STD_LOGIC; -- when FIFO is empty. 

mod_27_cnt : OUT STD_LOGIC_VECTOR(3 DOWNTO 0); -- 1.8KHz uart (115200 bps). 

parallel_rx : OUT STD_LOGIC_VECTOR(7 DOWNTO 0); -- parallel rx from uart_rx to FIFO_mf. 

usedw_out : OUT STD_LOGIC_VECTOR(3 DOWNTO 0) -- just a counter of FIFO. 

); 

END UART; 

 

I used the Quartus II to associate those pins above from UART to the FPGA: 

 

rst is a switch on the board. 

serial_rx is the serial rx on the board DE2-70. 

clock_50MHz is the 50MHz clock from the board.. 

rd is a button fr mthe board. 

full is a red led from the board. 

empty another red led. 

mod_27_cnt not associated, it is just for simulation visualization. 

parallel_rx is associated to 8 green LEDs . 

usedw_out not associated, it is just for simulation visualization. 

 

After load the code to the board, I opened the terminal (I use one from arduino app) and reset the switch (rst) on the board. 

 

After, for testing, I write 1 on the terminal, then 2, then 3.  

 

Then, I pressed the button (rd) and nothing happens. 

 

The green leds would expected to be flashing the 1 binary at first press. Then the 2 binary after second pressing. The same with 3 binary. 

 

It happens in the simulation with ModelSim Altera. 

 

As I am a newbie with FPGA, I would expect the simulations, as soon as they are synthesizable, happens in the board too. 

 

I attached the schematic from qartus II to help to visualize it. 

 

All the role are played (I think it is) by the mod_27_uart, that starts to count from 0 to 12 (ignore the 14 in the image, I correct it) to detect the start bit, and from 0 to 12 twice to detect each of the 8 data bits, and finally to 0 to 12 to detect the end bit. The mod_27_uart only starts to cout when the start bits on uart_rx is detected, so it is why the uart_rx controls the reset of the mod_27_uart. 

 

Please could some experienced help me with this issue? 

 

I appreciate your help.
0 Kudos
Altera_Forum
Honored Contributor II
2,153 Views

After some weeks I found the issue. 

 

My first theory is that Altera boards just work with Altera codes (IP core). 

 

The code attached works very well in the Altera ModelSim simulation, but it does not in my DE2 (http://www.altera.com/education/univ/materials/boards/de2/unv-de2-board.html). 

 

If I am wrong, the Altera ModelSim and the Quartus II synthesizer/compiler are wrong too. 

 

My code is just a buffered RX 115200bps UART. I atacched even the pin csv association and my simulation results. 

 

When I send a byte via terminal, the TX led blinks indicating that the buffer is empty, but nothing more than that happens, even if I reset the system. 

 

I doubt if it has any error in the code. 

 

Thanks any way.
0 Kudos
Altera_Forum
Honored Contributor II
2,153 Views

are rx and rd already synchronous to the 50MHz clock? if not, you need to synchronise them. If they are asynchronous you have the possibility of metastable registers in the real implementation.

0 Kudos
Altera_Forum
Honored Contributor II
2,153 Views

Yes, the mod_27_uart.vhd does that.  

It takes 27 cicles from 50MHz and generates one pulse to RX.  

After 16 (oversampling) cicles, the RX consider to sample a byte.  

It means that the RX does sampling in the middle of each byte that comes in uart. 

 

For ease of implementation, the FIFO is a megafunction, so it may ensure that it works well in the project. 

 

I atacched a table showing pins association. 

 

I folow this calculation to convert 50Mhz to 115200bps: 

------------------------------------------------------------------------------------------------------------------------------- 

50 mhz (board) to 1.841mhz (uart 115200) 

 

In 115200bps, one bit is send in 0,000008681 seconds. 

 

If each bit is sampled 16 times, each sample must occur in 0,000000543 seconds. 

 

This is equivalent to say: 1841620,626151013 Hertz (1.841,620 MHz ~ 1.841 MHz) 

 

So, in one cicle of 50MHz, I need to wait 50MHz/1.841MHz cicles (or 27,1 ciclos) of 50MHz to read each of one 16 samples for each bit. 

------------------------------------------------------------------------------------------------------------------------------- 

In resume, after 27 cicles from 50Mhz, I count one tick. After 16 ticks, I read a byte in TX. 

 

(Of course, for the first bit (start bit) I wait just 7 ticks.)
0 Kudos
Altera_Forum
Honored Contributor II
2,153 Views

I mean the serial RX and rd inputs to the system. If they are not synchronised to the 50MHz clock externally then you will have problems sampling them inside ther FPGA. They need to be at least double registered to avoid metastability problems and glitching.

0 Kudos
Altera_Forum
Honored Contributor II
2,153 Views

 

--- Quote Start ---  

I mean the serial RX and rd inputs to the system. If they are not synchronised to the 50MHz clock externally then you will have problems sampling them inside ther FPGA. They need to be at least double registered to avoid metastability problems and glitching. 

--- Quote End ---  

 

 

All the components are connected with the 50MHz clock from the board, as it can be seen in the schematic, through the "clk" inputs of each of the three components. 

 

As I am using the De2-70 ep2c70f896c6 Cyclone II, here (http://wiki.icmc.usp.br/images/0/04/de2-70-pins.txt)we can see the information about the pins of this board, i am using PIN_AD15 for 50MHz clock associated with the input named "clock_50MHz" in the schematic. This input is linked to the "clk" inputs of the three components. 

 

This "clk" input is the external 50MHz syncronization that the three components are using. 

 

Inside of mod_27_uart.vhd (http://www.alteraforum.com/forum/attachment.php?attachmentid=8640&d=1395413992) , I count the 27 cicles of 50MHz and generate one pulse to rx_uart.vhd (http://www.alteraforum.com/forum/attachment.php?attachmentid=8641&d=1395413997). In turn, the rx_uart.vhd (http://www.alteraforum.com/forum/attachment.php?attachmentid=8641&d=1395413997) counts 16 pulses comming from mod_27_uart.vhd (http://www.alteraforum.com/forum/attachment.php?attachmentid=8640&d=1395413992) to sample one bit (for start bit it counts just 8 pulses). All of them work with 50MHz.
0 Kudos
Altera_Forum
Honored Contributor II
2,153 Views

I am talking about the serial_rx and rd ports that come into the schematic. They are NOT synchronised into the 50MHz clock domain inside the FPGA. If they are not synchronised externally, you will run into problems on the board.

0 Kudos
Altera_Forum
Honored Contributor II
2,153 Views

Sorry, maybe I couldn't understand what you are trying to tell me, but,  

 

I suppose that I am dealing with two clocks, 50MHz (board) and the frequency of the UART (1.8KHz approximate frequency when 115200bps). 

 

the uart signal comming from my PC is operating in 115200bps, so 1.8KHz, the RS-232 on the board is, I think, dealing with this signal in 1.8KHz.  

 

The RS-232 on the board sends the serial data to the FPGA pin UART_RXD (PIN_D21) in 1.8KHz. 

 

The FPGa and all the components in VHDL are working with 50MHz, trhough the pins "clk" in each component. 

 

The mod27 component converts the 50MHz clock signal to the ~1.8KHz clock signal including the oversampling of each bit of the data comming: 

The mod27 does it counting 27 cycles of 50MHz and generating one pulse. The Uart rx count 7 of these pulses and read the start bit from the first byte. 

The uart rx counts 16 of these pulses and read the rest of bits from the first byte. 

 

Why are they not syncronized inside FPGA if the "clk" input from them are conecteted to the 50MHz clock of the board?
0 Kudos
Altera_Forum
Honored Contributor II
2,153 Views

You need to double register these 2 inputs using the 50MHz clock to prevent metastable events. 

if serial_rx or rd have a rising edge the same time the 50mhz clock has a rising edge, then any registers sampling these signals will go meta stable, and so any other register may read it as 0 or 1 (depending on voltages). Using a double register prevents metastability, because the 2nd register will force and output of 0 or 1, and never meta-stable state. 

 

You need this double register synchroniser or your internal logic may have meta-stable events.
0 Kudos
Altera_Forum
Honored Contributor II
2,153 Views

Really I got 5 warnings about time restrictions during the compilation. 

 

These warnings say that I need to specify some restrictions in a SDC file before compiling. 

 

I am reading the following documentation from Altera: 

 

White Paper - Understanding Metastability in FPGAs 

http://www.altera.com/literature/wp/wp-01082-quartus-ii-metastability.pdf 

14. Managing Metastability with the Quartus II Software  

http://www.altera.com/literature/hb/qts/qts_qii51018.pdf 

7. The Quartus II TimeQuest Timing Analyzer  

 

 

Is that the way (TimeQuest Timing Analyzer) to correct the metastability using quartus II? 

 

I attached a TimeQuest screenshot where it tells me that I need specify a SDC file. The first and the second process in the TimeQuest are checked as we can see in the screenshot. 

 

Thanks.
0 Kudos
Altera_Forum
Honored Contributor II
1,941 Views

No. You fix meta stability by inserting 2 registers on the serial_rx and rd inputs.

0 Kudos
Reply