From c8f7315518c85dbb14e50f428b4cf601aba4c89e Mon Sep 17 00:00:00 2001 From: Mark Pizzolato Date: Thu, 2 Jan 2020 06:42:46 -0800 Subject: [PATCH] SCP: Change regular expression API from regex to pcre --- Visual Studio Projects/3B2.vcproj | 6 +- Visual Studio Projects/ALTAIR.vcproj | 6 +- Visual Studio Projects/AltairZ80.vcproj | 6 +- Visual Studio Projects/B5500.vcproj | 6 +- Visual Studio Projects/BESM6.vcproj | 6 +- Visual Studio Projects/BuildROMs.vcproj | 2 +- Visual Studio Projects/CDC1700.vcproj | 6 +- Visual Studio Projects/ECLIPSE.vcproj | 6 +- Visual Studio Projects/FrontPanelTest.vcproj | 2 +- Visual Studio Projects/GRI.vcproj | 6 +- Visual Studio Projects/H316.vcproj | 6 +- Visual Studio Projects/HP2100.vcproj | 6 +- Visual Studio Projects/HP3000.vcproj | 6 +- Visual Studio Projects/I1401.vcproj | 6 +- Visual Studio Projects/I1620.vcproj | 6 +- Visual Studio Projects/I650.vcproj | 6 +- Visual Studio Projects/I701.vcproj | 6 +- Visual Studio Projects/I7010.vcproj | 6 +- Visual Studio Projects/I704.vcproj | 6 +- Visual Studio Projects/I7070.vcproj | 6 +- Visual Studio Projects/I7080.vcproj | 6 +- Visual Studio Projects/I7090.vcproj | 6 +- Visual Studio Projects/I7094.vcproj | 6 +- Visual Studio Projects/IBM1130.vcproj | 6 +- Visual Studio Projects/ID16.vcproj | 6 +- Visual Studio Projects/ID32.vcproj | 6 +- Visual Studio Projects/InfoServer100.vcproj | 6 +- Visual Studio Projects/InfoServer1000.vcproj | 6 +- .../InfoServer150VXT.vcproj | 6 +- Visual Studio Projects/MicroVAX1.vcproj | 6 +- Visual Studio Projects/MicroVAX2.vcproj | 6 +- Visual Studio Projects/MicroVAX2000.vcproj | 6 +- Visual Studio Projects/MicroVAX3100.vcproj | 6 +- Visual Studio Projects/MicroVAX3100M80.vcproj | 6 +- Visual Studio Projects/MicroVAX3100e.vcproj | 6 +- Visual Studio Projects/NOVA.vcproj | 6 +- Visual Studio Projects/PDP1.vcproj | 6 +- Visual Studio Projects/PDP10-KA.vcproj | 6 +- Visual Studio Projects/PDP10-KI.vcproj | 6 +- Visual Studio Projects/PDP10.vcproj | 6 +- Visual Studio Projects/PDP11.vcproj | 6 +- Visual Studio Projects/PDP15.vcproj | 6 +- Visual Studio Projects/PDP4.vcproj | 6 +- Visual Studio Projects/PDP6.vcproj | 6 +- Visual Studio Projects/PDP7.vcproj | 6 +- Visual Studio Projects/PDP8.vcproj | 6 +- Visual Studio Projects/PDP9.vcproj | 6 +- Visual Studio Projects/PDQ3.vcproj | 6 +- Visual Studio Projects/S3.vcproj | 6 +- Visual Studio Projects/SAGE.vcproj | 6 +- Visual Studio Projects/SDS.vcproj | 6 +- Visual Studio Projects/SSEM.vcproj | 6 +- Visual Studio Projects/TX-0.vcproj | 6 +- Visual Studio Projects/UC15.vcproj | 6 +- Visual Studio Projects/VAX.vcproj | 6 +- Visual Studio Projects/VAX730.vcproj | 6 +- Visual Studio Projects/VAX750.vcproj | 6 +- Visual Studio Projects/VAX780.vcproj | 6 +- Visual Studio Projects/VAX8200.vcproj | 6 +- Visual Studio Projects/VAX8600.vcproj | 6 +- .../VAXstation3100M30.vcproj | 6 +- .../VAXstation3100M38.vcproj | 6 +- .../VAXstation3100M76.vcproj | 6 +- .../VAXstation4000M60.vcproj | 6 +- .../VAXstation4000VLC.vcproj | 6 +- Visual Studio Projects/alpha.vcproj | 6 +- Visual Studio Projects/ibmpc.vcproj | 6 +- Visual Studio Projects/ibmpcxt.vcproj | 6 +- Visual Studio Projects/imds-210.vcproj | 6 +- Visual Studio Projects/imds-220.vcproj | 6 +- Visual Studio Projects/imds-225.vcproj | 6 +- Visual Studio Projects/imds-230.vcproj | 6 +- Visual Studio Projects/imds-800.vcproj | 6 +- Visual Studio Projects/imds-810.vcproj | 6 +- Visual Studio Projects/isys8010.vcproj | 6 +- Visual Studio Projects/isys8020.vcproj | 6 +- Visual Studio Projects/isys8024.vcproj | 6 +- Visual Studio Projects/isys8030.vcproj | 6 +- Visual Studio Projects/lgp.vcproj | 6 +- Visual Studio Projects/rtVAX1000.vcproj | 6 +- Visual Studio Projects/scelbi.vcproj | 6 +- Visual Studio Projects/sigma.vcproj | 6 +- Visual Studio Projects/swtp6800mp-a.vcproj | 6 +- Visual Studio Projects/swtp6800mp-a2.vcproj | 6 +- makefile | 16 ++--- scp.c | 59 ++++++++++--------- sim_defs.h | 6 +- 87 files changed, 289 insertions(+), 288 deletions(-) diff --git a/Visual Studio Projects/3B2.vcproj b/Visual Studio Projects/3B2.vcproj index 7b5220d0..9db32713 100644 --- a/Visual Studio Projects/3B2.vcproj +++ b/Visual Studio Projects/3B2.vcproj @@ -41,7 +41,7 @@ Name="VCCLCompilerTool" Optimization="0" AdditionalIncludeDirectories="../3B2/;./;../;../slirp;../slirp_glue;../slirp_glue/qemu;../slirp_glue/qemu/win32/include;../../windows-build/include;;../../windows-build/include/SDL2" - PreprocessorDefinitions="_CRT_NONSTDC_NO_WARNINGS;_CRT_SECURE_NO_WARNINGS;_WINSOCK_DEPRECATED_NO_WARNINGS;SIM_NEED_GIT_COMMIT_ID;HAVE_PCREPOSIX_H;PCRE_STATIC;USE_INT64;USE_ADDR64;USE_SHARED;PTW32_STATIC_LIB;SIM_ASYNCH_IO;USE_READER_THREAD;HAVE_SLIRP_NETWORK;USE_SIMH_SLIRP_DEBUG" + PreprocessorDefinitions="_CRT_NONSTDC_NO_WARNINGS;_CRT_SECURE_NO_WARNINGS;_WINSOCK_DEPRECATED_NO_WARNINGS;SIM_NEED_GIT_COMMIT_ID;HAVE_PCRE_H;PCRE_STATIC;USE_INT64;USE_ADDR64;USE_SHARED;PTW32_STATIC_LIB;SIM_ASYNCH_IO;USE_READER_THREAD;HAVE_SLIRP_NETWORK;USE_SIMH_SLIRP_DEBUG" KeepComments="false" BasicRuntimeChecks="0" RuntimeLibrary="1" @@ -62,7 +62,7 @@ /> match_pattern); /* deallocate the displa free (ep->act); /* deallocate action */ #if defined(USE_REGEX) if (ep->switches & EXP_TYP_REGEX) - regfree (&ep->regex); /* release compiled regex */ + pcre_free (ep->regex); /* release compiled regex */ #endif exp->size -= 1; /* decrement count */ for (i=ep-exp->rules; isize; i++) /* shuffle up remaining rules */ @@ -11941,7 +11939,7 @@ for (i=0; isize; i++) { free (exp->rules[i].act); /* deallocate action */ #if defined(USE_REGEX) if (exp->rules[i].switches & EXP_TYP_REGEX) - regfree (&exp->rules[i].regex); /* release compiled regex */ + pcre_free (exp->rules[i].regex); /* release compiled regex */ #endif } free (exp->rules); @@ -11973,25 +11971,21 @@ if (switches & EXP_TYP_REGEX) { return sim_messagef (SCPE_ARG, "RegEx support not available\n"); } #else /* USE_REGEX */ - int res; - regex_t re; + pcre *re; + const char *errmsg; + int erroffset, re_nsub; - memset (&re, 0, sizeof(re)); memcpy (match_buf, match+1, strlen(match)-2); /* extract string without surrounding quotes */ match_buf[strlen(match)-2] = '\0'; - res = regcomp (&re, (char *)match_buf, REG_EXTENDED | ((switches & EXP_TYP_REGEX_I) ? REG_ICASE : 0)); - if (res) { - size_t err_size = regerror (res, &re, NULL, 0); - char *err_buf = (char *)calloc (err_size+1, 1); - - regerror (res, &re, err_buf, err_size); - sim_messagef (SCPE_ARG, "Regular Expression Error: %s\n", err_buf); - free (err_buf); + re = pcre_compile (match_buf, (switches & EXP_TYP_REGEX_I) ? PCRE_CASELESS : 0, &errmsg, &erroffset, NULL); + if (re == NULL) { + sim_messagef (SCPE_ARG, "Regular Expression Error: %s\n", errmsg); free (match_buf); return SCPE_ARG|SCPE_NOMESSAGE; } - sim_debug (exp->dbit, exp->dptr, "Expect Regular Expression: \"%s\" has %d sub expressions\n", match_buf, (int)re.re_nsub); - regfree (&re); + (void)pcre_fullinfo(re, NULL, PCRE_INFO_CAPTURECOUNT, &re_nsub); + sim_debug (exp->dbit, exp->dptr, "Expect Regular Expression: \"%s\" has %d sub expressions\n", match_buf, re_nsub); + pcre_free (re); } #endif else { @@ -12031,9 +12025,13 @@ if ((match_buf == NULL) || (ep->match_pattern == NULL)) { } if (switches & EXP_TYP_REGEX) { #if defined(USE_REGEX) + const char *errmsg; + int erroffset; + memcpy (match_buf, match+1, strlen(match)-2); /* extract string without surrounding quotes */ match_buf[strlen(match)-2] = '\0'; - regcomp (&ep->regex, (char *)match_buf, REG_EXTENDED); + ep->regex = pcre_compile ((char *)match_buf, (switches & EXP_TYP_REGEX_I) ? PCRE_CASELESS : 0, &errmsg, &erroffset, NULL); + (void)pcre_fullinfo(ep->regex, NULL, PCRE_INFO_CAPTURECOUNT, &ep->re_nsub); #endif free (match_buf); match_buf = NULL; @@ -12168,7 +12166,8 @@ for (i=0; i < exp->size; i++) { ep = &exp->rules[i]; if (ep->switches & EXP_TYP_REGEX) { #if defined (USE_REGEX) - regmatch_t *matches; + int *ovector = NULL; + int rc; char *cbuf = (char *)exp->buf; static size_t sim_exp_match_sub_count = 0; @@ -12186,23 +12185,24 @@ for (i=0; i < exp->size; i++) { } } ++regex_checks; - matches = (regmatch_t *)calloc ((ep->regex.re_nsub + 1), sizeof(*matches)); + ovector = (int *)malloc (3 * (ep->re_nsub + 1) * sizeof (*ovector)); if (sim_deb && exp->dptr && (exp->dptr->dctrl & exp->dbit)) { char *estr = sim_encode_quoted_string (exp->buf, exp->buf_ins); sim_debug (exp->dbit, exp->dptr, "Checking String: %s\n", estr); sim_debug (exp->dbit, exp->dptr, "Against RegEx Match Rule: %s\n", ep->match_pattern); free (estr); } - if (!regexec (&ep->regex, cbuf, ep->regex.re_nsub + 1, matches, REG_NOTBOL)) { + rc = pcre_exec (ep->regex, NULL, cbuf, exp->buf_ins, 0, PCRE_NOTBOL, ovector, 3 * (ep->re_nsub + 1)); + if (rc >= 0) { size_t j; char *buf = (char *)malloc (1 + exp->buf_ins); - for (j=0; jregex.re_nsub + 1; j++) { + for (j=0; j < (size_t)rc; j++) { char env_name[32]; sprintf (env_name, "_EXPECT_MATCH_GROUP_%d", (int)j); - memcpy (buf, &cbuf[matches[j].rm_so], matches[j].rm_eo-matches[j].rm_so); - buf[matches[j].rm_eo-matches[j].rm_so] = '\0'; + memcpy (buf, &cbuf[ovector[2 * j]], ovector[2 * j + 1] - ovector[2 * j]); + buf[ovector[2 * j + 1] - ovector[2 * j]] = '\0'; setenv (env_name, buf, 1); /* Make the match and substrings available as environment variables */ sim_debug (exp->dbit, exp->dptr, "%s=%s\n", env_name, buf); } @@ -12212,12 +12212,13 @@ for (i=0; i < exp->size; i++) { sprintf (env_name, "_EXPECT_MATCH_GROUP_%d", (int)j); setenv (env_name, "", 1); /* Remove previous extra environment variables */ } - sim_exp_match_sub_count = ep->regex.re_nsub; - free (matches); + sim_exp_match_sub_count = ep->re_nsub; + free (ovector); + ovector = NULL; free (buf); break; } - free (matches); + free (ovector); #endif } else { diff --git a/sim_defs.h b/sim_defs.h index b793ae8e..f68d0a6f 100644 --- a/sim_defs.h +++ b/sim_defs.h @@ -146,8 +146,7 @@ extern int sim_vax_snprintf(char *buf, size_t buf_size, const char *fmt, ...); #ifdef USE_REGEX #undef USE_REGEX #endif -#if defined(HAVE_PCREPOSIX_H) -#include +#if defined(HAVE_PCRE_H) #include #define USE_REGEX 1 #endif @@ -815,7 +814,8 @@ struct EXPTAB { #define EXP_TYP_REGEX_I (SWMASK ('I')) /* regular expression pattern matching should be case independent */ #define EXP_TYP_TIME (SWMASK ('T')) /* halt delay is in microseconds instead of instructions */ #if defined(USE_REGEX) - regex_t regex; /* compiled regular expression */ + pcre *regex; /* compiled regular expression */ + int re_nsub; /* regular expression sub expression count */ #endif char *act; /* action string */ };