Home | History | Annotate | Line # | Download | only in common
GlobMatcher.cpp revision 1.1.2.2
      1  1.1.2.2  jkunz /*
      2  1.1.2.2  jkunz  * File:	GlobMatcher.cpp
      3  1.1.2.2  jkunz  *
      4  1.1.2.2  jkunz  * Copyright (c) Freescale Semiconductor, Inc. All rights reserved.
      5  1.1.2.2  jkunz  * See included license file for license details.
      6  1.1.2.2  jkunz  */
      7  1.1.2.2  jkunz 
      8  1.1.2.2  jkunz #include "GlobMatcher.h"
      9  1.1.2.2  jkunz 
     10  1.1.2.2  jkunz #ifndef NEGATE
     11  1.1.2.2  jkunz #define NEGATE	'^'			// std cset negation char
     12  1.1.2.2  jkunz #endif
     13  1.1.2.2  jkunz 
     14  1.1.2.2  jkunz using namespace elftosb;
     15  1.1.2.2  jkunz 
     16  1.1.2.2  jkunz //! The glob pattern must match the \e entire test value argument in order
     17  1.1.2.2  jkunz //! for the match to be considered successful. Thus, even if, for example,
     18  1.1.2.2  jkunz //! the pattern matches all but the last character the result will be false.
     19  1.1.2.2  jkunz //!
     20  1.1.2.2  jkunz //! \retval true The test value does match the glob pattern.
     21  1.1.2.2  jkunz //! \retval false The test value does not match the glob pattern.
     22  1.1.2.2  jkunz bool GlobMatcher::match(const std::string & testValue)
     23  1.1.2.2  jkunz {
     24  1.1.2.2  jkunz 	return globMatch(testValue.c_str(), m_pattern.c_str());
     25  1.1.2.2  jkunz }
     26  1.1.2.2  jkunz 
     27  1.1.2.2  jkunz //! \note This glob implementation was originally written by ozan s. yigit in
     28  1.1.2.2  jkunz //!		December 1994. This is public domain source code.
     29  1.1.2.2  jkunz bool GlobMatcher::globMatch(const char *str, const char *p)
     30  1.1.2.2  jkunz {
     31  1.1.2.2  jkunz 	int negate;
     32  1.1.2.2  jkunz 	int match;
     33  1.1.2.2  jkunz 	int c;
     34  1.1.2.2  jkunz 
     35  1.1.2.2  jkunz 	while (*p) {
     36  1.1.2.2  jkunz 		if (!*str && *p != '*')
     37  1.1.2.2  jkunz 			return false;
     38  1.1.2.2  jkunz 
     39  1.1.2.2  jkunz 		switch (c = *p++) {
     40  1.1.2.2  jkunz 
     41  1.1.2.2  jkunz 		case '*':
     42  1.1.2.2  jkunz 			while (*p == '*')
     43  1.1.2.2  jkunz 				p++;
     44  1.1.2.2  jkunz 
     45  1.1.2.2  jkunz 			if (!*p)
     46  1.1.2.2  jkunz 				return true;
     47  1.1.2.2  jkunz 
     48  1.1.2.2  jkunz 			if (*p != '?' && *p != '[' && *p != '\\')
     49  1.1.2.2  jkunz 				while (*str && *p != *str)
     50  1.1.2.2  jkunz 					str++;
     51  1.1.2.2  jkunz 
     52  1.1.2.2  jkunz 			while (*str) {
     53  1.1.2.2  jkunz 				if (globMatch(str, p))
     54  1.1.2.2  jkunz 					return true;
     55  1.1.2.2  jkunz 				str++;
     56  1.1.2.2  jkunz 			}
     57  1.1.2.2  jkunz 			return false;
     58  1.1.2.2  jkunz 
     59  1.1.2.2  jkunz 		case '?':
     60  1.1.2.2  jkunz 			if (*str)
     61  1.1.2.2  jkunz 				break;
     62  1.1.2.2  jkunz 			return false;
     63  1.1.2.2  jkunz 
     64  1.1.2.2  jkunz 		// set specification is inclusive, that is [a-z] is a, z and
     65  1.1.2.2  jkunz 		// everything in between. this means [z-a] may be interpreted
     66  1.1.2.2  jkunz 		// as a set that contains z, a and nothing in between.
     67  1.1.2.2  jkunz 		case '[':
     68  1.1.2.2  jkunz 			if (*p != NEGATE)
     69  1.1.2.2  jkunz 				negate = false;
     70  1.1.2.2  jkunz 			else {
     71  1.1.2.2  jkunz 				negate = true;
     72  1.1.2.2  jkunz 				p++;
     73  1.1.2.2  jkunz 			}
     74  1.1.2.2  jkunz 
     75  1.1.2.2  jkunz 			match = false;
     76  1.1.2.2  jkunz 
     77  1.1.2.2  jkunz 			while (!match && (c = *p++)) {
     78  1.1.2.2  jkunz 				if (!*p)
     79  1.1.2.2  jkunz 					return false;
     80  1.1.2.2  jkunz 				if (*p == '-') {	// c-c
     81  1.1.2.2  jkunz 					if (!*++p)
     82  1.1.2.2  jkunz 						return false;
     83  1.1.2.2  jkunz 					if (*p != ']') {
     84  1.1.2.2  jkunz 						if (*str == c || *str == *p ||
     85  1.1.2.2  jkunz 						    (*str > c && *str < *p))
     86  1.1.2.2  jkunz 							match = true;
     87  1.1.2.2  jkunz 					}
     88  1.1.2.2  jkunz 					else {		// c-]
     89  1.1.2.2  jkunz 						if (*str >= c)
     90  1.1.2.2  jkunz 							match = true;
     91  1.1.2.2  jkunz 						break;
     92  1.1.2.2  jkunz 					}
     93  1.1.2.2  jkunz 				}
     94  1.1.2.2  jkunz 				else {			// cc or c]
     95  1.1.2.2  jkunz 					if (c == *str)
     96  1.1.2.2  jkunz 						match = true;
     97  1.1.2.2  jkunz 					if (*p != ']') {
     98  1.1.2.2  jkunz 						if (*p == *str)
     99  1.1.2.2  jkunz 							match = true;
    100  1.1.2.2  jkunz 					}
    101  1.1.2.2  jkunz 					else
    102  1.1.2.2  jkunz 						break;
    103  1.1.2.2  jkunz 				}
    104  1.1.2.2  jkunz 			}
    105  1.1.2.2  jkunz 
    106  1.1.2.2  jkunz 			if (negate == match)
    107  1.1.2.2  jkunz 				return false;
    108  1.1.2.2  jkunz 			// if there is a match, skip past the cset and continue on
    109  1.1.2.2  jkunz 			while (*p && *p != ']')
    110  1.1.2.2  jkunz 				p++;
    111  1.1.2.2  jkunz 			if (!*p++)	// oops!
    112  1.1.2.2  jkunz 				return false;
    113  1.1.2.2  jkunz 			break;
    114  1.1.2.2  jkunz 
    115  1.1.2.2  jkunz 		case '\\':
    116  1.1.2.2  jkunz 			if (*p)
    117  1.1.2.2  jkunz 				c = *p++;
    118  1.1.2.2  jkunz 		default:
    119  1.1.2.2  jkunz 			if (c != *str)
    120  1.1.2.2  jkunz 				return false;
    121  1.1.2.2  jkunz 			break;
    122  1.1.2.2  jkunz 
    123  1.1.2.2  jkunz 		}
    124  1.1.2.2  jkunz 		str++;
    125  1.1.2.2  jkunz 	}
    126  1.1.2.2  jkunz 
    127  1.1.2.2  jkunz 	return !*str;
    128  1.1.2.2  jkunz }
    129  1.1.2.2  jkunz 
    130