Correctly include (POSIX) libraries in deeply embedded source / make files

In short: we have a large SDK containing ~ 1Gb of hairy code cracked together with the Elbonian Code Slaves, taped together with a quivering RPC lattice, shared memory, mutex / semaphores and spit. It is compiled on a Linux machine for the SoC built-in purpose.

As part of the impact in improving part of the code, I want to add POSIX semaphores to one of the sources, which is included by several RPC procedures.

However, just by writing the correct code and sticking to

#include <semaphore.h> 

above, of course, is not enough to compile.

Special flags are required in the makefile, depending on what you are reading, this can be any / all:

 -pthread -lpthread -lpthreads -lrt -rt 

I do not have much experience writing make files, and unfortunately, due to the size of the code base, there are several nested levels (more than 2000 make files in the SDK) with all kinds of dependencies, all spawning grounds from One True Makefile in the root folder.

There are a lot of macro definitions (TM) in makefiles that don't help my efforts to unravel the right spell.

Like a glimpse of the structure of the project and the file I'm trying to change, the folder structure looks something like this:

 /home/project/kernel/... Contains the Linux kernel & PSP / BSP /home/project/the_system/... Contains the software suite we're building 

And the file we are looking at is in:

 /home/project/the_system/core_app/interface/src/messaging.c 

Which itself is included, possibly in 5 other sources, for example:

 /home/project/the_system/core_app/interface/src/sys-control.c /home/project/the_system/core_app/interface/src/file-control.c /home/project/the_system/core_app/interface/src/audio-control.c 

... you get the idea. Then each of them can be enabled / called by other processes that want to communicate with each other. Did I say all this is terrible?

There are make files in almost every folder on this chain, a make file in a local folder

 /home/project/the_system/core_app/interface/src/Makefile 

something like this (I deleted a few bits for clarity, ignored objects without links):

  INCLUDES += -I./ -I$(PUBLIC_INCLUDE_DIR) -I$(LINUXKERNEL_INSTALL_DIR)/include -I$(CMEM_INSTALL_DIR)/packages/ti/sdo/linuxutils/cmem/include -lpthreads C_FLAGS += -Wall -g -O3 AR_FLAGS += -r CC = $(MVTOOL_PREFIX)gcc $(INCLUDES) $(C_FLAGS) -c AR = $(MVTOOL_PREFIX)ar REL_EXE1 = reboot_me REL_LIB1 = file-control.a REL_LIB3 = share_mem.a REL_LIB4 = sys-control.a REL_LIB5 = msg_util.a REL_LIB9 = messaging.a REL_LIB10 = sysctrl.a REL_LIB11 = audio-control.a REL_OBJ1 = file-control.o share_mem.o msg_util.o REL_OBJ3 = share_mem.o REL_OBJ4 = sys-control.o share_mem.o msg_util.o REL_OBJ5 = msg_util.o REL_OBJ9 = messaging.o REL_OBJ10 = sysctrl.o sys-control.o share_mem.o msg_util.o messaging.o audio-control.o REL_OBJ11 = audio-control.o messaging.o share_mem.o msg_util.o all: $(REL_EXE1) $(REL_LIB9) $(REL_LIB12) $(REL_LIB3) $(REL_LIB1) $(REL_LIB2) $(REL_LIB4) $(REL_LIB5) $(REL_LIB6) $(REL_LIB7) $(REL_LIB8) $(REL_LIB10) $(REL_LIB11) install $(REL_LIB1): $(REL_OBJ1) $(AR) $(AR_FLAGS) $(REL_LIB1) $(REL_OBJ1) $(REL_LIB2): $(REL_OBJ2) $(AR) $(AR_FLAGS) $(REL_LIB2) $(REL_OBJ2) $(REL_LIB3): $(REL_OBJ3) $(AR) $(AR_FLAGS) $(REL_LIB3) $(REL_OBJ3) $(REL_LIB4): $(REL_OBJ4) $(AR) $(AR_FLAGS) $(REL_LIB4) $(REL_OBJ4) $(REL_LIB5): $(REL_OBJ5) $(AR) $(AR_FLAGS) $(REL_LIB5) $(REL_OBJ5) $(REL_LIB7): $(REL_OBJ7) $(AR) $(AR_FLAGS) $(REL_LIB7) $(REL_OBJ7) $(REL_LIB8): $(REL_OBJ8) $(AR) $(AR_FLAGS) $(REL_LIB8) $(REL_OBJ8) $(REL_LIB9): $(REL_OBJ9) $(AR) $(AR_FLAGS) $(REL_LIB9) $(REL_OBJ9) $(REL_LIB10): $(REL_OBJ10) $(AR) $(AR_FLAGS) $(REL_LIB10) $(REL_OBJ10) $(REL_LIB11): $(REL_OBJ11) $(AR) $(AR_FLAGS) $(REL_LIB11) $(REL_OBJ11) $(REL_LIB12): $(REL_OBJ12) $(AR) $(AR_FLAGS) $(REL_LIB12) $(REL_OBJ12) file-control.o : file-control.c $(PUBLIC_INCLUDE_DIR)/file-control.h $(PUBLIC_INCLUDE_DIR)/Msg_Def.h\ $(PUBLIC_INCLUDE_DIR)/sys_env_type.h $(CC) $(C_FLAGS) -o $@ $< audio-control.o : audio-control.c $(PUBLIC_INCLUDE_DIR)/audio-control.h \ $(PUBLIC_INCLUDE_DIR)/Msg_Def.h $(PUBLIC_INCLUDE_DIR)/sys_env_type.h $(CC) $(C_FLAGS) -o $@ $< share_mem.o: share_mem.c $(PUBLIC_INCLUDE_DIR)/share_mem.h $(CC) $(C_FLAGS) -o $@ $< sys-control.o : sys-control.c $(PUBLIC_INCLUDE_DIR)/sys-control.h $(PUBLIC_INCLUDE_DIR)/Msg_Def.h\ $(PUBLIC_INCLUDE_DIR)/sys_env_type.h $(PUBLIC_INCLUDE_DIR)/share_mem.h $(CC) $(C_FLAGS) -o $@ $< msg_util.o: msg_util.c $(PUBLIC_INCLUDE_DIR)/Msg_Def.h $(CC) $(C_FLAGS) -o $@ $< messaging.o: messaging.c $(PUBLIC_INCLUDE_DIR)/messaging.h $(CC) $(C_FLAGS) -o $@ $< sysctrl.o: sysctrl.c $(PUBLIC_INCLUDE_DIR)/sysctrl.h $(PUBLIC_INCLUDE_DIR)/sys_env_type.h $(CC) $(C_FLAGS) -o $@ $< reboot_me: $(MVTOOL_PREFIX)gcc -g -Wall -static -c -o reboot_me.o reboot_me.c $(MVTOOL_PREFIX)gcc -o reboot_me reboot_me.o clean: -$(RM) -f *.o -$(RM) -f *.a -$(RM) -f $(REL_EXE1) -$(RM) -Rf $(APP_LIB_DIR) install: $(REL_EXE1) $(REL_LIB3) $(REL_LIB1) $(REL_LIB2) $(REL_LIB4) $(REL_LIB5) $(REL_LIB7) install -d $(APP_LIB_DIR) install $(REL_LIB1) $(APP_LIB_DIR) install $(REL_LIB2) $(APP_LIB_DIR) install $(REL_LIB3) $(APP_LIB_DIR) install $(REL_LIB4) $(APP_LIB_DIR) install $(REL_LIB5) $(APP_LIB_DIR) install $(REL_LIB7) $(APP_LIB_DIR) install $(REL_LIB8) $(APP_LIB_DIR) install $(REL_LIB9) $(APP_LIB_DIR) install $(REL_LIB10) $(APP_LIB_DIR) install $(REL_LIB11) $(APP_LIB_DIR) install $(REL_LIB12) $(APP_LIB_DIR) install $(REL_EXE1) $(EXEC_DIR) 

Anyway , adding

 #include <semaphore.h> 

up

 /home/project/the_system/core_app/interface/src/messaging.c 

What do I need to do to get this compiled correctly?


As a bonus question, is there a way to determine which one:

 -pthread -lpthread -lpthreads -lrt -rt 

Is this right for our particular build environment?


Edit to add (also TL; DR):

I seem to encounter exact duplication of the script mentioned in this question .

However, no matter where I attach the -lpthread and -lrt arguments, I get errors.

For example, I tried to add a call to pthread_mutex_trylock, and it will not compile:

 undefined reference to 'pthread_mutex_trylock' 

... even if existing functions calling pthread_mutex_lock compile OK.

+5
source share
2 answers

Well, finally, I got a hateful thing, unfortunately, more thanks to brute force and ignorance than some graceful coding genius master move.

However, if this helps some future generation, the following route was as follows:

  • Add -lrt -lpthread to C_FLAGS in my makefile example and then try make
  • When make failed, look at the place where it failed, download the makefile from this place and add -lrt -lpthread same way to this makefile.
  • Wet, rinse, repeat until make succeeds.

Now it seems to be working fine , of course, now 100 other bugs have been fixed, but at least I got them to compile at the end.

Nurse, screens!

0
source

I'm not sure what you mean by the first question. I will try to cover all the possibilities.

The answer to the second question was largely covered by Joachim.

Your system will try to build messaging.o if you change messaging.c , for example, if you add the header file to the beginning.

If you want to know how to succeed in this attempt, you need to specify the correct location of the semaphore.h file in the INCLUDES variable. This is a "system" file in one of the "system" include directories.

If you want you to restore messaging.o when semaphore.h has changed, you will need to read the section on advanced automatic dependency generation in the GNU Make Manual or on the MadScientist website http://mad-scientist.net/make/autodep. html

Or, use the ElectricAccelerator, which EricMelsky talks about all the time. This fantastic software has built-in automatic dependency generation. You do not have to do anything.

In addition, as you already know, the Makefile you are showing is very poorly written, very β€œnaive”. And it looks like you have a recursive system of several thousand similar poor Makefiles. Yes, that’s terrible.

And it seems that you personally do not want to fix this build system as such, you are just interested in adding some functions to the software itself.

So, I think you need to hire an expert consultant to write your company in the most advanced system, perhaps using ElectricAccelerator or the plain old GNU Make. Got a clue? Ehm, if Eric can plug stubs all the time, and he leaves with him, then I can too :)

0
source

Source: https://habr.com/ru/post/1203879/


All Articles