Je travaille sur une application qui lit l'audio en continu en utilisant l'API waveOut...
de winmm.dll
. L'application utilise des tampons "leapfrog", qui sont essentiellement un ensemble de tableaux d'échantillons que vous jetez dans la file d'attente audio. Windows les lit de manière homogène et chaque fois que la mémoire tampon est terminée, Windows appelle une fonction de rappel. À l'intérieur de cette fonction, je charge le jeu d'échantillons suivant dans le tampon, les traite cependant, puis restitue le tampon dans la file d'attente audio. De cette façon, l'audio joue indéfiniment.Problème avec le verrou waveOutWrite et waveOutGetPosition
Pour l'animation, j'essaie d'incorporer waveOutGetPosition
dans l'application (puisque les rappels "buffer done" sont assez irréguliers pour provoquer une animation saccadée). waveOutGetPosition
renvoie la position actuelle de la lecture, elle est donc hyper précise.
Le problème est que dans mon application, faire des appels à waveOutGetPosition
finit par bloquer l'application - le son s'arrête et l'appel ne revient jamais. J'ai réduit les choses à une application simple qui démontre le problème. Vous pouvez exécuter l'application ici:
http://www.musigenesis.com/SO/waveOut%20demo.exe
Si vous entendez juste un petit peu de piano à plusieurs reprises, il travaille. C'est juste pour montrer le problème. Le code source de ce projet est ici (toute la viande est en LeapFrogPlayer.cs):
http://www.musigenesis.com/SO/WaveOutDemo.zip
Le premier bouton exécute l'application en mode saute-mouton sans faire les appels à waveOutGetPosition
. Si vous cliquez dessus, l'application jouera pour toujours sans se casser (le bouton X le fermera et l'éteindra). Le second bouton démarre le saut de saut et démarre également un temporisateur de formulaires qui appelle le waveOutGetPosition
et affiche la position actuelle. Cliquez ici et l'application fonctionnera pendant un court moment, puis se verrouiller. Sur mon ordinateur portable, il se verrouille habituellement en 15-30 secondes; tout au plus cela a pris une minute.
Je n'ai aucune idée de comment résoudre ce problème, donc toute aide ou suggestion serait la bienvenue. J'ai trouvé très peu de messages sur ce problème, mais il semble qu'il y ait un blocage potentiel, soit à partir de plusieurs appels à waveOutGetPosition
ou à partir d'appels à cela et waveOutWrite
qui se produisent en même temps. Il est possible que j'appelle ça trop souvent pour que le système puisse le gérer.
Modifier: oublié de mentionner, je cours sous Windows Vista. Cela peut ne pas arriver du tout sur les autres systèmes d'exploitation.
Edit 2: Je l'ai trouvé peu de choses sur ce problème en ligne, à l'exception de ces (sans réponses) messages:
Edit 3: Eh bien, je suis maintenant capable de reproduire ce problème à volonté. Si j'appelle waveOutGetPosition
immédiatement après waveOutWrite
(dans la ligne de code suivante) l'application se bloque à chaque fois. Il se bloque également de manière particulièrement mauvaise - il semble bloquer tout mon système d'exploitation pendant un certain temps, pas seulement l'application elle-même. Il semble donc que waveOutGetPosition
deadlocks si elle se produit à presque en même temps que waveOutWrite
, pas seulement littéralement en même temps, ce qui pourrait expliquer pourquoi les verrous ne fonctionnent pas pour moi. Yeesh.
J'ai essayé, mais il est toujours en train de se bloquer. Je vais essayer de verrouiller les appels à waveOutPrepareHeader, aussi. Pourquoi avez-vous besoin de Build + Clean? Était-ce difficile de compiler le projet ou quelque chose? – MusiGenesis
A travaillé sur ma machine. Utilisez Debug + Break All, Debug + Windows + Threads pour voir où les threads sont bloqués. Personne n'aime les gros téléchargements avec des fichiers .exe provenant d'une URL Internet non fiable. –
Si quoi que ce soit, cette modification aggrave le problème. Cela semble se bloquer beaucoup plus vite, maintenant; environ la moitié du temps maintenant, il se bloque au premier appel à waveOutGetPosition. Est-ce que cela fonctionne sur votre ordinateur? – MusiGenesis