3
3
static int recursive = 0 ;
4
4
static int line_termination = '\n' ;
5
5
6
+ // What paths are we interested in?
7
+ static int nr_paths = 0 ;
8
+ static char * * paths = NULL ;
9
+ static int * pathlens = NULL ;
10
+
6
11
static int diff_tree_sha1 (const unsigned char * old , const unsigned char * new , const char * base );
7
12
8
13
static void update_tree_entry (void * * bufp , unsigned long * sizep )
@@ -131,9 +136,63 @@ static int compare_tree_entry(void *tree1, unsigned long size1, void *tree2, uns
131
136
return 0 ;
132
137
}
133
138
139
+ static int interesting (void * tree , unsigned long size , const char * base )
140
+ {
141
+ const char * path ;
142
+ unsigned mode ;
143
+ int i ;
144
+ int baselen , pathlen ;
145
+
146
+ if (!nr_paths )
147
+ return 1 ;
148
+
149
+ (void )extract (tree , size , & path , & mode );
150
+
151
+ pathlen = strlen (path );
152
+ baselen = strlen (base );
153
+
154
+ for (i = 0 ; i < nr_paths ; i ++ ) {
155
+ const char * match = paths [i ];
156
+ int matchlen = pathlens [i ];
157
+
158
+ if (baselen >= matchlen ) {
159
+ /* If it doesn't match, move along... */
160
+ if (strncmp (base , match , matchlen ))
161
+ continue ;
162
+
163
+ /* The base is a subdirectory of a path which was specified. */
164
+ return 1 ;
165
+ }
166
+
167
+ /* Does the base match? */
168
+ if (strncmp (base , match , baselen ))
169
+ continue ;
170
+
171
+ match += baselen ;
172
+ matchlen -= baselen ;
173
+
174
+ if (pathlen > matchlen )
175
+ continue ;
176
+
177
+ if (strncmp (path , match , pathlen ))
178
+ continue ;
179
+
180
+ return 1 ;
181
+ }
182
+ return 0 ; /* No matches */
183
+ }
184
+
134
185
static int diff_tree (void * tree1 , unsigned long size1 , void * tree2 , unsigned long size2 , const char * base )
135
186
{
136
187
while (size1 | size2 ) {
188
+ if (nr_paths && size1 && !interesting (tree1 , size1 , base )) {
189
+ update_tree_entry (& tree1 , & size1 );
190
+ continue ;
191
+ }
192
+ if (nr_paths && size2 && !interesting (tree2 , size2 , base )) {
193
+ update_tree_entry (& tree2 , & size2 );
194
+ continue ;
195
+ }
137
196
if (!size1 ) {
138
197
show_file ("+" , tree2 , size2 , base );
139
198
update_tree_entry (& tree2 , & size2 );
@@ -184,8 +243,12 @@ int main(int argc, char **argv)
184
243
{
185
244
unsigned char old [20 ], new [20 ];
186
245
187
- while ( argc > 3 ) {
246
+ for (;; ) {
188
247
char * arg = argv [1 ];
248
+
249
+ if (!arg || * arg != '-' )
250
+ break ;
251
+
189
252
argv ++ ;
190
253
argc -- ;
191
254
if (!strcmp (arg , "-r" )) {
@@ -199,7 +262,18 @@ int main(int argc, char **argv)
199
262
usage (diff_tree_usage );
200
263
}
201
264
202
- if (argc != 3 || get_sha1_hex (argv [1 ], old ) || get_sha1_hex (argv [2 ], new ))
265
+ if (argc < 3 || get_sha1_hex (argv [1 ], old ) || get_sha1_hex (argv [2 ], new ))
203
266
usage (diff_tree_usage );
267
+
268
+ if (argc > 3 ) {
269
+ int i ;
270
+
271
+ paths = & argv [3 ];
272
+ nr_paths = argc - 3 ;
273
+ pathlens = malloc (nr_paths * sizeof (int ));
274
+ for (i = 0 ; i < nr_paths ; i ++ )
275
+ pathlens [i ] = strlen (paths [i ]);
276
+ }
277
+
204
278
return diff_tree_sha1 (old , new , "" );
205
279
}
0 commit comments