Tech と Culture

テクノロジーとカルチャー

IJGソフト内部 ハフマン符号化 3

HUFF_DECODE は、 jdhuff.h で defineされています。

#define HUFF_DECODE(result,state,htbl,failaction,slowlabel) \
{ register int nb, look; \
 if (bits_left < HUFF_LOOKAHEAD) { \バッファ内に、8bit(キャッシュサイズ)以上データ有るかチェック
  if (! jpeg_fill_bit_buffer(&state,get_buffer,bits_left, 0)) {failaction;} \ 無ければバッファに8bit追加 
   get_buffer = state.get_buffer; bits_left = state.bits_left; \
  if (bits_left < HUFF_LOOKAHEAD) { \
   nb = 1; goto slowlabel; \   それでも8bit無い場合は、nb=1にして、jpeg_huff_decodeへ
  } \
 } \
 look = PEEK_BITS(HUFF_LOOKAHEAD); \  lookは先頭から8bit, PEEK_BITSはバッファはそのまま
 if *1 < 0) \ jpeg_huff_decodeをコール
   { failaction; } \
  get_buffer = state.get_buffer; bits_left = state.bits_left; \
  } \
}

jpeg_huff_decodeは、jdhuff.cに記述されている関数で、JPEG規格書と同様なアルゴリズムによってハフマンデコードを行う関数です。
jpeg_fill_bit_bufferは、内部バッファにデータを1byte取ってくる関数です。このフェッチの時にマーカーチェックや、パッディングビット(FFの次の00)の削除を行っています。
実際にファイルからREADしている関数は、jdatasrc.c内部にある、fill_input_buffer()です。
ここでは、ある程度のサイズまとめてファイルから読み込まれています。ハフマンデコード部分だけでなく、各種テーブルのREADもこの関数でまとめて読み取ったデータから順に読んでいます。
よって、ハフマン部分をハードウェア化しても、この辺りの処理を変更しなければ、ソフトウェア上でかなりの無駄な処理が行われてからハードウェアに転送されていることになってしまいます。
しかし、ここを変更すると、テーブル等のパース部分も作りなおしになって、かなり面倒くさいです。。。。。
どうしたものか。

いずれにしろ、ハードウェア化した後に考えれば良いと思いますのでとりあえずスルーします。

*1:nb = htbl->look_nbits[look]) != 0) { \ lookの値を用いてキャッシュチェック   DROP_BITS(nb); \              キャッシュにHITしたら、バッファからnb bit落とす   result = htbl->look_sym[look]; \      キャッシュから実際の値を取得  } else { \   nb = HUFF_LOOKAHEAD+1; \         キャッシュにHITしなかったので、nb=9にする slowlabel: \   if ((result=jpeg_huff_decode(&state,get_buffer,bits_left,htbl,nb