1

I am running a grep on a file that is about 13G in size. It is returning

Binary file file.xml matches

I was not expecting this, I thought it would return each line with my string so that I could run the following,

grep "searchString" ./file.xml | wc -l 

and return a count of all the occurrences of my searchString in my large file.

  • Out of interest, what does file file.xml return? – EightBitTony Jul 9 '13 at 13:18
  • file.xml: XML document text – Dan Ciborowski - MSFT Jul 9 '13 at 13:22
  • nit: This finds the number of lines having searchString, not the number of instances ("Hi, I'm searchString searchString searchString, how are you?") counts as one hit, not three. – Keith Davies Jan 25 '17 at 19:43
  • Also, might return "1" if this is a compact (i.e. not prettyprint, <xsl:output indent="no" />) file... which might also explain why it gets picked up as binary, no evident record breaks found within the first chunk of the file. I've been hosed on this trying to grep things in WordML files, ended up using xmllint --format infile.xml > infile.xml-formatted to get something usable. – Keith Davies Jan 25 '17 at 19:45
12

It looks like grep thinks your XML file is binary rather than text.

If you want to force grep to treat your file as text regardless of the contents, you can use its --text switch (assuming GNU grep), like so:

grep --text "searchString" ./file.xml | wc -l

Note that if all you want is to count matches, it's probably better to use grep --count rather than piping through wc -l, saving you a pipe and process invocation.

  • 1
    @MichaelKjörling grep --count will also return number of lines. From man: -c, --count Suppress normal output; instead print a count of matching lines for each input file. – rush Jul 9 '13 at 13:31
  • @rush Argh, you're right. Sorry, never mind that then. – a CVn Jul 9 '13 at 13:34
2

Looks like there are some uncommon symbols in the beginning of your file and grep detects it as binary. You can try --binary-files=text option.

grep --binary-files=text "searchString" file.xml | wc -l

From man page:

   --binary-files=TYPE
          If the first few bytes of a file indicate that the file contains
          binary  data, assume that the file is of type TYPE.  By default,
          TYPE is binary, and grep  normally  outputs  either  a  one-line
          message  saying  that  a  binary  file matches, or no message if
          there is no match.  If TYPE is without-match, grep assumes  that
          a  binary  file  does  not  match;  this is equivalent to the -I
          option.  If TYPE is text, grep processes a binary file as if  it
          were  text;  this is equivalent to the -a option.  Warning: grep
          --binary-files=text might output binary garbage, which can  have
          nasty  side  effects  if  the  output  is  a terminal and if the
          terminal driver interprets some of it as commands.
  • 2
    Or near-equivalently grep -a -c 'searchString' file.xml and avoid the superfluous wc -l. – tripleee Jul 9 '13 at 13:26
  • Just DOS carriage returns are enough to turn a file into "binary". – tripleee Jul 9 '13 at 13:40
  • @tripleee Not to be a nit, but I thought I already said that :) – a CVn Jul 9 '13 at 13:40
  • @MikaelKjörling: After I posted my comment, yes. Yours is now the better answer so you got my vote. – tripleee Jul 9 '13 at 13:42
-3

It looks like you have a mistake when using ./file.xml. If you try:

grep "searchString" file.xml | wc -l

Does it have any problems?

  • 6
    file.xml and ./file.xml refer to exactly the same file, with the additional safety net that in the latter case, the real name of file.xml can safely begin with e.g. -. – a CVn Jul 9 '13 at 13:09
  • 1
    not going to vote down but above comment is right no difference between what you have and what I tried. – Dan Ciborowski - MSFT Jul 9 '13 at 13:18

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.