Article ID: 000085194 Content Type: Troubleshooting Last Reviewed: 06/12/2013

Why does the Transceiver Reconfiguration Controller's reconfig_busy output get stuck high after a reset?

Environment

  • Arria® V GZ FPGA
  • Stratix® V GX FPGA
  • Quartus® II Subscription Edition
  • BUILT IN - ARTICLE INTRO SECOND COMPONENT
    Description

    The transceiver reconfiguration \'reconfig_busy\' output port may become stuck, asserted high after a reset assertion.  The transceiver channels connected to the affected reconfiguration controller may also become stuck in reset.  The \'reconfig_busy\' output port remains stuck even after resetting the reconfiguration controller; only reprogramming the device can resolve the issue.

    This symptom can be caused by the internal reset structure of the Transceiver Reconfiguration controller.  An asynchronous reset assertion to the logic driving the address bus of an M20K RAM can cause asynchronous logic propagation.  This can cause multiple address lines into the M20K to become asserted simultaneously, which can cause charge sharing between bit cells, corrupting the contents of the M20K. 

    This corruption affects the Stratix® V and Arria® V GZ devices Transceiver Reconfiguration Controller because it contains a Nios® II processor that is used for PMA calibration, and the processor\'s program code is stored in M20K RAM.  If the corruption occurs within the Nios® II program memory, this can cause the processor to lock up, resulting in the reconfig_busy output port becoming stuck asserted high.  Recovery from this situation is only possible by reprogramming the device, as M20K contents are only loaded during device programming.

    Resolution

    The fix for this issue will change the internal reset controller and reset structure of the Transceiver Reconfiguration Controller to use synchronous resets, as well as pre-emptively deasserting the M20K clock_enable port during a reset condition. 

    The fix will be available in a future version of the Quartus® II software.  A patch can be provided for earlier versions of the Quartus II software by submitting a service request in mySupport.  If a solution is required immediately, the fix can be manually applied using the following instructions.

    There are 9 files that need to be added or modified:

    • altera_reset_controller_early_ce_mod.v (add)
    • altera_reset_synchronizer_early_ce_mod.v (add)
    • QIP file associated with the Transceiver Reconfiguration Controller (modify)
    • alt_xcvr_reconfig.sv (modify)
    • alt_xcvr_reconfig_soc.sv (modify)
    • alt_xcvr_reconfig_cpu.v (modify)
    • alt_xcvr_reconfig_cpu_ram.sv (modify)
    • sv_xrbasic_lif_csr.sv (modify)
    • sv_xcvr_reconfig_mif_avmm.sv (modify)

    These 9 files should be located in the directory where the Transceiver Reconfiguration Controller was generated. 


    Download altera_reset_controller_early_ce_mod.v and place it in the directory where the Transceiver Reconfiguration files are kept:

    Download altera_reset_synchronizer_early_ce_mod.v and place it in the directory where the Transceiver Reconfiguration files are kept:

    In order to add these two files to your design, locate and modify the .qip file associated with the Transceiver Reconfiguration Controller instance and add the following two lines to the file:
    set_global_assignment -library "LIBRARY_NAME" -name VERILOG_FILE [file join $::quartus(qip_path) "LIBRARY_PATH/altera_reset_controller_early_ce_mod.v"]
    set_global_assignment -library "LIBRARY_NAME" -name VERILOG_FILE [file join $::quartus(qip_path) "LIBRARY_PATH/altera_reset_synchronizer_early_ce_mod.v"]

    In the above two lines, modify LIBRARY_NAME and LIBRARY_PATH to match the other entries in the Transceiver Reconfiguration Controller’s .qip file.

    For alt_xcvr_reconfig.sv, make the following modifications:

    • Locate the alt_xcvr_resync module instantiation, and reverse the connections between the ‘d’ and ‘reset’ ports.  Once modified, the instantiation should look like the following:

      alt_xcvr_resync #(
        .INIT_VALUE (1)
      ) inst_reconfig_reset_sync (
        .clk    (mgmt_clk_clk       ),
        .d      (mgmt_rst_reset     ),
        .reset  (1\'b0               ),
        .q      (r_mgmt_rst_reset   )
      );

    For alt_xcvr_reconfig_soc.sv, make the following modifications:

    Add the following wire definition near the top of the module:

    wire cpu_reset_req;

    Locate the instantiation of the alt_xcvr_reconfig_cpu module and add the following port:

    .ram_ce (cpu_reset_req),

    Locate the instantiation of the alt_xcvr_reconfig_cpu_ram module and add the following port:

    .ram_ce (cpu_reset_req),

    For alt_xcvr_reconfig_cpu.v, make the following modifications:

    • Add the following port to the top level:

    output wire ram_ce,

    • Add the following code to the module:

    wire m20k_gate;
    wire altera_ram_clock_enable;
    assign altera_ram_clock_enable = ~ m20k_gate;
    assign ram_ce = altera_ram_clock_enable;

    • Find the instantiation of altera_reset_controller and change this to an instantiation of altera_reset_controller_early_ce_mod.  Add the m20k_gate port to this instantiation, and connect it to the m20k_gate signal.  After making these modifications, the instantiation should look like the following:

     altera_reset_controller_early_ce_mod #(
      .NUM_RESET_INPUTS        (1),
      .OUTPUT_RESET_SYNC_EDGES ("deassert"),
      .SYNC_DEPTH              (2)
     ) rst_controller (
      .reset_in0  (~reset_reset_n),            // reset_in0.reset
      .clk        (clk_clk),                   //       clk.clk
      .reset_out  (reconfig_ctrl_reset_reset), // reset_out.reset
      .m20k_gate  (m20k_gate),
      .reset_in1  (1\'b0),                      // (terminated)
      .reset_in2  (1\'b0),                      // (terminated)
      .reset_in3  (1\'b0),                      // (terminated)
      .reset_in4  (1\'b0),                      // (terminated)
      .reset_in5  (1\'b0),                      // (terminated)
      .reset_in6  (1\'b0),                      // (terminated)
      .reset_in7  (1\'b0),                      // (terminated)
      .reset_in8  (1\'b0),                      // (terminated)
      .reset_in9  (1\'b0),                      // (terminated)
      .reset_in10 (1\'b0),                      // (terminated)
      .reset_in11 (1\'b0),                      // (terminated)
      .reset_in12 (1\'b0),                      // (terminated)
      .reset_in13 (1\'b0),                      // (terminated)
      .reset_in14 (1\'b0),                      // (terminated)
      .reset_in15 (1\'b0)                       // (terminated)
     );

    For the alt_xcvr_reconfig_cpu_ram.sv file, make the following modifications:

    • Add the following input port:

    input ram_ce,

    • Find the altsyncram instantiation and modify the clocken0 port to connect it to the new ram_ce input port:

    .clocken0       (ram_ce),

    • Modify the defparam clock_enable_input/output_a/b definitions as follows:

    altsyncram_component.clock_enable_input_a = "NORMAL",
    altsyncram_component.clock_enable_input_b = "NORMAL",
    altsyncram_component.clock_enable_output_a = "NORMAL",
    altsyncram_component.clock_enable_output_b = "NORMAL",

    For the sv_xrbasic_lif_csr.sv file, make the following modifications:

    • Locate the sequential always block that controls the logical channel address.  This always block can be identified by the comment “// logical channel register” above it.  Remove the reset condition from the sensitivity list.  Once modified, the start of the always block should look like the following:

    // logical channel register
    always @(posedge reconfig_clk) begin
      if (reset == 1) begin
      …

    • Locate the sequential always block that controls the native reconfig address register.  This always block can be identified by the comment “// native reconfig address register, can be interpretted as channel offset address, or physical address” above it.  Remove the reset condition from the sensitivity list.  Once modified, the start of the always block should look like the following:

    // native reconfig address register, can be interpretted as channel offset address, or physical address
    always @(posedge reconfig_clk ) begin
      if (reset == 1) begin
      …

    For the sv_xcvr_reconfig_mif_avmm.sv file, this change is only necessary if channel or PLL reconfiguration is enabled in the Transceiver Reconfiguration Controller Megawizard GUI.  Make the following modification:

    • Locate the sequential always block that has the “// Avalon output and internal storage” comment above it and remove the reset condition from the sensitivity list.  Once modified, the start of the always block should look like the following:

    // Avalon output and internal storage
    always @(posedge clk )
    begin
      if (reset) begin
      …

    Once all these changes have been made, your design will need to be recompiled.

    Disclaimer

    1

    All postings and use of the content on this site are subject to Intel.com Terms of Use.