-1

I have some C code and I just verified after a painstaking effort doing things manually in Excel that my executable compiled via gcc -O0 runs correctly but if I compile with -O2 my output is bad.

What might cause this? I've tracked down the problem so far to where it reads in the data, that is for the total set of input files that it reads from, every line of data (numbers from a text file) that I read I immediately print to standard output and redirect into a file called either O0.txt or O2.txt. If I compare these files, I see significant differences in numbers when I expect to see the exact same.

this is gcc-4.3.4 suse linux

here is a snippet of the code to show what is not working with -O2 but it does work with -O0 based on the printf and redirecting output to either O0.txt or O2.txt

# include <stdio.h>
# include <stdlib.h>
# include <string.h>
# include <ctype.h>

# define ZZ 8192

double x[9000];
double y[9000];

double z[2][17][20][3600];

void Read_Data ( FILE *fp, const int R, const int S, const int T, const int type, const int M )
{
   char line[ZZ];
   int count;
   double a, b, c, d, e, f, g, h;

   for ( r = 0; r < 12; r++ )   /* skip past header */
      fgets( line, LS, fp );

   for ( r = 0; r < R; r++ )
   {
      for ( s = 0; s < S; s++ )
      {
         for ( t = 0; t < T; t++ )
         {
            sscanf( line, "%d %lf %lf %lf   %lf %lf   %lf %lf   %lf %lf    %lf %lf", &a, &b, &c, &d, &e, &f, &g, &h );

            if (( a == 0 ) && ( b == 0 ))
               x[t] = 1e-9;
            else
               x[t] = a*a + b*b;

            if (( g == 0 ) && ( h == 0 ))
               y[t] = 1e-9;
            else
               y[t] = g*g + h*h;

printf("%18.12e  %18.12e      %18.12e  %18.12e\n", a, b, c, d );

            fgets( line, ZZ, fp );
         }

         if ( type == 1 )
         {
            z[0][M][r][s] = Find_Median( x, T );
            z[1][M][r][s] = Find_Median( y, T );
         }
         else if ( type == 2 )
         {
            sum_x = 0;   sumy = 0;
            for ( tt = 0; tt < T; tt+ )
            {
               sumx += x[tt];
               sumy += y[tt];
            }
            z[0][M][r][s] = sumx / ((double)T);
            z[1][M][r][s] = sumy / ((double)T);
         }
      }
   }
}

int main ( int argc, char *argv[] )
{
   FILE *fpi;

   Parse_Command_line( argc, argv );

/* other code here */

   T has value of 10
   S has value of 10
   R has value of 180

/* other code here */

   fpi = fopen("mydata", "r" );

   for ( m = 0; m < 17; m++ )
   {
      Read_Data( fpi, R, S, T, m);
   }

/* other code here */

   return 0;
}
ron
  • 967
  • 6
  • 23
  • `for ( r = 0; r < 12; r++ )` Where is `r` defined? – wildplasser Feb 22 '18 at 01:11
  • `sscanf( line, "%d %lf %lf %lf %lf %lf %lf %lf %lf %lf %lf %lf", &a, &b, &c, &d, &e, &f, &g, &h );` you used `%d` but `a` is a `double` – phuclv Feb 22 '18 at 01:49
  • in any cases [if you see different results when optimizing, most probably there's UB somewhere](https://stackoverflow.com/q/20706528/995714) – phuclv Feb 22 '18 at 02:02
  • trust me `r` is defined, this is a **snippet** of the code. The compile flags of just `-O2 -lm -Wall` are used and there are **zero** warnings. Because I had to obsure the code and change variable names to post it here, there are bound to be some minor errors in the above text like the `scanf` – ron Feb 22 '18 at 15:01
  • I have confirmed there is a **problem with -O2 with gcc-4.3-4 the system compiler in SLES 11.4 x86_64** but the problem does not happen in SLES 12.3 with gcc 4.8.5. Would this be considered a compiler problem or bug? – ron Feb 22 '18 at 15:02
  • the function of the code as a whole is to read in some data in an ascii text file, which is signal data, so there are so many samples withing loop T that we want to do either a median or mean on to troubleshoot something else. It was written quickly to just get something working, **I am asking if there is some *obvious deficiency* with the above snippet that goes against the C11 standard or something like that where one would say don't do it like that for this reason...** – ron Feb 22 '18 at 15:07
  • **gcc-5 which is version 5.3.1 20160301 [gcc-5-branch revision 233849] (Suse Linux) works** this is on SLES 11.4 x86-84, kernel 3.0.101-108.18-default – ron Feb 22 '18 at 15:32

1 Answers1

0

I found the error in the read routine, it was not a compiler problem.

Although for some reason the problem did not manifest itself compiling with -O2 on gcc-4.8.5 or anything later that I had available.

the above code snippet is even corrected, must have had tunnel vision, the problem in the original source code was

/* here was the problem in original code */
for ( r = 0; r < r; r++ )   /* skip past header */
   fgets( line, LS, fp );

did not skip past header using gcc_4.3.4 with the -O2 option but would work with -O0 or -O1

-O2- did allow the program to read in all the data from the file correctly
and the program ran correctly when compiling with

gcc-4.8  {sles 11.4 installed by novell update}
gcc-5 {sles 11.4 installed by novell update}
gcc-4.8.5 {native in sles 12.3}

gcc 7.x as of 2018-02-20 manually built from source

I got the original code running in sles 11.4 compiled with gcc_4.3.4 with -O2

ron
  • 967
  • 6
  • 23