[comp.unix.aix] cc -O producing faulty code

s900387@minyos.xx.rmit.oz.au (Craig Macbride) (06/01/91)

I have found a situation where a perfectly simple piece of C code which does
some strcpy()s and fprintf()s works fine without the -O switch, but produces
code which generates incorrect output when -O is used. (The code produced by
the optimiser is also longer - I assume it's optimising for speed?)

Has anyone else come across this situation on an RS6000 before? I always used
to compile everything with -O on Unix machines, but it seems not a very safe
thing to do with this compiler.

-- 
 _--_|\		Craig Macbride	<s900387@minyos.xx.rmit.oz.au>
/      \
\_.--.*/	The above are simply my comments, not necessarily
      v		the views of any other being or organisation.

drake@drake.almaden.ibm.com (06/02/91)

How about posting an example, and the level of AIX you're running?


Sam Drake / IBM Almaden Research Center 
Internet:  drake@ibm.com            BITNET:  DRAKE at ALMADEN
Usenet:    ...!uunet!ibmarc!drake   Phone:   (408) 927-1861

jfh@rpp386.cactus.org (John F Haugh II) (06/02/91)

In article <1991Jun1.065826.5526@minyos.xx.rmit.oz.au> s900387@minyos.xx.rmit.oz.au (Craig Macbride) writes:
>I have found a situation where a perfectly simple piece of C code which does
>some strcpy()s and fprintf()s works fine without the -O switch, but produces
>code which generates incorrect output when -O is used. (The code produced by
>the optimiser is also longer - I assume it's optimising for speed?)
>
>Has anyone else come across this situation on an RS6000 before? I always used
>to compile everything with -O on Unix machines, but it seems not a very safe
>thing to do with this compiler.

You need to give the level of the compiler that is failing as well as an
example of the code that breaks the optimizer.

I will start with the statement that most compiler bugs aren't.  I saw
quite a few things that were called "compiler bugs" that were really
caused by incorrect argument passing.  The proper argument just happened
to be in the correct register when optimization was turned off.

Now that I've said that, the S/6000 compiler has, in the past, had problems
with generating bad code with the optimizer turned on.  So far as I know,
the currently being delivered compiler has no such problems.  You need to
come up with the smallest fragment of (correct) code that reproduces the
problem and send it off to Defect Support.
-- 
John F. Haugh II        | Distribution to  | UUCP: ...!cs.utexas.edu!rpp386!jfh
Ma Bell: (512) 255-8251 | GEnie PROHIBITED :-) |  Domain: jfh@rpp386.cactus.org
"If liberals interpreted the 2nd Amendment the same way they interpret the
 rest of the Constitution, gun ownership would be mandatory."

s900387@minyos.xx.rmit.oz.au (Craig Macbride) (06/02/91)

drake@drake.almaden.ibm.com writes:

>How about posting an example, and the level of AIX you're running?

Release 1, Version 3. An example follows, with test script and result. You
will notice that I've put the optimised program's output through "cat -v" to
make it at least keep to ASCII characters. :-)

It seems very strange that code which occurs after the fprintf() statement
seems to be causing the result of it to change. The full-sized program was,
of course, using the variable new_usual_dom in output as well, but like all
code which didn't affect the problem, I've removed it.

-------------------------------program-------------------------------------
#include <stdio.h>
#include <string.h>
#include <memory.h>

char lga_name[100];
char usual_dom[100];

char line[1000];

char new_lga_name[100];
char new_usual_dom[100];

main(argc,argv)
int argc;
char **argv;
{
while (fgets(line,1000,stdin) != NULL)
{
	memcpy(usual_dom,line+31,20);
	usual_dom[20] = '\0';
	memcpy(lga_name,line+51,10);
	lga_name[10] = '\0';

	if (strcmp(lga_name,"ELTHAM    ")==0) strcpy(new_lga_name,"2640");
	else if (strcmp(lga_name,"PRESTON   ")==0) strcpy(new_lga_name,"6000");
	else if (strcmp(lga_name,"WHIT/SEA  ")==0) strcpy(new_lga_name,"8040");
	else if (strcmp(lga_name,"D/VALLEY  ")==0) strcpy(new_lga_name,"2280");
	else if (strcmp(lga_name,"UNKNOWN   ")==0) strcpy(new_lga_name,"9999");
	else strcpy(new_lga_name,"0000");

	fprintf(stdout, "'%s'\n", new_lga_name);

#ifndef KILL3
if (strcmp(usual_dom,"it doesn't seem to  ")==0) strcpy(new_usual_dom,"1");
else if (strcmp(usual_dom,"matter what this    ")==0) strcpy(new_usual_dom,"2");
else if (strcmp(usual_dom,"text is exactly, nor")==0) strcpy(new_usual_dom,"3");
else if (strcmp(usual_dom,"matter that it is   ")==0) strcpy(new_usual_dom,"4");
else if (strcmp(usual_dom,"_after_ the fprintf ")==0) strcpy(new_usual_dom,"5");
else if (strcmp(usual_dom,"... it still causes ")==0) strcpy(new_usual_dom,"6");
else if (strcmp(usual_dom,"the optimised output")==0) strcpy(new_usual_dom,"7");
else if (strcmp(usual_dom,"to be wrong...      ")==0) strcpy(new_usual_dom,"7");
else if (strcmp(usual_dom,"                    ")==0) strcpy(new_usual_dom,"7");
else if (strcmp(usual_dom,"xxxxxxxxxxxxxxx     ")==0) strcpy(new_usual_dom,"7");
else if (strcmp(usual_dom,"OTHER               ")==0) strcpy(new_usual_dom,"7");
else if (strcmp(usual_dom,"UNKNOWN             ")==0) strcpy(new_usual_dom,"0");
else strcpy(new_usual_dom,"X");
#endif
}
exit(0);
}

-------------------------------script to test it---------------------------
echo Normal
cc -o x x.c
x < in

echo Optimised
cc -O -o xopt x.c
xopt < in | cat -v

echo Optimised with what should be irrelevant code removed
cc -O -DKILL3 -o xopt2 x.c
xopt2 < in
-------------------------------output of test------------------------------
Normal
'8040'
'6000'
Optimised
' ^ClD'
' ^Cl0'
Optimised with what should be irrelevant code removed
'8040'
'6000'
-- 
 _--_|\		Craig Macbride	<s900387@minyos.xx.rmit.oz.au>
/      \
\_.--.*/	The above are simply my comments, not necessarily
      v		the views of any other being or organisation.

hbergh@nl.oracle.com (06/10/91)

In article <1991Jun2.124226.17523@minyos.xx.rmit.oz.au> s900387@minyos.xx.rmit.oz.au (Craig Macbride) writes:
>drake@drake.almaden.ibm.com writes:
>
>>How about posting an example, and the level of AIX you're running?
>
>Release 1, Version 3. An example follows, with test script and result. You
>will notice that I've put the optimised program's output through "cat -v" to
>make it at least keep to ASCII characters. :-)

	That's very good! Although Jim probably wanted to know the update
	level of the C compiler. You can see what that is by typing
	'lslpp -h xlccmp.obj' and look for the line with ACTIVE.
	You can also have the compiler generate a listing with -qsource
	or -qlist (assembly) and its version number will be on the first line.

	Your test shows the problem with the 1.1.1.1 compiler (also shipped
	with xlccmp.obj 1.1.2.15) and can be solved by adding the 
	-U__STR__ option, as Bjorn Engsig pointed out in an earlier post.
	This will tell the compiler not to inline strcmp and strcpy.

	The xlc compiler version 1.1.3.13 that is shipped with xlccmp.obj
	1.1.5.10 (3005 update, aka AIX 3.1.5) doesn't have this problem.

> _--_|\		Craig Macbride	<s900387@minyos.xx.rmit.oz.au>
>/      \
>\_.--.*/	The above are simply my comments, not necessarily
>      v		the views of any other being or organisation.



	Regards,

	Herbert van den Bergh                    hbergh@oracle.com
	Oracle Europe                            or uunet!oracle!hbergh
-- 

	Regards,

	Herbert van den Bergh                    hbergh@oracle.com