C++ Compilation Bug

C++ compilation bug?

This is due to undefined behavior, you are accessing the array mc out of bounds on the last iteration of your loop. Some compilers may perform aggressive loop optimization around the assumptions of no undefined behavior. The logic would be similar to the following:

  • Accessing mc out of bounds is undefined behavior
  • Assume no undefined behavior
  • Therefore di < 4 is always true since otherwise mc[di] would invoke undefined behavior

gcc with optimization turned on and using the -fno-aggressive-loop-optimizations flag causes the infinite loop behavior to disappear(see it live). While a live example with optimization but without -fno-aggressive-loop-optimizations exhibits the infinite loop behavior you observe.

A godbolt live example of the code shows the di < 4 check is removed and replaced with and unconditional jmp:

jmp .L6

This is almost identical to the case outlined in GCC pre-4.8 Breaks Broken SPEC 2006 Benchmarks. The comments to this article are excellent and well worth the read. It notes that clang caught the case in the article using -fsanitize=undefined which I can not reproduce for this case but gcc using -fsanitize=undefined does (see it live). Probably the most infamous bug around an optimizer making an inference around undefined behavior is the Linux kernel null pointer check removal.

Although this is an aggressive optimizations, it is important to note that as the C++ standard says undefined behavior is:

behavior for which this International Standard imposes no requirements

Which essentially means anything is possible and it notes (emphasis mine):

[...]Permissible undefined behavior
ranges from ignoring the situation completely with unpredictable results, to behaving during translation or
program execution in a documented manner characteristic of the environment (with or without the issuance of
a diagnostic message), to terminating a translation or execution (with the issuance of a diagnostic message).[...]

In order to get a warning from gcc we need to move the cout outside the loop and then we see the following warning (see it live):

warning: iteration 3u invokes undefined behavior [-Waggressive-loop-optimizations]
for(di=0; di<4;di++,delta=mc[di]){ }
^

which would have likely been sufficient to provide the OP with enough information to figure out what was going on. Inconsistency like this are typical of the types of behavior we can see with undefined behavior. To get a better understanding of why such waring can be inconsitent in the face of undefined behavior Why can't you warn when optimizing based on undefined behavior? is a good read.

Note, -fno-aggressive-loop-optimizations is documented in the gcc 4.8 release notes.

Issue with my C program : compilation error occurs

You are compiling your code written in C with a C++ compiler.

Just change your .c files to .cpp files, and compile using g++ rather than gcc if you are on Unix systems.

C compiler bug or program error?

I am pretty much convinced that this is a compiler bug based on the following:

  • Copying the data over using pointers (e.g. something along the lines of while (len-- > 0) *dst++ = *src++;) works fine. Thus this does not look like a problem of RAM size, pointer size, etc.

  • More relevant perhaps: If I just replace one of the two constants (NUM_OF_OBJS or MAX_OBJ_SIZE) with a static variable (thus preventing the compiler from precalculating the total count) it works fine.

Unfortunately I contacted IAR (providing a link to this SO question) and this is their answer:

Sorry to read that you don't have a license/support-agreement (SUA).
An examination such as needed for this case can take time, and we
(post-sales-support) prioritize to put time and effort to users with
valid SUA.

Along with some generic comments which are not particularly useful.

So I guess I'll just assume this is a bug and work around it in my code (there are many possible workarounds, including the two described above).

gcc c Compiler error

To the naive reader, what you have in the question is valid C.

However, in order to achieve maximum portability, C compilers are allowed to be extremely fussy about the characters that you are allowed to type into your editor as a candidate for compilation.

I suspect that you have a character in the file that is not part of the ASCII set.

I suggest you re-type the code from scratch, using no other character than ASCII, and watch the error disappear.

Once you've done that, "diff" that with your original version.

Compilation error while including header file in compile command

#define defines a macro for a preprocessor - it means that before compilation, every instance of defined macro (after its definition) is replaced, in Your case after #define STR ... every instance of STR is replaced with specified constant. More about macros here

#include just copy a file and paste it in specified place. More about headers here

First example works because you included your header and code looks like this:

/*
stuff included by stdio.h
*/
int main(void) {
printf("%s", "flag a is activated.\n");
}

And it can compile easily. But in the second example you try to compile every file separately, so the first file looks like this:

/*
stuff included by stdio.h
*/
int main(void) {
printf("%s", STR); //preprocessor doesn't recognise STR as a macro
}

And the second file is empty. So now the compiler tries to compile it and it doesn't know what STR is, so you have an error.

If you want to keep it as a #define then you need to include the header.

You can read more about preprocessing here. If you want to see the output of preprocessor then you need to use a -E flag, for example: gcc main.c -E -o mainPreprocessed.c

Please, next time include code as a text, not an image - it will be easier for people to answer.

One more thing: *.c files are for code (that you add in your g++ command) and *.h files are for headers (that you include with #include).

Compilation Error in C code

You probably are using a pre C99 compiler. Or you are at least telling your compiler to behave like this be providing the option -ansi, which might make the compiler stick to the C89 standard.

The C89 standard does not allow variable definitions somewhere else but at beginning of a block.

To get around this for the 1st error modify this:

void readSector(char* buffer, int sector)
{
int rel_sec = mod(sector,18) + 1;
int head = div(sector,18);
head = mod(head,2);
int track = div(sector,36);
...

to look like this:

void readSector(char* buffer, int sector)
{
int rel_sec = mod(sector,18) + 1;
int head = div(sector,18);
int track = div(sector,36);
head = mod(head,2);
...

For the 2nd error change:

int mod(int num, int den) 
{
int i = 0;
while(num -den*i >= 0)
i++;
i--;
int x = num - den*i;
return x;
}

for example like this:

int mod(int num, int den) 
{
int i = 0;
while(num -den*i >= 0)
i++;
i--;

{
int x = num - den*i;
return x;
}
}

Compilation error with preprocessor #error

You can use -D and CFLAGGS to define macro's in your source code.

make CFLAGS=-DHAVE_POLL

Now

#ifdef HAVE_POLL

becomes true

edit

Also check if the Makefile itself uses $(CFLAGS) as arguments



Related Topics



Leave a reply



Submit