Fast bidirectional FPGA to microcontroller interface

From ScienceZero
Jump to: navigation, search

The interface is 11 wires, two control lines, one DDR clock (transfer on both rising and falling edge) and 8 data bits. The maximum transfer rate from a 60 MHz LPC2119 ARM chip to a Spartan 2E FPGA is 7 MB/s, that is identical to the maximum theoretical transfer rate at 8 bit. Chips with the fast I/O feature should be able to do up to 30 MB/s.

First the address and increment is loaded, after that a transfer can be done at every clock edge. Since the data is transferred at the same time as the clock there is a shift register in the FPGA that generates a delay so the data is not captured until the data is stable. This means that the FPGA must be clocked significantly faster than the bus clock.

Since the increment can be any value this code is very usable for graphics and just a small change is needed to make it draw textured lines.


//************************************
//  CPU <--> FPGA interface (11 lines)
//  d0-d7 armDataBus
//  m0-m1 armMode
//    clk armClock
//
//  mm
//  00 write data, increment
//  01 read data, increment
//  10 load address
//  11 load increment
//************************************

inout [7:0] armDataBus;
input armClock;
input [1:0] armMode;

reg armPrevClock;
reg [5:0] armDelay;
reg [31:0] armAddress, armIncrement;
reg [31:0] read_a;  


always @(posedge clk) begin
  if (armPrevClock != armClock)
    begin
      armDelay <=6'b001000;
      armPrevClock <= armClock;
    end
  else
    armDelay <= armDelay >> 1;
  
  if (armDelay[0])
    begin
      case (armMode)
        2'b00 :
          begin
            ram[armAddress] <= armDataBus;
            armAddress <= armAddress + armIncrement;
          end
        2'b01 : armAddress <= armAddress + armIncrement;
        2'b10 : armAddress <= {armAddress[23:0], armDataBus};
        2'b11 : armIncrement <= {armIncrement[23:0], armDataBus};
      endcase
    end
    read_a <= armAddress;
end
assign armDataBus = (armMode == 2'b01) ? ram[read_a] : 8'hzz;