March 11, 2006

透過 Intel Pentium4 SSE2 指令集對 MPEG-2 Video 作最佳化 (1)

最近在工作中又複習了 MPEG-2 Video coding 與內部實做,並針對特定硬體平台作效能提昇,寫完技術報告時,心情輕鬆許多,很想大喊:"I did it, I did it!"。在工作之餘,我也對 open source codec 產生興趣,恰好對 MPEG-2 實做與效能衝擊的部份有足夠的認知,所以我試著以 Intel Pentium4 SSE2 指令集,來對 MPEG-2 Video coding 作最佳化。

簡單來說,MPEG-2 decoding 有兩大效能瓶頸,一個是 Inverse DCT (idct),另一個是 MC (Motion Compensation),在我的 hacking 中,已經初步有了不錯的突破。我挑選 MPlayer 作為 codebase,並且改善了 MC 的效能,可 [在此取得 patch] (GPL),同時我也改善了 libmpeg2 多餘的 cpu detection 處理。以下是實測數據:
(1) Baseline (使用 MPlayer 原本的 mmxext MC):
MPEG-PS file format detected.
VIDEO:  MPEG2  720x480  (aspect 2)  29.970 fps  2376.0 kbps (297.0 kbyte/s)

BENCHMARKs: VC:  10.785s VO:   3.092s A:   0.595s Sys:  20.772s =   35.244s
BENCHMARK%: VC: 30.6027% VO:  8.7722% A:  1.6879% Sys: 58.9372% = 100.0000%

 time   seconds   seconds    calls  ms/call  ms/call  name
 15.58     12.83    12.83  3013243     0.00     0.00  mmxext_idct
 14.70     24.94    12.11   515616     0.02     0.02  MC_put_xy_16_mmxext
 12.40     35.15    10.21    56139     0.18     0.18  fast_memcpy
  6.69     40.66     5.51  1826892     0.00     0.00  slice_intra_DCT
  6.34     45.88     5.22  1500758     0.00     0.00  MC_put_o_8_mmxext
  5.44     50.36     4.48  1758006     0.00     0.00  get_non_intra_block
  3.95     53.61     3.25    30480     0.11     2.16  mpeg2_slice
  3.28     56.31     2.70  1069690     0.00     0.03  motion_fr_frame_420
  3.21     58.95     2.64   112816     0.02     0.02  MC_avg_xy_16_mmxext
  3.14     61.54     2.59  1826892     0.00     0.01  mpeg2_idct_copy_mmxext

(2) SSE2-optimized-MC (我剛剛的 hacking):
MPEG-PS file format detected.
VIDEO:  MPEG2  720x480  (aspect 2)  29.970 fps  2376.0 kbps (297.0 kbyte/s)

BENCHMARKs: VC:  10.712s VO:   5.277s A:   0.598s Sys:  17.861s =   34.448s
BENCHMARK%: VC: 31.0958% VO: 15.3193% A:  1.7352% Sys: 51.8497% = 100.0000%

  %   cumulative   self              self     total
 time   seconds   seconds    calls  ms/call  ms/call  name
 16.32     13.24    13.24  3013243     0.00     0.00  mmxext_idct
 12.43     23.33    10.09    56139     0.18     0.18  fast_memcpy
 10.67     31.99     8.66   515616     0.02     0.02  MC_put_xy_16_sse2
  7.16     37.80     5.81  1826892     0.00     0.00  slice_intra_DCT
  6.85     43.36     5.56  1500758     0.00     0.00  MC_put_o_8_sse2
  5.73     48.01     4.65  1758006     0.00     0.00  get_non_intra_block
  4.97     52.04     4.03    30480     0.13     2.10  mpeg2_slice
  3.27     54.69     2.65  1069690     0.00     0.03  motion_fr_frame_420
  3.24     57.32     2.63   205987     0.01     0.01  MC_put_x_16_sse2
  3.11     59.84     2.52  1826892     0.00     0.01  mpeg2_idct_copy_mmxext
  2.93     62.22     2.38   112816     0.02     0.02  MC_avg_xy_16_sse2

「數字會說話」,可以發現 MC_xxx 的 motion compensation 運算速度獲得提昇,於是整體的 benchmark 比值也提高,對於播放中的 MPEG-2 影片來說,系統的 idle time 增加,這也意味著對能源的使用可更經濟。

有 Pentium4 或相容機種的朋友,歡迎測試這個 patch。稍後我會試著探討以 SSE2 指令集改善 MPlayer 的 MPEG-2 IDCT 運算。 (按:這是怎麼一回事:我的正職工作就在作 codec,下班後,還是在改善 codec 效能,永遠忙不完)
由 jserv 發表於 March 11, 2006 12:34 AM
迴響

jserv++

Huahua 發表於 March 11, 2006 12:39 AM

jserv++

strong 發表於 March 11, 2006 04:01 PM

請問benchmark是怎麼做的呢?

cat 發表於 March 11, 2006 07:03 PM

To cat,

使用 mplayer -benchmark 搭配 gprof 即可產生上列的 benchmark 資訊。

jserv 發表於 March 11, 2006 07:24 PM
發表迴響









記住我的資訊?