Forum Discussion

Altera_Forum's avatar
Altera_Forum
Icon for Honored Contributor rankHonored Contributor
14 years ago

Creating a bidirectional bus

I want to connect a USB chip (FT245R) to a CPLD. To do that I need a bidirectional 8-bit bus. I thought I could declare the pins to be bidirectional and with a mux, read to or write from the pins as necessary. My Verilog code for the mux is:

[code]

always @(negedge clk) begin: TESTUSB_MUX

if ((TXE == 0)) begin

USBBUS <= OUTBUS;

end

else if ((RXF == 0)) begin

INBUS <= USBBUS;

end

end

[\code]

But the Fitter generates errors, e.g., Error: Can't reserve pin "USBBUS[0]" because its name already exists with a different direction

How can a bidirectional bus be created?

13 Replies

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Thanks for your reply. I made the changes you suggested but now Quartus generates this error message: error (10219): verilog hdl continuous assignment error at testusb.v(353): object "inbus" on left-hand side of assignment must have a net type

    Line 353 is the assignment to inbus in:

    if (read condition) begin

    inbus <= USBBUS_i;

    end

    I made the following changes indicated by <<<<

     
    input wire  USBBUS;
    wire  USBBUS_i;
    reg  USBBUS_o;
    reg USBBUS_oe;
    assign USBBUS_i = USBBUS;
    assign USBBUS = USBBUS_oe == 1'b1 ? USBBUS_o : 8'hzz;   
     
    wire  inbus_i;            //<<<<
    assign inbus_i = inbus;     //<<<<
     
    always @(negedge clk) begin
        if(TXE == 0) begin
            USBBUS_o <= outbus;
            USBBUS_oe <= 1'b1;
        end
        else begin
            USBBUS_o <= 8'hxx;        
            USBBUS_oe <= 1'b0;
        end
        if (RXF == 0) begin
            inbus_i <= USBBUS_i;    //<<<<
        end
    end
    

    but that didn't solve the problem
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    You cannot use a "wire" in an "always" statement. It's a Verilog idiosyncranie.

    What people usually do, when dealing with bi-directional signals is to decompose it in 3 variants (input, output and output enable) like this.

    input wire  USBBUS;
    wire  USBBUS_i;
    reg  USBBUS_o;
    reg USBBUS_oe;
    assign USBBUS_i = USBBUS;
    assign USBBUS = USBBUS_oe == 1'b1 ? USBBUS_o : 8'hzz;
    always @ (negedge clk) begin
    if(write condition) begin
    USBBUS_o <= outbus;
    USBBUS_oe <= 1'b1;
    end
    else begin
    USBBUS_o <= 8'hxx;
    USBBUS_oe <= 1'b0;
    end
    if (read condition) begin
    inbus <= USBBUS_i;
    end
    end
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    I rewrote my code as:

    output [7:0] USBBUS;

    wire [7:0] USBBUS;

    reg [7:0] outbus;

    wire [7:0] inbus;

    always @(negedge clk) begin

    if ((TXE == 0)) begin

    USBBUS <= outbus;

    end

    else if ((RXF == 0)) begin

    inbus <= USBBUS;

    end

    else begin

    USBBUS <= 8'hz;

    end

    end

    Now my error is: error (10137): verilog hdl procedural assignment error at testusb.v(344): object "usbbus" on left-hand side of assignment must have a variable data type

    Any suggestions?