@@ -522,6 +522,53 @@ static int match_basename(const char *basename, int basenamelen,
522
522
return 0 ;
523
523
}
524
524
525
+ static int match_pathname (const char * pathname , int pathlen ,
526
+ const char * base , int baselen ,
527
+ const char * pattern , int prefix , int patternlen ,
528
+ int flags )
529
+ {
530
+ const char * name ;
531
+ int namelen ;
532
+
533
+ /*
534
+ * match with FNM_PATHNAME; the pattern has base implicitly
535
+ * in front of it.
536
+ */
537
+ if (* pattern == '/' ) {
538
+ pattern ++ ;
539
+ prefix -- ;
540
+ }
541
+
542
+ /*
543
+ * baselen does not count the trailing slash. base[] may or
544
+ * may not end with a trailing slash though.
545
+ */
546
+ if (pathlen < baselen + 1 ||
547
+ (baselen && pathname [baselen ] != '/' ) ||
548
+ strncmp_icase (pathname , base , baselen ))
549
+ return 0 ;
550
+
551
+ namelen = baselen ? pathlen - baselen - 1 : pathlen ;
552
+ name = pathname + pathlen - namelen ;
553
+
554
+ if (prefix ) {
555
+ /*
556
+ * if the non-wildcard part is longer than the
557
+ * remaining pathname, surely it cannot match.
558
+ */
559
+ if (prefix > namelen )
560
+ return 0 ;
561
+
562
+ if (strncmp_icase (pattern , name , prefix ))
563
+ return 0 ;
564
+ pattern += prefix ;
565
+ name += prefix ;
566
+ namelen -= prefix ;
567
+ }
568
+
569
+ return fnmatch_icase (pattern , name , FNM_PATHNAME ) == 0 ;
570
+ }
571
+
525
572
/* Scan the list and let the last match determine the fate.
526
573
* Return 1 for exclude, 0 for include and -1 for undecided.
527
574
*/
@@ -536,9 +583,9 @@ int excluded_from_list(const char *pathname,
536
583
537
584
for (i = el -> nr - 1 ; 0 <= i ; i -- ) {
538
585
struct exclude * x = el -> excludes [i ];
539
- const char * name , * exclude = x -> pattern ;
586
+ const char * exclude = x -> pattern ;
540
587
int to_exclude = x -> to_exclude ;
541
- int namelen , prefix = x -> nowildcardlen ;
588
+ int prefix = x -> nowildcardlen ;
542
589
543
590
if (x -> flags & EXC_FLAG_MUSTBEDIR ) {
544
591
if (* dtype == DT_UNKNOWN )
@@ -556,36 +603,10 @@ int excluded_from_list(const char *pathname,
556
603
continue ;
557
604
}
558
605
559
- /* match with FNM_PATHNAME:
560
- * exclude has base (baselen long) implicitly in front of it.
561
- */
562
- if (* exclude == '/' ) {
563
- exclude ++ ;
564
- prefix -- ;
565
- }
566
-
567
- if (pathlen < x -> baselen ||
568
- (x -> baselen && pathname [x -> baselen - 1 ] != '/' ) ||
569
- strncmp_icase (pathname , x -> base , x -> baselen ))
570
- continue ;
571
-
572
- namelen = x -> baselen ? pathlen - x -> baselen : pathlen ;
573
- name = pathname + pathlen - namelen ;
574
-
575
- /* if the non-wildcard part is longer than the
576
- remaining pathname, surely it cannot match */
577
- if (prefix > namelen )
578
- continue ;
579
-
580
- if (prefix ) {
581
- if (strncmp_icase (exclude , name , prefix ))
582
- continue ;
583
- exclude += prefix ;
584
- name += prefix ;
585
- namelen -= prefix ;
586
- }
587
-
588
- if (!fnmatch_icase (exclude , name , FNM_PATHNAME ))
606
+ assert (x -> baselen == 0 || x -> base [x -> baselen - 1 ] == '/' );
607
+ if (match_pathname (pathname , pathlen ,
608
+ x -> base , x -> baselen ? x -> baselen - 1 : 0 ,
609
+ exclude , prefix , x -> patternlen , x -> flags ))
589
610
return to_exclude ;
590
611
}
591
612
return -1 ; /* undecided */
0 commit comments