Issues with static library and the cmake build

Hello,

I am experimenting with different build options using CMAKE for module creation. My proposed build process looks something like this

Step 1: Build static library (MY_LIB.lib) from several source files for my px4 module. This happens outside of the main CMAKE build process

Step 2: Generate a CMAKE list from the above build. Move the files over (header, library.a and cmakelist.txt) into Firmware\src\module<my_module>

Step 3: Initiate the build process (ie: make px4fmu-v2_ekf2)

My Cmakelist.txt looks something like this:

px4_add_module(
	MODULE examples__module_app
	MAIN my_module_app
	STACK_MAIN 2000
	SRCS
	          empty_file.c

	DEPENDS
		platforms__common
	)

target_link_libraries(examples__ module_app MY_LIB.lib)

Where MY_LIB.lib is the shared library I built manually by hand.

Unfortunately I’m stuck with a bit of a problem here. It seems that when I compile my source files into a static library and start the build process there seems to be some linking problems at the very end of Step3.

For instance, certain POSIX functions like ‘perror’ or ‘timer_create’ are undefined references when using the shared library method. The strange thing is that if I did not use the shared library method and built my module by listing all the individual .c files

In my CMAKE list like so:

px4_add_module(
	MODULE examples__module_app
	MAIN my_module_app
	STACK_MAIN 2000
	SRCS
	          	Main.c #contains POSIX functoins like timer_create
empty_file.c

	DEPENDS
		platforms__common
	)

This works without issues.

In Step1, I made sure to have the same include paths and build define macros from the ones that get generated by CMAKE. I referrred to the generated flags found within flags.cmake
Ie: build_px4fmu-v2_ekf2\src\module<module_name>\flags.make\

Current include dirs for Step1:

Firmware/src 
Firmware/build_px4fmu-v2_ekf2 
Firmware/build_px4fmu-v2_ekf2/src
Firmware/src/modules 
Firmware/src/include 
Firmware/src/lib 
Firmware/src/platforms Firmware/src/drivers/boards/px4fmu-v2 
Firmware/build_px4fmu-v2_ekf2/src/modules/px4_messages 
Firmware/build_px4fmu-v2_ekf2/src/modules 
Firmware/mavlink/include/mavlink 
Firmware/src/lib/DriverFramework/framework/include 
Firmware/src/lib/matrix 
Firmware/build_px4fmu-v2_ekf2/px4fmu-v2/NuttX/nuttx-export/include 
Firmware/build_px4fmu-v2_ekf2/px4fmu-v2/NuttX/nuttx-export/include/cxx
Firmware/build_px4fmu-v2_ekf2/px4fmu-v2/NuttX/nuttx-export/arch/chip 
Firmware/build_px4fmu-v2_ekf2/px4fmu-v2/NuttX/nuttx-export/arch/common 
Firmware/build_px4fmu-v2_ekf2/external/Install/include 

Another question:
Is there a way to over-ride the common flags for a module in the CMAKE process with my own? it seems the common build flags apply to all modules. Ideally, i’d like to customize everything inside flags.make

1 Like

I don’t know specifically what the problem is, but it sounds like you’re missing flags when building the lib externally. If you want to see exactly how your app is built within PX4 you can go into build_px4fmu-v2_ekf2 and run either make VERBOSE=1 or ninja -v (depending if you have ninja and the build system detected it).

Is there a reason your lib can’t be built by PX4? If you still want it to be standalone you can keep it separate using cmake and include it with add_subdirectory(path_to_lib_src). Then it would be built using its standalone cmake config, but also inherit PX4 build flags.

Thanks for the reply.

The reason why i’m doing this is because i need to build my module with a different set of compile flags that are going to differ from the common build flags. In other words, I don’t want to inherit all the PX4 build flags, i need to specify my own and over-ride several others. I don’t see a straight forward way of over-riding flags for module builds. If there is a way to do this then I would probably completely switch over to using cmake for everything and not deal with having to do a separate build (ie: step1 of building a static lib outside of cmake).

From looking at the verbose build, it looks like MY_LIB.lib gets linked at the very end rather than into the MODULE. For instance, in the last line of the verbose build output I see:

--start-group ../../module/my_module_app/libmodule__my_module_app.a

But later on I also see:

../../../src/module/my_module_app/MY_LIB.lib

Ideally MY_LIB.lib should be inside libmodule__my_module_app.a. The way the CMAKE is interpreting my cmakelist.txt doesn’t match with what I think should happen.

I do also see options for linking, for instance

px4_add_module(
	MODULE modules__attitude_estimator_ekf
	MAIN attitude_estimator_ekf
	STACK_MAIN 1200
	LINK_FLAGS
		-<insert link flags here?>
	SRCS
	
	DEPENDS
		platforms__common
	)

However, any flag i write here never shows up in the build. I’ve checked flags.cmake in the build output dir and it does not show up. Is there a certain method I need to apply to add link flags here?

I am having a slightly related issue. I am trying to add a linear algebra library, Armadillo, to the px4 code. I am new to linux and cmake so I am still making sense of the terminologies used.

I already have Armadillo installed on my IDE, QT creator, but I do not know where and how to include it to the px4 Master folder for it to be linked to it. I want to code my own attitude controller and an extensive matrix and vector library that is why I opted for Armadillo.

I greatly appreciate the assistance. Again, please dumb it down if you can, I am still learning the linux and cmake ropes. Thank you!

1 Like