1313#include "parse-options.h"
1414#include "userdiff.h"
1515#include "grep.h"
16+ #include "quote.h"
1617
1718#ifndef NO_EXTERNAL_GREP
1819#ifdef __unix__
@@ -157,35 +158,22 @@ static int grep_sha1(struct grep_opt *opt, const unsigned char *sha1, const char
157158 unsigned long size ;
158159 char * data ;
159160 enum object_type type ;
160- char * to_free = NULL ;
161161 int hit ;
162+ struct strbuf pathbuf = STRBUF_INIT ;
162163
163164 data = read_sha1_file (sha1 , & type , & size );
164165 if (!data ) {
165166 error ("'%s': unable to read %s" , name , sha1_to_hex (sha1 ));
166167 return 0 ;
167168 }
168169 if (opt -> relative && opt -> prefix_length ) {
169- static char name_buf [PATH_MAX ];
170- char * cp ;
171- int name_len = strlen (name ) - opt -> prefix_length + 1 ;
172-
173- if (!tree_name_len )
174- name += opt -> prefix_length ;
175- else {
176- if (ARRAY_SIZE (name_buf ) <= name_len )
177- cp = to_free = xmalloc (name_len );
178- else
179- cp = name_buf ;
180- memcpy (cp , name , tree_name_len );
181- strcpy (cp + tree_name_len ,
182- name + tree_name_len + opt -> prefix_length );
183- name = cp ;
184- }
170+ quote_path_relative (name + tree_name_len , -1 , & pathbuf , opt -> prefix );
171+ strbuf_insert (& pathbuf , 0 , name , tree_name_len );
172+ name = pathbuf .buf ;
185173 }
186174 hit = grep_buffer (opt , name , data , size );
175+ strbuf_release (& pathbuf );
187176 free (data );
188- free (to_free );
189177 return hit ;
190178}
191179
@@ -195,6 +183,7 @@ static int grep_file(struct grep_opt *opt, const char *filename)
195183 int i ;
196184 char * data ;
197185 size_t sz ;
186+ struct strbuf buf = STRBUF_INIT ;
198187
199188 if (lstat (filename , & st ) < 0 ) {
200189 err_ret :
@@ -219,8 +208,9 @@ static int grep_file(struct grep_opt *opt, const char *filename)
219208 }
220209 close (i );
221210 if (opt -> relative && opt -> prefix_length )
222- filename += opt -> prefix_length ;
211+ filename = quote_path_relative ( filename , -1 , & buf , opt -> prefix ) ;
223212 i = grep_buffer (opt , filename , data , sz );
213+ strbuf_release (& buf );
224214 free (data );
225215 return i ;
226216}
@@ -503,6 +493,7 @@ static int grep_cache(struct grep_opt *opt, const char **paths, int cached,
503493 hit = external_grep (opt , paths , cached );
504494 if (hit >= 0 )
505495 return hit ;
496+ hit = 0 ;
506497 }
507498#endif
508499
@@ -798,6 +789,7 @@ int cmd_grep(int argc, const char **argv, const char *prefix)
798789 };
799790
800791 memset (& opt , 0 , sizeof (opt ));
792+ opt .prefix = prefix ;
801793 opt .prefix_length = (prefix && * prefix ) ? strlen (prefix ) : 0 ;
802794 opt .relative = 1 ;
803795 opt .pathname = 1 ;
@@ -868,15 +860,8 @@ int cmd_grep(int argc, const char **argv, const char *prefix)
868860 verify_filename (prefix , argv [j ]);
869861 }
870862
871- if (i < argc ) {
863+ if (i < argc )
872864 paths = get_pathspec (prefix , argv + i );
873- if (opt .prefix_length && opt .relative ) {
874- /* Make sure we do not get outside of paths */
875- for (i = 0 ; paths [i ]; i ++ )
876- if (strncmp (prefix , paths [i ], opt .prefix_length ))
877- die ("git grep: cannot generate relative filenames containing '..'" );
878- }
879- }
880865 else if (prefix ) {
881866 paths = xcalloc (2 , sizeof (const char * ));
882867 paths [0 ] = prefix ;
0 commit comments