- don't check empty segments generated by String.split() - don't continue to add segments if the matcher fails to match input - don't add empty heads - don't iterate over empty heads. Bug: 440732 Change-Id: I7d04dccfe24d91275d17ba246662337d6dba66df Signed-off-by: Andrey Loskutov <loskutov@gmx.de> Signed-off-by: Matthias Sohn <matthias.sohn@sap.com>tags/v3.5.0.201409071800-rc1
return new WildCardHead(star); | return new WildCardHead(star); | ||||
} | } | ||||
private void extendStringToMatchByOneCharacter(final char c) { | |||||
/** | |||||
* @param c new character to append | |||||
* @return true to continue, false if the matcher can stop appending | |||||
*/ | |||||
private boolean extendStringToMatchByOneCharacter(final char c) { | |||||
final List<Head> newHeads = listForLocalUseage; | final List<Head> newHeads = listForLocalUseage; | ||||
newHeads.clear(); | newHeads.clear(); | ||||
List<Head> lastAddedHeads = null; | List<Head> lastAddedHeads = null; | ||||
// This is the case with the heads "a" and "*" of "a*b" which | // This is the case with the heads "a" and "*" of "a*b" which | ||||
// both can return the list ["*","b"] | // both can return the list ["*","b"] | ||||
if (headsToAdd != lastAddedHeads) { | if (headsToAdd != lastAddedHeads) { | ||||
newHeads.addAll(headsToAdd); | |||||
if (!headsToAdd.isEmpty()) | |||||
newHeads.addAll(headsToAdd); | |||||
lastAddedHeads = headsToAdd; | lastAddedHeads = headsToAdd; | ||||
} | } | ||||
} | } | ||||
listForLocalUseage = heads; | listForLocalUseage = heads; | ||||
heads = newHeads; | heads = newHeads; | ||||
return !newHeads.isEmpty(); | |||||
} | } | ||||
private static int indexOfUnescaped(final String searchString, | private static int indexOfUnescaped(final String searchString, | ||||
public void append(final String stringToMatch) { | public void append(final String stringToMatch) { | ||||
for (int i = 0; i < stringToMatch.length(); i++) { | for (int i = 0; i < stringToMatch.length(); i++) { | ||||
final char c = stringToMatch.charAt(i); | final char c = stringToMatch.charAt(i); | ||||
extendStringToMatchByOneCharacter(c); | |||||
if (!extendStringToMatchByOneCharacter(c)) | |||||
break; | |||||
} | } | ||||
} | } | ||||
* @return true, if the string currently being matched does match. | * @return true, if the string currently being matched does match. | ||||
*/ | */ | ||||
public boolean isMatch() { | public boolean isMatch() { | ||||
if (heads.isEmpty()) | |||||
return false; | |||||
final ListIterator<Head> headIterator = heads | final ListIterator<Head> headIterator = heads | ||||
.listIterator(heads.size()); | .listIterator(heads.size()); | ||||
while (headIterator.hasPrevious()) { | while (headIterator.hasPrevious()) { |
final String[] segments = target.split("/"); //$NON-NLS-1$ | final String[] segments = target.split("/"); //$NON-NLS-1$ | ||||
for (int idx = 0; idx < segments.length; idx++) { | for (int idx = 0; idx < segments.length; idx++) { | ||||
final String segmentName = segments[idx]; | final String segmentName = segments[idx]; | ||||
// String.split("/") creates empty segment for leading slash | |||||
if (segmentName.length() == 0) | |||||
continue; | |||||
if (segmentName.equals(pattern) && | if (segmentName.equals(pattern) && | ||||
doesMatchDirectoryExpectations(isDirectory, idx, segments.length)) | doesMatchDirectoryExpectations(isDirectory, idx, segments.length)) | ||||
return true; | return true; | ||||
if (nameOnly) { | if (nameOnly) { | ||||
for (int idx = 0; idx < segments.length; idx++) { | for (int idx = 0; idx < segments.length; idx++) { | ||||
final String segmentName = segments[idx]; | final String segmentName = segments[idx]; | ||||
// String.split("/") creates empty segment for leading slash | |||||
if (segmentName.length() == 0) | |||||
continue; | |||||
//Iterate through each sub-directory | //Iterate through each sub-directory | ||||
matcher.reset(); | matcher.reset(); | ||||
matcher.append(segmentName); | matcher.append(segmentName); | ||||
//TODO: This is the slowest operation | //TODO: This is the slowest operation | ||||
//This matches e.g. "/src/ne?" to "/src/new/file.c" | //This matches e.g. "/src/ne?" to "/src/new/file.c" | ||||
matcher.reset(); | matcher.reset(); | ||||
for (int idx = 0; idx < segments.length; idx++) { | for (int idx = 0; idx < segments.length; idx++) { | ||||
final String segmentName = segments[idx]; | final String segmentName = segments[idx]; | ||||
if (segmentName.length() > 0) { | |||||
matcher.append("/" + segmentName); //$NON-NLS-1$ | |||||
} | |||||
// String.split("/") creates empty segment for leading slash | |||||
if (segmentName.length() == 0) | |||||
continue; | |||||
if (matcher.isMatch() && | |||||
doesMatchDirectoryExpectations(isDirectory, idx, segments.length)) | |||||
matcher.append("/" + segmentName); //$NON-NLS-1$ | |||||
if (matcher.isMatch() | |||||
&& doesMatchDirectoryExpectations(isDirectory, idx, | |||||
segments.length)) | |||||
return true; | return true; | ||||
} | } | ||||
} | } |