diff --git a/src/modules/Regexp/Makefile.in b/src/modules/Regexp/Makefile.in
index 21853b9fc4c4f4ec9110cbd08caed4824af78aa6..33850edf041a572cd9ebea8590df1d3ff985c135 100644
--- a/src/modules/Regexp/Makefile.in
+++ b/src/modules/Regexp/Makefile.in
@@ -1,6 +1,6 @@
 SRCDIR=@srcdir@
 VPATH=@srcdir@:@srcdir@/../..:../..
-OBJS=regexp.o glue.o
+OBJS=glue.o @REGEXP_OBJS@ 
 
 @dynamic_module_makefile@
 @dependencies@
\ No newline at end of file
diff --git a/src/modules/Regexp/configure.in b/src/modules/Regexp/configure.in
index ed3283c8eec415697210f9591f054dac166c5e4c..67ddee25ddce4b09cca50ca1b69f5d00706675dd 100644
--- a/src/modules/Regexp/configure.in
+++ b/src/modules/Regexp/configure.in
@@ -1,7 +1,24 @@
-AC_INIT(regexp.c)
+AC_INIT(pike_regexp.c)
+AC_CONFIG_HEADER(config.h)
 
 sinclude(../module_configure.in)
 
+AC_HAVE_HEADERS(regexp.h)
+
+AC_CHECK_FUNCS(regcomp regexec regerror regfree)
+
+AC_MSG_CHECKING(C lib has regexps)
+
+if test $ac_cv_header_regexp_h$ac_cv_func_regcomp$ac_cv_func_regexec$ac_cv_func_regerror$ac_cv_func_regfree = yesyesyesyesyes ; then
+    AC_DEFINE(USE_SYSTEM_REGEXP)
+    REGEXP_OBJS=""
+    AC_MSG_RESULT(yes)
+else
+    REGEXP_OBJS="pike_regexp.o"
+    AC_MSG_RESULT(no)
+fi
+
+AC_SUBST(REGEXP_OBJS)
 
 AC_OUTPUT(Makefile,echo FOO >stamp-h )
 
diff --git a/src/modules/Regexp/glue.c b/src/modules/Regexp/glue.c
index 9da6245d8aeb83cb7574379c8f0c5a69bab9b722..d12810c6df6c2c367ee09062138848eabd8d7a5b 100644
--- a/src/modules/Regexp/glue.c
+++ b/src/modules/Regexp/glue.c
@@ -3,6 +3,11 @@
 ||| Pike is distributed as GPL (General Public License)
 ||| See the files COPYING and DISCLAIMER for more information.
 \*/
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif /* HAVE_CONFIG_H */
+
 #include "global.h"
 #include "types.h"
 #include "interpret.h"
@@ -11,47 +16,93 @@
 #include "array.h"
 #include "object.h"
 #include "macros.h"
+#include "threads.h"
 
+#ifdef USE_SYSTEM_REGEXP
 #include <regexp.h>
 
+struct regexp_glue
+{
+  regex_t regexp;
+  int num_paren;
+};
+#else
+#include <pike_regexp.h>
+
 struct regexp_glue
 {
   struct regexp *regexp;
 };
 
+#endif /* USE_SYSTEM_REGEXP */
+
+
 #define THIS ((struct regexp_glue *)(fp->current_storage))
 
 static void do_free()
 {
   if(THIS->regexp)
   {
+#ifdef USE_SYSTEM_REGEXP
+    regfree(&(THIS->regexp));
+#else
     free((char *)THIS->regexp);
     THIS->regexp=0;
+#endif /* USE_SYSTEM_REGEXP */
   }
 }
 
 static void regexp_create(INT32 args)
 {
+  const char *str;
+
   do_free();
   if(args)
   {
-    if(sp[-args].type != T_STRING)
-      error("Bad argument 1 to regexp->create()\n");
+    get_all_args("Regexp.regexp->create", args, "%s", &str);
+
+#ifdef USE_SYSTEM_REGEXP
+    {
+      int err = regcomp(&(THIS->regexp), str, 0);
+      int i;
+      char *paren_ptr;
+
+      if (err) {
+	char buf[1024];
 
+	regerror(err, &(THIS->regexp), buf, 1024);
+	error("Regexp.regexp->create(): Compilation failed:%s\n", buf);
+      }
+      for (i=0,paren_ptr=str; paren_ptr = strchr(paren_ptr, '('); i++) {
+	paren_ptr++;
+      }
+      THIS->num_paren = i;
+    }
+#else
     THIS->regexp=regcomp(sp[-args].u.string->str, 0);
+#endif
   }
 }
 
 static void regexp_match(INT32 args)
 {
   int i;
-  if(!args)
-    error("Too few arguments to regexp->match()\n");
-
-  if(sp[-args].type != T_STRING)
-    error("Bad argument 1 to regexp->match()\n");
-
-  i=regexec(THIS->regexp, sp[-args].u.string->str);
+  const char *str;
+#ifdef USE_SYSTEM_REGEXP
+  regex_t *regexp = &(THIS->regexp);
+#else
+  struct regexp *regexp = THIS->regexp;
+#endif /* USE_SYSTEM_REGEXP */
+
+  get_all_args("Regexp.regexp->match", args, "%s", &str);
+  
+#ifdef USE_SYSTEM_REGEXP
+  ALLOW_THREADS();
+  i = !regexec(regexp, str, 0, NULL, 0);
+  DISALLOW_THREADS();
+#else
+  i=regexec(regexp, str);
+#endif /* USE_SYSTEM_REGEXP */
   pop_n_elems(args);
   push_int(i);
 }
@@ -59,14 +110,47 @@ static void regexp_match(INT32 args)
 static void regexp_split(INT32 args)
 {
   struct pike_string *s;
+#ifdef USE_SYSTEM_REGEXP
+  regex_t *r;
+  regmatch_t *pmatch;
+  size_t nmatch;
+  int match;
+#else  
   struct regexp *r;
-  if(!args)
-    error("Too few arguments to regexp->split()\n");
+#endif /* USE_SYSTEM_REGEXP */
+
+  get_all_args("Regexp.regexp->split", args, "%S", &s);
+
+#ifdef USE_SYSTEM_REGEXP
+  r = &(THIS->regexp);
+  nmatch = THIS->num_paren+1;
+  pmatch = xalloc(sizeof(regmatch_t)*nmatch);
 
-  if(sp[-args].type != T_STRING)
-    error("Bad argument 1 to regexp->split()\n");
+  THREADS_ALLOW();
+  match = !regexec(r, s->str, nmatch, pmatch, 0);
+  THREADS_DISALLOW();
+
+  if (match) {
+    int i,j;
+    
+    s->refs++;
+    pop_n_elems(args);
 
-  s=sp[-args].u.string;
+    for (i=1; i < nmatch; i++) {
+      if (pmatch[i].rm_sp && pmatch[i].rm_so != -1) {
+	push_string(make_shared_binary_string(pmatch[i].rm_sp,
+					      pmatch[i].rm_eo-pmatch[i].rm_so));
+      } else {
+	push_int(0);
+      }
+    }
+    f_aggregate_array(nmatch-1);
+    free_string(s);
+  } else {
+    pop_n_elems(args);
+    push_int(0);
+  }
+#else
   if(regexec(r=THIS->regexp, s->str))
   {
     int i,j;
@@ -90,11 +174,16 @@ static void regexp_split(INT32 args)
     pop_n_elems(args);
     push_int(0);
   }
+#endif /* USE_SYSTEM_REGEXP */
 }
 
 static void init_regexp_glue(struct object *o)
 {
+#ifdef USE_SYSTEM_REGEXP
+  MEMCLR(THIS, sizeof(struct regexp_glue));
+#else
   THIS->regexp=0;
+#endif /* USE_SYSTEM_REGEXP */
 }
 
 static void exit_regexp_glue(struct object *o)