• Create Account

# std c89 not working with gcc?

6 replies to this topic

### #1TheComet  Members   -  Reputation: 1016

Like
0Likes
Like

Posted 02 February 2014 - 06:46 PM

Hi

The following code compiles using gcc with std=c89, even though it shouldn't.

int main( int argc, char** argv )
{
int a = 2;
if( a == 0 )
return 0;
int b = 4;
return 0;
}

I'm developing software that strictly requires to follow the c89 standard, which states that all declarations must be at the beginning of the respective block. Why is gcc ignoring this? This is how I invoke gcc:

\$ gcc -std=c89 -W -Wall -Wextra -o test main.c

Compiling the same code using Visual Studio 2010's nmake produces the correct errors.

2) Someone posts the exact same thing after you

3) You get down-voted, he gets up-voted

### #2SiCrane  Moderators   -  Reputation: 8939

Like
3Likes
Like

Posted 02 February 2014 - 06:55 PM

Did you try using -pedantic or -pedantic-error?

### #3richardurich  Members   -  Reputation: 1127

Like
2Likes
Like

Posted 02 February 2014 - 08:14 PM

There is no ability to check for strict C89 compliance with gcc. From gcc's docs:

"Some users try to use -Wpedantic to check programs for strict ISO C conformance. They soon find that it does not do quite what they want: it finds some non-ISO practices, but not all—only those for which ISO C requires a diagnostic, and some others for which diagnostics have been added." (http://gcc.gnu.org/onlinedocs/gcc/Warning-Options.html)

For Visual Studio, /Za disables extensions. I'm not sure how close that gets you to strict C89, but be aware you can't even include windows.h when specifying /Za.

I don't really understand how you're in this situation though. If you're working for someone else who is requiring the strict C89 compliance, they should tell you what compiler and settings are used for the release builds. And how else would you be required to have strict c89 compliance than working for someone demanding it?

### #4TheComet  Members   -  Reputation: 1016

Like
0Likes
Like

Posted 03 February 2014 - 04:13 AM

Thanks for the info.

The problem is finding common ground between all of the compilers. The project is supposed to be cross-platform, and is mainly being developed on Windows using vc10 (which, I was told, follows the C89 standard pretty strictly). I was hoping I would be able to develop it on my linux machine, serving as the developer for linux line endings, but gcc is extremely loose and forgiving.

I do have the option of developing it in a VM with Windows and vc10 if I have to.

For now, I'm using the following flags. They appear to do the job:

-std=c89 -W -Wall -Wextra -pedantic -Wmissing-prototypes -Wstrict-prototypes -Wold-style-definition

I've also read that some warnings are only available when using the optimizer, e.g. -O3

----

I feel this is a general issue with gcc: It's extremely loose with everything, and not just C code. I've seen it compile C++ code that clang or MSVC will spit back. In fact, rapidxml is such an example; it will only compile under gcc and not clang or MSVC.

Is clang perhaps a better tool for this situation?

2) Someone posts the exact same thing after you

3) You get down-voted, he gets up-voted

### #5BitMaster  Crossbones+   -  Reputation: 2762

Like
0Likes
Like

Posted 03 February 2014 - 04:48 AM

I feel this is a general issue with gcc: It's extremely loose with everything, and not just C code. I've seen it compile C++ code that clang or MSVC will spit back. In fact, rapidxml is such an example; it will only compile under gcc and not clang or MSVC.

At least in the C++ world, my experience has been exactly the opposite. MSVC compiles C++ code (especially looking at templates here) which it never should according to the standard. Especially when telling gcc to be sufficiently pedantic, writing standard-conforming code with gcc is far easier.
I have been working on a project which was built both on Windows (MSVC) and Linux (gcc) in the past. Usually compilation problems originated in Windows programmers, extremely seldom the other way around.

I don't have enough experience with clang to comment on it, but according to my last information, clang on Windows was still not reliable enough to risk using it an production system.

I'd be interested to know what exactly is the problem with rapidxml. Is it possible the library detects C++11-capable compiler and fails because MSVC only supports a rather pitiful part of that?

### #6richardurich  Members   -  Reputation: 1127

Like
1Likes
Like

Posted 03 February 2014 - 06:18 AM

I should have considered cross-platform tools development, especially since you mentioned C instead of C++. For that, the language standard is irrelevant. As you correctly recognize, you're really interested in the common ground between compilers instead of the language. To do that, you can set up a build process that builds using as many compilers as possible to try to catch violations. Use -Wpedantic and the equivalent in other compilers. Work around the Visual Studio problems like Microsoft-supplied headers generating warnings, and then avoid adding any warnings from your code. If you're providing headers for others to include, you need to do this since developers often judge your tool on its ability to avoid generating warnings.

I'm surprised to hear rapidxml doesn't compile on Visual Studio since they used to explicitly test that it does compile on Visual Studio (excluding VS6 obviously).

Clang is better at standards compliance and more descriptive with errors, so it might be worth using. I wouldn't use the executables generated by Clang without testing performance though, as they still have a few extremely weak areas.

### #7TheComet  Members   -  Reputation: 1016

Like
0Likes
Like

Posted 03 February 2014 - 07:58 AM

I'm surprised to hear rapidxml doesn't compile on Visual Studio since they used to explicitly test that it does compile on Visual Studio (excluding VS6 obviously).

I just tested rapidXML using g++, clang++, and MSVC, and it appears they patched it.

The bug I was talking about was: http://sourceforge.net/p/rapidxml/bugs/16/

The patch we used to fix it back then was:

@@ -100,7 +100,21 @@
}

///////////////////////////////////////////////////////////////////////////
-        // Internal printing operations
+        // Internal printing operations
+
+        // =====================================
+        // fix for clang for this bug in gcc and others: http://sourceforge.net/p/rapidxml/bugs/16/
+        // would compile with gcc, but not with clang
+
+        template<class OutIt, class Ch> inline OutIt print_children(OutIt out, const xml_node<Ch> *node, int flags, int indent);
+        template<class OutIt, class Ch> inline OutIt print_element_node(OutIt out, const xml_node<Ch> *node, int flags, int indent);
+        template<class OutIt, class Ch> inline OutIt print_data_node(OutIt out, const xml_node<Ch> *node, int flags, int indent);
+        template<class OutIt, class Ch> inline OutIt print_cdata_node(OutIt out, const xml_node<Ch> *node, int flags, int indent);
+        template<class OutIt, class Ch> inline OutIt print_declaration_node(OutIt out, const xml_node<Ch> *node, int flags, int indent);
+        template<class OutIt, class Ch> inline OutIt print_comment_node(OutIt out, const xml_node<Ch> *node, int flags, int indent);
+        template<class OutIt, class Ch> inline OutIt print_doctype_node(OutIt out, const xml_node<Ch> *node, int flags, int indent);
+        template<class OutIt, class Ch> inline OutIt print_pi_node(OutIt out, const xml_node<Ch> *node, int flags, int indent);
+
+        // =====================================

// Print node
template<class OutIt, class Ch>


rampidXML would compile in gcc but not in clang, because some templated functions were depending on other templated functions that were not declared yet. I guess you could say that gcc was "smart enough" to apply some kind of post-lookup to fix this, but the reality is that the code was incorrect.

It's things like that that I'm worried about with this project.