--- ../vdr-1.5.12-dvbs2-other/lirc.c	2006-05-28 10:48:13.000000000 +0200
+++ lirc.c	2008-01-08 22:28:38.000000000 +0100
@@ -13,10 +13,24 @@
 #include <netinet/in.h>
 #include <sys/socket.h>
 
-#define REPEATDELAY 350 // ms
-#define REPEATFREQ 100 // ms
-#define REPEATTIMEOUT 500 // ms
-#define RECONNECTDELAY 3000 // ms
+#ifndef LIRC_PUSHFREQ
+#define LIRC_PUSHFREQ 3 // 1/s
+#endif
+#ifndef LIRC_REPEATDELAY
+#define LIRC_REPEATDELAY 350 // ms
+#endif
+#ifndef LIRC_REPEATFREQ
+#define LIRC_REPEATFREQ 10 // 1/s
+#endif
+#ifndef LIRC_REPEATTIMEOUT
+#define LIRC_REPEATTIMEOUT 500 // ms
+#endif
+#ifndef LIRC_RECONNECTDELAY
+#define LIRC_RECONNECTDELAY 3000 // ms
+#endif
+#ifndef LIRC_PRIORITYBOOST
+#define LIRC_PRIORITYBOOST 0
+#endif
 
 cLircRemote::cLircRemote(const char *DeviceName)
 :cRemote("LIRC")
@@ -68,17 +82,33 @@ void cLircRemote::Action(void)
   bool repeat = false;
   int timeout = -1;
 
+  if (LIRC_PRIORITYBOOST)
+     SetPriority(GetPriority() - LIRC_PRIORITYBOOST);
   while (Running() && f >= 0) {
-
         bool ready = cFile::FileReady(f, timeout);
-        int ret = ready ? safe_read(f, buf, sizeof(buf)) : -1;
+        int ret = -1;
+        if (ready) {
+           // read one line of the line oriented lirc protocol
+           for (ret = 0; ret < (int)sizeof(buf); ret++) {
+               int ch = readchar(f);
+               if (ch < 0) {
+                  ret = -1;
+                  break;
+                  }
+               if (ch == '\n') {
+                  buf[ret++] = '\0';
+                  break;
+                  }
+               buf[ret] = ch;
+               }
+           }
 
         if (ready && ret <= 0 ) {
-           esyslog("ERROR: lircd connection broken, trying to reconnect every %.1f seconds", float(RECONNECTDELAY) / 1000);
+           esyslog("ERROR: lircd connection broken, trying to reconnect every %.1f seconds", float(LIRC_RECONNECTDELAY) / 1000);
            close(f);
            f = -1;
            while (Running() && f < 0) {
-                 cCondWait::SleepMs(RECONNECTDELAY);
+                 cCondWait::SleepMs(LIRC_RECONNECTDELAY);
                  if (Connect()) {
                     isyslog("reconnected to lircd");
                     break;
@@ -94,7 +124,7 @@ void cLircRemote::Action(void)
               continue;
               }
            if (count == 0) {
-              if (strcmp(KeyName, LastKeyName) == 0 && FirstTime.Elapsed() < REPEATDELAY)
+              if (strcmp(KeyName, LastKeyName) == 0 && FirstTime.Elapsed() < (1000 / LIRC_PUSHFREQ))
                  continue; // skip keys coming in too fast
               if (repeat)
                  Put(LastKeyName, false, true);
@@ -104,18 +134,18 @@ void cLircRemote::Action(void)
               timeout = -1;
               }
            else {
-              if (LastTime.Elapsed() < REPEATFREQ)
+              if (LastTime.Elapsed() < (1000 / LIRC_REPEATFREQ))
                  continue; // repeat function kicks in after a short delay (after last key instead of first key)
-              if (FirstTime.Elapsed() < REPEATDELAY)
+              if (FirstTime.Elapsed() < LIRC_REPEATDELAY)
                  continue; // skip keys coming in too fast (for count != 0 as well)
               repeat = true;
-              timeout = REPEATDELAY;
+              timeout = LIRC_REPEATDELAY;
               }
            LastTime.Set();
            Put(KeyName, repeat);
            }
         else if (repeat) { // the last one was a repeat, so let's generate a release
-           if (LastTime.Elapsed() >= REPEATTIMEOUT) {
+           if (LastTime.Elapsed() >= LIRC_REPEATTIMEOUT) {
               Put(LastKeyName, false, true);
               repeat = false;
               *LastKeyName = 0;
--- ../vdr-1.5.12-dvbs2-other/Makefile	2008-01-01 22:55:18.000000000 +0100
+++ Makefile	2008-01-08 22:23:41.000000000 +0100
@@ -58,6 +59,25 @@ RCU_DEVICE  ?= /dev/ttyS1
 
 DEFINES += -DLIRC_DEVICE=\"$(LIRC_DEVICE)\" -DRCU_DEVICE=\"$(RCU_DEVICE)\"
 
+ifdef LIRC_PUSHFREQ
+DEFINES += -DLIRC_PUSHFREQ=$(LIRC_PUSHFREQ)
+endif
+ifdef LIRC_REPEATDELAY
+DEFINES += -DLIRCD_REPEATDELAY=$(LIRC_REPEATDELAY)
+endif
+ifdef LIRC_REPEATFREQ
+DEFINES += -DLIRC_REPEATFREQ=$(LIRC_REPEATFREQ)
+endif
+ifdef LIRC_REPEATTIMEOUT
+DEFINES += -DLIRC_REPEATTIMEOUT=$(LIRC_REPEATTIMEOUT)
+endif
+ifdef LIRC_RECONNECTDELAY
+DEFINES += -DLIRC_RECONNECTDELAY=$(LIRC_RECONNECTDELAY)
+endif
+ifdef LIRC_PRIORITYBOOST
+DEFINES += -DLIRC_PRIORITYBOOST=$(LIRC_PRIORITYBOOST)
+endif
+
 DEFINES += -D_GNU_SOURCE
 
 DEFINES += -DVIDEODIR=\"$(VIDEODIR)\"
--- ../vdr-1.5.12-dvbs2-other/thread.c	2007-10-19 16:30:13.000000000 +0200
+++ thread.c	2008-01-08 22:39:48.000000000 +0100
@@ -218,9 +218,20 @@ cThread::~cThread()
   free(description);
 }
 
+int cThread::GetPriority(void)
+{
+  errno = 0;
+  int Priority = getpriority(PRIO_PROCESS, 0);
+  if (Priority == -1 && errno != 0) {
+     LOG_ERROR;
+     Priority = 0;
+     }
+  return Priority;
+}
+
 void cThread::SetPriority(int Priority)
 {
-  if (setpriority(PRIO_PROCESS, 0, Priority) < 0)
+  if (setpriority(PRIO_PROCESS, 0, max(-20, min(Priority, 19))) < 0)
      LOG_ERROR;
 }
 
--- ../vdr-1.5.12-dvbs2-other/thread.h	2007-02-24 17:13:28.000000000 +0100
+++ thread.h	2008-01-07 22:52:19.000000000 +0100
@@ -86,6 +86,7 @@ private:
   static tThreadId mainThreadId;
   static void *StartThread(cThread *Thread);
 protected:
+  int GetPriority(void);
   void SetPriority(int Priority);
   void Lock(void) { mutex.Lock(); }
   void Unlock(void) { mutex.Unlock(); }
--- ../vdr-1.5.12-dvbs2-other/tools.c	2008-01-01 22:55:18.000000000 +0100
+++ tools.c	2008-01-06 01:50:17.000000000 +0100
@@ -84,6 +84,14 @@ ssize_t safe_write(int filedes, const vo
   return p < 0 ? p : written;
 }
 
+int readchar(int filedes)
+{
+  char c;
+  if (safe_read(filedes, &c, sizeof(c)) != 1)
+     return -1;
+  return c;
+}
+
 void writechar(int filedes, char c)
 {
   safe_write(filedes, &c, sizeof(c));
--- ../vdr-1.5.12-dvbs2-other/tools.h	2008-01-01 22:55:18.000000000 +0100
+++ tools.h	2008-01-06 01:57:03.000000000 +0100
@@ -164,6 +164,7 @@ public:
 
 ssize_t safe_read(int filedes, void *buffer, size_t size);
 ssize_t safe_write(int filedes, const void *buffer, size_t size);
+int readchar(int filedes);
 void writechar(int filedes, char c);
 int WriteAllOrNothing(int fd, const uchar *Data, int Length, int TimeoutMs = 0, int RetryMs = 0);
     ///< Writes either all Data to the given file descriptor, or nothing at all.
