diff --git a/ossc.qsf b/ossc.qsf
index cc59c9f..533bb81 100644
--- a/ossc.qsf
+++ b/ossc.qsf
@@ -218,7 +218,7 @@ set_global_assignment -name ENABLE_SIGNALTAP OFF
set_global_assignment -name USE_SIGNALTAP_FILE output_files/ossc_la.stp
set_global_assignment -name FITTER_EFFORT "AUTO FIT"
-set_global_assignment -name SEED 2
+set_global_assignment -name SEED 4
diff --git a/rtl/pll_2x.ppf b/rtl/pll_2x.ppf
index df82f86..3d83c85 100644
--- a/rtl/pll_2x.ppf
+++ b/rtl/pll_2x.ppf
@@ -10,6 +10,7 @@
+
diff --git a/rtl/pll_2x.v b/rtl/pll_2x.v
index 303d5eb..b84a7be 100644
--- a/rtl/pll_2x.v
+++ b/rtl/pll_2x.v
@@ -45,6 +45,7 @@ module pll_2x (
scanclk,
scanclkena,
scandata,
+ activeclock,
c0,
c1,
locked,
@@ -59,6 +60,7 @@ module pll_2x (
input scanclk;
input scanclkena;
input scandata;
+ output activeclock;
output c0;
output c1;
output locked;
@@ -76,34 +78,36 @@ module pll_2x (
// synopsys translate_on
`endif
- wire [4:0] sub_wire0;
- wire sub_wire3;
+ wire sub_wire0;
+ wire [4:0] sub_wire1;
wire sub_wire4;
wire sub_wire5;
- wire sub_wire8 = inclk1;
- wire [1:1] sub_wire2 = sub_wire0[1:1];
- wire [0:0] sub_wire1 = sub_wire0[0:0];
- wire c0 = sub_wire1;
- wire c1 = sub_wire2;
- wire locked = sub_wire3;
- wire scandataout = sub_wire4;
- wire scandone = sub_wire5;
- wire sub_wire6 = inclk0;
- wire [1:0] sub_wire7 = {sub_wire8, sub_wire6};
+ wire sub_wire6;
+ wire sub_wire9 = inclk1;
+ wire activeclock = sub_wire0;
+ wire [1:1] sub_wire3 = sub_wire1[1:1];
+ wire [0:0] sub_wire2 = sub_wire1[0:0];
+ wire c0 = sub_wire2;
+ wire c1 = sub_wire3;
+ wire locked = sub_wire4;
+ wire scandataout = sub_wire5;
+ wire scandone = sub_wire6;
+ wire sub_wire7 = inclk0;
+ wire [1:0] sub_wire8 = {sub_wire9, sub_wire7};
altpll altpll_component (
.areset (areset),
.clkswitch (clkswitch),
.configupdate (configupdate),
- .inclk (sub_wire7),
+ .inclk (sub_wire8),
.scanclk (scanclk),
.scanclkena (scanclkena),
.scandata (scandata),
- .clk (sub_wire0),
- .locked (sub_wire3),
- .scandataout (sub_wire4),
- .scandone (sub_wire5),
- .activeclock (),
+ .activeclock (sub_wire0),
+ .clk (sub_wire1),
+ .locked (sub_wire4),
+ .scandataout (sub_wire5),
+ .scandone (sub_wire6),
.clkbad (),
.clkena ({6{1'b1}}),
.clkloss (),
@@ -147,7 +151,7 @@ module pll_2x (
altpll_component.lpm_type = "altpll",
altpll_component.operation_mode = "NORMAL",
altpll_component.pll_type = "AUTO",
- altpll_component.port_activeclock = "PORT_UNUSED",
+ altpll_component.port_activeclock = "PORT_USED",
altpll_component.port_areset = "PORT_USED",
altpll_component.port_clkbad0 = "PORT_UNUSED",
altpll_component.port_clkbad1 = "PORT_UNUSED",
@@ -205,7 +209,7 @@ endmodule
// ============================================================
// CNX file retrieval info
// ============================================================
-// Retrieval info: PRIVATE: ACTIVECLK_CHECK STRING "0"
+// Retrieval info: PRIVATE: ACTIVECLK_CHECK STRING "1"
// Retrieval info: PRIVATE: BANDWIDTH STRING "1.000"
// Retrieval info: PRIVATE: BANDWIDTH_FEATURE_ENABLED STRING "1"
// Retrieval info: PRIVATE: BANDWIDTH_FREQ_UNIT STRING "MHz"
@@ -316,7 +320,7 @@ endmodule
// Retrieval info: CONSTANT: LPM_TYPE STRING "altpll"
// Retrieval info: CONSTANT: OPERATION_MODE STRING "NORMAL"
// Retrieval info: CONSTANT: PLL_TYPE STRING "AUTO"
-// Retrieval info: CONSTANT: PORT_ACTIVECLOCK STRING "PORT_UNUSED"
+// Retrieval info: CONSTANT: PORT_ACTIVECLOCK STRING "PORT_USED"
// Retrieval info: CONSTANT: PORT_ARESET STRING "PORT_USED"
// Retrieval info: CONSTANT: PORT_CLKBAD0 STRING "PORT_UNUSED"
// Retrieval info: CONSTANT: PORT_CLKBAD1 STRING "PORT_UNUSED"
@@ -363,6 +367,7 @@ endmodule
// Retrieval info: CONSTANT: WIDTH_CLOCK NUMERIC "5"
// Retrieval info: CONSTANT: scan_chain_mif_file STRING "pll_2x.hex"
// Retrieval info: USED_PORT: @clk 0 0 5 0 OUTPUT_CLK_EXT VCC "@clk[4..0]"
+// Retrieval info: USED_PORT: activeclock 0 0 0 0 OUTPUT GND "activeclock"
// Retrieval info: USED_PORT: areset 0 0 0 0 INPUT GND "areset"
// Retrieval info: USED_PORT: c0 0 0 0 0 OUTPUT_CLK_EXT VCC "c0"
// Retrieval info: USED_PORT: c1 0 0 0 0 OUTPUT_CLK_EXT VCC "c1"
@@ -384,6 +389,7 @@ endmodule
// Retrieval info: CONNECT: @scanclk 0 0 0 0 scanclk 0 0 0 0
// Retrieval info: CONNECT: @scanclkena 0 0 0 0 scanclkena 0 0 0 0
// Retrieval info: CONNECT: @scandata 0 0 0 0 scandata 0 0 0 0
+// Retrieval info: CONNECT: activeclock 0 0 0 0 @activeclock 0 0 0 0
// Retrieval info: CONNECT: c0 0 0 0 0 @clk 0 0 1 0
// Retrieval info: CONNECT: c1 0 0 0 0 @clk 0 0 1 1
// Retrieval info: CONNECT: locked 0 0 0 0 @locked 0 0 0 0
diff --git a/rtl/pll_config_default_data.mif b/rtl/pll_config_default_data.mif
new file mode 100644
index 0000000..9f68d5e
--- /dev/null
+++ b/rtl/pll_config_default_data.mif
@@ -0,0 +1,174 @@
+-- Copyright (C) 2017 Intel Corporation. All rights reserved.
+-- Your use of Intel Corporation's design tools, logic functions
+-- and other software and tools, and its AMPP partner logic
+-- functions, and any output files from any of the foregoing
+-- (including device programming or simulation files), and any
+-- associated documentation or information are expressly subject
+-- to the terms and conditions of the Intel Program License
+-- Subscription Agreement, the Intel Quartus Prime License Agreement,
+-- the Intel FPGA IP License Agreement, or other applicable license
+-- agreement, including, without limitation, that your use is for
+-- the sole purpose of programming logic devices manufactured by
+-- Intel and sold by Intel or its authorized distributors. Please
+-- refer to the applicable agreement for further details.
+
+-- MIF file representing initial state of PLL Scan Chain
+-- Device Family: Cyclone IV E
+-- Device Part: -
+-- Device Speed Grade: 8
+-- PLL Scan Chain: Fast PLL (144 bits)
+-- File Name: /home/markus/Code/ossc/rtl/pll_config_default_data.mif
+-- Generated: Wed Oct 9 22:20:06 2019
+
+WIDTH=1;
+DEPTH=144;
+
+ADDRESS_RADIX=UNS;
+DATA_RADIX=UNS;
+
+CONTENT BEGIN
+ 0 : 0; -- Reserved Bits = 0 (1 bit(s))
+ 1 : 0; -- Reserved Bits = 0 (1 bit(s))
+ 2 : 0; -- Loop Filter Capacitance = 0 (2 bit(s)) (Setting 0)
+ 3 : 0;
+ 4 : 1; -- Loop Filter Resistance = 27 (5 bit(s)) (Setting 27)
+ 5 : 1;
+ 6 : 0;
+ 7 : 1;
+ 8 : 1;
+ 9 : 0; -- VCO Post Scale = 0 (1 bit(s)) (VCO post-scale divider counter value = 2)
+ 10 : 0; -- Reserved Bits = 0 (5 bit(s))
+ 11 : 0;
+ 12 : 0;
+ 13 : 0;
+ 14 : 0;
+ 15 : 0; -- Charge Pump Current = 1 (3 bit(s)) (Setting 1)
+ 16 : 0;
+ 17 : 1;
+ 18 : 1; -- N counter: Bypass = 1 (1 bit(s))
+ 19 : 0; -- N counter: High Count = 0 (8 bit(s))
+ 20 : 0;
+ 21 : 0;
+ 22 : 0;
+ 23 : 0;
+ 24 : 0;
+ 25 : 0;
+ 26 : 0;
+ 27 : 0; -- N counter: Odd Division = 0 (1 bit(s))
+ 28 : 0; -- N counter: Low Count = 0 (8 bit(s))
+ 29 : 0;
+ 30 : 0;
+ 31 : 0;
+ 32 : 0;
+ 33 : 0;
+ 34 : 0;
+ 35 : 0;
+ 36 : 0; -- M counter: Bypass = 0 (1 bit(s))
+ 37 : 0; -- M counter: High Count = 8 (8 bit(s))
+ 38 : 0;
+ 39 : 0;
+ 40 : 0;
+ 41 : 1;
+ 42 : 0;
+ 43 : 0;
+ 44 : 0;
+ 45 : 0; -- M counter: Odd Division = 0 (1 bit(s))
+ 46 : 0; -- M counter: Low Count = 8 (8 bit(s))
+ 47 : 0;
+ 48 : 0;
+ 49 : 0;
+ 50 : 1;
+ 51 : 0;
+ 52 : 0;
+ 53 : 0;
+ 54 : 0; -- clk0 counter: Bypass = 0 (1 bit(s))
+ 55 : 0; -- clk0 counter: High Count = 8 (8 bit(s))
+ 56 : 0;
+ 57 : 0;
+ 58 : 0;
+ 59 : 1;
+ 60 : 0;
+ 61 : 0;
+ 62 : 0;
+ 63 : 0; -- clk0 counter: Odd Division = 0 (1 bit(s))
+ 64 : 0; -- clk0 counter: Low Count = 8 (8 bit(s))
+ 65 : 0;
+ 66 : 0;
+ 67 : 0;
+ 68 : 1;
+ 69 : 0;
+ 70 : 0;
+ 71 : 0;
+ 72 : 0; -- clk1 counter: Bypass = 0 (1 bit(s))
+ 73 : 0; -- clk1 counter: High Count = 8 (8 bit(s))
+ 74 : 0;
+ 75 : 0;
+ 76 : 0;
+ 77 : 1;
+ 78 : 0;
+ 79 : 0;
+ 80 : 0;
+ 81 : 0; -- clk1 counter: Odd Division = 0 (1 bit(s))
+ 82 : 0; -- clk1 counter: Low Count = 8 (8 bit(s))
+ 83 : 0;
+ 84 : 0;
+ 85 : 0;
+ 86 : 1;
+ 87 : 0;
+ 88 : 0;
+ 89 : 0;
+ 90 : 1; -- clk2 counter: Bypass = 1 (1 bit(s))
+ 91 : 0; -- clk2 counter: High Count = 0 (8 bit(s))
+ 92 : 0;
+ 93 : 0;
+ 94 : 0;
+ 95 : 0;
+ 96 : 0;
+ 97 : 0;
+ 98 : 0;
+ 99 : 0; -- clk2 counter: Odd Division = 0 (1 bit(s))
+ 100 : 0; -- clk2 counter: Low Count = 0 (8 bit(s))
+ 101 : 0;
+ 102 : 0;
+ 103 : 0;
+ 104 : 0;
+ 105 : 0;
+ 106 : 0;
+ 107 : 0;
+ 108 : 1; -- clk3 counter: Bypass = 1 (1 bit(s))
+ 109 : 0; -- clk3 counter: High Count = 0 (8 bit(s))
+ 110 : 0;
+ 111 : 0;
+ 112 : 0;
+ 113 : 0;
+ 114 : 0;
+ 115 : 0;
+ 116 : 0;
+ 117 : 0; -- clk3 counter: Odd Division = 0 (1 bit(s))
+ 118 : 0; -- clk3 counter: Low Count = 0 (8 bit(s))
+ 119 : 0;
+ 120 : 0;
+ 121 : 0;
+ 122 : 0;
+ 123 : 0;
+ 124 : 0;
+ 125 : 0;
+ 126 : 1; -- clk4 counter: Bypass = 1 (1 bit(s))
+ 127 : 0; -- clk4 counter: High Count = 0 (8 bit(s))
+ 128 : 0;
+ 129 : 0;
+ 130 : 0;
+ 131 : 0;
+ 132 : 0;
+ 133 : 0;
+ 134 : 0;
+ 135 : 0; -- clk4 counter: Odd Division = 0 (1 bit(s))
+ 136 : 0; -- clk4 counter: Low Count = 0 (8 bit(s))
+ 137 : 0;
+ 138 : 0;
+ 139 : 0;
+ 140 : 0;
+ 141 : 0;
+ 142 : 0;
+ 143 : 0;
+END;
diff --git a/rtl/scanconverter.v b/rtl/scanconverter.v
index 4891f1b..21bf069 100644
--- a/rtl/scanconverter.v
+++ b/rtl/scanconverter.v
@@ -121,11 +121,13 @@ module scanconverter (
output pll_scandone
);
-//clock-related signals
+//clock-related signals and registers
wire pclk_act;
wire pclk_1x, pclk_2x, pclk_3x, pclk_4x, pclk_5x;
wire [1:0] pclk_mux_sel;
wire pll_lock;
+wire pll_activeclock;
+reg pll_clkswitch;
//RGB signals®isters: 8 bits per component -> 16.7M colors
wire [7:0] R_act, G_act, B_act;
@@ -492,13 +494,14 @@ endcase
pll_2x pll_pclk (
.areset(pll_areset),
- .clkswitch(enable_sc),
+ .clkswitch(pll_clkswitch),
.configupdate(pll_configupdate),
.inclk0(clk27), // set videogen clock to primary (power-on default) since both reference clocks must be running during switchover
.inclk1(PCLK_in), // is the secondary input clock fully compensated?
.scanclk(pll_scanclk),
.scanclkena(pll_scanclkena),
.scandata(pll_scandata),
+ .activeclock(pll_activeclock),
.c0(pclk_2x), // pclk_3x in secondary config
.c1(pclk_5x), // pclk_4x in secondary config
.locked(pll_lock),
@@ -807,6 +810,12 @@ begin
end
end
+// Control PLL reference clock switchover
+always @(posedge clk27)
+begin
+ pll_clkswitch <= (pll_activeclock != enable_sc);
+end
+
//Forward status flag to CPU
assign vsync_flag = ~VSYNC_in_cc_LL;
diff --git a/software/sys_controller/ossc/av_controller.c b/software/sys_controller/ossc/av_controller.c
index 8b76800..dc33154 100644
--- a/software/sys_controller/ossc/av_controller.c
+++ b/software/sys_controller/ossc/av_controller.c
@@ -97,6 +97,7 @@ alt_u32 read_it2(alt_u32 regaddr);
// 8. Compare your MIF/HEX to the captured scan chain and update it accordingly
// 9. Dump the updated scan chain data to an array like below (last 16 bits are 0)
// 10. PLL can be then reconfigured with custom pll_reconfig as shown in program_mode()
+const alt_u32 pll_config_default_data[] = {0x0d806000, 0x00402010, 0x08040220, 0x00004022, 0x00000000};
const alt_u32 pll_config_2x_5x_data[] = {0x0dc06000, 0x00783c11, 0x070180e0, 0x0000180e, 0x00000000};
const alt_u32 pll_config_3x_4x_data[] = {0x0d806000, 0x00301804, 0x02014060, 0x00001406, 0x00000000};
@@ -745,6 +746,11 @@ int init_hw()
sys_ctrl = AV_RESET_N|LCD_BL|SD_SPI_SS_N|LCD_CS_N|REMOTE_EVENT;
IOWR_ALTERA_AVALON_PIO_DATA(PIO_0_BASE, sys_ctrl);
+ // Reload initial PLL config (needed after jtagm_reset_req if config has changed).
+ // Note that test pattern gets restored only if pclk was active before jtagm_reset_req assertion.
+ memcpy((void*)pll_reconfig->pll_config_data.data, pll_config_default_data, sizeof(pll_config_default_data));
+ pll_reconfig->pll_config_status.update = 1;
+
//wait >500ms for SD card interface to be stable
//over 200ms and LCD may be buggy?
usleep(200000);