On Fri, Feb 18, 2011 at 03:25:46PM +0100, Jean-Denis Muys scratched on the wall: > > On 18 f?vr. 2011, at 15:12, Philip Graham Willoughby wrote: > > > Adding casts to get rid of warnings is usually the wrong answer in my > > experience. Certainly you should never cast the return value of a > > function call because that hides the problems you get when it's > > implicitly returning int because a required header is missing. I > > used to see a lot of C code (usually from Windows programmers - > > does MSVC encourage this?) which has stuff like this all over the place:
Yes, MSVC does encourage it. Or, rather, MS Visual Studio makes you jump through many, many hoops to treat a .c file as a C file, and compile it with a C compiler. It assumes you'll always be working in C++. The standard templates in our setup don't even allow you to create a .c file-- you're only choice is .cpp. Even if you add a .c file, you need to dig deep into the "Advanced" settings to tell Studio to actually use the C compiler, and not the C++ compiler. This is likely because their C compiler doesn't seem to support the Common Language Runtime, which limits the ability to mix C and C#, for example. So they just assume you want to use the C++ compiler for everything. Most people don't know enough about the two language to think this matters. However, since C++ doesn't implicitly cast void* pointers, it will throw warnings for properly written C code, and the code monkeys of the world will just paste in a hard cast and hit recompile, thinking they "fixed" the warning when all they really did was cover up deeper problems. Forcing casts of void* in C++ was one of the less insightful language changes, and seems to have totally missed most of the the point of void* pointers. I suppose they thought they were making up for it with all the C++ style casts, but I rarely see people use those. About the only one I do see is dynamic_cast<>, and 99% of the time when you're using that, your doing something very anti-OOP, and your class design is broken. > > struct something *fred = (struct something *)malloc(sizeof(struct > > something)); > > > > Casting the return from malloc is never necessary - void * is > > assignable to any non-function pointer type by definition. > > > > It becomes an extremely bad idea when you're building on a platform > > with 64-bit pointers and a 32-bit int (such as everything I use) > > and you have the optimiser turned on ? in this case if <stdlib.h> > > isn't included none of your allocations will work properly and > > your program will crash. > My pure C must be rusted. Could you please elaborate why this line breaks > with 64-bit pointers and 32-bit ints? Undefined functions in C are assumed to return "int." Many people think functions like malloc() are pre-defined by the compiler, but this is usually not true. However, to make things much worse, many compilers** *will* suppress "function not defined" warnings for libc functions like malloc(), because the compiler "knows" the linker will pick it up and deal with it later. ** I have no idea if the latest versions of the Studio compilers do this or not. I would actually guess they *do* throw the warning. Hence, if the header is there, and malloc() is defined, it all works. If the header is not there, it will still compile, sometimes without warning, but the cast will hide the mismatched-type warning of assigning a 32-bit int to a 64-bit pointer, and the code will crash. The original code (without the cast) likely triggered a warning, but someone "fixed" the warning (or, rather, made it go away) by putting the cast in there. In the argument of getting rid of warnings, it is worth remembering that warnings are there for a reason, and just because you got the warning to go away doesn't mean you actually fixed the problem-- it just means you got rid of the warning. Putting in casts are a big example of this, especially to/from void* when you're working in a C code base. They're rarely the answer. While I strive for clean code, I've also given up on warnings. I have a pure-C code base that I need to maintain on Win32 (Visual Studio C (NOT C++!)), Win64, Xbox (Visual Studio), PS3 (PPC-only, gcc-derived), Mac OS X 32 & 64 (gcc), iOS, Linux, and will likely be moving to other platforms. Given the wide array of compilers and their roots, it is nearly impossible to get code that will compile warning-free on every platform without resorting to #if defined() branches to support three different lines of what is essentially the same statement. Not going there. -j -- Jay A. Kreibich < J A Y @ K R E I B I.C H > "Intelligence is like underwear: it is important that you have it, but showing it to the wrong people has the tendency to make them feel uncomfortable." -- Angela Johnson _______________________________________________ sqlite-users mailing list sqlite-users@sqlite.org http://sqlite.org:8080/cgi-bin/mailman/listinfo/sqlite-users