X11 linking issue potentially musl libc related - makefile

I am running Alpine Linux with musl libc attempting to install-
https://github.com/patrickhaller/no-wm/
with-
make install
I have musl-dev and libx11-dev installed.
libx11-dev puts libs in /usr/lib not /usr/X11/lib. see-
https://pkgs.alpinelinux.org/contents?branch=edge&name=libx11-dev&arch=x86&repo=main
So I changed the Makefile line to-
X11LIB = -lX11 -L/usr/lib/
I confirmed libX11.so is at that directory location.
Yet my install still fails with this output-
$ make install
gcc -O2 -Wall -std=c99 -pedantic -lX11 -L/usr/lib/ x-alt-tab-mru.c -o x-alt-tab-mru
/usr/lib/gcc/aarch64-alpine-linux-musl/10.2.0/../../../../aarch64-alpine-linux-musl/bin/ld: /tmp/cckobJdo.o: in function `x_alt_tab':
x-alt-tab-mru.c:(.text+0x70): undefined reference to `XGetWMHints'
/usr/lib/gcc/aarch64-alpine-linux-musl/10.2.0/../../../../aarch64-alpine-linux-musl/bin/ld: x-alt-tab-mru.c:(.text+0x84): undefined reference to `XGetWindowAttributes'
/usr/lib/gcc/aarch64-alpine-linux-musl/10.2.0/../../../../aarch64-alpine-linux-musl/bin/ld: x-alt-tab-mru.c:(.text+0xec): undefined reference to `XLowerWindow'
/usr/lib/gcc/aarch64-alpine-linux-musl/10.2.0/../../../../aarch64-alpine-linux-musl/bin/ld: x-alt-tab-mru.c:(.text+0xf8): undefined reference to `XRaiseWindow'
/usr/lib/gcc/aarch64-alpine-linux-musl/10.2.0/../../../../aarch64-alpine-linux-musl/bin/ld: x-alt-tab-mru.c:(.text+0x10c): undefined reference to `XSetInputFocus'
/usr/lib/gcc/aarch64-alpine-linux-musl/10.2.0/../../../../aarch64-alpine-linux-musl/bin/ld: x-alt-tab-mru.c:(.text+0x11c): undefined reference to `XRestackWindows'
/usr/lib/gcc/aarch64-alpine-linux-musl/10.2.0/../../../../aarch64-alpine-linux-musl/bin/ld: x-alt-tab-mru.c:(.text+0x128): undefined reference to `XSync'
/usr/lib/gcc/aarch64-alpine-linux-musl/10.2.0/../../../../aarch64-alpine-linux-musl/bin/ld: /tmp/cckobJdo.o: in function `main':
x-alt-tab-mru.c:(.text.startup+0x34): undefined reference to `XOpenDisplay'
/usr/lib/gcc/aarch64-alpine-linux-musl/10.2.0/../../../../aarch64-alpine-linux-musl/bin/ld: x-alt-tab-mru.c:(.text.startup+0x44): undefined reference to `XSync'
/usr/lib/gcc/aarch64-alpine-linux-musl/10.2.0/../../../../aarch64-alpine-linux-musl/bin/ld: x-alt-tab-mru.c:(.text.startup+0x70): undefined reference to `XQueryTree'
collect2: error: ld returned 1 exit status
make: *** [Makefile:19: x-alt-tab-mru] Error 1
I've confirmed the headers in that x-alt-tab-mru.c file are present in the correct location and were included with libx11-dev.
What can I do next to troubleshoot this and get it to compile? I've chased down everything I could think of..

The order of arguments on the link command line is significant. -L options apply only to searching for libraries designated later on the command line, and, at least for static linking, undefined symbols in one object among those being linked are resolved only against other objects designated later on the command line. Behavior may (or may not) vary a bit when linking shared libraries, but to be safe, you should always order the objects to be linked (source files, object files, and libraries) according to their dependencies.
In particular, then,
in the unlikely event that you need -L/usr/lib at all, it should come before -lX11, and
the -lX11 option should appear after x-alt-tab-mru.c in the link command.

Related

net-snmp flags in CMAKE

Before anything, I just want to say I am very new to CMAKE, almost never used it but now forced to...
I am trying to include snmp features in a previous project, using Net-SNMP library. But first, I wrote a minimalistic code just to test my functions. According to the library tutorial, this is how I must compile the code:
First, I must create object file:
gcc -I. `net-snmp-config --cflags` -c -o tfsnmpset.o tfsnmpset.c
Then, I must generate the executable:
gcc -o tfsnmpset tfsnmpset.o `net-snmp-config --libs`
By doing this, the program compiles perfectly and everything is fine.
Now the project in which I want to incorporate that piece of code uses CMakeLists.txt to generate its makefile.
My question is, how do I include the following flags in my CMakeLists.txt?
When creating object files: `net-snmp-config --cflags`
When generating executable: `net-snmp-config --libs`
I actually tried to build a library out of my code that uses Net-SNMP that I could just use in my main project:
cmake_minimum_required(VERSION 3.12)
project(snmp_daemon C)
set(CMAKE_C_STANDARD 99)
SET(CMAKE_C_COMPILER /usr/bin/gcc)
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -I. `net-snmp-config --cflags`" )
add_library(tfsnmpset tfsnmp.c tfsnmp.h)
add_executable(snmp_daemon main.c ./tfsnmp.h)
target_link_libraries(snmp_daemon tfsnmpset)
The errors:
/media/user/xtra/apps/clion-2018.2.1/bin/cmake/linux/bin/cmake --build /home/fabrice/projects/snmp-daemon/cmake-build-debug --target snmp_daemon -- -j 2
[ 25%] Linking C static library libtfsnmpset.a
[ 50%] Built target tfsnmpset
[ 75%] Linking C executable snmp_daemon
libtfsnmpset.a(tfsnmp.c.o): In function `tfsnmpset':
/home/user/projects/snmp-daemon/tfsnmp.c:121: undefined reference to `snmp_parse_args'
/home/user/projects/snmp-daemon/tfsnmp.c:147: undefined reference to `snmp_get_do_debugging'
/home/user/projects/snmp-daemon/tfsnmp.c:147: undefined reference to `debugmsgtoken'
/home/user/projects/snmp-daemon/tfsnmp.c:147: undefined reference to `debugmsg'
/home/user/projects/snmp-daemon/tfsnmp.c:147: undefined reference to `debugmsgtoken'
/home/user/projects/snmp-daemon/tfsnmp.c:147: undefined reference to `debugmsg'
/home/user/projects/snmp-daemon/tfsnmp.c:194: undefined reference to `snmp_open'
/home/user/projects/snmp-daemon/tfsnmp.c:199: undefined reference to `snmp_sess_perror'
/home/user/projects/snmp-daemon/tfsnmp.c:207: undefined reference to `snmp_pdu_create'
/home/user/projects/snmp-daemon/tfsnmp.c:210: undefined reference to `snmp_parse_oid'
/home/user/projects/snmp-daemon/tfsnmp.c:211: undefined reference to `snmp_perror'
/home/user/projects/snmp-daemon/tfsnmp.c:214: undefined reference to `snmp_add_var'
/home/user/projects/snmp-daemon/tfsnmp.c:216: undefined reference to `snmp_perror'
/home/user/projects/snmp-daemon/tfsnmp.c:222: undefined reference to `snmp_close'
/home/user/projects/snmp-daemon/tfsnmp.c:230: undefined reference to `snmp_synch_response'
/home/user/projects/snmp-daemon/tfsnmp.c:236: undefined reference to `print_variable'
/home/user/projects/snmp-daemon/tfsnmp.c:239: undefined reference to `snmp_errstring'
/home/user/projects/snmp-daemon/tfsnmp.c:247: undefined reference to `fprint_objid'
/home/user/projects/snmp-daemon/tfsnmp.c:257: undefined reference to `snmp_sess_perror'
/home/user/projects/snmp-daemon/tfsnmp.c:262: undefined reference to `snmp_free_pdu'
/home/user/projects/snmp-daemon/tfsnmp.c:263: undefined reference to `snmp_close'
collect2: error: ld returned 1 exit status
CMakeFiles/snmp_daemon.dir/build.make:84: recipe for target 'snmp_daemon' failed
make[3]: *** [snmp_daemon] Error 1
CMakeFiles/Makefile2:72: recipe for target 'CMakeFiles/snmp_daemon.dir/all' failed
make[2]: *** [CMakeFiles/snmp_daemon.dir/all] Error 2
CMakeFiles/Makefile2:84: recipe for target 'CMakeFiles/snmp_daemon.dir/rule' failed
make[1]: *** [CMakeFiles/snmp_daemon.dir/rule] Error 2
Makefile:118: recipe for target 'snmp_daemon' failed
make: *** [snmp_daemon] Error 2
You should link to snmp libraries
find_library(NETSNMPAGENT "netsnmpagent")
find_library(NETSNMPMIBS "netsnmpmibs")
find_library(NETSNMP "netsnmp")
target_link_libraries(snmp_daemon tfsnmpset ${NETSNMPAGENT} ${NETSNMPMIBS} ${NETSNMP})

GCC ICU 57 static linking

I am trying to link ICU 57 to my binary file. That does not work even thought (I think at least) I am linking the static lib files.
Here is a blunt example:
gcc -static /usr/lib/libicui18n.a /usr/lib/libicuuc.a /usr/lib/libicudata.a /usr/lib/libicule.a /usr/lib/libiculx.a /usr/lib/libicutu.a /usr/lib/libicuuc.a /usr/lib/libicuio.a obj/ex.o obj/msg.o -o bin/ex
This is the error message that I get:
src/msg.c:5: undefined reference to `u_fopen_57'
src/msg.c:9: undefined reference to `u_fgetfile_57'
src/msg.c:10: undefined reference to `u_fgetfile_57'
src/msg.c:11: undefined reference to `u_frewind_57'
src/msg.c:18: undefined reference to `u_fgetc_57'
src/msg.c:17: undefined reference to `u_feof_57'
src/msg.c:25: undefined reference to `u_fclose_57'
Linking the dynamic libs works fine though.
If you can, I'd recommend using pkg-config as I recommended here,
specifically with pkg-config --static … as explained here

SuperLU with OpenBLAS: undefined reference to `pthread_atfork'

When compiling the SuperLU 4.3 library using OpenBLAS instead of regular BLAS distributions, this error keeps coming up:
>gcc cdrive.o sp_cconvert.o cgst01.o cgst02.o cgst04.o cgst07.o sp_ienv.o \
> libtmglib.a /a/location/lib/libsuperlu_4.3.a ->L/a/location/lib/libopenblas.a -lopenblas -lm -o ctest
>/a/location/lib/libopenblas.a(memory.o): In function >'openblas_fork_handler':
>memory.c:(.text+0x3e0): undefined reference to 'pthread_atfork'
>/a/location/lib/libopenblas.a(blas_server.o): In function >'blas_thread_shutdown_':
>blas_server.c:(.text+0x25e): undefined reference to 'pthread_join'
>/a/location/lib/libopenblas.a(blas_server.o): In function >'goto_set_num_threads':
>blas_server.c:(.text+0x403): undefined reference to 'pthread_create'
>/a/location/lib/libopenblas.a(blas_server.o): In function >'blas_thread_init':
>blas_server.c:(.text+0x721): undefined reference to 'pthread_create'
You need to link pthread / libpthread. Depending on the linker, this might be done automatically, but not in your case.

gcc newly installed libraries (libexpat1-dev) not recognised in current terminal (debian)

I've spent quite a bit of time trying to get an expat based sample program to compile.
I was receiving the following error message when I tried to compile
gcc -Wall -lexpat line.c -o blah
line.c: In function ‘main’:
line.c:99:8: warning: format ‘%d’ expects argument of type ‘int’, but argument 3 has type ‘XML_Size’ [-Wformat]
/tmp/ccUa3vfD.o: In function `printcurrent':
line.c:(.text+0x42): undefined reference to `XML_SetDefaultHandler'
line.c:(.text+0x4d): undefined reference to `XML_DefaultCurrent'
line.c:(.text+0x60): undefined reference to `XML_SetDefaultHandler'
/tmp/ccUa3vfD.o: In function `main':
line.c:(.text+0x162): undefined reference to `XML_ParserCreate'
line.c:(.text+0x1ad): undefined reference to `XML_UseParserAsHandlerArg'
line.c:(.text+0x1c9): undefined reference to `XML_SetElementHandler'
line.c:(.text+0x1dd): undefined reference to `XML_SetCharacterDataHandler'
line.c:(.text+0x1f1): undefined reference to `XML_SetProcessingInstructionHandler'
line.c:(.text+0x2b2): undefined reference to `XML_Parse'
line.c:(.text+0x2c2): undefined reference to `XML_GetErrorCode'
line.c:(.text+0x2ca): undefined reference to `XML_ErrorString'
line.c:(.text+0x2d8): undefined reference to `XML_GetCurrentLineNumber'
collect2: ld returned 1 exit status
I had already run the following commands:
sudo apt-get install expat libexpat1 libexpat1-dev libxmltok1-dev
So I messed around for ages, trying to get the error message to go away so I could compile this (simple) little program, but to no avail.
Eventually, out of sheer randomness, I decided to switch to a Virtual Terminal.
I ran exactly the same command, this time it worked without a problem.
Can anyone tell me why this is? Is there something I need to run in order to refresh the library paths?
The linker line (i.e. the flags you give with -l and your input file names) are order-dependent. Libraries are only used to define functions used on their left side, but not on their right. Use:
gcc -Wall line.c -lexpat -o blah
See the question library is linked but reference is undefined for more information.

Can't build static boost-filesystem

I've this example code.
#include <iostream>
#include <boost/filesystem.hpp>
using namespace std;
int main()
{
return 0;
}
It can be correctly build with: g++ -lboost_system-mt -lboost_filesystem-mt 1.cpp
But if I add -static, then it complains:
/tmp/cc1JEbRQ.o: In function `__static_initialization_and_destruction_0(int, int)':
1.cpp:(.text+0xb0): undefined reference to `boost::system::get_system_category()'
1.cpp:(.text+0xba): undefined reference to `boost::system::get_generic_category()'
1.cpp:(.text+0xc4): undefined reference to `boost::system::get_generic_category()'
1.cpp:(.text+0xce): undefined reference to `boost::system::get_generic_category()'
1.cpp:(.text+0xd8): undefined reference to `boost::system::get_system_category()'
collect2: ld returned 1 exit status
How do I fix that? Thanks
You probably need to reverse the order of your libraries for static linking to succeed, because boost_filesystem depends on boost_system:
g++ 1.cpp -static -lboost_filesystem-mt -lboost_system-mt
This is because the run-time linker does a topological dependency sort to load shared libraries in correct order, whereas static linking doesn't do that.
Alternatively, you can force static linking to do several passes over the list of libraries to try to resolve remaining undefined symbols:
man ld:
-( archives -)
--start-group archives --end-group
The archives should be a list of archive files. They may be either
explicit file names, or -l options.
The specified archives are searched repeatedly until no new
undefined references are created. Normally, an archive is searched
only once in the order that it is specified on the command line.
If a symbol in that archive is needed to resolve an undefined
symbol referred to by an object in an archive that appears later on
the command line, the linker would not be able to resolve that
reference. By grouping the archives, they all be searched
repeatedly until all possible references are resolved.
Using this option has a significant performance cost. It is best
to use it only when there are unavoidable circular references
between two or more archives.
e.g:
g++ 1.cpp -static -Wl,--start-group -lboost_system-mt -lboost_filesystem-mt -Wl,--end-group

Resources