GT核内部自动复位状态机

这篇具有很好参考价值的文章主要介绍了GT核内部自动复位状态机。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

前言:

明确设计思路,精准定位问题,对于我们后期理解迭代工程有很大的帮助。

这就是我们常说的40%设计,20%编写和剩下的40%时间进行调试优化

今天为大家带来的是通过理解手册和GT核复位状态机源码,解决GT核接收端复位完成标识位一直为低的原因。

问题:

由于CMOS经过配置后的数据输出只能观察到VS和HS,而四路视频流则通过GTP接口传输至FPGA,无法直接进行ILA抓取;

目前的设计是通过配置GT核后生成官方demo,进行更改从而接收数据流,通过观察rx_data来反映CMOS传输像素;

通过问题定位,发现本应该自动复位的GT核出现了RX_RESETDONE信号一直为低,即RX复位未完成

AMD问题贴

gt rxdata数据全0,FPGA数字图像采集与处理,fpga开发

UG482 GTP Transceivers:

Reset and Initialization:

GTP收发器必须在FPGA器件上电和配置后进行初始化,然后才能使用。GTP收发器的发射器(TX)和接收器(RX)可以独立并行初始化,如图2-11所示。GTP 收发器的 TX 和 RX 初始化包括两个步骤:

  1. 初始化关联的PLL驱动TX/RX
  2. 初始化 TX 和 RX 数据路径 (PMA + PCS)

GTP 收发器的 TX 和 RX 可以接收来自 PLL0 或 PLL1 的时钟。TX 和 RX 使用的关联 PLL (PLL0 /PLL1) 必须先初始化,然后再初始化 TX 和 RX。TX和RX使用的任何PLL都是单独复位的,其复位操作完全独立于所有TX和RX复位。TX 和 RX 数据路径只有在关联的 PLL 锁定后才能初始化。

gt rxdata数据全0,FPGA数字图像采集与处理,fpga开发

通过官方手册可以发现只有当FPGA上电后,先进行锁相环复位,后对RX/TX进行复位,RX/TX RESETDONE复位完成标识位才会拉高。

PLL Reset:

PLL(PLL0 和 PLL1)必须使用 PLL0PD 和 PLL1PD 端口关断,直到在逻辑中检测到参考时钟边沿。取消 PLL0PD/PLL1PD 后,必须复位PLL0 和 PLL1 才能使用。每个GTPE2_COMMON有六个专用端口用于PLL复位。如图2-12所示,PLL0RESET是复位PLL0的输入,PLL1RESET是复位PLL1的输入。PLL0LOCK 和 PLL1LOCK 是指示重置过程已完成的输出。这种异步PLL0RESET和PLL1RESET脉冲宽度的准则是参考时钟的一个周期。由内部 GTP 生成的实际 PLL0 和 PLL1 复位。

收发器电路比PLL0RESET长得多,PLL1RESET 高脉冲持续时间。PLL锁定所需的时间受几个因素的影响,例如带宽设置和时钟频率。

gt rxdata数据全0,FPGA数字图像采集与处理,fpga开发

仿真模拟:

大家可以配置GT核,然后右键Open IP Example Design生成官方demo,通过观察仿真理解GT核自动复位的时序。

gt rxdata数据全0,FPGA数字图像采集与处理,fpga开发

  1. 通过观察可以发现仿真一段时间后,gt0_pll0reset_out拉高,同时可以看到gt0_pll0reflost_in由1变为0(该信号存在问题,大家都知道产生复位后频率丢失reflost应该拉高,等待频率稳定后该信号再拉低,后续通过上板也会纠正该信号的仿真)。
  2. 等待复位一段时间后,gt0_pll0lock_in拉高,表示锁相环频率信号稳定,此时已经完成锁相环复位工作。
  3. 等待一段时间后,首先gt0_rx_mmcm_reset_out信号拉低,然后gt0_rx_mmcm_lock_in拉高,从而影响slvsec_gtp_GT_USRCLK_SOURCE模块产生gt_rxusrclk和gt_rxusrclk2时钟信号。
  4. 由用户控制gt0_data_valid_in数据有效标识信号,最终通过观察gt0_rxdata_out可以发现高速数据流。

源码分析:

大家看完复位相关的手册和仿真模拟可能觉得太难了,毕竟手册上还提到了顺序和单一两种复位方式,好在官方IP核支持通过软复位进行自动复位,实现一条龙服务,快速上手该IP核。


首先我们通过波形图状态机帮助大家理解GT核自动复位的过程,避免来自源码的恐惧。

gt rxdata数据全0,FPGA数字图像采集与处理,fpga开发

TIME(ns)是状态机执行的时间点,目前该GT核仅使用RX端,所以RX_PLL0_USED为TRUE,TX_PLL0_USED为FALSE。

  1. SOFT_RESET拉低后,状态机开始运转,起始为INIT state,然后需要计数600ns后拉高init_wait_done信号。
  2. 检测到init_wait_done信号拉高后,复位状态机跳转至ASSERT_ALL_RESETS state
  3. 在ASSERT state下,初始时refclk_lost为0,标识参考时钟未丢失,于是产生核内部产生PLL0_RESET,并将pll_reset_assert信号拉高。
  4. PLL0_RESET拉高的同时,关于锁相环复位的pll0_lock_sync拉低,refclk_lost信号拉高。
  5. 检测到pll0_lock_sync拉低,复位状态机跳转至WAIT_FOR_PLL_LOCK state
  6. 从时序图也可以看出,等待了大约10_000ns后,复位状态机跳转至RELEASE_PLL_RESET state
  7. 在改状态下,检测到pll0_lock_sync拉高,即锁相环复位完成,频率稳定,复位状态机跳转至VERIFY_RECCLK_STABLE state
  8. 该状态下,gtrxreset_i信号由高变低,即复位和初始化的第二步,RX PMA和RX PCS复位将完成。
  9. 由时序图可知,等待21_000ns后,复位状态机跳转至RELEASE_MMCM_RESET state
  10. 在MMCM状态下,当检测到rxpmaresetdone_sync信号拉高后,mmcm_reset_i信号拉低,至此将产生gt_rxusrclk/2时钟信号。

以下便是GT核内部关于复位状态机的源码,我们所绘制的时序图也是通过分析源码帮助大家理解,大家可以通过查看源码逻辑加深印象。

always @(posedge STABLE_CLOCK) 
  begin
      if (SOFT_RESET == 1'b1)
      //if (SOFT_RESET == 1'b1 || (rx_state != INIT && rx_state != ASSERT_ALL_RESETS && refclk_lost == 1'b1))
      begin 
        rx_state                <= `DLY  INIT;
        RXUSERRDY               <= `DLY  1'b0;
        gtrxreset_i             <= `DLY  1'b0;
        mmcm_reset_i            <= `DLY  1'b0;
        rx_fsm_reset_done_int   <= `DLY  1'b0;
        PLL0_RESET              <= `DLY  1'b0;
        PLL1_RESET              <= `DLY  1'b0;
        pll_reset_asserted      <= `DLY  1'b0;
        reset_time_out          <= `DLY  1'b1;
        retry_counter_int       <= `DLY  0;
        run_phase_alignment_int <= `DLY  1'b0;
        check_tlock_max         <= `DLY  1'b0;
        RESET_PHALIGNMENT       <= `DLY  1'b1;
        recclk_mon_count_reset  <= `DLY  1'b1;
      end
      else
      begin
        
        case (rx_state)
           INIT :
           begin 
            //Initial state after configuration. This state will be left after
            //approx. 500 ns and not be re-entered. 
            if (init_wait_done == 1'b1)
              rx_state  <= `DLY  ASSERT_ALL_RESETS;
           end

           ASSERT_ALL_RESETS :
           begin 
            //This is the state into which the FSM will always jump back if any
            //time-outs will occur. 
            //The number of retries is reported on the output RETRY_COUNTER. In 
            //case the transceiver never comes up for some reason, this machine 
            //will still continue its best and rerun until the FPGA is turned off
            //or the transceivers come up correctly.
            if (RX_PLL0_USED == "TRUE" )
             begin
              if ((pll_reset_asserted == 1'b0 && refclk_lost == 1'b0))
              begin
                PLL0_RESET          <= `DLY  1'b1;
                pll_reset_asserted  <= `DLY  1'b1;
              end
              else
                PLL0_RESET          <= `DLY  1'b0;
             end 
            else 
            begin
              if ((pll_reset_asserted == 1'b0 && refclk_lost == 1'b0))
              begin
                PLL1_RESET          <= `DLY  1'b1;
                pll_reset_asserted  <= `DLY  1'b1;
              end
              else
                PLL1_RESET          <= `DLY  1'b0;
            end
            RXUSERRDY               <= `DLY  1'b0;
            gtrxreset_i             <= `DLY  1'b1;
            mmcm_reset_i            <= `DLY  1'b1;
            run_phase_alignment_int <= `DLY  1'b0;    
            RESET_PHALIGNMENT       <= `DLY  1'b1;
            check_tlock_max         <= `DLY  1'b0;
            recclk_mon_count_reset  <= `DLY  1'b1;
            if ((RX_PLL0_USED == "TRUE" &&  pll0lock_sync == 1'b0 && pll_reset_asserted) ||
               (RX_PLL0_USED == "FALSE" && pll1lock_sync == 1'b0 && pll_reset_asserted ))
           begin
              rx_state              <= `DLY  WAIT_FOR_PLL_LOCK;
              reset_time_out        <= `DLY  1'b1;
           end 
           end           
           
           WAIT_FOR_PLL_LOCK :
           begin
              if(wait_time_done)
                 rx_state        <= `DLY RELEASE_PLL_RESET;  
           end     
 
           RELEASE_PLL_RESET : 
           begin
            //PLL-Reset of the GTX gets released and the time-out counter
            //starts running.
            pll_reset_asserted  <= `DLY  1'b0;
            reset_time_out      <= `DLY  1'b0;
            
            if ((RX_PLL0_USED == "TRUE"  && TX_PLL0_USED == "FALSE" && pll0lock_sync == 1'b1) ||
                (RX_PLL0_USED == "FALSE" && TX_PLL0_USED == "TRUE"  && pll1lock_sync == 1'b1)) 
            begin 
              rx_state                <= `DLY  VERIFY_RECCLK_STABLE;
              reset_time_out          <= `DLY  1'b1;
              recclk_mon_count_reset  <= `DLY  1'b0;
            end
            else if ((RX_PLL0_USED == "TRUE"  && pll0lock_sync == 1'b1) ||
                     (RX_PLL0_USED == "FALSE" && pll1lock_sync == 1'b1)) 
            begin 
              rx_state                <= `DLY  VERIFY_RECCLK_STABLE;
              reset_time_out          <= `DLY  1'b1;
              recclk_mon_count_reset  <= `DLY  1'b0;
            end
           
            if (time_out_2ms == 1'b1) 
            begin
              if (retry_counter_int == MAX_RETRIES) 
                // If too many retries are performed compared to what is specified in 
                // the generic, the counter simply wraps around.
                retry_counter_int <= `DLY  0;
              else
              begin
                retry_counter_int <= `DLY  retry_counter_int + 1;
              end
              rx_state            <= `DLY  ASSERT_ALL_RESETS; 
            end            
           end

           VERIFY_RECCLK_STABLE :
           begin
            //reset_time_out  <= `DLY  '0';
            //Time-out counter is not released in this state as here the FSM
            //does not wait for a certain period of time but checks on the number
            //of retries in the CDR PPM detector. 
            gtrxreset_i <= `DLY  1'b0;
            if (RECCLK_STABLE == 1'b1)
            begin
              rx_state        <= `DLY  RELEASE_MMCM_RESET;
              reset_time_out  <= `DLY  1'b1;
            end           

            if (recclk_mon_restart_count == 2)
            begin
              //If two retries are performed in the CDR "Lock" (=CDR PPM-detector) 
              //the whole initialisation-sequence gets restarted.
              if (retry_counter_int == MAX_RETRIES) 
                // If too many retries are performed compared to what is specified in 
                // the generic, the counter simply wraps around.
                retry_counter_int <= `DLY  0;
              else
              begin
                retry_counter_int <= `DLY  retry_counter_int + 1;
              end 
              rx_state            <= `DLY  ASSERT_ALL_RESETS; 
            end   
           end          
          
           RELEASE_MMCM_RESET :
           begin 
            //Release of the MMCM-reset. Waiting for the MMCM to lock.
            check_tlock_max <= `DLY  1'b1;
            
            if (rxpmaresetdone_sync == 1'b1 )
            begin
            mmcm_reset_i <= `DLY  1'b0;
            reset_time_out  <= `DLY  1'b0;
            end 
        
            if (mmcm_lock_reclocked == 1'b1)
            begin
              rx_state <= `DLY  WAIT_FOR_RXUSRCLK;
              reset_time_out  <= `DLY  1'b1;
            end           
            
            if (time_tlock_max == 1'b1 && reset_time_out  == 1'b0 )
            begin
              if (retry_counter_int == MAX_RETRIES)
                // If too many retries are performed compared to what is specified in 
                // the generic, the counter simply wraps around.
                retry_counter_int <= `DLY  0;
              else
              begin
                retry_counter_int <= `DLY  retry_counter_int + 1;
              end
              rx_state            <= `DLY  ASSERT_ALL_RESETS; 
            end 
           end            
           
           WAIT_FOR_RXUSRCLK :
           begin
              if(wait_time_done)
               rx_state <= `DLY WAIT_RESET_DONE;  
           end  

           WAIT_RESET_DONE :
           
           ......//后续还有几个状态,大家感兴趣可以查看核内部源码slvsec_gtp_TX_STARTUP_FSM

        endcase
      end
  end 

结果展示:

gt rxdata数据全0,FPGA数字图像采集与处理,fpga开发

通过上板波形图大家可以发现,gt_reset拉低后,等待了大概630ns(ILA频率为100MHz,时钟周期10ns),产生了锁相环复位信号,和我们通过观察源码绘制的时序图一致。

【gt0_pll0reset_out】:该复位信号拉高的同时,lock拉低,lost拉高,而不是仿真的那种时序。


至此GT核自动复位已经结束,可以通过各个通道的rxdata捕获到数据了。

gt rxdata数据全0,FPGA数字图像采集与处理,fpga开发文章来源地址https://www.toymoban.com/news/detail-844553.html

到了这里,关于GT核内部自动复位状态机的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • < Python全景系列-2 > Python数据类型大盘点

    欢迎来到我们的系列博客《Python全景系列》!在这个系列中,我们将带领你从Python的基础知识开始,一步步深入到高级话题,帮助你掌握这门强大而灵活的编程语法。无论你是编程新手,还是有一定基础的开发者,这个系列都将提供你需要的知识和技能。 Python作为一门强大且

    2024年02月05日
    浏览(46)
  • Rust中的智能指针:Box<T> Rc<T> Arc<T> Cell<T> RefCell<T> Weak<T>

    智能指针(smart pointers)是一类数据结构,是拥有数据所有权和额外功能的指针。是指针的进一步发展 指针(pointer)是一个包含内存地址的变量的通用概念。这个地址引用,或 ” 指向”(points at)一些其 他数据 。引用以 符号为标志并借用了他们所 指向的值。除了引用数据

    2023年04月20日
    浏览(59)
  • C++ 中 <iterator> <functional> <numeric> 库好用的函数

    简述:迭代器省代码用的。 std::advance 记忆方法:advance-前进。 形如: advance(it, step) ,表示 it 迭代器自增 step 步。 实现类似于: 或 std::next std::prev 记忆方法:自己问英语老师。 形如 next(it, n) 及 prev(it, n) ,默认 n = 1 ,表示迭代器前移、后移 n 位。 为 std::advance 的变体,区

    2024年02月05日
    浏览(66)
  • Java笔记(16) Collection集合-->Set集合-->HashSet

    Set是无序集合(添加和取出的顺序不一致,但取出的顺序是固定的),没有索引 不允许重复元素,所以最多包含一个null JDK API中Set接口的实现类有: Abstract, ConcurrentHashMap.KeySetView, ConcurrentSkipListSet, CopyOnWriteArraySet, EnumSet, HashSet, JobStateReasons, LinkedHashSet, TreeSet Set接口和List接口一

    2023年04月15日
    浏览(59)
  • 逍遥自在学C语言 | 位运算符>>的高级用法

    在上一篇文章中,我们介绍了 运算符的高级用法,本篇文章,我们将介绍 运算符的一些高级用法。 第一位闪亮登场,有请今后会一直教我们C语言的老师 —— 自在。 第二位上场的是和我们一起学习的小白程序猿 —— 逍遥。 除法运算需要比位移运算需要更多的计算资源,某

    2023年04月16日
    浏览(50)
  • C++学习笔记八:极限和数学运算<limits><cmath>

    1) limits库: 1.1 源文档: https://en.cppreference.com/w/cpp/types/numeric_limits #include limits   1.2 库函数: 函数解释: 对于一个浮点数,lowest表示最小的可表示的负数,min表示最小的可表示的接近0的数,max表示最大的可表示的正数 对于一个有符号整数,min表示可以表示的最小的负数,

    2024年02月05日
    浏览(40)
  • 详解dedecms后台编辑器将回车<br>改为<p>的方法

    DEDECMS编辑器默认回车[确认键]是返回 这样的。 有时候我们需要返回 这样的,今天我们就讲讲后台编辑器将回车将 改为 的有效教程吧。 方法也很简单,首先我们找到dedecms后来台编辑器的配置文件。 所在路径为:/include/ckeditor/config.js 我们打开它,里面有两个字: 替换为 这

    2024年02月02日
    浏览(49)
  • 构建 dotnet&vue 应用镜像->推送到 Nexus 仓库->部署为 k8s 服务实践

    前面分享了 k8s 的部署安装,本篇来点实操,将会把一个 .net core + vue 的项目(zhontai),打包构建成 docker 镜像,推送到 nexus 镜像仓库,并部署到 k8s 中 要实现项目的部署,除了准备要部署的环境(k8s),还需要准备项目所用到的各中间件,本文旨在分享部署的一个整体流程

    2024年02月03日
    浏览(45)
  • 【gt+】RS485详解

    RS232接口标准出现较早。 接口的电平值较高,易损坏接口电路的芯片; 与TTL电平不兼容,需使用电平转换电路与TTL电路连接; 传输速率较低,异步传输时为20Kbps; 接口使用一根信号线和一根信号返回线构成共地的传输形式,容易产生共模干扰,抗噪声干扰性弱; 传输距离有

    2024年02月16日
    浏览(37)
  • GT高速收发器

    GT高速收发器概述 10G以太网子系统通过AXI4-Stream接口提供10gb /s以太网MAC、物理编码子层(PCS)和物理介质附件(PMA)传输和接收功能。该子系统还提供了可选的高精度时间戳功能,兼容IEEE Std 1588-2008(也称为IEEE1588v2)。这适用于10GBASE-R标准。10G以太网MAC子系统框图如图所示。 Xilinx

    2024年02月05日
    浏览(43)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包