/ Dev / snd / de eğlence için rasgele gürültü oluşturma


41

Son zamanlarda, büyülü / dev klasörünü araştırıyorum. Biraz ses çıkarmak için bir ses cihazına rastgele veri yazmak istiyorum.

ALSA kullanıyorum.

Bu yüzden kediyi / dev klasöründeki oynatma dosyasına rasgele veri aktarması talimatını verdim ...

 cat file-of-random-data > /dev/snd/pcmC0D0p

sonra kediden bir hata gibi görünen şeyi alıyorum

 cat: write error: File descriptor in bad state

Bunu nasıl düzeltebilirim, böylece ses kartımdan lezzetli bir statik oyun oynayabilirim?


1
Sanırım rastgele PCM verilerini göndermeniz ya da belki önce cihazı birkaç ioctl ile kurmanız gerekebilir - sadece rastgele baytları dökemezsiniz.
Gilles 'SO- kötülük'

@Gilles Wikipedia'ya göre .wav PCM ve rastgele dosyayı bir .wav dosyasıyla değiştirdiğimde aynı sonucu alıyorum. Bazı giriş / çıkış kontrollerini ayarlayacağım.
jones

Birileri bazı ioctls kurma konusunda bir öğretici için bir işaretçi var mı? İoctls denilen bir şey için, bir API olarak ALSA'nın giriş ve çıkış için arayüz sağlaması gerektiğini düşündüm?
jones

İşte pcm verilerinin doğrudan cihaz dosyasına nasıl yazılacağına dair örnek bir çalışma: github.com/igor-liferenko/pcm
Igor Liferenko

Yanıtlar:


46

Bunun sizin için çalışmamasının sebebi, arayüzün kullanımdan kaldırılmış olmasından kaynaklanıyor. Normalde, /dev/dspartık en azından zor olmadan, artık kullanarak ses yazamazsınız .

Sisteminizde sizin için bu başaracak bir program yok: padsp. Bu, dosyayı /dev/audioveya /dev/dspdosyayı yeni Ses Sunucusu sistemine eşleyecektir.

Terminali çalıştırın ve ile kök moduna geçin sudo su.

Ardından, cat /dev/urandomçıktının içine girip boruları alıyorum ve bu verileri göndermek için komutu padspkullanıyorum . Terminalinize bir ton çöp alırsınız, böylece yönlendirmek isteyebilirsiniz .tee/dev/audio/dev/null

Süper kullanıcınıza girdikten sonra bu komutu deneyin:

cat /dev/urandom | padsp tee /dev/audio > /dev/null

Fareniz gibi diğer aygıtlarla da denemek isteyebilirsiniz: /dev/psauxÖrneğin: veya USB sürücüsü gibi. Hatta hafızanızı onun içinden geçirebilirsiniz: /dev/mem

Umarım bu neden daha önce çalışmadığını açıklar.

Şahsen, fareyi ve hafızayı rastgele statik oynamaktan çok daha ilginç buldum!


1
Çok teşekkürler! Aradığım şey buydu. Soruyu gönderdikten 7 ay sonra cevaplandı! :-)
jones

3
sudoAyrıcalıklar bunun için gerekli değil gibi görünüyor .
iyrin

2
çok teşekkürler. İkiliklerin çok ilginç olduğunu gördüm. / usr / bin / ls / usr / bin / gnome-terminal / usr / bin / mysql gibi şeyler
parlak değil

hmm, garip, 'tee' bunu yapabilir ancak 'dd = / dev / audio' yapamaz.
Jasen,

@Jasen dd bir kerede çok fazla yazıyor olabilir. padsp, alsa aracılığıyla yönlendirmek için / dev / audio'yu simüle eder. padsp'siz dd, çekirdek OSS emülasyonu etkin olmadığı sürece / dev / audio bile görmez (ve varsayılan olarak değil). Sanırım sürücü içi tamponlardan çok daha büyük bir blok yazmak bile başarısız olabilir.
Paul Stelian

8

cat /dev/urandom | aplay yazılması gereken komuttur. Eğer "audio" grubunda değilseniz, sudo ile aplay önekini alabilirsiniz. Bu aynı zamanda herhangi bir servet ile karışmaz ( pulseaudioBu komut aktifken koşuyordum ve "gürültüyü" doğru bir şekilde duydum.).

DÜZENLEME (6 Ağustos 2019): komuta eski bir versiyonunda benim de vardı padsp teearalarında bir şey catve aplay. Şimdi bu alanda çalışıyorum, bunun kesinlikle bir anlam ifade etmediğinin farkındayım. Ayrıca, güncellenmiş komutu (şu anda bu cevabın başında görülebilen) çalıştığını biliyorum, çünkü işte günde birkaç kez kullanıyorum.


6
ALSA kullanıyorum ve "padsp tee" gerekli değil.
Geremia

1
Pulseaudio deneyimlerimde (ve PA kapalıyken Ubuntu ne kullanıyorsa) padsp teegerekli olan (o zamanlar tam olarak 12.04.2 vardı) Kök olsa bile, verileri doğrudan cihazlara atmaya çalışmamalısınız ( bildiğim kadarıyla birkaç dosya okunabilir ve / dev klasöründe hiçbiri yazılamaz), çünkü bir hatayla karşılaşabilirsiniz (en iyi durumda, her güncellemeyle daha yaygın hale gelir), çekirdeğe çarpabilir veya cihazı kırabilir, Nadir durumlarda. Kişi bunu yapmak için aplay gibi ayrıcalıklı olmayan unsurları kullanmalıdır (maalesef ses grubu veya root gerekli). @geremia
Paul Stelian

Komik şimdi nasıl bir padsp teeşeyin gerçekten hiç bir şey ifade etmediğini görüyorum . İşyerinde, ses sürücüsünü yazarken ilerleme kaydettiğimi test etmek için bu satır olmadan benzer bir şey kullanıyorum. Şimdi cevabımı güncelleyecektir.
Paul Stelian,

3

/ Dev / audio veya / dev / snd altındaki diğer cihazlardan birini deneyin. Hepsi ses veri havuzu değil, bir mikser, mikrofon veya başka bir şey yakalamış olabilirsiniz.


1
Cevap için teşekkürler. / Proc / asound / devices / dev / snd / pcmC0D0p, ses çalma için doğru cihazdır (dolayısıyla 'p')
jones

1
Ayrıca, emin değilim, ancak oynatma için birden fazla dev "dosya" olabilir mi? Ben yok olması bir '/ dev / ses' Bence '/ dev / ses' (2.5 öncesi) eski çekirdekler üzerinde kullanılan ÖSS ile ilgili bir şey var
Jones

2

pulseaudioCihazda kilitlenecek olan bir ses arka plan programı (örn. )? Sanırım üzerinde başka bir şey olup olmadığını bulabilirsin lsof.


1
Yararlı öneri için teşekkürler. Ben kullanarak, bir çek vardı grepve lsof. pulseaudiokullanıyor /dev/snd/controlC0ancak açık değil /dev/snd/pcmC0D0p. /var/lockCihazın kilitlenmesi için bir dosya olup olmadığını bularak iki kez kontrol ettim . ls -alklasörün boş olduğunu söyler. Yani pcmC0D0p üzerinde kilit olmadığını tahmin ediyorum
jones

jones Kumandaya bir kilit tutmak sürücüye bağlı olarak tüm kartı kilitlemek için yeterli olabilir. (8 yıl sonra cevap verdiğim için özür dilerim, şimdi kendim öğrendim)
Paul Stelian

0

TL; DR: Cihazın parametreleri, verileri okumadan veya yazmadan önce ayarlanmalıdır.

Adım adım:

  1. PCM cihazını açın. Ör: fd = open("/dev/snd/pcmC0D0p", O_RDWR). Açtıktan sonra PCM OPENdurumu var.

  2. İle parametreleri ayarlayın ioctl(fd, SNDRV_PCM_IOCTL_HW_PARAMS, (struct snd_pcm_hw_params*) p). Donanım parametreleri yapısının maskeleri (her bit bir değerdir) ve aralıklarla ([minimum, maksimum] aralık) vardır. Ayarlanmayan parametrelerin doldurulması zorunludur (maskeler için ayarlanan tüm bitler / değerler; aralıklar için tam aralık). Donanım parametrelerini ayarladıktan sonra PCM SETUPdurumu açıktır . Kod için TinyALSA'nın pcm_set_config () bölümüne bakın .

    Ayar ACCESS, FORMAT, RATE, CHANNELS, PERIOD_SIZEve PERIODSyeterlidir. Diğer parametreler, BUFFER_SIZEbazı cihazlarda çoklu olmayan olarak ayarlanması dışında, bunların varyantlarıdır PERIOD_SIZE.

  3. ioctl(fd, SNDRV_PCM_IOCTL_PREPARE)Aygıt ve ALSA çalışma zamanı değişkenlerini hazırlamak için arayın . Bundan sonra, PCM PREPAREDdurumdaydı.

  4. Okumaya başla (yakala) veya yazmaya başla (oynat).

Bir PCM cihazına okumak veya yazmak için minimal bir uygulama, donanım parametrelerinin manipülasyonu etrafında kodunun çoğuna sahip olacaktır.


Aplay kullandığı için (en azından üzerinde geliştirdiğim sistemde) fiili okuma / yazma çalışmasının olup olmadığından emin değilim. ALSA'nın kendisi okuma / yazma giriş noktalarını alan ve onları ioctl'lere çeviren bir ambalajı var mı?
Paul Stelian,

@PaulStelian Evet. Pcm için dosya işlemlerinin tanımına bakın . İçinde snd_pcm_read()ve snd_pcm_write(), bayt çerçevelerine dönüştürülür .
Ricardo Biehl Pasquali
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.