2009年2月16日 星期一

Demo 之 Murphy’s Law

"Anything that can go wrong, will"

“如果有件事有可能會出錯,它就一定會出錯。”

 

不只!就連不太可能會出錯的,在關鍵時刻也會出錯!!

 

星期四到台北 Demo,之前已經演練了非常多次,測試了很久的時間,整個影像就是很順。真正到了 Demo 現場,機器架好,很有信心地把程式跑起來。

喵喵樂!為什麼昨天下午還跑得好好的程式,現在開始抖起來了!我的心也跟著抖起來了。

原本很順的畫面,現在變成會回頭;換句話說,就是人往前走,會後退抽一下,再往前走,再後退抽一下;嚴重的時候還會來回抽動好幾下。

把所有的設定全部檢查過,無誤;重新 reboot 再 run,照抖;全部的線重新接過,再抖。

火大換 CODEC,換成原本因為效能考量不 demo 的 H.264,咦?不抖了。見鬼了。

再換回 H.263,咦?又抖了,哪有這樣的啦!

在現場以為前一天 H.263 改到什麼東西,導致整個影像不正常。馬上決定改 demo 會卡卡的 H.264,至少畫面不會跳來跳去。

 

回到新竹後,開始查原因。查出來的時候差點飆淚:原因出在光線。

我們測試的環境,一向是在日光燈底下;當天 demo 現場是鵝黃色美術燈那種燈光,導致 webcam 認為環境很暗;又很巧,webcam 會自動隨著環境的光線調整光量;調整進光量的兩個因素,一個是快門,一個是光圈;webcam 的光圈已經固定,所以能動的只有快門;也就是說,光線越暗,快門的時間越長;快門越長,我們從下指令要從 webcam capture 一張畫面等待的時間要越久。

在每秒鐘 10 張 frame 的情況下,display 每 100ms 就會跑一次,只要 capture 並 encode 一張 frame 的時間超過 100 ms,就有可能發生 capture 一張,display 兩張以上的情況。也就是說,display 跑了兩次,會拿到同樣的東西。

照這麼說來,理論上畫面只會停在最後一個畫面,為什麼會跳來跳去?原因在於,實作 display 的同事,參考的 sample code,使用了 ping-pong buffer;簡單地說,buffer 有兩個,分別存了最後一張和倒數第二張的 frame;display 在存取時,會照著 buffer 1, buffer 2, buffer 1, buffer 2 的順序不斷抓 frame 出來 play。當 decoder 沒有資料寫入,把 buffer 更新時, display 就會一直抓到上一張、上上一張、上一張、上上一張;最後結果就是變成我們看到的,我又跳過來啦,我又跳過去啦,我又跳過來啦,打我啊笨蛋的情況。

 

所以,天時、地利、人和,缺一不可,在 demo 的時候,集所有不可能於一身的情況發生了,它就開始抖了。

 

再次證明了 Murphy’s Law 的真理。

沒有留言: