cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 
AndreasBMadsen
Contributor
Contributor
564 Views
Registered: ‎10-30-2020

VHDL function stops working after being run 5 times

Jump to solution

Hi

Sorry for this post being so long, but I wanted to give a bit of background to my problem.

My situation is this. I am working on some VHDL code for a Virtex-7 that will be used to test an external IC. This IC contains a set of registers and has an I2C slave interface that can be used to access them. To make the future work easier, I am making an IP that is supposed to make it easier to access these registers by handling the I2C transactions themselves. This way it will only be necessary to give a starting address, number of addresses to be read and a start signal in order to have the contents of several registers written to a FIFO that can then easily be read by the VHDL code yet to be developed. Similarly, a write operation can be issued by setting an address, writing data to the FIFO and issuing a command to start writing this data to consecutive registers of the external IC.

I am using Xilinx' AXI IIC IP core for the I2C itself. For each data transfer from the external IC to the FIFO, I will therefore need to perform a series of AXI operations to/from the AXI IIC IP. This is why I have made another VHDL module to make it easier to perform these operations:

AndreasBMadsen_0-1617275365315.png

So now, in order to e.g. write the value 0xFFFFFFFF to register 0x120 of the AXI IIC IP, I would:

  1. Wait for the signal 'wbusy' to go low
  2. Put the value 0x120 onto the 'waddr' bus
  3. Put the value 0xFFFFFFFF onto the 'wdata' bus
  4. Generate a pulse on the signal 'wenter'
  5. Wait for a falling edge on 'wbusy' before continuing

However, this is still a number of operations that will need to be performed sequentially each time I want to write to a register. I have previously made my VHDL code like this and it works just fine, but I wanted to try to find a more elegant solution by using an impure function.

What I have made looks like this:

AndreasBMadsen_1-1617275888433.png

I have declared a state signal external to the function so that it retains its value between successive calls. It returns a boolean value of 'false' each time it is run except for the last one, where the transfer is complete and it returns 'true'. This means that if I want to write to n registers in the IIC IP in a row, I can make a state machine with n states that calls this function like so (example from another part of my code, where the IIC IP is initialized):

AndreasBMadsen_3-1617276201704.png

The function call simply acts as the condition in an if-statement so that the code will only advance to the next state when the AXI transfer is complete. Now this seems to work perfectly fine for some time - 5 times to be more exact. But on the 6th time, it stops working. To try to figure out what was going wrong, I created the signal led_out, whose value defaults to 0, but is set to a different value for each state. Bits 8 to 11 are used to indicate the state of the AXI function FSM. So for example, during the first 5 uses of the function, I can use an ILA to see that these bits correctly go through the values 2, 3 and 4. However, on the 6th run, the value code stops progressing through the state machine and the value stays at 0 (default value), indicating that the function is never even entered. Even if it is entered, but none of the cases are entered, the value should still be 1, but remains 0. I have no idea what is going wrong and it is driving me mad.

Can anyone see what could be wrong? I contemplated whether it could be some optimization algorithm during the synthesis/implementation that somehow results in this, but I suspect that it is probably not so.

Thanks in advance

0 Kudos
1 Solution

Accepted Solutions
dpaul24
Scholar
Scholar
462 Views
Registered: ‎08-07-2014

@AndreasBMadsen ,

I guess I will have to make some VHDL code to act as the external IC in order to generate I2C inputs to the IIC IP. Is this what you would usually do?

Yes. If your design has an i2c master your testbench needs to emulate an i2c slave and vice-versa. The testbench code need not be synthesizeable code, it should just be able to emulate a slave or master behavior. It is up to you how you want the testbench bench to look like.

------------FPGA enthusiast------------
Consider giving "Kudos" if you like my answer. Please mark my post "Accept as solution" if my answer has solved your problem

View solution in original post

7 Replies
drjohnsmith
Teacher
Teacher
537 Views
Registered: ‎07-09-2009

simulate

 

<== If this was helpful, please feel free to give Kudos, and close if it answers your question ==>
AndreasBMadsen
Contributor
Contributor
503 Views
Registered: ‎10-30-2020

The trouble is that there is no simulation model for the IIC IP

0 Kudos
drjohnsmith
Teacher
Teacher
488 Views
Registered: ‎07-09-2009

If you have the IP, then can you not run the vivado simulator using that ?

 

<== If this was helpful, please feel free to give Kudos, and close if it answers your question ==>
dpaul24
Scholar
Scholar
475 Views
Registered: ‎08-07-2014

@AndreasBMadsen ,

Having a simulation model or not of IIC makes no difference. What @drjohnsmith probably meant was to simulate the entire design. 

Debugging using simulation is much more easier and meaningful than using ILA. After creating a design it is a MUST to simulate it to ensure the design is doing what is meant to do.

I use ILAs for debugging only for errors which cannot be reproduced via simulation.

------------FPGA enthusiast------------
Consider giving "Kudos" if you like my answer. Please mark my post "Accept as solution" if my answer has solved your problem

AndreasBMadsen
Contributor
Contributor
468 Views
Registered: ‎10-30-2020

The only problem is I don't know how to do it best. I guess I will have to make some VHDL code to act as the external IC in order to generate I2C inputs to the IIC IP. Is this what you would usually do?

0 Kudos
dpaul24
Scholar
Scholar
463 Views
Registered: ‎08-07-2014

@AndreasBMadsen ,

I guess I will have to make some VHDL code to act as the external IC in order to generate I2C inputs to the IIC IP. Is this what you would usually do?

Yes. If your design has an i2c master your testbench needs to emulate an i2c slave and vice-versa. The testbench code need not be synthesizeable code, it should just be able to emulate a slave or master behavior. It is up to you how you want the testbench bench to look like.

------------FPGA enthusiast------------
Consider giving "Kudos" if you like my answer. Please mark my post "Accept as solution" if my answer has solved your problem

View solution in original post

drjohnsmith
Teacher
Teacher
333 Views
Registered: ‎07-09-2009

might help 

https://opencores.org/projects/i2cslave

 

<== If this was helpful, please feel free to give Kudos, and close if it answers your question ==>
0 Kudos