Linux で複数の USB ウェブカメラを使用する

bandwidth debian linux usb webcam

Debian/Linux で複数の USB ウェブカメラを実行すると、以下のようなエラーが発生します

libv4l2: error turning on stream: No space left on device
VIDIOC_STREAMON: No space left on device

当初は OpenCV のプログラミングの問題と思われていたものが、チーズや xawtv を実行することで同じエラーが発生した後、謎のハードウェア/ソフトウェアの問題の探求に変わりました

どうやらWebカメラがUSBホストコントローラ上で利用可能なすべての帯域幅を要求することが原因のようです。それを念頭に置いて、1台のカメラがどのくらいの帯域幅を使用しているかを確認するために、wiresharkとcapinfosを実行することにしました

4 megabits per second at 320x240
14 megabits per second at 640x480
32 megabits per second at 1280x720

面白いですね。320×240で2台のカメラが動作するのに、それ以上の解像度では失敗する理由が説明できるかもしれません。まるでUSBコントローラがUSB 1の速度でしか動作していないかのように、lsusbは両方のWebカメラが480メガビット/秒をサポートしているはずのデバイスに属していることを示しています

ある解決策では、次のコマンドを実行することで、Web カメラに最大値を要求するのではなく、帯域幅の使用量を計算するように強制することが提案されていました

sudo rmmod uvcvideo
sudo modprobe uvcvideo quirks=128

残念ながらこれでは何も変わりませんでしたので、別の解決策を試してみることにしました。on StackOverflow の投稿は、私のウェブカムに低い FPS や MJPEG のような圧縮されたビデオフォーマットを使うように指示することを提案していましたが、v4lctl list を実行しても、私のウェブカムはどちらもビデオモードの変更をサポートしているようには見えません

そこで行き詰まったのがなぜUSB2の最大速度以下で動作している2つのウェブカメラがこのエラーを出すのでしょうか?

ps.ディスク容量の問題ではなく、ウェブカメラを起動してもdfの表示に変化はありません

pps: もし違いがあれば、lsusb の出力は以下の通りです

  32  rachelderp  2012-06-02


ベストアンサー

チンチン!freenodeの#v4lの親切な人たちの助けを借りて、これを解決することができました

長い話:v4l2-ctlはUSBカメラの問題をデバッグするための最高のツールです。全ての利用可能なコマンドとマニュアルページを読んでみてください。v4l2-ctl を使って、私のカメラが圧縮ビデオモードをサポートしていないことを発見しました。以下のコマンドを実行することで、カメラがどのモードをサポートしているかを確認することができます

v4l2-ctl -d /dev/video0 --list-formats

このように出力されるはずです

 ioctl: VIDIOC_ENUM_FMT
Index       : 0
Type        : Video Capture
Pixel Format: 'MJPG' (compressed)
Name        : MJPEG

Index       : 1
Type        : Video Capture
Pixel Format: 'YUYV'
Name        : YUV 4:2:2 (YUYV)

返されたピクセル フォーマットが「YUYV」、「IUYV」、「I420」、または「GBRG」のみの場合、これらのフォーマットは非圧縮であるため、USB コントローラ*1 台につき 1 台のカメラしか実行できません。MJPEG またはその他の圧縮形式をサポートする複数の Web カメラを使用しても問題ありません

私のように OpenCV を使っている人は,デフォルトのピクセルフォーマットが圧縮されていなくても気にしないでください.

**320×240以下の解像度で満足している場合を除きます

26  rachelderp  2012-06-06


答えは SwDevRefugee さんが書いた uvcvideo の修正を使うことです。彼と私はOpenWrt用に改造されたコードをコンパイルするのに成功しました。私が実行しているバージョンはOpenWRT DESIGNATED DRIVER (Bleeding Edge, r48130)で、tplink wdr3600ルータ上で実行しています

結果:私は、USB 2.0ハブを介して、MJPG形式で1280×960と15fpsでシミュレート実行している3*c270(ロジクール)を持つことができます。私は、申し訳ありませんが、フックアップする第四のc270を持っていません

私はまた、YUVフォーマットで2*c270と1*GEMBIRD 640*480*15fpsを持つことができますが、2番目のGEMBIRDを追加すると、恐ろしい “Unable to start capture.No space left device”(ここではスペース==帯域幅)につながります。あなたがよく知っているように、ここではスペース==帯域幅、”デバイス上に残されたスペースがありません” (あなたはよく知っているように:))。GEMBIRD (1908:2311) == http://www.penguin.cz/~utx/hardware/USB_Camera_AX2311/

3*c270でのCPU使用率は、wdr3600ではかなり妥当です

Mem: 50600K used, 75444K free, 320K shrd, 3436K buff, 8800K cached

CPU:  16% usr  27% sys   0% nic  45% idle   0% io   0% irq  10% sirq

Load average: 1.20 0.85 0.44 4/60 2546

PID  PPID USER     STAT   VSZ %VSZ %CPU COMMAND

2240  1679 root     S    15348  12%  17% mjpg_streamer --input input_uvc.so --

2505  1679 root     S    15368  12%  11% mjpg_streamer --input input_uvc.so --

2239  1679 root     S    15532  12%  11% mjpg_streamer --input input_uvc.so --

コミュニティが何らかの評価とサポートをしてくれれば、SwDevRefugee は喜んでコードを uvc-linux に入れてくれると思います

8  reikred  2016-01-09


uvcvideo ドライバを見てみると、quirks=128 モジュールパラメータはストリームが mjpeg 圧縮されている場合は無視されます

私が選んだウェブカメラは、ロジクールC500とロジクールC270でしたが、C500の1280×1024で生成された画像は100kバイト、C270の1280×960で生成された画像は200kバイトであることがわかりました

C270を10fpsで実行した場合、必要なビットレートは10x200000x8 = 16Mbit/sとなります。Ubuntu 14.04では、uvcdriverモジュールはフレームレートに関係なく常に196Mbit/sを割り当てます。C500の場合は少しはマシになっていますが、まだ帯域幅を占有しています

V4L2 インタフェースを介してドライバに「圧縮」係数を提供できるように uvcvideo ドライバを修正しました。v4l2_pix_format 構造体の priv 属性を使って値を指定しています。ドライバでは、非圧縮画像のサイズを計算し、圧縮率で割って、使用する USB 帯域幅を計算します

デフォルトでは、カメラが特に圧縮しにくい画像に遭遇した場合に大きな余裕を持って圧縮率10を使用しています。1280×960と10fpsで動作するC270は41Mbit/sを使用しており、1つのバスで4台のカメラを簡単に動作させることができます

この機能に興味のある人がいれば、uvcvideoメンテナに「圧縮」係数の概念を検討してもらうことを試みます

4  SwDevAlien  2015-12-27


私もスペースエラーが出ました。うまくいったのは、カメラの1つを外して、据え置きPCの別のUSBポートに接続したことでした – 6、7つのUSBポートが散らばっています。show_webcams 0 1’を実行すると、突然2つの画像が表示されました

-1  Peter Thejll  2016-06-19


タイトルとURLをコピーしました