This patch adds selection logic to ALSA timer initialization, trying to find 
the best available ALSA timer (a non slave timer with lowest resolution).

Currently muse uses only the ALSA system timer, even when the system has an 
ALSA RTC or ALSA HPET drivers available, which are probably better for many 
users.

This patch applies to muse CVS REL07 branch, dated 20090214 (post 1.0rc1 
release).

Also available at:
https://sourceforge.net/tracker2/?func=detail&aid=2599030&group_id=93414&atid=604224

Regards,
Pedro
Index: muse/driver/alsatimer.cpp
===================================================================
RCS file: /cvsroot/lmuse/muse/muse/driver/alsatimer.cpp,v
retrieving revision 1.1.2.7
diff -u -b -r1.1.2.7 alsatimer.cpp
--- muse/driver/alsatimer.cpp	27 Jan 2007 14:52:42 -0000	1.1.2.7
+++ muse/driver/alsatimer.cpp	14 Feb 2009 09:21:57 -0000
@@ -10,6 +10,7 @@
   //=========================================================
         
   #include "alsatimer.h"
+  #include <climits>
 
 #define TIMER_DEBUG 0
   
@@ -45,6 +46,16 @@
     int card = 0;
     int device = SND_TIMER_GLOBAL_SYSTEM;
     int subdevice = 0;
+    int test_ids[] = { SND_TIMER_GLOBAL_SYSTEM
+                     , SND_TIMER_GLOBAL_RTC
+#ifdef SND_TIMER_GLOBAL_HPET
+                     , SND_TIMER_GLOBAL_HPET
+#endif
+                     };
+    int max_ids = sizeof(test_ids) / sizeof(int);
+    long best_res = LONG_MAX;
+    int best_dev = SND_TIMER_GLOBAL_SYSTEM;
+    int i;
 
     if (id || info || params) {
       fprintf(stderr,"AlsaTimer::initTimer(): called on initialised timer!\n");
@@ -54,6 +65,27 @@
     snd_timer_info_malloc(&info);
     snd_timer_params_malloc(&params);
 
+    for (i = 0; i < max_ids; ++i) {
+      device = test_ids[i];
+      sprintf(timername, "hw:CLASS=%i,SCLASS=%i,CARD=%i,DEV=%i,SUBDEV=%i", devclass, sclass, card, device, subdevice);
+      if ((err = snd_timer_open(&handle, timername, SND_TIMER_OPEN_NONBLOCK)) < 0) {
+        continue;
+        }
+      if ((err = snd_timer_info(handle, info)) < 0) {
+        snd_timer_close(handle);
+        continue;
+        }
+      // select a non slave timer with the lowest resolution value
+      int is_slave = snd_timer_info_is_slave(info);
+      long res = snd_timer_info_get_resolution(info);
+      if ((is_slave == 0) && (best_res > res)) {
+        best_res = res;
+        best_dev = device;
+        }
+      snd_timer_close(handle);
+      }
+    device = best_dev;
+
     sprintf(timername, "hw:CLASS=%i,SCLASS=%i,CARD=%i,DEV=%i,SUBDEV=%i", devclass, sclass, card, device, subdevice);
     if ((err = snd_timer_open(&handle, timername, SND_TIMER_OPEN_NONBLOCK))<0) {
       fprintf(stderr, "AlsaTimer::initTimer(): timer open %i (%s)\n", err, snd_strerror(err));
@@ -64,6 +96,9 @@
       return -1;
       }
 
+    if(TIMER_DEBUG)
+      fprintf(stderr, "AlsaTimer::initTimer(): best available ALSA timer: %s\n", snd_timer_info_get_name(info));
+
     snd_timer_params_set_auto_start(params, 1);
     snd_timer_params_set_ticks(params, 1);
       
_______________________________________________
Linux-audio-dev mailing list
[email protected]
http://lists.linuxaudio.org/mailman/listinfo/linux-audio-dev

Reply via email to