This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

Best way to create clocked IO on GPIO pins

I have a DM643x DSP device with an FPGA.  This FPGA is loaded on device powerup via a two wire interface, connected via two GPIO pins (called DATA0 and DCLK).  You set DATA0, then set DCLK and then clear DCLK.  I want to do this as fast as possible.  

My hardware guys say that the FPGA can handle basically any speed the DSP can generate, but that the GPIO has a speed limit (28Mhz?).

In the code below, I have a function BusyWaitDelayNsec(5) to throttle the GPIO.  However, I don't really know how to cause a small delay like this in a portable manner.  Do you have a suggestion for this?

Do I need a delay? Or will the GPIO throttle itself?

 

    for (int i = 0; i < rbfFileSize; i++) {

        for (int j = 0; j < 8; j++) {

            if ((pData[i] >> j) & 0x01)

                SetFPGA_DATA0();

            else

                ClearFPGA_DATA0();

          // Toggle the clock

        SetFPGA_DCLK();

        BusyWaitDelayNsec(5);

        ClearFPGA_DCLK();

        BusyWaitDelayNsec(5);

        }

    }

 

 

 

 

  • You could potentially use the display sub-system to do this, which could run with a clock speed up to 74.25MHz.

    The DSS can be configured into 1 bit color index mode which would then cycle through your data in a bitwise fashion.

    The DSS can also be configured to de-activate the clock during what would be video blanking times.

    BR,

    Steve

  • Kurt@Banner said:
    My hardware guys say that the FPGA can handle basically any speed the DSP can generate, but that the GPIO has a speed limit (28Mhz?).

    They are correct that there is some speed limit for a GPIO-generated clock. It would depend on the DSP clock speed and anything else going on in the system that could interfere, but I believe their 28MHz number.

    Since the FPGA can take anything you can throw at it, why do you need the BusyWaitDelayNsec(5)? "Nsec" does not sound like nano-seconds so it must be N-seconds which is really slow - certainly I am confused by the name. And it should work without those delays in there anyway, right? If the FPGA is just using the DCLK as a static clock, then having a duty cycle less than 50% should be okay, and faster.

    To increase your speed even more, and assuming that you put DATA0 and DCLK on the same GPIO bank or pair of banks, then you should be able to cut out one extra write. If the FPGA uses the rising edge of DCLK to latch the data (90% likely) then you can use the OUT_DATANN registers instead of the SET_ and CLR_ registers (make sure you read OUT_DATANN once to make sure what the rest of the bits are). For example, if DCLK is bit 0 and DATA0 is bit 1, then the following sequence would send 0, 1, 1, 0 to DATA0:

    0x0 (00b)
    0x1 (01b)
    0x2 (10b)
    0x3 (11b)
    0x2 (10b)
    0x3 (11b)
    0x0 (00b)
    0x1 (01b)
    0x0 (00b) - just to bring DCLK back to 0

     

    If this answers your question, please click  Verify Answer  on this post; if not, please reply back with more information to help us answer your question.

  • The Nsec(5) function was an attempt to delay 5 nanoseconds.   That would theoretically create a 10ns pulse or 100Mhz.  I tried to use the 64 bit TSC clock, but this doesn't seem to be a good way to make such a small delay.  

    So a question would be:  How would one make a small delay.  For example, if my DSP runs at 400Mhz (2.5ns), how would you delay 10ns or 50ns.  The goal would be some technique that would work over time as we change compiler version, or ramp up the DSP speed.

    The first question probably is the nature of the 28Mhz limit.  This came from the TI docs.  How is it supposed to be implemented?

    I tried removing the Nsec delays - the FPGA loaded fine.  I just don't know if clocking a GPIO pin as fast as possible violates this 28Mhz spec.

    Thanks for the further speedup idea - I see I can remove one in three cycles.

     

  • Kurt@Banner said:
    This came from the TI docs.

    Doc number and page and where on the page, please, if you want me to explain it. But it probably does not matter that much.

    There is a limitation to how fast you can write to GPIO registers. These registers reside on the Config SCR and reads/writes go through several clock cycles of delay when the DSP tries to access them. 28MHz is probably the fastest you can get with code that just continuously writes to these registers to toggle one pin.

    With that understanding, you can see that trying to add a 5ns delay is not going to result in a 100MHz clock rate. You can slow it down all you want and it will not get faster.

    I recommend you just do the bit-banging like you are now (with the OUT_DATAnn register to save one write), and be content with that performance.

  •  

    It turns out the 28Mhz was a calculated value for a particular DSP clock speed, based on the table in the part spec:   GPIO Peripheral Input/Output Electrical Data/Timing,   

    Switching Characteristics Over Recommended Operating Conditions for GPIO Outputs.  

    We now see that this spec is informing us that the GPIO has a max speed - don't expect the IO pins to toggle an faster than this.   Since our FPGA can handle clock speeds faster than this rate, we can bit-bang the data in without delays.

    So, thanks for the help, I think we are set.

     

     

     

  • I'm late on this thread, but what you're describing sounds like exactly the sort of thing you would do with a serial port, i.e. data synchronous with a clock.  I think McBSP would be a good way to do this.  It's much more efficient too because you can write a single 32-bit word and let the McBSP hardware take care of outputting each bit of that 32-bit word synchronously with a clock.  You could also "feed" the McBSP with EDMA if you wanted (perhaps not necessary if this is just boot-time init).