]> diplodocus.org Git - flac-archive/commitdiff
switch to regex.h
authorepg@pretzelnet.org <>
Mon, 13 Jan 2014 06:56:18 +0000 (22:56 -0800)
committerepg@pretzelnet.org <>
Mon, 13 Jan 2014 06:56:18 +0000 (22:56 -0800)
id3v2-grep.cc

index be463ce..549644e 100644 (file)
@@ -1,4 +1,5 @@
 extern "C" {
 extern "C" {
+#include <regex.h>
 #include <unistd.h>
 }
 
 #include <unistd.h>
 }
 
@@ -24,12 +25,11 @@ static enum { PRINT_BOTH, PRINT_FILE, PRINT_MATCH, PRINT_NONE,
               PRINT_DEFAULT } print = PRINT_DEFAULT;
 static enum { GREP_BOTH, GREP_ID, GREP_TEXT } grep_frame = GREP_BOTH;
 
               PRINT_DEFAULT } print = PRINT_DEFAULT;
 static enum { GREP_BOTH, GREP_ID, GREP_TEXT } grep_frame = GREP_BOTH;
 
-// TODO: use regexec(3)
-static bool
-grep(const string &pattern,  TagLib::MPEG::File &file, const char *fn)
+static int
+grep(const regex_t &regex,  TagLib::MPEG::File &file, const char *fn)
 {
     if (!file.hasID3v2Tag()) {
 {
     if (!file.hasID3v2Tag()) {
-        return false;
+        return REG_NOMATCH;
     }
     bool found = false;
     for (const auto *frame : file.ID3v2Tag()->frameList()) {
     }
     bool found = false;
     for (const auto *frame : file.ID3v2Tag()->frameList()) {
@@ -46,9 +46,13 @@ grep(const string &pattern,  TagLib::MPEG::File &file, const char *fn)
             break;
         }
         const string &s = sstream.str();
             break;
         }
         const string &s = sstream.str();
-        if (s.find(pattern, 0) == string::npos) {
+        int status = regexec(&regex, s.c_str(), 0, nullptr, 0);
+        if (status == REG_NOMATCH) {
             continue;
         }
             continue;
         }
+        if (status != 0) {
+            return status;
+        }
         found = true;
         if (print == PRINT_BOTH) {
             cout << fn << ":" << s << endl;
         found = true;
         if (print == PRINT_BOTH) {
             cout << fn << ":" << s << endl;
@@ -59,18 +63,33 @@ grep(const string &pattern,  TagLib::MPEG::File &file, const char *fn)
     if (found && print == PRINT_FILE) {
         cout << fn << endl;
     }
     if (found && print == PRINT_FILE) {
         cout << fn << endl;
     }
-    return found;
+    return found ? 0 : REG_NOMATCH;
+}
+
+static void
+regex_error(int status, const regex_t &regex)
+{
+    char message[512];
+    regerror(status, &regex, message, sizeof(message));
+    cerr << message << endl;
 }
 
 int
 main(int argc, char **argv)
 {
 }
 
 int
 main(int argc, char **argv)
 {
-    char *pattern_c = nullptr;
+    bool ignore_case = false, use_ere = false;
+    char *pattern = nullptr;
     int c;
     int c;
-    while ((c = getopt(argc, argv, "e:HhlqsQ:")) != -1) {
+    while ((c = getopt(argc, argv, "Eie:HhlqsQ:")) != -1) {
         switch (c) {
         switch (c) {
+        case 'E':
+            use_ere = true;
+            break;
+        case 'i':
+            ignore_case = true;
+            break;
         case 'e':
         case 'e':
-            pattern_c = optarg;
+            pattern = optarg;
             break;
         case 'H':
             print = PRINT_BOTH;
             break;
         case 'H':
             print = PRINT_BOTH;
@@ -105,15 +124,23 @@ main(int argc, char **argv)
     argc -= optind; argv += optind;
 
     // TODO: multiple patterns
     argc -= optind; argv += optind;
 
     // TODO: multiple patterns
-    if (pattern_c == nullptr) {
+    if (pattern == nullptr) {
         if (argc == 0) {
             cerr << "no pattern" << endl;
             return 2;
         }
         if (argc == 0) {
             cerr << "no pattern" << endl;
             return 2;
         }
-        pattern_c = *argv++;
+        pattern = *argv++;
         argc--;
     }
         argc--;
     }
-    string pattern(pattern_c);
+    int cflags = REG_NOSUB;
+    if (ignore_case)  cflags |= REG_ICASE;
+    if (use_ere)  cflags |= REG_EXTENDED;
+    regex_t regex;
+    int status = regcomp(&regex, pattern, cflags);
+    if (status != 0) {
+        regex_error(status, regex);
+        return 3;
+    }
 
     if (print == PRINT_DEFAULT) {
         print = argc > 1 ? PRINT_BOTH : PRINT_MATCH;
 
     if (print == PRINT_DEFAULT) {
         print = argc > 1 ? PRINT_BOTH : PRINT_MATCH;
@@ -131,11 +158,17 @@ main(int argc, char **argv)
             bad_files++;
             continue;
         }
             bad_files++;
             continue;
         }
-        found |= grep(pattern, f, fn);
+        int status = grep(regex, f, fn);
+        if (status == 0) {
+            found = true;
+        } else if (status != REG_NOMATCH) {
+            regex_error(status, regex);
+            return 3;
+        }
     }
 
     if (bad_files > 0) {
     }
 
     if (bad_files > 0) {
-        return 3;
+        return 4;
     }
     if (found) {
         return 0;
     }
     if (found) {
         return 0;