0

こんにちは、同時に 3 つの入力デバイスからキャプチャする必要があるプログラムを作成しています (この場合は、3 つの同一の USB Web カメラです)。

まず第一に、ALSA はおなじみの UNIX パラダイム「すべてがファイルである」に基づいていないため、通常の poll(3) 呼び出しは使用できません。すべてのデバイス間でデータ ストリームが安定している必要があることがわかっているので、今のところ、次のようにします。

while(!stop)
  for(i = 0; i < input_device_count; i++)
  {
    snd_pcm_readi(handle[i], buffer, frames);
    write(fd_out[i], buffer, size);
  }

このコードは、各デバイスを反復処理して読み取り、以前に開いていたファイルに結果を書き込みます。それは機能しますが、これを行うにはより良い方法があると思います。これも mmap を使用するため、カーネル空間からユーザー、およびカーネルに再度コピーする必要はありません。

ちょっとの間、3 つの入力が同期していると仮定しましょう。上記のコードは、3 つのデバイスから同時に記録を開始することを保証するものではありません。それを保証する方法はありますか?実際、snd_pcm_prepare() や snd_pcm_start() のような呼び出しのセマンティクスは何ですか? 今はそれらを使用していません。snd_pcm_readi() に直行します。

コード例を検索しようとしましたが、同時に複数のキャプチャに関係するものは見つかりませんでした。ヒントをいただければ幸いです。

4

1 に答える 1

2

ALSA は、おなじみの UNIX パラダイム「すべてがファイルである」に基づいています。したがって、複数のデバイスを処理するには、poll(3) を使用する必要があります。

複数のファイルの上に実装される ALSA プラグインがあるため、PCM デバイスごとに複数のハンドルが存在する可能性があります。デバイスごとにsnd_pcm_poll_descriptors_countを呼び出しpollfdて必要な構造体の数を確認し、次にsnd_pcm_poll_descriptorsを呼び出してファイル ハンドルとそれぞれのeventビットを取得します。

ループでは、 を呼び出した後、構造体の値を直接poll読み取るのではなく、snd_pcm_poll_descriptors_revents を呼び出してそれらを元に戻す必要があります。pollfd


複数のデバイスが同時に起動するようにするには、snd_pcm_linkを呼び出します。ただし、これはデバイスが同じ速度で動作することを保証するものではありません。

于 2013-11-06T07:54:44.917 に答える