]> granicus.if.org Git - nethack/commitdiff
Implement a new system-based matching harness.
authorSean Hunt <scshunt@csclub.uwaterloo.ca>
Fri, 3 Apr 2015 18:07:53 +0000 (14:07 -0400)
committerSean Hunt <scshunt@csclub.uwaterloo.ca>
Sun, 12 Apr 2015 15:46:26 +0000 (11:46 -0400)
The intent is to look for platform-specific facilities for regex
matching, to provide portable MENUCOLORS configuration files.

This is a prototype implementation being committed to see if Windows can
use the POSIX regex implementation provided with the C++11 standard
library. If this works, I will write a harness for POSIX regexes and for
pmatch(), and those can be linked in by platforms as appropriate.

pmatch() should be used only as a very last resort, because it breaks
compatibility between platforms.

include/color.h
include/config.h
include/nhregex.h [new file with mode: 0644]
src/options.c
sys/share/cppregex.cpp [new file with mode: 0644]

index f7bec4a08e6e01c808e7a593e9d0d46b35642188..56c43af1546304f366b73007bc97650ff0fb9e14 100644 (file)
@@ -1,4 +1,4 @@
-/* NetHack 3.5 color.h $NHDT-Date$  $NHDT-Branch$:$NHDT-Revision$ */
+/* NetHack 3.5 color.h $NHDT-Date: 1428084467 2015/04/03 18:07:47 $  $NHDT-Branch: scshunt-regex $:$NHDT-Revision: 1.7 $ */
 /* NetHack 3.5 color.h $Date: 2009/05/06 10:44:34 $  $Revision: 1.5 $ */
 /*     SCCS Id: @(#)color.h    3.5     1992/02/02      */
 /* Copyright (c) Steve Linhart, Eric Raymond, 1989. */
@@ -7,9 +7,7 @@
 #ifndef COLOR_H
 #define COLOR_H
 
-#ifdef MENU_COLOR_REGEX
-#include <regex.h>
-#endif
+#include <nhregex.h>
 
 /*
  * The color scheme used is tailored for an IBM PC.  It consists of the
 #define HI_ZAP         CLR_BRIGHT_BLUE
 
 struct menucoloring {
-# ifdef MENU_COLOR_REGEX
-#  ifdef MENU_COLOR_REGEX_POSIX
-    regex_t match;
-#  else
-    struct re_pattern_buffer match;
-#  endif
-# else
-    char *match;
-# endif
+    struct nhregex *match;
     int color, attr;
     struct menucoloring *next;
 };
index 4cce7dba823a90182bc3ee5f89718a68349a097c..5fc3d0d8fd1c297e0b2fe83fb869615600aaea10 100644 (file)
@@ -1,4 +1,4 @@
-/* NetHack 3.5 config.h        $NHDT-Date: 1425083082 2015/02/28 00:24:42 $  $NHDT-Branch: master $:$NHDT-Revision: 1.51 $ */
+/* NetHack 3.5 config.h        $NHDT-Date: 1428084467 2015/04/03 18:07:47 $  $NHDT-Branch: scshunt-regex $:$NHDT-Revision: 1.76 $ */
 /* NetHack 3.5 config.h        $Date: 2012/01/27 20:15:26 $  $Revision: 1.37 $ */
 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
 /* NetHack may be freely redistributed.  See license for details. */
@@ -436,18 +436,6 @@ typedef unsigned char      uchar;
  * bugs left here.
  */
 
-/* Menucolors */
-/* HACK: this is being added to fix the builds temporarily.
- * Remove it whenever we finally get a real regex for Win32 */
-#ifdef UNIX
-# define MENU_COLOR_REGEX  /* use GNU regex */
-/*# define MENU_COLOR_REGEX_POSIX*/ /* use POSIX regex */
-#endif
-/* if neither is defined, uses pmatch()
- * pmatch() provides basic globbing: '*' and '?' wildcards.
- */
-
-
 #define STATUS_VIA_WINDOWPORT  /* re-work of the status line updating process */
 #define STATUS_HILITES         /* support hilites of status fields */
 /* #define WINCHAIN*/          /* stacked window systems */
diff --git a/include/nhregex.h b/include/nhregex.h
new file mode 100644 (file)
index 0000000..1708b56
--- /dev/null
@@ -0,0 +1,19 @@
+/* NetHack 3.5 nhregex.h       $NHDT-Date: 1428084467 2015/04/03 18:07:47 $  $NHDT-Branch: scshunt-regex $:$NHDT-Revision: 1.0 $ */
+/* NetHack 3.5 nhregex.h       $Date: 2009/05/06 10:44:33 $  $Revision: 1.4 $ */
+/* Copyright (c) Sean Hunt  2015.                                 */
+/* NetHack may be freely redistributed.  See license for details. */
+
+#ifndef NHREGEX_H
+#define NHREGEX_H
+
+#include <hack.h>
+
+struct nhregex;
+
+struct nhregex *regex_init(void);
+boolean regex_compile(const char *s, struct nhregex *re);
+const char *regex_error_desc(struct nhregex *re);
+boolean regex_match(const char *s, struct nhregex *re);
+void regex_free(struct nhregex *re);
+
+#endif
index c65f3db28cf2abc1756a258c2ddb95e4eff8954f..3925b2a14048481f968e1d9b903cc7543f50fbd0 100644 (file)
@@ -1,4 +1,4 @@
-/* NetHack 3.5 options.c       $NHDT-Date: 1427073746 2015/03/23 01:22:26 $  $NHDT-Branch: master $:$NHDT-Revision: 1.164 $ */
+/* NetHack 3.5 options.c       $NHDT-Date: 1428084467 2015/04/03 18:07:47 $  $NHDT-Branch: scshunt-regex $:$NHDT-Revision: 1.181 $ */
 /* NetHack 3.5 options.c       $Date: 2012/04/09 02:56:30 $  $Revision: 1.153 $ */
 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
 /* NetHack may be freely redistributed.  See license for details. */
@@ -15,6 +15,7 @@ NEARDATA struct instance_flags iflags;        /* provide linkage */
 #define static
 #else
 #include "hack.h"
+#include "nhregex.h"
 #include "tcap.h"
 #include <ctype.h>
 #endif
@@ -1170,11 +1171,6 @@ char *str;
     int i, c = NO_COLOR, a = ATR_NONE;
     struct menucoloring *tmp;
     char *tmps, *cs = strchr(str, '=');
-#ifdef MENU_COLOR_REGEX_POSIX
-    int errnum;
-    char errbuf[80];
-#endif
-    const char *err = (char *)0;
 
     if (!cs || !str) return FALSE;
 
@@ -1217,28 +1213,9 @@ char *str;
     }
 
     tmp = (struct menucoloring *)alloc(sizeof(struct menucoloring));
-#ifdef MENU_COLOR_REGEX
-#ifdef MENU_COLOR_REGEX_POSIX
-    errnum = regcomp(&tmp->match, tmps, REG_EXTENDED | REG_NOSUB);
-    if (errnum != 0)
-    {
-       regerror(errnum, &tmp->match, errbuf, sizeof(errbuf));
-       err = errbuf;
-    }
-#else
-    tmp->match.translate = 0;
-    tmp->match.fastmap = 0;
-    tmp->match.buffer = 0;
-    tmp->match.allocated = 0;
-    tmp->match.regs_allocated = REGS_FIXED;
-    err = re_compile_pattern(tmps, strlen(tmps), &tmp->match);
-#endif
-#else
-    tmp->match = (char *)alloc(strlen(tmps)+1);
-    (void) memcpy((genericptr_t)tmp->match, (genericptr_t)tmps, strlen(tmps)+1);
-#endif
-    if (err) {
-       raw_printf("\nMenucolor regex error: %s\n", err);
+    tmp->match = regex_init();
+    if (!regex_compile(tmps, tmp->match)) {
+       raw_printf("\nMenucolor regex error: %s\n", regex_error_desc(tmp->match));
        wait_synch();
        free(tmp);
        return FALSE;
@@ -1259,15 +1236,7 @@ int *color, *attr;
     struct menucoloring *tmpmc;
     if (iflags.use_menu_color)
        for (tmpmc = menu_colorings; tmpmc; tmpmc = tmpmc->next)
-#ifdef MENU_COLOR_REGEX
-# ifdef MENU_COLOR_REGEX_POSIX
-           if (regexec(&tmpmc->match, str, 0, NULL, 0) == 0) {
-# else
-           if (re_search(&tmpmc->match, str, strlen(str), 0, 9999, 0) >= 0) {
-# endif
-#else
-           if (pmatch(tmpmc->match, str)) {
-#endif
+            if (regex_match(str, tmpmc->match)) {
                *color = tmpmc->color;
                *attr = tmpmc->attr;
                return TRUE;
@@ -1282,11 +1251,7 @@ free_menu_coloring()
 
     while (tmp) {
        struct menucoloring *tmp2 = tmp->next;
-#ifdef MENU_COLOR_REGEX
-       (void) regfree(&tmp->match);
-#else
-       free(tmp->match);
-#endif
+        regex_free(tmp->match);
        free(tmp);
        tmp = tmp2;
     }
diff --git a/sys/share/cppregex.cpp b/sys/share/cppregex.cpp
new file mode 100644 (file)
index 0000000..446929c
--- /dev/null
@@ -0,0 +1,51 @@
+/* NetHack 3.5  cppregex.cpp   $NHDT-Date$  $NHDT-Branch$:$NHDT-Revision$ */
+/* NetHack 3.5 cppregex.cpp    $Date: 2009/05/06 10:44:33 $  $Revision: 1.4 $ */
+/* Copyright (c) Sean Hunt  2015.                                 */
+/* NetHack may be freely redistributed.  See license for details. */
+
+#include <regex>
+#include <memory>
+
+extern "C" {
+  #include <nhregex.h>
+
+  struct nhregex {
+    std::unique_ptr<std::regex> re;
+    std::unique_ptr<std::regex_error> err;
+  };
+
+  struct nhregex *regex_init(void) {
+    return new nhregex;
+  }
+
+  boolean regex_compile(const char *s, struct nhregex *re) {
+    if (!re)
+      return FALSE;
+    try {
+      re->re.reset(new std::regex(s, std::regex::extended | std::regex::nosubs | std::regex::optimize));
+      re->err.reset(nullptr);
+      return TRUE;
+    } catch (const std::regex_error& err) {
+      re->err.reset(new std::regex_error(err));
+      re->re.reset(nullptr);
+      return FALSE;
+    }
+  }
+
+  const char *regex_error_desc(struct nhregex *re) {
+    if (re->err)
+      return re->err->what();
+    else
+      return nullptr;
+  }
+
+  boolean regex_match(const char *s, struct nhregex *re) {
+    if (!re->re)
+      return false;
+    return regex_search(s, *re->re, std::regex_constants::match_any);
+  }
+
+  void regex_free(struct nhregex *re) {
+    delete re;
+  }
+}