[pinmux] Add JTAG reset mux
Signed-off-by: Michael Schaffner <msf@opentitan.org>
diff --git a/hw/ip/pinmux/data/pinmux.hjson b/hw/ip/pinmux/data/pinmux.hjson
index 88f245b..9261175 100644
--- a/hw/ip/pinmux/data/pinmux.hjson
+++ b/hw/ip/pinmux/data/pinmux.hjson
@@ -17,6 +17,7 @@
{ protocol: "tlul", direction: "device" }
],
regwidth: "32",
+ scan: "true",
wakeup_list: [
{ name: "aon_wkup_req",
@@ -63,7 +64,7 @@
package: "jtag_pkg"
}
// Testmode signals to AST
- { struct: "dft_strap_test",
+ { struct: "dft_strap_test_req",
type: "uni",
name: "dft_strap_test",
act: "req",
diff --git a/hw/ip/pinmux/data/pinmux.hjson.tpl b/hw/ip/pinmux/data/pinmux.hjson.tpl
index 317b09e..66e72d5 100644
--- a/hw/ip/pinmux/data/pinmux.hjson.tpl
+++ b/hw/ip/pinmux/data/pinmux.hjson.tpl
@@ -29,6 +29,7 @@
{ protocol: "tlul", direction: "device" }
],
regwidth: "32",
+ scan: "true",
wakeup_list: [
{ name: "aon_wkup_req",
diff --git a/hw/ip/pinmux/rtl/pinmux.sv b/hw/ip/pinmux/rtl/pinmux.sv
index 78aa55f..76822db 100644
--- a/hw/ip/pinmux/rtl/pinmux.sv
+++ b/hw/ip/pinmux/rtl/pinmux.sv
@@ -17,6 +17,8 @@
) (
input clk_i,
input rst_ni,
+ // Scan enable
+ input lc_ctrl_pkg::lc_tx_t scanmode_i,
// Slow always-on clock
input clk_aon_i,
input rst_aon_ni,
@@ -152,6 +154,7 @@
) u_pinmux_strap_sampling (
.clk_i,
.rst_ni,
+ .scanmode_i,
// To padring side
.out_padring_o ( {dio_out_o, mio_out_o} ),
.oe_padring_o ( {dio_oe_o , mio_oe_o } ),
diff --git a/hw/ip/pinmux/rtl/pinmux_strap_sampling.sv b/hw/ip/pinmux/rtl/pinmux_strap_sampling.sv
index 2fcc9b3..949ecf5 100644
--- a/hw/ip/pinmux/rtl/pinmux_strap_sampling.sv
+++ b/hw/ip/pinmux/rtl/pinmux_strap_sampling.sv
@@ -12,6 +12,7 @@
) (
input clk_i,
input rst_ni,
+ input lc_ctrl_pkg::lc_tx_t scanmode_i,
// To padring side
output logic [NumIOs-1:0] out_padring_o,
output logic [NumIOs-1:0] oe_padring_o,
@@ -35,12 +36,25 @@
input jtag_pkg::jtag_rsp_t dft_jtag_i
);
+
/////////////////////////////////////
// Life cycle signal synchronizers //
/////////////////////////////////////
lc_ctrl_pkg::lc_tx_t [1:0] lc_hw_debug_en;
lc_ctrl_pkg::lc_tx_t [1:0] lc_dft_en;
+ lc_ctrl_pkg::lc_tx_t [0:0] scanmode;
+
+ prim_lc_sync #(
+ .NumCopies(1),
+ .AsyncOn(0)
+ ) u_por_scanmode_sync (
+ .clk_i(1'b0), // unused clock
+ .rst_ni(1'b1), // unused reset
+ .lc_en_i(scanmode_i),
+ .lc_en_o(scanmode)
+ );
+
prim_lc_sync #(
.NumCopies(2)
) u_prim_lc_sync_rv (
@@ -215,9 +229,20 @@
// Inputs connections
assign jtag_req.tck = in_padring_i[TargetCfg.tck_idx];
assign jtag_req.tms = in_padring_i[TargetCfg.tms_idx];
- assign jtag_req.trst_n = in_padring_i[TargetCfg.trst_idx];
assign jtag_req.tdi = in_padring_i[TargetCfg.tdi_idx];
+ // Note that this resets the selected TAP controller in
+ // scanmode. If the TAP controller needs to be active during
+ // reset, this reset bypass needs to be adapted accordingly.
+ prim_clock_mux2 #(
+ .NoFpgaBufG(1'b1)
+ ) u_rst_por_aon_n_mux (
+ .clk0_i(in_padring_i[TargetCfg.trst_idx]),
+ .clk1_i(rst_ni),
+ .sel_i(scanmode[0] == lc_ctrl_pkg::On),
+ .clk_o(jtag_req.trst_n)
+ );
+
// Input tie-off muxes
for (genvar k = 0; k < NumIOs; k++) begin : gen_input_tie_off
if (k == TargetCfg.tck_idx ||
diff --git a/hw/top_earlgrey/ip/pinmux/data/autogen/pinmux.hjson b/hw/top_earlgrey/ip/pinmux/data/autogen/pinmux.hjson
index 801c5e3..ed94b5e 100644
--- a/hw/top_earlgrey/ip/pinmux/data/autogen/pinmux.hjson
+++ b/hw/top_earlgrey/ip/pinmux/data/autogen/pinmux.hjson
@@ -25,6 +25,7 @@
{ protocol: "tlul", direction: "device" }
],
regwidth: "32",
+ scan: "true",
wakeup_list: [
{ name: "aon_wkup_req",
diff --git a/hw/top_earlgrey/rtl/autogen/top_earlgrey.sv b/hw/top_earlgrey/rtl/autogen/top_earlgrey.sv
index 36d7832..be011ea 100644
--- a/hw/top_earlgrey/rtl/autogen/top_earlgrey.sv
+++ b/hw/top_earlgrey/rtl/autogen/top_earlgrey.sv
@@ -1715,6 +1715,7 @@
.dio_oe_o,
.dio_in_i,
+ .scanmode_i,
// Clock and reset connections
.clk_i (clkmgr_aon_clocks.clk_io_div4_powerup),