Grep command linux recursive8/30/2023 ![]() Even the creators of your grep.exe pretend *.c in Windows is expanded by the shell here they say "filename wildcards are interpreted by the command shell, not by the program". Like many tools in Windows grep probably doesn't bother to provide a custom function to get from a string to an array of arguments, some standard function provided by Windows is used, so it looks like cmd.exe does the job. In your case the string contains *.c and the expansion is done after grep starts, by grep not before, not by cmd.exe. In Windows grep.exe (any executable in general) gets a string (a somewhat "digested" string, still a string), not an array it creates an array for itself. In Unix/Linux grep (any executable in general) gets an array of arguments after a shell "digests" the command presented as a string. (like you probably did) then the executable will (be able to) see *.c before it gets expanded. If grep ( grep.exe) is actually an executable in Windows and you run it in cmd.exe as grep -r iflag *.c In Unix/Linux grep cannot do anything about it because the tool starts after *.c is expanded by the shell. We saw that in Linux your command results in *.c being expanded first, recursiveness starting later. Your grep in Windows is from the GnuWin project, it is designed to reasonably mimic the GNU grep you can find in Linux. It's good to know what parts of your command (in general: any command) are (or may be) expanded by the (or a) shell.Īnd now, finally, the nuances of Windows. Note -include=*.c is still a pattern your shell may expand if you want your code to be robust then you should escape or quote the asterisk. You want the other way around and one method to do it is with -include=*.c (the other is with globstar where the shell handles the recursiveness, but it can give you argument list too long error so it's better to let grep do this). In short, the reason your code doesn't work is *.c is expanded first (before grep runs), recursiveness starts later (when grep runs). You would need to quote or escape the pattern to protect it from the shell (see this question). There are tools that actually interpret such patterns in some circumstances (in fact grep -include is an example).Įven if grep was designed to interpret this *.c in your code as a pattern in the way you expected, in many cases your code wouldn't work. If it sees *.c where it expects a pathname then it will try to read a file named *.c. This cannot help you because grep itself is not designed to expand patterns in an argument it interprets as pathname. If you escape or quote the asterisk in *.c (examples: \*.c, "*.c", '*'.c) then it will not be expanded and the word will be passed to grep literally as *.c.If there is no match in the current working directory then ( in some shells) *.c will not be expanded and it will be passed to grep literally as *.c.There are two scenarios where grep actually sees this *.c: The job of picking all pathnames matching the pattern would be done by the shell. dir1/subdir/baz.c), grep would not see the pattern itself, -r might be irrelevant. If you properly used such pattern, the shell would pass all matching paths to grep (e.g. ![]() This feature is called "globstar" and one may need to explicitly enable it in a shell. In some shells you can use a glob that can match files in subdirectories. foo.c is a file of the type directory then -r will make grep descend into the directory but grep will read all files in the directory (it is still not aware of *.c you typed).
0 Comments
Leave a Reply.AuthorWrite something about yourself. No need to be fancy, just an overview. ArchivesCategories |