1254721Semaste//===-- RegularExpression.cpp -----------------------------------*- C++ -*-===// 2254721Semaste// 3254721Semaste// The LLVM Compiler Infrastructure 4254721Semaste// 5254721Semaste// This file is distributed under the University of Illinois Open Source 6254721Semaste// License. See LICENSE.TXT for details. 7254721Semaste// 8254721Semaste//===----------------------------------------------------------------------===// 9254721Semaste 10254721Semaste#include "lldb/Core/RegularExpression.h" 11254721Semaste#include "llvm/ADT/StringRef.h" 12254721Semaste#include <string.h> 13254721Semaste 14254721Semasteusing namespace lldb_private; 15254721Semaste 16254721Semaste//---------------------------------------------------------------------- 17254721Semaste// Default constructor 18254721Semaste//---------------------------------------------------------------------- 19254721SemasteRegularExpression::RegularExpression() : 20254721Semaste m_re(), 21254721Semaste m_comp_err (1), 22254721Semaste m_preg(), 23254721Semaste m_compile_flags(REG_EXTENDED) 24254721Semaste{ 25254721Semaste memset(&m_preg,0,sizeof(m_preg)); 26254721Semaste} 27254721Semaste 28254721Semaste//---------------------------------------------------------------------- 29254721Semaste// Constructor that compiles "re" using "flags" and stores the 30254721Semaste// resulting compiled regular expression into this object. 31254721Semaste//---------------------------------------------------------------------- 32254721SemasteRegularExpression::RegularExpression(const char* re, int flags) : 33254721Semaste m_re(), 34254721Semaste m_comp_err (1), 35254721Semaste m_preg(), 36254721Semaste m_compile_flags(flags) 37254721Semaste{ 38254721Semaste memset(&m_preg,0,sizeof(m_preg)); 39254721Semaste Compile(re); 40254721Semaste} 41254721Semaste 42254721Semaste//---------------------------------------------------------------------- 43254721Semaste// Constructor that compiles "re" using "flags" and stores the 44254721Semaste// resulting compiled regular expression into this object. 45254721Semaste//---------------------------------------------------------------------- 46254721SemasteRegularExpression::RegularExpression(const char* re) : 47254721Semaste m_re(), 48254721Semaste m_comp_err (1), 49254721Semaste m_preg(), 50254721Semaste m_compile_flags(REG_EXTENDED) 51254721Semaste{ 52254721Semaste memset(&m_preg,0,sizeof(m_preg)); 53254721Semaste Compile(re); 54254721Semaste} 55254721Semaste 56254721SemasteRegularExpression::RegularExpression(const RegularExpression &rhs) 57254721Semaste{ 58254721Semaste memset(&m_preg,0,sizeof(m_preg)); 59254721Semaste Compile(rhs.GetText(), rhs.GetCompileFlags()); 60254721Semaste} 61254721Semaste 62254721Semasteconst RegularExpression & 63254721SemasteRegularExpression::operator= (const RegularExpression &rhs) 64254721Semaste{ 65254721Semaste if (&rhs != this) 66254721Semaste { 67254721Semaste Compile (rhs.GetText(), rhs.GetCompileFlags()); 68254721Semaste } 69254721Semaste return *this; 70254721Semaste} 71254721Semaste//---------------------------------------------------------------------- 72254721Semaste// Destructor 73254721Semaste// 74254721Semaste// Any previosuly compiled regular expression contained in this 75254721Semaste// object will be freed. 76254721Semaste//---------------------------------------------------------------------- 77254721SemasteRegularExpression::~RegularExpression() 78254721Semaste{ 79254721Semaste Free(); 80254721Semaste} 81254721Semaste 82254721Semaste//---------------------------------------------------------------------- 83254721Semaste// Compile a regular expression using the supplied regular 84254721Semaste// expression text and flags. The compied regular expression lives 85254721Semaste// in this object so that it can be readily used for regular 86254721Semaste// expression matches. Execute() can be called after the regular 87254721Semaste// expression is compiled. Any previosuly compiled regular 88254721Semaste// expression contained in this object will be freed. 89254721Semaste// 90254721Semaste// RETURNS 91254721Semaste// True of the refular expression compiles successfully, false 92254721Semaste// otherwise. 93254721Semaste//---------------------------------------------------------------------- 94254721Semastebool 95254721SemasteRegularExpression::Compile(const char* re) 96254721Semaste{ 97254721Semaste return Compile (re, m_compile_flags); 98254721Semaste} 99254721Semaste 100254721Semastebool 101254721SemasteRegularExpression::Compile(const char* re, int flags) 102254721Semaste{ 103254721Semaste Free(); 104254721Semaste m_compile_flags = flags; 105254721Semaste 106254721Semaste if (re && re[0]) 107254721Semaste { 108254721Semaste m_re = re; 109254721Semaste m_comp_err = ::regcomp (&m_preg, re, flags); 110254721Semaste } 111254721Semaste else 112254721Semaste { 113254721Semaste // No valid regular expression 114254721Semaste m_comp_err = 1; 115254721Semaste } 116254721Semaste 117254721Semaste return m_comp_err == 0; 118254721Semaste} 119254721Semaste 120254721Semaste//---------------------------------------------------------------------- 121254721Semaste// Execute a regular expression match using the compiled regular 122254721Semaste// expression that is already in this object against the match 123254721Semaste// string "s". If any parens are used for regular expression 124254721Semaste// matches "match_count" should indicate the number of regmatch_t 125254721Semaste// values that are present in "match_ptr". The regular expression 126254721Semaste// will be executed using the "execute_flags". 127254721Semaste//--------------------------------------------------------------------- 128254721Semastebool 129254721SemasteRegularExpression::Execute(const char* s, Match *match, int execute_flags) const 130254721Semaste{ 131254721Semaste int err = 1; 132254721Semaste if (s != NULL && m_comp_err == 0) 133254721Semaste { 134254721Semaste if (match) 135254721Semaste { 136254721Semaste err = ::regexec (&m_preg, 137254721Semaste s, 138254721Semaste match->GetSize(), 139254721Semaste match->GetData(), 140254721Semaste execute_flags); 141254721Semaste } 142254721Semaste else 143254721Semaste { 144254721Semaste err = ::regexec (&m_preg, 145254721Semaste s, 146254721Semaste 0, 147254721Semaste NULL, 148254721Semaste execute_flags); 149254721Semaste } 150254721Semaste } 151254721Semaste 152254721Semaste if (err != 0) 153254721Semaste { 154254721Semaste // The regular expression didn't compile, so clear the matches 155254721Semaste if (match) 156254721Semaste match->Clear(); 157254721Semaste return false; 158254721Semaste } 159254721Semaste return true; 160254721Semaste} 161254721Semaste 162254721Semastebool 163254721SemasteRegularExpression::Match::GetMatchAtIndex (const char* s, uint32_t idx, std::string& match_str) const 164254721Semaste{ 165254721Semaste if (idx < m_matches.size()) 166254721Semaste { 167254721Semaste if (m_matches[idx].rm_eo == m_matches[idx].rm_so) 168254721Semaste { 169254721Semaste // Matched the empty string... 170254721Semaste match_str.clear(); 171254721Semaste return true; 172254721Semaste } 173254721Semaste else if (m_matches[idx].rm_eo > m_matches[idx].rm_so) 174254721Semaste { 175254721Semaste match_str.assign (s + m_matches[idx].rm_so, 176254721Semaste m_matches[idx].rm_eo - m_matches[idx].rm_so); 177254721Semaste return true; 178254721Semaste } 179254721Semaste } 180254721Semaste return false; 181254721Semaste} 182254721Semaste 183254721Semastebool 184254721SemasteRegularExpression::Match::GetMatchAtIndex (const char* s, uint32_t idx, llvm::StringRef& match_str) const 185254721Semaste{ 186254721Semaste if (idx < m_matches.size()) 187254721Semaste { 188254721Semaste if (m_matches[idx].rm_eo == m_matches[idx].rm_so) 189254721Semaste { 190254721Semaste // Matched the empty string... 191254721Semaste match_str = llvm::StringRef(); 192254721Semaste return true; 193254721Semaste } 194254721Semaste else if (m_matches[idx].rm_eo > m_matches[idx].rm_so) 195254721Semaste { 196254721Semaste match_str = llvm::StringRef (s + m_matches[idx].rm_so, m_matches[idx].rm_eo - m_matches[idx].rm_so); 197254721Semaste return true; 198254721Semaste } 199254721Semaste } 200254721Semaste return false; 201254721Semaste} 202254721Semaste 203254721Semastebool 204254721SemasteRegularExpression::Match::GetMatchSpanningIndices (const char* s, uint32_t idx1, uint32_t idx2, llvm::StringRef& match_str) const 205254721Semaste{ 206254721Semaste if (idx1 < m_matches.size() && idx2 < m_matches.size()) 207254721Semaste { 208254721Semaste if (m_matches[idx1].rm_so == m_matches[idx2].rm_eo) 209254721Semaste { 210254721Semaste // Matched the empty string... 211254721Semaste match_str = llvm::StringRef(); 212254721Semaste return true; 213254721Semaste } 214254721Semaste else if (m_matches[idx1].rm_so < m_matches[idx2].rm_eo) 215254721Semaste { 216254721Semaste match_str = llvm::StringRef (s + m_matches[idx1].rm_so, m_matches[idx2].rm_eo - m_matches[idx1].rm_so); 217254721Semaste return true; 218254721Semaste } 219254721Semaste } 220254721Semaste return false; 221254721Semaste} 222254721Semaste 223254721Semaste 224254721Semaste//---------------------------------------------------------------------- 225254721Semaste// Returns true if the regular expression compiled and is ready 226254721Semaste// for execution. 227254721Semaste//---------------------------------------------------------------------- 228254721Semastebool 229254721SemasteRegularExpression::IsValid () const 230254721Semaste{ 231254721Semaste return m_comp_err == 0; 232254721Semaste} 233254721Semaste 234254721Semaste//---------------------------------------------------------------------- 235254721Semaste// Returns the text that was used to compile the current regular 236254721Semaste// expression. 237254721Semaste//---------------------------------------------------------------------- 238254721Semasteconst char* 239254721SemasteRegularExpression::GetText () const 240254721Semaste{ 241254721Semaste if (m_re.empty()) 242254721Semaste return NULL; 243254721Semaste return m_re.c_str(); 244254721Semaste} 245254721Semaste 246254721Semaste//---------------------------------------------------------------------- 247254721Semaste// Free any contained compiled regular expressions. 248254721Semaste//---------------------------------------------------------------------- 249254721Semastevoid 250254721SemasteRegularExpression::Free() 251254721Semaste{ 252254721Semaste if (m_comp_err == 0) 253254721Semaste { 254254721Semaste m_re.clear(); 255254721Semaste regfree(&m_preg); 256254721Semaste // Set a compile error since we no longer have a valid regex 257254721Semaste m_comp_err = 1; 258254721Semaste } 259254721Semaste} 260254721Semaste 261254721Semastesize_t 262254721SemasteRegularExpression::GetErrorAsCString (char *err_str, size_t err_str_max_len) const 263254721Semaste{ 264254721Semaste if (m_comp_err == 0) 265254721Semaste { 266254721Semaste if (err_str && err_str_max_len) 267254721Semaste *err_str = '\0'; 268254721Semaste return 0; 269254721Semaste } 270254721Semaste 271254721Semaste return ::regerror (m_comp_err, &m_preg, err_str, err_str_max_len); 272254721Semaste} 273254721Semaste 274254721Semastebool 275254721SemasteRegularExpression::operator < (const RegularExpression& rhs) const 276254721Semaste{ 277254721Semaste return (m_re < rhs.m_re); 278254721Semaste} 279254721Semaste 280