Package: xpdf
Version: 3.03-16+experimental2
Severity: important

>From 3.03-12 (50c3fa13d) onwards, after GlobalParams was changed to
XPDFParams, it appears that key binding directives in the configuration
file (~/.xpdfrc) are being ignored.

This is obviously a pretty severe loss of functionality.

To fix this, please just copy-and-paste the following functions from
GlobalParams to XPDFParams: parseBind, parseUnbind, parseKey. Also add
the corresponding else if cases in parseLine.

I have tested this and it seems to work for me for key bindings. I have
attached a patch below for XPDFParams.{h,cc}, but I am not familiar
enough with Debian's oackaging system to submit it as a git-pullable
patch. My apologies, but it should be easy enough to adapt it.


--- xpdf/XPDFParams.h.orig      2014-02-17 12:20:41.000000000 +0100
+++ xpdf/XPDFParams.h   2014-02-17 12:30:07.475615604 +0100
@@ -87,12 +87,18 @@
   GString *getInitialZoom();
   GBool getContinuousView();
   int getPSPaperWidth();
   int getPSPaperHeight();
 
 private:
+  void parseBind(GList *tokens, GString *fileName, int line);
+  void parseUnbind(GList *tokens, GString *fileName, int line);
+  GBool parseKey(GString *modKeyStr, GString *contextStr,
+                int *code, int *mods, int *context,
+                const char *cmdName,
+                GList *tokens, GString *fileName, int line);
   void parseCommand(const char *cmdName, GString **val,
                     GList *tokens, GString *fileName, int line);
   void parseYesNo(const char *cmdName, GBool *flag,
                   GList *tokens, GString *fileName, int line);
   GBool parseYesNo2(char *token, GBool *flag);
   void parsePSFile(GList *tokens, GString *fileName, int line);
--- xpdf/XPDFParams.cc.orig     2014-02-17 12:20:41.000000000 +0100
+++ xpdf/XPDFParams.cc  2014-02-17 12:30:07.475615604 +0100
@@ -163,12 +163,206 @@
     }
   }
   unlockXpdfParams;
   return cmds;
 }
 
+void XpdfParams::parseBind(GList *tokens, GString *fileName, int line) {
+  KeyBinding *binding;
+  GList *cmds;
+  int code, mods, context, i;
+
+  if (tokens->getLength() < 4) {
+    error(errConfig, -1, "Bad 'bind' config file command ({0:t}:{1:d})",
+         fileName, line);
+    return;
+  }
+  if (!parseKey((GString *)tokens->get(1), (GString *)tokens->get(2),
+               &code, &mods, &context,
+               "bind", tokens, fileName, line)) {
+    return;
+  }
+  for (i = 0; i < keyBindings->getLength(); ++i) {
+    binding = (KeyBinding *)keyBindings->get(i);
+    if (binding->code == code &&
+       binding->mods == mods &&
+       binding->context == context) {
+      delete (KeyBinding *)keyBindings->del(i);
+      break;
+    }
+  }
+  cmds = new GList();
+  for (i = 3; i < tokens->getLength(); ++i) {
+    cmds->append(((GString *)tokens->get(i))->copy());
+  }
+  keyBindings->append(new KeyBinding(code, mods, context, cmds));
+}
+
+void XpdfParams::parseUnbind(GList *tokens, GString *fileName, int line) {
+  KeyBinding *binding;
+  int code, mods, context, i;
+
+  if (tokens->getLength() != 3) {
+    error(errConfig, -1, "Bad 'unbind' config file command ({0:t}:{1:d})",
+         fileName, line);
+    return;
+  }
+  if (!parseKey((GString *)tokens->get(1), (GString *)tokens->get(2),
+               &code, &mods, &context,
+               "unbind", tokens, fileName, line)) {
+    return;
+  }
+  for (i = 0; i < keyBindings->getLength(); ++i) {
+    binding = (KeyBinding *)keyBindings->get(i);
+    if (binding->code == code &&
+       binding->mods == mods &&
+       binding->context == context) {
+      delete (KeyBinding *)keyBindings->del(i);
+      break;
+    }
+  }
+}
+
+GBool XpdfParams::parseKey(GString *modKeyStr, GString *contextStr,
+                            int *code, int *mods, int *context,
+                            const char *cmdName,
+                            GList *tokens, GString *fileName, int line) {
+  char *p0;
+  int btn;
+
+  *mods = xpdfKeyModNone;
+  p0 = modKeyStr->getCString();
+  while (1) {
+    if (!strncmp(p0, "shift-", 6)) {
+      *mods |= xpdfKeyModShift;
+      p0 += 6;
+    } else if (!strncmp(p0, "ctrl-", 5)) {
+      *mods |= xpdfKeyModCtrl;
+      p0 += 5;
+    } else if (!strncmp(p0, "alt-", 4)) {
+      *mods |= xpdfKeyModAlt;
+      p0 += 4;
+    } else {
+      break;
+    }
+  }
+
+  if (!strcmp(p0, "space")) {
+    *code = ' ';
+  } else if (!strcmp(p0, "tab")) {
+    *code = xpdfKeyCodeTab;
+  } else if (!strcmp(p0, "return")) {
+    *code = xpdfKeyCodeReturn;
+  } else if (!strcmp(p0, "enter")) {
+    *code = xpdfKeyCodeEnter;
+  } else if (!strcmp(p0, "backspace")) {
+    *code = xpdfKeyCodeBackspace;
+  } else if (!strcmp(p0, "insert")) {
+    *code = xpdfKeyCodeInsert;
+  } else if (!strcmp(p0, "delete")) {
+    *code = xpdfKeyCodeDelete;
+  } else if (!strcmp(p0, "home")) {
+    *code = xpdfKeyCodeHome;
+  } else if (!strcmp(p0, "end")) {
+    *code = xpdfKeyCodeEnd;
+  } else if (!strcmp(p0, "pgup")) {
+    *code = xpdfKeyCodePgUp;
+  } else if (!strcmp(p0, "pgdn")) {
+    *code = xpdfKeyCodePgDn;
+  } else if (!strcmp(p0, "left")) {
+    *code = xpdfKeyCodeLeft;
+  } else if (!strcmp(p0, "right")) {
+    *code = xpdfKeyCodeRight;
+  } else if (!strcmp(p0, "up")) {
+    *code = xpdfKeyCodeUp;
+  } else if (!strcmp(p0, "down")) {
+    *code = xpdfKeyCodeDown;
+  } else if (p0[0] == 'f' && p0[1] >= '1' && p0[1] <= '9' && !p0[2]) {
+    *code = xpdfKeyCodeF1 + (p0[1] - '1');
+  } else if (p0[0] == 'f' &&
+            ((p0[1] >= '1' && p0[1] <= '2' && p0[2] >= '0' && p0[2] <= '9') ||
+             (p0[1] == '3' && p0[2] >= '0' && p0[2] <= '5')) &&
+            !p0[3]) {
+    *code = xpdfKeyCodeF1 + 10 * (p0[1] - '0') + (p0[2] - '0') - 1;
+  } else if (!strncmp(p0, "mousePress", 10) &&
+            p0[10] >= '0' && p0[10] <= '9' &&
+            (!p0[11] || (p0[11] >= '0' && p0[11] <= '9' && !p0[12])) &&
+            (btn = atoi(p0 + 10)) >= 1 && btn <= 32) {
+    *code = xpdfKeyCodeMousePress1 + btn - 1;
+  } else if (!strncmp(p0, "mouseRelease", 12) &&
+            p0[12] >= '0' && p0[12] <= '9' &&
+            (!p0[13] || (p0[13] >= '0' && p0[13] <= '9' && !p0[14])) &&
+            (btn = atoi(p0 + 12)) >= 1 && btn <= 32) {
+    *code = xpdfKeyCodeMouseRelease1 + btn - 1;
+  } else if (*p0 >= 0x20 && *p0 <= 0x7e && !p0[1]) {
+    *code = (int)*p0;
+  } else {
+    error(errConfig, -1,
+         "Bad key/modifier in '{0:s}' config file command ({1:t}:{2:d})",
+         cmdName, fileName, line);
+    return gFalse;
+  }
+
+  p0 = contextStr->getCString();
+  if (!strcmp(p0, "any")) {
+    *context = xpdfKeyContextAny;
+  } else {
+    *context = xpdfKeyContextAny;
+    while (1) {
+      if (!strncmp(p0, "fullScreen", 10)) {
+       *context |= xpdfKeyContextFullScreen;
+       p0 += 10;
+      } else if (!strncmp(p0, "window", 6)) {
+       *context |= xpdfKeyContextWindow;
+       p0 += 6;
+      } else if (!strncmp(p0, "continuous", 10)) {
+       *context |= xpdfKeyContextContinuous;
+       p0 += 10;
+      } else if (!strncmp(p0, "singlePage", 10)) {
+       *context |= xpdfKeyContextSinglePage;
+       p0 += 10;
+      } else if (!strncmp(p0, "overLink", 8)) {
+       *context |= xpdfKeyContextOverLink;
+       p0 += 8;
+      } else if (!strncmp(p0, "offLink", 7)) {
+       *context |= xpdfKeyContextOffLink;
+       p0 += 7;
+      } else if (!strncmp(p0, "outline", 7)) {
+       *context |= xpdfKeyContextOutline;
+       p0 += 7;
+      } else if (!strncmp(p0, "mainWin", 7)) {
+       *context |= xpdfKeyContextMainWin;
+       p0 += 7;
+      } else if (!strncmp(p0, "scrLockOn", 9)) {
+       *context |= xpdfKeyContextScrLockOn;
+       p0 += 9;
+      } else if (!strncmp(p0, "scrLockOff", 10)) {
+       *context |= xpdfKeyContextScrLockOff;
+       p0 += 10;
+      } else {
+       error(errConfig, -1,
+             "Bad context in '{0:s}' config file command ({1:t}:{2:d})",
+             cmdName, fileName, line);
+       return gFalse;
+      }
+      if (!*p0) {
+       break;
+      }
+      if (*p0 != ',') {
+       error(errConfig, -1,
+             "Bad context in '{0:s}' config file command ({1:t}:{2:d})",
+             cmdName, fileName, line);
+       return gFalse;
+      }
+      ++p0;
+    }
+  }
+
+  return gTrue;
+}
+
 void XpdfParams::parseCommand(const char *cmdName, GString **val,
                               GList *tokens, GString *fileName, int line) {
   if (tokens->getLength() != 2) {
     error(errConfig, -1, "Bad '{0:s}' config file command ({1:t}:{2:d})",
           cmdName, fileName, line);
     return;
@@ -296,12 +490,16 @@
     } else if (!cmd->cmp("launchCommand")) {
       parseCommand("launchCommand", &launchCommand, tokens, fileName, line);
     } else if (!cmd->cmp("urlCommand")) {
       parseCommand("urlCommand", &urlCommand, tokens, fileName, line);
     } else if (!cmd->cmp("movieCommand")) {
       parseCommand("movieCommand", &movieCommand, tokens, fileName, line);
+    } else if (!cmd->cmp("bind")) {
+      parseBind(tokens, fileName, line);
+    } else if (!cmd->cmp("unbind")) {
+      parseUnbind(tokens, fileName, line);
     }
   }
 
   deleteGList(tokens, GString);
 }
 

-- System Information:
Debian Release: jessie/sid
  APT prefers testing
  APT policy: (990, 'testing'), (500, 'unstable'), (500, 'stable'), (1, 
'experimental')
Architecture: amd64 (x86_64)
Foreign Architectures: i386

Kernel: Linux 3.12-1-amd64 (SMP w/4 CPU cores)
Locale: LANG=en_US.UTF-8, LC_CTYPE=en_US.UTF-8 (charmap=UTF-8) (ignored: LC_ALL 
set to en_US.UTF-8)
Shell: /bin/sh linked to /bin/dash

Versions of packages xpdf depends on:
ii  libc6         2.17-97
ii  libgcc1       1:4.8.2-15
ii  libpoppler44  0.24.5-1
ii  libstdc++6    4.8.2-15
ii  libx11-6      2:1.6.2-1
ii  libxm4        2.3.4-5
ii  libxt6        1:1.1.4-1

Versions of packages xpdf recommends:
ii  cups-bsd       1.7.1-4
ii  gsfonts-x11    0.22
ii  poppler-data   0.4.6-4
ii  poppler-utils  0.22.5-4

xpdf suggests no packages.

-- no debconf information


-- 
To UNSUBSCRIBE, email to debian-bugs-dist-requ...@lists.debian.org
with a subject of "unsubscribe". Trouble? Contact listmas...@lists.debian.org

Reply via email to