I I am using TINYFPGA BX for the first time. I have questions


#1

I am testing a tinyFPGA BX and tried to run an example that blinks the LED through a tool called ATOM.

link : https://tinyfpga.com/bx/guide.html

16MHz clock

set_io --warn-no-port CLK B2 # input

  1. The code dose not have the frequency setting, so I wonder why the above code works at 16Mhz.

  2. I want to program the code that uses 50Mhz clk on the FPGA through ATOM.
    However, the example does not include SDC file,
    so I wonder how CLK works and wonder how to change CLK to 50Mhz.

  3. I want to add a pull up option for i2c communication, but I wonder how to add it.
    Attach the code below with the error code

set_io --warn-no-port SCL B6 -res_pul up
set_io --warn-no-port SDA A6 -res_pul up

  1. If you use tools such as Quartus, other modules are automatically set as sub-modules when you set the top module, and I wonder how the TOP module settings are set in ATOM.
    image
    Thank you for reading : )

#2
  1. resolved
    set_io -pullup yes SCL B6 #-res_pul up
    set_io -pullup yes SDA A6 #-res_pul up

#3

The hardware clock on the TinyFPGA BX is locked at 16MHz. This is essentially unchangeable, and is set by the oscillator circuitry.

That’s not quite the end of the story though. There’s a trick you can use internally in the FPGA to scale the clock. This is known as a PLL (Phase Locked Loop). A PLL allows you to take a clock at a certain frequency and scale it (either up or down).

The open source tools for the ICE40 come with a tool called icepll which can be used to generate the appropriate configuration for the PLL that comes built in to the ICE40 chips.

For example, if you wanted to generate a 50MHz clock for use inside the FPGA from the 16MHz external clock, you could use icepll to create a verilog module:

$ icepll -i 16 -o 50 -m -f 50mhz.v
F_PLLIN:    16.000 MHz (given)
F_PLLOUT:   50.000 MHz (requested)
F_PLLOUT:   50.000 MHz (achieved)

FEEDBACK: SIMPLE
F_PFD:   16.000 MHz
F_VCO:  800.000 MHz

DIVR:  0 (4'b0000)
DIVF: 49 (7'b0110001)
DIVQ:  4 (3'b100)

FILTER_RANGE: 1 (3'b001)

PLL configuration written to: 50mhz.v
$ cat 50mhz.v 
/**
 * PLL configuration
 *
 * This Verilog module was generated automatically
 * using the icepll tool from the IceStorm project.
 * Use at your own risk.
 *
 * Given input frequency:        16.000 MHz
 * Requested output frequency:   50.000 MHz
 * Achieved output frequency:    50.000 MHz
 */

module pll(
	input  clock_in,
	output clock_out,
	output locked
	);

SB_PLL40_CORE #(
		.FEEDBACK_PATH("SIMPLE"),
		.DIVR(4'b0000),		// DIVR =  0
		.DIVF(7'b0110001),	// DIVF = 49
		.DIVQ(3'b100),		// DIVQ =  4
		.FILTER_RANGE(3'b001)	// FILTER_RANGE = 1
	) uut (
		.LOCK(locked),
		.RESETB(1'b1),
		.BYPASS(1'b0),
		.REFERENCECLK(clock_in),
		.PLLOUTCORE(clock_out)
		);

endmodule

… as you can see the generated module takes the input clock (you should provide the 16MHz clock), and provides an output clock and a signal to let you know when the output clock is actually stable.

Because of the way that PLL’s work you might find that you can’t accurately generate all frequencies, but for most cases you should be able to get close.

Hope that helps some.

D.