32 bit compilation failing on 64 bit Ubuntu 16.04 - c

I have an application that requires the use of glib and a 32 bit library supplied by a third party.
When I compile on 32 bit Ubuntu the application builds and runs successfully.
However when I try the same on 64 bit Ubuntu it fails to build because of the following error:
/usr/include/glib-2.0/glib/gtypes.h: In function ‘_GLIB_CHECKED_ADD_U64’:
/usr/include/glib-2.0/glib/gmacros.h:217:53: error: size of array ‘_GStaticAssertCompileTimeAssertion_0’ is negative
#define G_STATIC_ASSERT(expr) typedef char G_PASTE (_GStaticAssertCompileTimeAssertion_, __COUNTER__)[(expr) ? 1 : -1] G_GNUC_UNUSED
^
/usr/include/glib-2.0/glib/gmacros.h:214:47: note: in definition of macro ‘G_PASTE_ARGS’
#define G_PASTE_ARGS(identifier1,identifier2) identifier1 ## identifier2
^
/usr/include/glib-2.0/glib/gmacros.h:217:44: note: in expansion of macro ‘G_PASTE’
#define G_STATIC_ASSERT(expr) typedef char G_PASTE (_GStaticAssertCompileTimeAssertion_, __COUNTER__)[(expr) ? 1 : -1] G_GNUC_UNUSED
^
/usr/include/glib-2.0/glib/gtypes.h:422:3: note: in expansion of macro ‘G_STATIC_ASSERT’
G_STATIC_ASSERT(sizeof (unsigned long long) == sizeof (guint64));
^
Note: I have gcc-multilib and g++-multilib.
I also tried changing the defines inside /usr/lib/x86_64-linux-gnu/glib-2.0/include/glibconfig.h from 8 to 4 with no success.
I also tried installing libglib2.0-dev:i686 but pkg config in cmake can not find glib. I am also using the appropriate -m32 flags for C, CXX and LD
Any help with this issue would be greatly appreciated.

No idea why glib wouldn't try to use int64_t instead of duplicating that. Seems silly to me. Maybe they do this on purpose to increase the chance of breaking if you do what you did, and try to compile 32-bit code using a 64-bit glib install.
To compile 32-bit apps, you need 32-bit library object files (.so). They will come with a glibconfig.h that has appropriate typedefs for -m32.
Installing libglib2.0-dev:i686 should be the right approach. I assume you eventually got that sorted out, so the app you're building finds the -I include paths and -L library paths for it.

Related

STM32 Cmake STM32Workbench project

I am trying to write a CMakeLists.txt file for my STM32 project. I am using cmake files from this repo: https://github.com/ObKo/stm32-cmake. Building from command line works fine. I am doing it in that way:
cmake -C "..\STM32F207ZCTx_config.cmake" -DCMAKE_BUILD_TYPE=DEBUG -G "Eclipse CDT4 - Unix Makefiles" ..
make.exe -j4
In cache file I have some variables set:
set(CMAKE_MAKE_PROGRAM "D:/STM32Workbench/plugins/fr.ac6.mcu.externaltools.arm-none.win32_1.16.0.201807130628/tools/make/make.exe" CACHE STRING "stm32 make")
set(CMAKE_TOOLCHAIN_FILE "stm32-cmake/gcc_stm32.cmake" CACHE STRING "stm32 toolchain")
set(TOOLCHAIN_PREFIX "D:/STM32Workbench/plugins/fr.ac6.mcu.externaltools.arm-none.win32_1.16.0.201807130628/tools/compiler" CACHE STRING "arm toolchain path")
When I import created project to STM32 Workbench it generates a lot of errors "unresolved external" regarding stdint.h types (e.g. uint8_t, int32_t).
After some debugging this problem I realized that there are missing some defines which are used by stdint.h header. I checked out the compiler with this command:
arm-none-eabi-gcc.exe -dM -E out.h
And got the list of defines in arm-none-eabi-gcc:
#define __UINTMAX_TYPE__ long long unsigned int
#define __INT_FAST16_TYPE__ int
#define __INT_FAST64_TYPE__ long long int
#define __INT_FAST32_TYPE__ int
#define __UINT_LEAST16_TYPE__ short unsigned int
#define __SIZE_TYPE__ unsigned int
#define __INT_LEAST16_TYPE__ short int
... and much more
These defines are needed by stdint.h to create correct uint8_t and other types.
I can add manually these defines to Eclipse project, but I am wondering if there is method to add these defines to Eclipse project automagically from CMake?
Any help will be appreciated.
Problem was in STM32Workbench. Sources were excluded from build and from indexer.
To fix it - right mouse click on source, Properties, C/C++ General, Preprocessor Include Paths, uncheck Exclude resource from build.
Now the indexer is able to find all sources and all "unresolved external" errors are gone!

Compiling a Linux program under Mac OS X

I am trying to use make under Mac OS X (El Capitan) to compile a program which I know to work under Linux. The program makes use of USB libraries. I had to modify the config.mk file for these libraries to be found, but now I end up with errors in the compilation (undeclared identifiers).
Link to source: https://github.com/pali/0xFFFF
It requires usb.h, which seems to be part of usblib-compat. I installed the latter by brew install usblib-compat. But still usb.h couldn't be seen, although I knew where it was: specifically, symbolic link to usb.h and to the library may be found under /usr/local/include and under /usr/local/lib, respectively.
After many trials, I progressed somehow. Namely, the file config.mk is clearly read during the make'ing process, although I have to admit that it is not clear to me how this is done; anyway, I noticed two lines commented:
CPPFLAGS += -I/usr/local/include
LDFLAGS += -L/usr/local/lib -Wl,-R/usr/local/lib
(for the sake of precision, in the original config.mk the local dir was replaced by a pkg dir. I replaced it in these lines.)
I uncommented them and now something happens: the usb.h is found. I think the first of these variable definitions tells the compiler where to look tor header files, and the second tells the linker where to look for libraries - but again it is not completely clear to me.
In any case, I have still problems. Namely, the make'ing process outputs two warnings and an error, and then stops:
usb-device.c:90:57: warning: unused parameter 'udev' [-Wunused-parameter]
static void usb_reattach_kernel_driver(usb_dev_handle * udev, int interface) {
^
usb-device.c:90:67: warning: unused parameter 'interface' [-Wunused-parameter]
static void usb_reattach_kernel_driver(usb_dev_handle * udev, int interface) {
usb-device.c:324:13: error: use of undeclared identifier 'RTLD_DEFAULT' if ( dlsym(RTLD_DEFAULT, "libusb_init") )
Seems this program is difficult to port from Linux to Mac, although I think it should be portable. If anyone has any idea about what to do (apart from running a Linux distribution...), it would be much appreciated.
EDIT
dlfcn.h has the following:
#if !defined(_POSIX_C_SOURCE) || defined(_DARWIN_C_SOURCE)
#define RTLD_NOLOAD 0x10
#define RTLD_NODELETE 0x80
#define RTLD_FIRST 0x100 /* Mac OS X 10.5 and later */
/*
* Special handle arguments for dlsym().
*/
#define RTLD_NEXT ((void *) -1) /* Search subsequent objects. */
#define RTLD_DEFAULT ((void *) -2) /* Use default search algorithm. */
#define RTLD_SELF ((void *) -3) /* Search this and subsequent objects (Mac OS X 10.5 and later) */
#endif /* not POSIX */
Ok, finally I have been successful. I think it be worth publishing my solution - maybe others could find it useful.
So, the first point is: if I run make in the program's main folder, usb.h is not found. Then, we have to install the corresponding library.
There are two possibilities for this to be done. The first and more obvious would be to install, through home brew, libusb-1.0 and libusb-compat (the latter provides a compatibility interface for programs that use libusb-0.1, which is the first version of libusb, and is not compatible with libusb-1.0. usb.h is included in libusb-compat):
brew install libusb
brew install libusb-compat
However, this leads to other problems, as reported in the other answer. I had worked around them, but eventually found out that my program got angry when using libusb-compat (if I understand correctly, interfacing the usb port through two layers of libraries is too slow for a flasher).
So, the other possibility: installing the actual libusb-0.1. This is not available through home brew. It is however available through ports, with the name of libusb-legacy. So, I had to install ports, install the X-code command line utilities (which required first going to Apples' website to accept their legal things...) and run
sudo port install libusb-legacy
Ok, now calling make would not do the trick since the compiler is not able to find the library yet. For that, I had to edit the config.mk file which is included in the main directory of the program, uncommenting the last two lines, and editing them somewhat in order to point to the directory where libusb-legacy is stored:
CPPFLAGS += -I/opt/local/include/libusb-legacy -D_DARWIN_C_SOURCE
LDFLAGS += -L/opt/local/lib/libusb-legacy
(the -D_DARWIN_C_SOURCE defines the environmental variable required for other variables to be defined by the libraries. In the Makefile in the src directory, in fact, _POSIX_C_SOURCE is defined.)
Do you think all this did the job? No. In fact at this point I ended up with another error: the linker not being able to find some library called -lusb. I don't know why this syntax, but after some thought I realised that -lusb is somewhat a short for libusb. And the libusb I am using is actually called libusb-legacy... So I went into the Makefile in the src directory, where -lusb is introduced, and changed -lusb to -lusb-compat. Tah-dah! Compiled. A few warnings about non-used variables and a comparison between two different types of integers, but nothing more. And the program runs - after a few trials, I have been able to reflash my bricked phone, which now is alive again! Very happy!!! :)
Looking at the dlfcn.h source code, it seems that the identifier is defined only if _POSIX_C_SOURCE is not defined, or _DARWIN_C_SOURCE is defined. Thus I'd just add #define _DARWIN_C_SOURCE;
Or you could add the corresponding -D switch in the config.mk:
CPPFLAGS += -I/usr/local/include -D_DARWIN_C_SOURCE

typedef and #define with same name

A little background:
I'm trying to port some .ksh files that I have running on Solaris to run on Windows using Cygwin. There is a difference between the ksh implementation running on the Solaris box and the pdksh implementation that is easily installable in Cygwin that deals with subshells - you can check this question for the details if you'd like.
Because of this difference, I'm trying to build the AST toolkit found here because the binaries are no longer available from AT&T according to this question.
My Question:
When I try to build according to the instructions on the GitHub site, I wind up with an error compiling a file called fastfind.c:
+ cc -D_BLD_STATIC -D_BLD_DLL -D_BLD_ast -I. -I/ast-master/src/lib/libast -Icomp -I/ast-master/src/lib/libast/comp -Imisc -I/ast-master/src/lib/libast/misc -Iinclude -I/ast-master/src/lib/libast/include -Istd -I/ast-master/src/lib/libast/std -D_PACKAGE_ast -c /ast-master/src/lib/libast/misc/fastfind.c,
In file included from /ast-master/src/lib/libast/std/stdio.h:22:0,
from ./ast_wchar.h:87,
from /ast-master/src/lib/libast/include/regex.h:39,
from /ast-master/src/lib/libast/misc/findlib.h:35,
from /ast-master/src/lib/libast/misc/fastfind.c:77:
./ast_stdio.h:82:15: error: conflicting types for '_sfio_FILE'
#define FILE _sfio_FILE
^
./ast_stdio.h:80:24: note: previous declaration of '_sfio_FILE' was here
typedef struct _sfio_s _sfio_FILE;
^
mamake [lib/libast]: *** exit code 1 making fastfind.o
Lines 80-82 of the file ast_stdio.h are as follows:
80: typedef struct _sfio_s _sfio_FILE;
81:
82: #define FILE _sfio_FILE
Also, the top of the ast_stdio.h file have this:
/* : : generated by proto : : */
/* : : generated from /ast-master/src/lib/libast/features/stdio by iffe version 2012-07-17 : : */
Lastly, here's my relevant cc information:
$ cc --version
cc (GCC) 5.4.0
A little disclaimer: my C is rusty as I've been a Java guy for the past 14 years. My understanding is that the #define directive gets evaluated by the preprocessor, so line 82 would essentially replace the string FILE with _sfio_FILE in the code, and the typedef line wouldn't be evaluated until actual compilation.
Obviously I'm wrong, or this error wouldn't be happening. And obviously this code compiles for someone, or it wouldn't have been released this way. Any insights as to what's going on here and how I can make this file compile are appreciated. I found this question which seems close to what I'm asking, but there's either something different between my case and that question's, or my C brain is not able to comprehend why that question should cover my particular situation.
Thanks for your time!
The error was due to a change in glibc. See Red Hat Bugzilla #1477082 for more information and what changes to source files are needed.

PostgreSQL: compile C function on Windows 8 64bit

I'm learning how to compile a C trigger to load on PostgreSQL
When compile the "trigf.c" (in the example at http://www.postgresql.org/docs/9.3/interactive/trigger-example.html), I get some issue related to int64 error (c.h header)
#ifdef HAVE_LONG_INT_64
/* Plain "long int" fits, use it */
#ifndef HAVE_INT64
typedef long int int64;
#endif
#ifndef HAVE_UINT64
typedef unsigned long int uint64;
#endif
#elif defined(HAVE_LONG_LONG_INT_64)
/* We have working support for "long long int", use that */
#ifndef HAVE_INT64
typedef long long int int64;
#endif
#ifndef HAVE_UINT64
typedef unsigned long long int uint64;
#endif
#else
/* neither HAVE_LONG_INT_64 nor HAVE_LONG_LONG_INT_64 */
#error must have a working 64-bit integer datatype
#endif
-> [Error] #error must have a working 64-bit integer datatype
I don't know how to solve that problem, because clearly that there is a working 64 bit integer datatype that I can use.
Edit: I installed pgsql from binary. The C compiler I used for compile the C function file is MinGW GCC 4.7.2. (Using the path of Dev-cpp mingw gcc).
The command line is :
gcc -fpic -c "D:\trigf.c"
At the first time, it showed an error that in c.h: not found libintl.h (no such file or directory). Then I download the Lib Intl - 0.14.4 (library for native language support). The installation create a folder: C:\Program Files (x86)\GnuWin32.
I edited the environment variable CPATH, added C:\Program Files (x86)\GnuWin32\include folder, which contained libintl.h.
I ran the command again, and I met with the above error.
Update: It turns out not to be too hard to build extensions stand-alone with MSVC on Windows. I wrote a blog post detailing the process today.
The usual way to build extensions on Windows is to do it inside a working PostgreSQL build tree.
See these instructions on the PostgreSQL wiki.
You might be able to do it using MinGW and PGXS using a suitable Makefile instead.
Just trying to compile a standalone .c file is unlikely to work as there are a variety of paths and preprocessor definitions required.
It doesn't help that the current PostgreSQL packages don't include headers for public dependencies, which is really rather frustrating. You can safely compile without ENABLE_NLS defined even if the target PostgreSQL was built with ENABLE_NLS, though, and in this case libintl.h won't be required.

Building RabbitMQ-C on Windows using MinGW

Pretty much what the title says. I have been trying to build RabbitMQ under Windows using MinGW with no success. Judging by the amount of people I see asking questions about how to use it, I suspect I am making a silly mistake, but I don't know what it is. I'm on Win7-64 and I'm extracting the repo, creating a build directory in it, and running
cmake -G "MinGW Makefiles" ..
which seems to work, and then
cmake --build .
which throws a bunch of function re declaration errors. Does anybody know what I'm botching here?
Just for good measure, a small sampling of the errors:
Linking C shared library librabbitmq.1.dll
CMakeFiles\rabbitmq.dir/objects.a(amqp_api.c.obj):amqp_api.c:(.rdata+0x3c): mult
iple definition of `amqp_empty_array'
CMakeFiles\rabbitmq.dir/objects.a(amqp_framing.c.obj):amqp_framing.c:(.bss+0x0):
first defined here
CMakeFiles\rabbitmq.dir/objects.a(amqp_api.c.obj):amqp_api.c:(.rdata+0x44): mult
iple definition of `amqp_empty_table'
CMakeFiles\rabbitmq.dir/objects.a(amqp_framing.c.obj):amqp_framing.c:(.bss+0x8):
first defined here
CMakeFiles\rabbitmq.dir/objects.a(amqp_api.c.obj):amqp_api.c:(.rdata+0x4c): mult
iple definition of `amqp_empty_bytes'
CMakeFiles\rabbitmq.dir/objects.a(amqp_framing.c.obj):amqp_framing.c:(.bss+0x10)
: first defined here
CMakeFiles\rabbitmq.dir/objects.a(amqp_connection.c.obj):amqp_connection.c:(.bss
+0x0): multiple definition of `amqp_empty_array'
CMakeFiles\rabbitmq.dir/objects.a(amqp_framing.c.obj):amqp_framing.c:(.bss+0x0):
first defined here
CMakeFiles\rabbitmq.dir/objects.a(amqp_connection.c.obj):amqp_connection.c:(.bss
+0x8): multiple definition of `amqp_empty_table'
CMakeFiles\rlibrabbitmq\CMakeFiles\rabbitmq.dir\build.make:271: recipe for targe
t 'librabbitmq/librabbitmq.1.dll' failed
EDIT:
After some time, I have determined that the problem is that the pre-processor directives have some errors in the way they are written. I'm not going to close this for now, and if I ever get the time to fix the whole thing, I will come back here and leave an answer with a solution.
I've been analyzing macros defined in amqp.h file and I've added the extern modifier to the AMQP_PUBLIC_VARIABLE macro when build a non static library.
78 #elif defined(_WIN32) && defined(__MINGW32__)
79 # if defined(AMQP_BUILD) && !defined(AMQP_STATIC)
80 # define AMQP_PUBLIC_FUNCTION __declspec(dllexport)
81 # define AMQP_PUBLIC_VARIABLE __declspec(dllexport) extern
Another thing was, that I've had to modify the WINVER macro on file '/MinGW/include/windef.h' inside MinGW environment to fit with new windows versions.
11 #ifndef WINVER
12 #define WINVER 0x0501
After that, I've built the librabbitmq.1.dll library without problems using cmake -G "MinGW Makefiles" .. && cmake --build . commands

Resources