From: engdahl@brutus.aa.ab.com (Jon Engdahl)
Subject: "ignore asm comments" option for diff
Organization: GNUs Not Usenet
Distribution: gnu
Date: Thu, 13 Aug 1992 23:37:02 GMT

Enclosed is a context diff for an "ignore the assembly comments, just
show me what code changed" option to diff. It is a superset of -b,
except that anything from the first `;' to the end of the line is
treated as whitespace. NOTE - a `;' inside quotes is not detected. This
is a bit crude, but it helps me out a great deal (yes, I still write a
lot of asm code, sigh).

The option flag is -j, after me (Jonathan). Change the letter if you
want - I just picked the first letter that came to mind, since the
ones that seemed mnemonic to me were used already.

There may be a bug in the -B, sometimes inserted comment lines are
listed when they shouldn't be - inserted blank lines are also sometimes
listed. I haven't looked into it to find out why - it's not a major
problem yet.

I also put in a couple of #ifndefs to get this to work under DJGPP. I
didn't take time to look at what I was hacking out - I was just
whacking away at undefined externs (fork, etc). It seems to do what I
want it to do under DOS, but I don't even know what features I
eliminated.

Needed enhancements: specify the comment delimiter, like // for C++,
/* */ for C. Not a high priority need, since nobody comments C code
anyhow ;-)

No guarantees - I haven't tested the change exhaustively - but it seems
to be doing what I want it to do.

I usually use the -j option like so:

	diff -c5 -j -B old new | pardif | more


[Pardif is a program that I wrote which takes a couple forms of diff
listing and shows it in two parallel columns. Column width is an
optional parameter.  Like so (I made the columns narrow for mail,
default is 80 on each side): 

diff -c5 old/diff.c ./diff.c
*** old/diff.c	Sun Jan  6 18:53:25 1991
--- ./diff.c	Thu Aug 13 18:35:16 1992
***************
-----------------------------------------+----------------------------------------
*** 120,129 ****                         | --- 120,130 ----
                                         |   
                                         |     /* Do our initializations. */
                                         |     output_style = OUTPUT_NORMAL;
                                         |     always_text_flag = FALSE;
                                         |     ignore_space_change_flag = FALSE;
                                         | +   ignore_asm_comments_flag = FALSE;
                                         |     ignore_all_space_flag = FALSE;
                                         |     length_varies = FALSE;
                                         |     ignore_case_flag = FALSE;
                                         |     ignore_blank_lines_flag = FALSE;
                                         |     ignore_regexp = 0;
-----------------------------------------+----------------------------------------
***************
-----------------------------------------+----------------------------------------
*** 145,155 ****                         | --- 146,156 ----
    no_discards = 0;                     |     no_discards = 0;
                                         |   
    /* Decode the options.  */           |     /* Decode the options.  */
                                         |   
    while ((c = getopt_long (argc, argv, |     while ((c = getopt_long (argc, argv,
! 			   "0123456789ab | ! 			   "0123456789ab
  			   longopts, &lo |   			   longopts, &lo
      {                                  |       {
        if (c == 0)		/* Long  |         if (c == 0)		/* Long 
  	c = longopts[longind].val;       |   	c = longopts[longind].val;
        switch (c)                       |         switch (c)
-----------------------------------------+----------------------------------------

Someone told me there is a standard way of doing this, but I never
looked it up. Let me know if anyone is interested in pardif. I
would like to publish some of the "non-mission-critical" software I have
written, but at the present, I pretty much live in a black hole. I
figured no one could complain about sending this fix out, but I would
have to check about anything more than this.]


Let me know if you decide to incorporate my hack - so I will know I
won't have to put it back in every time I upgrade diff.


Jonathan Engdahl, Sr. Project Engineer  | engdahl@aa.ab.com   313-998-2450
Allen-Bradley Co.                       | A Rockwell International Company
555 Briarwood Circle,                   | Industrial Communication Network
Ann Arbor, MI, 48108, USA               | system design, software, ASICs




The following diff is against diff 1.15


-----------------begin cut here ----------------
diff -c5 old/ChangeLog ./ChangeLog
*** old/ChangeLog	Sun Jan  6 19:03:20 1991
--- ./ChangeLog	Thu Aug 13 18:45:55 1992
***************
*** 1,5 ****
--- 1,10 ----
+ Thu Aug 13 18:45:00 1992 Jonathan Engdahl (engdahl at aa.ab.com)
+ 
+ 	* added -j option to diff for treating assembly language
+ 	comments the same as -b whitespace.
+ 
  Sun Jan  6 18:42:23 1991  Michael I Bushnell  (mib at geech.ai.mit.edu)
  
  	* Version 1.15 released.
  
  	* version.c: Updated from 1.15 alpha to 1.15
diff -c5 old/README ./README
*** old/README	Sun Jan  6 18:31:41 1991
--- ./README	Thu Aug 13 18:56:12 1992
***************
*** 72,81 ****
--- 72,86 ----
  	
     -I regexp
  	ignore changes that just insert or delete lines that
  	match the specified regexp.
  
+    -j	ignore assembly language comments which are delimited by `;'.
+ 	This is a superset of -b, so whitespace changes will be ignored also.
+ 	Any assembly comment will be treated as if it were whitespace, so only
+ 	changes to the code will show up in the difference listing.
+ 
     -L label
  	Use the specified label in file header lines output by the -c option.
  	This option may be given zero, one, or two times,
  	to affect neither label, just the first file's label, or both labels.
  	A file's default label is its name, a tab, and its modification date.
***************
*** 154,158 ****
--- 159,171 ----
  whether it is real.  When a match is not real, mark both the
  "matching" lines as changed.  Then build an edit script as usual.
  
  The output routines would have to be changed to scan the files
  sequentially looking for the text to print.
+ 
+ Known bugs:
+ 
+ The -B option sometimes misses inserted blank lines, and winds up
+ showing them. When using the -j option (ignore assembly comments),
+ inserted comment lines are sometimes shown, since -j makes a comment line
+ look like a blank line.
+ 
diff -c5 old/diff.c ./diff.c
*** old/diff.c	Sun Jan  6 18:53:25 1991
--- ./diff.c	Thu Aug 13 18:35:16 1992
***************
*** 120,129 ****
--- 120,130 ----
  
    /* Do our initializations. */
    output_style = OUTPUT_NORMAL;
    always_text_flag = FALSE;
    ignore_space_change_flag = FALSE;
+   ignore_asm_comments_flag = FALSE;
    ignore_all_space_flag = FALSE;
    length_varies = FALSE;
    ignore_case_flag = FALSE;
    ignore_blank_lines_flag = FALSE;
    ignore_regexp = 0;
***************
*** 145,155 ****
    no_discards = 0;
  
    /* Decode the options.  */
  
    while ((c = getopt_long (argc, argv,
! 			   "0123456789abBcC:dD:efF:hHiI:lL:nNpqrsS:tTuvw",
  			   longopts, &longind)) != EOF)
      {
        if (c == 0)		/* Long option. */
  	c = longopts[longind].val;
        switch (c)
--- 146,156 ----
    no_discards = 0;
  
    /* Decode the options.  */
  
    while ((c = getopt_long (argc, argv,
! 			   "0123456789abBcC:dD:efF:hHiI:jlL:nNpqrsS:tTuvw",
  			   longopts, &longind)) != EOF)
      {
        if (c == 0)		/* Long option. */
  	c = longopts[longind].val;
        switch (c)
***************
*** 182,191 ****
--- 183,198 ----
  	  break;
  
  	case 'b':
  	  /* Ignore changes in amount of whitespace.  */
  	  ignore_space_change_flag = 1;
+ 	  length_varies = 1;
+ 	  break;
+ 
+ 	case 'j':
+ 	  /* ignore assembly language comments  (delimited by ';') */
+ 	  ignore_asm_comments_flag = 1;
  	  length_varies = 1;
  	  break;
  
  	case 'B':
  	  /* Ignore changes affecting only blank lines.  */
diff -c5 old/diff.h ./diff.h
*** old/diff.h	Sun Jan  6 18:04:45 1991
--- ./diff.h	Thu Aug 13 18:35:17 1992
***************
*** 139,148 ****
--- 139,151 ----
  EXTERN int	always_text_flag;
  
  /* Ignore changes in horizontal whitespace (-b).  */
  EXTERN int      ignore_space_change_flag;
  
+ /* Ignore changes in horizontal whitespace (-b).  */
+ EXTERN int      ignore_asm_comments_flag;
+ 
  /* Ignore all horizontal whitespace (-w).  */
  EXTERN int      ignore_all_space_flag;
  
  /* Ignore changes that affect only blank lines (-B).  */
  EXTERN int      ignore_blank_lines_flag;
diff -c5 old/io.c ./io.c
*** old/io.c	Thu Nov 29 16:15:43 1990
--- ./io.c	Thu Aug 13 18:35:17 1992
***************
*** 238,247 ****
--- 238,265 ----
  		      h = HASH (h, tolower (c));
  		    else
  		      h = HASH (h, c);
  		    ++p;
  		  }
+ 	      else if (ignore_asm_comments_flag)
+ 
+ 		while ((c = *p) != '\n')
+ 		  {
+ 		    if (c == ' ' || c == '\t' || c == ';')
+ 		      {
+ 			while ((c = *p) == ' ' || c == '\t')++p;
+ 			if (c == ';')while((c = *p) != '\n')++p;
+ 			if (c == '\n')break;
+ 			h = HASH (h, ' ');
+ 		      }
+ 		    /* C is now the first non-space.  */
+ 		    if (isupper (c))
+ 		      h = HASH (h, tolower (c));
+ 		    else
+ 		      h = HASH (h, c);
+ 		    ++p;
+ 		  }
  	      else
  		while ((c = *p) != '\n')
  		  {
  		    if (isupper (c))
  		      h = HASH (h, tolower (c));
***************
*** 266,275 ****
--- 284,307 ----
  		      {
  			while ((c = *p) == ' ' || c == '\t')
  			  ++p;
  			if (c == '\n')
  			  break;
+ 			h = HASH (h, ' ');
+ 		      }
+ 		    /* C is not the first non-space.  */
+ 		    h = HASH (h, c);
+ 		    ++p;
+ 		  }
+ 	      else if (ignore_asm_comments_flag)
+ 		while ((c = *p) != '\n')
+ 		  {
+ 		    if (c == ' ' || c == '\t' || c == ';')
+ 		      {
+ 			while ((c = *p) == ' ' || c == '\t')++p;
+ 			if (c == ';')while((c = *p) != '\n')++p;
+ 			if (c == '\n')break;
  			h = HASH (h, ' ');
  		      }
  		    /* C is not the first non-space.  */
  		    h = HASH (h, c);
  		    ++p;
diff -c5 old/util.c ./util.c
*** old/util.c	Sun Jan  6 18:14:14 1991
--- ./util.c	Thu Aug 13 18:35:17 1992
***************
*** 127,136 ****
--- 127,137 ----
    strcat (name, " ");
    strcat (name, name0);
    strcat (name, " ");
    strcat (name, name1);
  
+ #ifndef MSDOS
    if (paginate_flag)
      {
        int pipes[2];
        int desc;
  
***************
*** 162,171 ****
--- 163,173 ----
  	  close (pipes[0]);
  	  outfile = fdopen (pipes[1], "w");
  	} 
      }
    else
+ #endif /* MSDOS */
      {
  
        /* If -l was not specified, output the diff straight to `stdout'.  */
  
        outfile = stdout;
***************
*** 186,196 ****
--- 188,200 ----
  finish_output ()
  {
    if (outfile != stdout)
      {
        fclose (outfile);
+ #ifndef MSDOS
        wait (0);
+ #endif
      }
  }
  
  /* Compare two lines (typically one from each input file)
     according to the command line options.
***************
*** 233,243 ****
      return 0;
  
    /* Not exactly identical, but perhaps they match anyway
       when case or whitespace is ignored.  */
  
!   if (ignore_case_flag || ignore_space_change_flag || ignore_all_space_flag)
      {
        t1 = s1->text;
        t2 = s2->text;
  
        while (1)
--- 237,247 ----
      return 0;
  
    /* Not exactly identical, but perhaps they match anyway
       when case or whitespace is ignored.  */
  
!   if (ignore_case_flag || ignore_space_change_flag || ignore_all_space_flag || ignore_asm_comments_flag)
      {
        t1 = s1->text;
        t2 = s2->text;
  
        while (1)
***************
*** 281,290 ****
--- 285,332 ----
  		    {
  		      c2 = *t2++;
  		      if (c2 == end_char)
  			break;
  		      if (c2 != ' ' && c2 != '\t')
+ 			{
+ 			  --t2;
+ 			  c2 = ' ';
+ 			  break;
+ 			}
+ 		    }
+ 		}
+ 	    }
+ 
+ 	  else if (ignore_asm_comments_flag)
+ 	    {
+ 	      if (c1 == ' ' || c1 == '\t' || c1 == ';')
+ 		{
+ 		  while (1)
+ 		    {
+ 		      if(c1==';')while((c1=*t1)!=end_char)t1++;
+ 		      c1 = *t1++;
+ 		      if (c1 == end_char)
+ 			break;
+ 		      if (c1 != ' ' && c1 != '\t' && c1 != ';')
+ 			{
+ 			  --t1;
+ 			  c1 = ' ';
+ 			  break;
+ 			}
+ 		    }
+ 		}
+ 
+ 	      /* Likewise for line 2.  */
+ 	      if (c2 == ' ' || c2 == '\t' || c2 == ';')
+ 		{
+ 		  while (1)
+ 		    {
+ 		      if(c2==';')while((c2=*t2)!=end_char)t2++;
+ 		      c2 = *t2++;
+ 		      if (c2 == end_char)
+ 			break;
+ 		      if (c2 != ' ' && c2 != '\t' && c2 != ';')
  			{
  			  --t2;
  			  c2 = ' ';
  			  break;
  			}
------------------ end cut here ------------------------

Newsgroups: gnu.utils.bug