Previous journal: | Next journal: |
---|---|
0103-2023-06-26.md | 0105-2023-06-29.md |
Let's call it vga_cursor
. Files:
-
vga_cursor.qpf
: Quartus Prime Project File:DATE = "13:54:50 June 12, 2023" QUARTUS_VERSION = "12.0" # Revisions PROJECT_REVISION = "vga_cursor"
-
vga_cursor.sdc
: Synopsys Design Constraints File. Sets timing constraints/priorities, including clock sources. I need to learn more about this. The main lines that matter in my case are:# Standard 50MHz oscillator on the DE0-Nano board, called CLOCK_50: create_clock -name {CLOCK_50} -period 20.000 -waveform { 0.000 10.000 } [get_ports {CLOCK_50}] # My clock_25 signal derived thru RTL as CLOCK_50 divided by 2: create_generated_clock -name {clock_25} -source [get_ports {CLOCK_50}] -divide_by 2 [get_pins {clock_25|q}] derive_pll_clocks derive_clock_uncertainty
-
vga_cursor.qsf
: Quartus Prime Settings File. Sets FPGA chip type and its pin mapping inc. GPIOs, clock, LEDs, switches, etc. Can be built byDE0_Nano_SystemBuilder.exe
, though a lot of it can probably be recycled.It also specifies the top-level entity and which files are part of the project, for example these lines:
... set_global_assignment -name TOP_LEVEL_ENTITY "vga_cursor" ... set_global_assignment -name VERILOG_FILE vga_cursor.v set_global_assignment -name SDC_FILE vga_cursor.sdc
Click here to see the full contents a file...
#============================================================ # Build by Terasic System Builder #============================================================ set_global_assignment -name FAMILY "Cyclone IV E" set_global_assignment -name DEVICE EP4CE22F17C6 set_global_assignment -name TOP_LEVEL_ENTITY "vga_cursor" set_global_assignment -name ORIGINAL_QUARTUS_VERSION "12.0" set_global_assignment -name LAST_QUARTUS_VERSION "22.1std.0 Lite Edition" set_global_assignment -name PROJECT_CREATION_TIME_DATE "13:54:50 JUNE 12,2023" set_global_assignment -name DEVICE_FILTER_PACKAGE FBGA set_global_assignment -name DEVICE_FILTER_PIN_COUNT 256 set_global_assignment -name DEVICE_FILTER_SPEED_GRADE 6 #============================================================ # CLOCK #============================================================ set_location_assignment PIN_R8 -to CLOCK_50 set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to CLOCK_50 #============================================================ # LED #============================================================ set_location_assignment PIN_A15 -to LED[0] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to LED[0] set_location_assignment PIN_A13 -to LED[1] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to LED[1] set_location_assignment PIN_B13 -to LED[2] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to LED[2] set_location_assignment PIN_A11 -to LED[3] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to LED[3] set_location_assignment PIN_D1 -to LED[4] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to LED[4] set_location_assignment PIN_F3 -to LED[5] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to LED[5] set_location_assignment PIN_B1 -to LED[6] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to LED[6] set_location_assignment PIN_L3 -to LED[7] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to LED[7] #============================================================ # KEY #============================================================ set_location_assignment PIN_J15 -to KEY[0] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to KEY[0] set_location_assignment PIN_E1 -to KEY[1] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to KEY[1] #============================================================ # SW #============================================================ set_location_assignment PIN_M1 -to SW[0] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to SW[0] set_location_assignment PIN_T8 -to SW[1] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to SW[1] set_location_assignment PIN_B9 -to SW[2] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to SW[2] set_location_assignment PIN_M15 -to SW[3] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to SW[3] #============================================================ # GPIO_0, GPIO_0 connect to GPIO Default #============================================================ set_location_assignment PIN_A8 -to gpio0_IN[0] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0_IN[0] set_location_assignment PIN_D3 -to gpio0[0] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[0] set_location_assignment PIN_B8 -to gpio0_IN[1] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0_IN[1] set_location_assignment PIN_C3 -to gpio0[1] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[1] set_location_assignment PIN_A2 -to gpio0[2] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[2] set_location_assignment PIN_A3 -to gpio0[3] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[3] set_location_assignment PIN_B3 -to gpio0[4] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[4] set_location_assignment PIN_B4 -to gpio0[5] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[5] set_location_assignment PIN_A4 -to gpio0[6] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[6] set_location_assignment PIN_B5 -to gpio0[7] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[7] set_location_assignment PIN_A5 -to gpio0[8] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[8] set_location_assignment PIN_D5 -to gpio0[9] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[9] set_location_assignment PIN_B6 -to gpio0[10] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[10] set_location_assignment PIN_A6 -to gpio0[11] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[11] set_location_assignment PIN_B7 -to gpio0[12] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[12] set_location_assignment PIN_D6 -to gpio0[13] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[13] set_location_assignment PIN_A7 -to gpio0[14] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[14] set_location_assignment PIN_C6 -to gpio0[15] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[15] set_location_assignment PIN_C8 -to gpio0[16] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[16] set_location_assignment PIN_E6 -to gpio0[17] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[17] set_location_assignment PIN_E7 -to gpio0[18] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[18] set_location_assignment PIN_D8 -to gpio0[19] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[19] set_location_assignment PIN_E8 -to gpio0[20] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[20] set_location_assignment PIN_F8 -to gpio0[21] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[21] set_location_assignment PIN_F9 -to gpio0[22] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[22] set_location_assignment PIN_E9 -to gpio0[23] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[23] set_location_assignment PIN_C9 -to gpio0[24] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[24] set_location_assignment PIN_D9 -to gpio0[25] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[25] set_location_assignment PIN_E11 -to gpio0[26] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[26] set_location_assignment PIN_E10 -to gpio0[27] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[27] set_location_assignment PIN_C11 -to gpio0[28] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[28] set_location_assignment PIN_B11 -to gpio0[29] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[29] set_location_assignment PIN_A12 -to gpio0[30] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[30] set_location_assignment PIN_D11 -to gpio0[31] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[31] set_location_assignment PIN_D12 -to gpio0[32] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[32] set_location_assignment PIN_B12 -to gpio0[33] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio0[33] #============================================================ # GPIO_1, GPIO_1 connect to GPIO Default #============================================================ set_location_assignment PIN_T9 -to gpio1_IN[0] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1_IN[0] set_location_assignment PIN_F13 -to gpio1[0] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[0] set_location_assignment PIN_R9 -to gpio1_IN[1] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1_IN[1] set_location_assignment PIN_T15 -to gpio1[1] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[1] set_location_assignment PIN_T14 -to gpio1[2] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[2] set_location_assignment PIN_T13 -to gpio1[3] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[3] set_location_assignment PIN_R13 -to gpio1[4] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[4] set_location_assignment PIN_T12 -to gpio1[5] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[5] set_location_assignment PIN_R12 -to gpio1[6] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[6] set_location_assignment PIN_T11 -to gpio1[7] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[7] set_location_assignment PIN_T10 -to gpio1[8] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[8] set_location_assignment PIN_R11 -to gpio1[9] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[9] set_location_assignment PIN_P11 -to gpio1[10] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[10] set_location_assignment PIN_R10 -to gpio1[11] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[11] set_location_assignment PIN_N12 -to gpio1[12] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[12] set_location_assignment PIN_P9 -to gpio1[13] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[13] set_location_assignment PIN_N9 -to gpio1[14] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[14] set_location_assignment PIN_N11 -to gpio1[15] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[15] set_location_assignment PIN_L16 -to gpio1[16] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[16] set_location_assignment PIN_K16 -to gpio1[17] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[17] set_location_assignment PIN_R16 -to gpio1[18] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[18] set_location_assignment PIN_L15 -to gpio1[19] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[19] set_location_assignment PIN_P15 -to gpio1[20] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[20] set_location_assignment PIN_P16 -to gpio1[21] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[21] set_location_assignment PIN_R14 -to gpio1[22] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[22] set_location_assignment PIN_N16 -to gpio1[23] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[23] set_location_assignment PIN_N15 -to gpio1[24] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[24] set_location_assignment PIN_P14 -to gpio1[25] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[25] set_location_assignment PIN_L14 -to gpio1[26] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[26] set_location_assignment PIN_N14 -to gpio1[27] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[27] set_location_assignment PIN_M10 -to gpio1[28] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[28] set_location_assignment PIN_L13 -to gpio1[29] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[29] set_location_assignment PIN_J16 -to gpio1[30] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[30] set_location_assignment PIN_K15 -to gpio1[31] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[31] set_location_assignment PIN_J13 -to gpio1[32] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[32] set_location_assignment PIN_J14 -to gpio1[33] set_instance_assignment -name IO_STANDARD "3.3-V LVTTL" -to gpio1[33] #============================================================ # End of pin assignments by Terasic System Builder #============================================================ set_global_assignment -name VERILOG_FILE vga_cursor.v set_global_assignment -name SDC_FILE vga_cursor.SDC set_global_assignment -name MIN_CORE_JUNCTION_TEMP 0 set_global_assignment -name MAX_CORE_JUNCTION_TEMP 85 set_global_assignment -name POWER_PRESET_COOLING_SOLUTION "23 MM HEAT SINK WITH 200 LFPM AIRFLOW" set_global_assignment -name POWER_BOARD_THERMAL_MODEL "NONE (CONSERVATIVE)" set_global_assignment -name PARTITION_NETLIST_TYPE SOURCE -section_id Top set_global_assignment -name PARTITION_FITTER_PRESERVATION_LEVEL PLACEMENT_AND_ROUTING -section_id Top set_global_assignment -name PARTITION_COLOR 16764057 -section_id Top set_instance_assignment -name PARTITION_HIERARCHY root_partition -to | -section_id Top
-
Before opening the project in Quartus, create a source file matching the
VERILOG_FILE
above, e.g.vga_cursor.v
, and ensure it has the essentials in it, including a module matching theTOP_LEVEL_ENTITY
:`default_nettype none `timescale 1ns / 1ps module vga_cursor( input CLOCK_50, output [7:0] LED, // DE0-Nano LEDs near gpio0. input [1:0] KEY, // DE0-Nano pushbuttons near gpio0. input [3:0] SW, // DE0-Nano DIP switches near gpio1. input [33:0] gpio0, //NOTE: For safety these are currently set as input-only, since Pi Pico connects directly to these. input [1:0] gpio0_IN, inout [33:0] gpio1, //NOTE: inOut; mix of inputs and outputs. input [1:0] gpio1_IN ); reg clock_25; always @(posedge CLOCK_50) clock_25 <= ~clock_25; endmodule
NOTE that in my case:
- It also has the
clock_25
generator that my SDC file refers to. - It defines all of
gpio0
asinput
only (not bi-directional, unlikegpio1
) because I have a device attached (PicoDeo) and I want to make sure there won't accidentally be bus contention.
- It also has the
-
.gitignore
to take care of all the Quartus generated output files and subdirectories:*.rpt *.done *.smsg *.summary *.jdi *.bak *.qws *.pin *.sld *.cdf db/ incremental_db/ output_files/
I've started the vga_cursor
project. For now I can run raybox-bridge and it will
present the mouse cursor data to the FPGA design, which in turn tracks the mouse cursor on the attached
VGA display.
This first version of vga_cursor just reads the cursor data directly from the X and Y GPIOs, without any synchronisation or metastability avoidance. As a result (and as predicted) it can glitch if the cursor happens to move while the screen is being rendered: I'm using registers to track when the raster scan enters and leaves the cursor region instead of comparators, so moving the mouse rapidly exposes some of the glitches.
Next steps:
- There is a 1-clock delay in activating the horizontal cursor register (given it IS a register) so what's the best way to handle that?
- What happens if we get rid of the registers and use comparators instead?
- Try speeding up the PicoDeo data rate, and see if the USB interface can keep up: Maybe 2ms instead of 5?
- Try a simple "sample during vblank" and see how that goes.
- Try metastability avoidance on this.
- Finally, try a resilient and true "write a series of bytes anytime" design: Should it just be clocked and have metastability avoidance?
- Learn how to use FPGA PLLs in Quartus.
- Is there anything of interest to learn about Quartus SRAM Object Files (.sof)?
- Try checking out Matt Venn's VGA Clock and other people's VGA projects to get a better feel for how to use Verilog modules to make actual modular designs with layered VGA output.