上篇文章提到說
由於STA的設計上沒辦法去檢查不同clk domain的兩個register之間timing是否可以滿足所需,
因為沒有一個比較的基準點,
所以需要靠其他的方式來解決這種沒辦法check timing卻又要他保證function work的機制
那麼對於解CDC issue來說
最常見的招數就是2DFF
不過究竟2DFF解決了什麼樣的現象
他真的內涵我也是思考了好一陣子才悟出
這邊就來分享一下
2DFF 顧名思義 為兩級Filpflop的架構
大家都說只需要靠敲兩T Register就可以解掉metastable把訊號拿去用了
但是實際上這個設計只是解掉了metastable並不代表value正確
因此使用上有一個限制就是沒辦法利用2DFF來解Multibits的register
如果本身多bits的register每個bits之間是有關連的則無法使用2DFF的方法解CDC issue
如果還是有這個需求就必須換別種架構來解決
來說明一下上面提到的
2DFF可以解掉metastable卻沒辦法保證value正確,所以multibits reg沒辦法使用是甚麼意思?
大家不都是說因為第1T的訊號不穩但是通常第2T就穩定了嗎
這樣還不保證value正確?
實際上是這樣的
來看一張常看到的例子
clk0和clk1為async的,意味著兩者個clk在toggle的時機互不知道,
由clk0帶動的Q0發起了req後傳遞到D1的input上等待clk1 rising edge去抓Data
但是剛好Q0的toggle點落在了D1的setup/hold check的區間內導致出現了timing violation,也就是metastable的原因
那麼等到再下個clk1的rising edge此時因為Q0的訊號已經維持stable
不再會有發生timing violation的風險,因此clk1的第2次就可以抓到完美的req=1的訊號
Q2即再後面的cycle也成功抓取
因此這張圖看到了幾個重點
所謂的metastable是因為兩著clk不知道對方甚麼時候會變化,
所以只好造著自己自身的clk動作,在下游的reg在準備要抓Data時上游剛好動了,
因此讓下游端的reg發生了timing violation形成了metastable的訊號.
但是第二個cycle因為源頭的req不再改變因此可以完美的滿足Timing check,
因此在2T過後就不太會看到metastable的問題.
不知道大家有沒有發現實際上在說明的時候是有些假設在裡面的,
這些假設也就成為了使用上的Constraint,只要Constraint不滿足則這個架構就廢了
第一個就是
上面所說req不再動,所以下1T可以滿足timing check
也就是說,我們對於req的訊號長度是有一定要求的,
如果我req一直瘋狂跳動那麼這架構肯定不work,
那麼req最短要拉多久呢
從上面的圖中可以看到,我希望在clk1第二個rising edge要取值的時候還要看到是stable的
因此最短最短req需要可以維持3個clk1 edge的長度,這裡的edge部論是rising或falling都算是1個,加起來要是3個就好(上下上 或 下上下)
只要Reg0可以拉住req維持住3個edge的長度(e.g. req拉個3T後才放掉),
或是clk1頻率快於clk0 1.5倍的速度,
則最少最少一定會讓clk1端的reg取到一次stable的value (x=unstable, o=stable)
第二個是不能使用在multibits上
從上圖可以發現說,123張的圖中Q1 toggle起來的時機點各不相同
有些在第一個1個edge就敲到了有些則要在後面的edge才會成功取樣到
假設圖二是reg的bit0 突然則是reg的bit1
Q[1:0] = {0,0} -> {1,1} 對應到的 reg[1:0]的變化會是 {0,1} -> {1,1}
兩個bits抵達的時間各不相同(抵達時間會根據apr時reg擺放位置的不同有所差異),
雖然reg1幫忙消除了metastable的問題,但是卻不保證當T的value是正確的,
有可能因為metastable的關係先取到0下一個cycle在變1
也有可能直接就取到1了
這時候會讓function在抓到{0,1}的時候就拿去用了導致後續的錯誤
但如果你的multibits是彼此之間沒關聯的只是單純把原先個別獨立的訊號merge起來則不在這個限制內
第三個則是Q0必須提供一個夠可靠的訊號,
因此Q0到D1的中間絕對不能有Combinational circuit,
因為組合邏輯並沒有時序的概念從輸入改變到輸出穩定前會不斷的0/1/0/1的跳動
這樣會讓D1取到中間暫態的glitch
如同 [Verilog] 10分鐘看懂ic design的reset 內文提過的
這時因為沒有sta的約束不知道Combinational要何時stable
如果D_in剛好取到glitch則會讓function有錯誤的output
因此最後來總結一下
2DFF最常用來解CDC造成的metastable問題
但是他有一些Constraint
同時也意味著req的performance被限制住了,無法頻繁的一直toggle.
另外如果不知道clkB到底碰到了3個edge了沒,則可靠scenario來控,換算頻率差放慢update req的速度,或是改成ack base的2DFF,讓clkB順利取直後回傳ack給clkA端的req reg告知可以update新的vaule.
<note.>
clk1比clk0快1.5倍的概念在於說
我只要clk1取樣的速度比clk0快就能保證reg0在下次變動之前就能取到一次stable的值
不過1.5這個倍率經過我servey相關的paper後依然沒有找到比較好的rule來說明
只有提到是實驗過後得出來的答案
我自己的觀點是clk1>clk0 2倍就能保證一定可以在req拉起後常是取樣兩次
其中一次一定會是stable的,因此得到最長可能需要2倍
最短則是clk1 至少 > clk0 1倍 確保在clk0 1T內能成功數完3個edge
因此頻差被夾在 1 < clk1/clk0 < 2
至於為甚麼是1.5則還額外考量了setup/hold time check所需使用掉的時間
因此由實驗得到了這個經驗值
如果各位讀者對倍率的算法有研究也歡迎一起討論
#CDC #2DFF #Clock domain crossing #STA #setup time #hold time