libzypp  10.5.0
Regex.cc
Go to the documentation of this file.
00001 /*---------------------------------------------------------------------\
00002 |                          ____ _   __ __ ___                          |
00003 |                         |__  / \ / / . \ . \                         |
00004 |                           / / \ V /|  _/  _/                         |
00005 |                          / /__ | | | | | |                           |
00006 |                         /_____||_| |_| |_|                           |
00007 |                                                                      |
00008 \---------------------------------------------------------------------*/
00012 #include <cstdio>
00013 #include <cstdarg>
00014 
00015 #include <iostream>
00016 
00017 #include "zypp/base/Regex.h"
00018 
00019 using namespace zypp;
00020 using namespace zypp::str;
00021 
00022 regex::regex()
00023   : m_flags(match_extended)
00024   , m_valid(false)
00025 {
00026 
00027 }
00028 
00029 void regex::assign(const std::string& str,int flags)
00030 {
00031   m_valid = true;
00032   m_str = str;
00033   m_flags = flags;
00034   int err;
00035   char errbuff[100];
00036   if (!(flags & normal)) {
00037     flags |= match_extended;
00038     flags &= ~(normal);
00039   }
00040 
00041   if ((err = regcomp(&m_preg, str.c_str(), flags))) {
00042     m_valid = false;
00043     regerror(err, &m_preg, errbuff, sizeof(errbuff));
00044     ZYPP_THROW(regex_error(std::string(errbuff)));
00045   }
00046 }
00047 
00048 regex::regex(const std::string& str, int flags)
00049 {
00050   assign(str, flags);
00051 }
00052 
00053 regex::~regex() throw()
00054 {
00055   if (m_valid)
00056     regfree(&m_preg);
00057 }
00058 
00059 bool zypp::str::regex_match(const char * s, smatch& matches, const regex& regex)
00060 {
00061   bool r = s && regex.m_valid && !regexec(&regex.m_preg, s, 12, &matches.pmatch[0], 0);
00062   if (r)
00063     matches.match_str = s;
00064   return r;
00065 }
00066 
00067 bool zypp::str::regex_match(const char * s,  const regex& regex)
00068 {
00069   return s && !regexec(&regex.m_preg, s, 0, NULL, 0);
00070 }
00071 
00072 smatch::smatch()
00073 {
00074   memset(&pmatch, -1, sizeof(pmatch));
00075 }
00076 
00077 std::string smatch::operator[](unsigned i) const
00078 {
00079   if ( i < sizeof(pmatch)/sizeof(*pmatch) && pmatch[i].rm_so != -1 )
00080     return match_str.substr( pmatch[i].rm_so, pmatch[i].rm_eo-pmatch[i].rm_so );
00081 
00082   return std::string();
00083 }
00084 
00085 
00086 unsigned smatch::size() const
00087 {
00088   unsigned matches = unsigned(-1);
00089   // Get highest (pmatch[i].rm_so != -1). Just looking for the 1st
00090   // (pmatch[i].rm_so == -1) is wrong as optional mayches "()?"
00091   // may be embeded.
00092   for ( unsigned i = 0; i < sizeof(pmatch)/sizeof(*pmatch); ++i )
00093   {
00094     if ( pmatch[i].rm_so != -1 )
00095       matches = i;
00096   }
00097   return ++matches;
00098 }