How can I tell i'm compiling on a mac? - c-preprocessor

I'm using a compiled-from-source gcc for the avr. My gcc configure options are:
${PWD}/../gcc/configure --prefix="${PWD}/../build/" --exec-prefix="${PWD}/../build/" --datadir="${PWD}/../build/" --target=avr --enable-languages=c --disable-libssp --disable-lto --disable-nls --disable-libgomp --disable-gdbtk --disable-threads --enable-poison-system-directories
When I use the following snippet of preprocessor magic
#if defined __APPLE__
#error "Apple"
#else
#error "Ahh"
#endif
it is outputting
error: #error "Ahh"
If I run avr-cpp -dM version.h I see __APPLE__ is not defined. If I run cpp -dM version.h I see that __APPLE__ is defined. What do I have to change in my configure line (or elsewhere) to get my compiled-from-source gcc to have __APPLE__ defined correctly?
I'm on a mac compiling for the avr as apposed to being on windows compiling for the avr.

Probably all you can potentially need is HERE
and specifically about Mac here

Related

gcc compile with 32-bit architecture not working

I am trying to compile a C file with gcc. The code in header file will need specified architecture in order to compile.
#if defined( _8BIT_ARCHITECTURE )
#include "type8.h"
#elif defined( _16BIT_ARCHITECTURE )
#include "type16.h"
#elif defined( _32BIT_ARCHITECTURE )
#include "type32.h"
#else
#error ARCHITECTURE not defined
#endif
When using Visual Studio, I can configure the platform into 32-bit and it can build successfully. But how do I do the same thing with gcc commands?
I was trying to use:
gcc -m32 -c myFile.c -I /somePath/
But it keeps giving me the error statement:
#error ARCHITECTURE not defined
Adding -D_32BIT_ARCHITECTURE fix the issue

Resolve TCC warnings on macOS

I'm looking for a C interpreter to use while making a simple C utility to avoid compiling all the time. I installed TCC as suggested here but I get warnings and errors. How do I run TCC correctly?
$ tcc -run hello.c
.../usr/include/sys/cdefs.h:81: warning: #warning "Unsupported compiler detected"
#if !defined(__GNUC__) || __GNUC__ < 4
#warning "Unsupported compiler detected"
#endif
Setting __GNUC__ causes an error later on:
tcc -D__GNUC__=4 -run hello.c
.../usr/include/i386/_types.h:98: error: ';' expected (got "__darwin_va_list")
#if (__GNUC__ > 2)
typedef __builtin_va_list __darwin_va_list; /* va_list */
#else
typedef void * __darwin_va_list; /* va_list */
#endif
My environment:
~$ gcc --version
Apple LLVM version 9.0.0 (clang-900.0.39.2)
Target: x86_64-apple-darwin16.7.0
If TCC is not fit for macOS, please suggest a C interpreter that plays nicely.
For sure one that will work is CERN's Cling or any other based on LLVM/Clang, since that is what Apple uses in macOS.
The block comment immediately above the line your first message complains about is
/* This SDK is designed to work with clang and specific versions of
* gcc >= 4.0 with Apple's patch sets */
#if !defined(__GNUC__) || __GNUC__ < 4
#warning "Unsupported compiler detected"
#endif
which is pretty clear - you do need gcc or clang. Fortunately both of those compilers are really easy to install - use https://www.macports.org.
I wouldn't bother with a C interpreter - it's not an interpreted language.
First of all, tcc is not an "interpreter" it is a very fast compiler that can be used to compile and run your C code as if it were script.
Secondly, the "Unsupported compiler detected" warning is just that, a warning. I get that warning all the time and my code still compiles and runs no problem. If the warning bothers you, you can simply run tcc with the -w option to suppress the warnings (probably only advisable if you are re-running a file that you already know has no issues).
For example, if you are running the C code as if it's a script using the tcc shebang line, you can change it to this
#!/usr/local/bin/tcc -w -run
There can be a couple of other issues when running tcc on macOS. The main one is missing include files. On macOS the include files may not be installed to /usr/include/. See this question for the fix. Once Xcode had properly installed the headers, I still needed to update my environment variable to get tcc to find them.
export C_INCLUDE_PATH="/usr/include:$C_INCLUDE_PATH"
You can see where tcc is looking for header by running tcc -vv.

Trying to compile simple dll written in C using gcc fails

Trying to compile a simple DLL written in C using gcc.
Tried following many tutorials, but can't get it to compile even when I strip the file down to the very basics.
test_dll.c
#include <stdio.h>
__declspec(dllexport) int __stdcall hello() {
printf ("Hello World!\n");
}
Trying to compile this using the command
gcc -c test_dll.c
Failing, getting this output
test_dll.c: In function '__declspec':
test_dll.c:3:37: error: expected '=', ',', ';', 'asm' or '__attribute__' before 'hello'
__declspec(dllexport) int __stdcall hello() {
^
test_dll.c:5:1: error: expected '{' at end of input
}
^
gcc version
gcc version 4.8.4 (Ubuntu 4.8.4-2ubuntu1~14.04.3)
It depends on what you're trying to do:
1. build a library for linux on linux
then remove the __declspec(dllexport) and __stdcall. On linux, you need nothing special in the source code for building a library. Note that libraries aren't DLLs on linux, they're named *.so (shared object). You'll have to compile with -fPIC and link with -shared to create your .so file. Please use google for more details on this.
2. build a windows DLL on linux
Install mingw packages (search for them in your package manager). Then, instead of just gcc, invoke the cross compiler targeting windows/mingw, e.g. i686-w64-mingw32-gcc.
3. allow to build libraries cross-platform, including windows
If you want to be able to build a library from the same code on windows and linux, you'll need some preprocessor magic for this, so __declespec() is only used when targeting windows. I normally use something like this:
#undef my___cdecl
#undef SOEXPORT
#undef SOLOCAL
#undef DECLEXPORT
#ifdef __cplusplus
# define my___cdecl extern "C"
#else
# define my___cdecl
#endif
#ifndef __GNUC__
# define __attribute__(x)
#endif
#ifdef _WIN32
# define SOEXPORT my___cdecl __declspec(dllexport)
# define SOLOCAL
#else
# define DECLEXPORT my___cdecl
# if __GNUC__ >= 4
# define SOEXPORT my___cdecl __attribute__((visibility("default")))
# define SOLOCAL __attribute__((visibility("hidden")))
# else
# define SOEXPORT my___cdecl
# define SOLOCAL
# endif
#endif
#ifdef _WIN32
# undef DECLEXPORT
# ifdef BUILDING_MYLIB
# define DECLEXPORT __declspec(dllexport)
# else
# ifdef MYLIB_STATIC
# define DECLEXPORT my___cdecl
# else
# define DECLEXPORT my___cdecl __declspec(dllimport)
# endif
# endif
#endif
Then put a DECLEXPORT in front of each declaration to be exported by the lib and SOEXPORT in front of each definition. That's just a quick example.
Since you are compiling on Linux, the gcc takes Linux as the target.
What you want to do is cross compile for Windows. Which means you will need a cross compiler. The one available for Ubuntu Linux is mingw.
You can install it using
apt-get install gcc-mingw32
Then you can compile with
gcc-mingw32 -c test_dll.c
Further compiling into dll would need
gcc-mingw32 --shared test_dll.o -o test_dll.dll
This dll can then be used on Windows.

how to use macro __GNUC__ and __GNUC_MINOR__ in configure.ac

I need to test the version of gcc in configure.ac, then I do this:
    
#if defined(__GNUC__) && (__GNUC__ > 3)
CFLAGS = xxxx  
#else
CFLAGS = xxxx
#endif 
but this failed, the CFLAGS in if expression is never used, and the gcc i'm using now is 4.1.2.
Then I wrote a simple c program to print out the __GNUC__ __GNUC_MINOR__, it works very well.
did I miss something? how can I use the two macros in configure.ac?     
That's not how autoconf works. autoconf.ac is not a C file that gets processed by the C preprocessor. Autoconf macros are something entirely different. You should look for a tutorial. If I remember correctly, this is a decent one. (Somebody will surely comment if it isn't :)
To check whether the compiler supports a particular flag, you should use the AX_CHECK_COMPILE_FLAG macro from the Autoconf Archive.
CFLAGS is reserved as an environment variable by the autotools. ./configure --help lists some others. Ideally, the user should supply the appropriate compiler flags, e.g.,
CC="gcc -std=c99" CFLAGS="-pipe -Wall -pedantic -O2" ./configure
and it's entirely reasonable to have a README file with the package if there are issues with different compilers. The best modern tutorial I'm aware of is the Autotools Mythbuster.
Now, if you want to proceed with this anyway as an interim solution, it is possible to modify CFLAGS...
AC_COMPILE_IFELSE([AC_LANG_PROGRAM(
[[#if defined (__GNUC__) && (__GNUC__ > 3)
#error "GCC4" /* not an actual error - just using the fail condition. */
#endif]])],
[CFLAGS=<your non-GCC4 flags here>], [CFLAGS=<your GCC4 flags here>])
If adding options to CFLAGS, this can be done with automake's CFLAGS primary - but that's another answer in itself.

Is there a way to list all C preprocessor defines?

Is there a way to list all C preprocessor defines?
I'm on a mac with a compiled from source gcc and
#if defined __APPLE__
#error "Apple"
#else
#error "Ahh"
#endif
is giving me:
error: #error "Ahh"
my compile configure options are:
${PWD}/../gcc/configure --prefix="${PWD}/../build/" --exec-prefix="${PWD}/../build/" --datadir="${PWD}/../build/" --target=avr --enable-languages=c --disable-libssp --disable-lto --disable-nls --disable-libgomp --disable-gdbtk --disable-threads --enable-poison-system-directories
If you are using gnu cpp, you can pass the option -dM to emit all defined macros. That is:
$ cpp -dM foo.c
will tell you everything that is defined for foo.c. There will be extra defines passed on the command line by make, and probably more things in config.h, but if you grab the output of make and rerun the commands with -Xpreprocessor -dM added you should see everything.

Resources