1
$\begingroup$

I have been attempting to implement a Kalman filter on an FPGA in VHDL and have got to the point that it works. However I have the issue that each variable requires 64 bits to be represented to get the expected behaviour in simulation. With my current implementation about 95% usage of the FPGA is required for a 2D Kalman filter, when I really require a minimum of a 3D filter for my application. It also only runs at a rate of ~400KHz when I require 4MHz (ideally more) for my application.

I require an operating rate of 4MHz, i.e. it reads from the ADC, performs an iteration of the Kalman filter (a 3D Kalman filter) and writes to the DAC in 250ns. Ideally I would have a 16 bit ADC and DAC (could maybe be slightly lower) between $-1V$ to $+1V$.

A colleague proposed I use a DSP instead as the floating point implementation the programming a lot easier. In addition, as I have much more experience in writing efficient C code I am more inclined to use a DSP to solve my problem, in fact I already have a working C implementation that I prototyped before implemented the VHDL implementation. The C code I completed in a couple of days, whereas the VHDL implementation has so far taken me a couple of months of work (albeit not continuous work).

In my research I came across the TMS320C6678 Lite Evaluation Module which, with it's high GFlop rate of around 20GFlops (with a single core, 160GFlops if I can make use of all 8), should allow me to have ~5000 Flops with which to implement a single Kalman filter operation, which should be more than enough. Another StackOverFlow user, however informs me that connecting an ADC/DAC with 16 bit precision and a sample rate of around 4MS/s would be very difficult due to having to use a PCIexpress bus, is this correct? I saw some people online discussing using the SPI connection to connect the specified board to an ADC/DAC.

(100MS/s is what I can currently achieve with a NI 5781 ADC/DAC and a NI PXIe-7961R FPGA, although my current Kalman filter implementation cannot operate at these sorts of speeds) Is there a DSP which is more appropriate for my application and will allow me to achieve the sorts of speed I require and be able to interface with an ADC/DAC at the sorts of speeds I require? (Using either fixed point or floating point arithmetic)

If this is not the case, would it perhaps be worth learning to use Vivado High-Level Synthesis (HLS) so that my C code can be turned into VHDL, would this perhaps be more efficient than I can achieve with my current knowledge of/skill in VHDL?

Are there any other device options I have missed? I remember someone suggesting a software define radio at some point for my application?

If none of these is a reasonable option, could someone suggest some online/book resources for learning techniques to make my VHDL code more efficient?

The covariance matrix is a 2x2 marrix, each value is stored using 64 bits. My clock is a 40MHz clock downsampled by 9 to be 3.0769 (as my synthesiser reports it must be about 3MHz or less). Observations are 16 bit samples at 40/13/7 MHz ~400KHz (as each kalman filter iteration takes 7 clock cycles). Also my current implementation is all fixed point, done with the signed data type. For most values I multiply all the values by 2*N and truncate them to integers before storing them as the signed data type.

And for the elements of the covariance matrix, which are smaller, I use a different value, 2**M offset. I once tried to change it so they each had their own fixed point location/multiplicative offset but each time I operate 2 numbers together I need to bit-shift them so they have the same offset/fixed point location otherwise I couldn't correct the answer back at the end by bit-shifting. This lead to increased resource usage and therefore I stopped attempting this.

$\endgroup$
  • $\begingroup$ The NVIDEA Jetson board is really interesting and it has multiple types of I/O. You do have to learn some CUDA $\endgroup$ – Stanley Pawlukiewicz Jun 19 '17 at 0:27
  • $\begingroup$ I'm not shooting down the idea to move to a different computing platform, especially if you find it easier to use. That being said, I find it difficult to believe that you can achieve a faster implementation in a single DSP that you cannot achieve in a reasonably large FPGA. How big is the covariance matrix you are using for your Kalman filter? Your observations are 16-bit samples entering at 4 MHz? What is your clock? How did you determine pipeline requirements? Are you using resource sharing? Also, why did you choose floating point? Is it possible that a larger fixed point format would work? $\endgroup$ – hops Jun 19 '17 at 0:33
  • $\begingroup$ The covariance matrix is a 2x2 marrix, each value is stored using 64 bits. My clock is a 40MHz clock downsampled by 9 to be 3.0769 (as my synthesiser reports it must be about 3MHz or less). Observations are 16 bit samples at 40/13/7 MHz ~400KHz (as each kalman filter iteration takes 7 clock cycles). I'm afraid I'm not sure what you mean by pipeline requirements and resource sharing Also my current implementation is all fixed point, done with the signed data type. For most values I multiply all the values by 2*N and truncate them to integers before storing them as the signed data type. $\endgroup$ – SomeRandomPhysicist Jun 19 '17 at 1:58
  • $\begingroup$ And for the elements of the covariance matrix, which are smaller, I use a different value, 2**M offset. I once tried to change it so they each had their own fixed point location/multiplicative offset but each time I operate 2 numbers together I need to bit-shift them so they have the same offset/fixed point location otherwise I couldn't correct the answer back at the end by bit-shifting. This lead to increased resource usage and therefore I stopped attempting this. $\endgroup$ – SomeRandomPhysicist Jun 19 '17 at 1:58
  • $\begingroup$ I'm guessing I must be doing something very wrong from your comment, could you maybe look at the code and tell me where I am going wrong? I would not be comfortable with sharing it publicly but would like to get some feedback from someone who knows more than me. Being mostly self-taught in FPGA/VHDL programming and trained in languages such as C and Python I may be making all the wrong approaches, or may simply be ignorant of the correct way of doing things in VHDL. $\endgroup$ – SomeRandomPhysicist Jun 19 '17 at 2:06
1
$\begingroup$

The conclusion of my discussion with hops and Marcus was that getting a DSP to operate with an ADC and DAC at the latency required for my application (<=250ns for 4MHz) would be difficult and require writing some custom interface. We concluded that the best option is to continue to work with the FPGA and improve my VHDL implementation using pipelining, bit widening to reduce my usage of large numbers of bits and turning my functions into architecture blocks. An alternative solution was to attempt to use Vivado HLS to generate VHDL code from C code.

$\endgroup$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.