How do I link a static lib to a yocto autotools project in Eclipse - eclipse

I have created a Yocto autotools project in Eclipse (based on a Hello World project).
I wanted to separate my code into a number of libs and then link them in a form of static libs (.a) to my project.
Now I have one app and a number of static libs. However, no matter what I try I can't get my code to compile. Each separate lib compiles and produces a .a file, but my app doesn't.
After searching the web I have a possible solution - add a direct link to my static libs:
MyApp_CPPFLAGS="-I$LOCATION"
MyApp_LDADD="/home/xxx/workspace/MyApp/Encoding2/Debug/libEncoding2.a"
This is my Makefile.am file, where libEncoding2.a exist in that path.
The error I get is:
make[2]: *** No rule to make target `"/home/xxx/workspace/MyApp/Encoding2/Debug/libEncoding2.a"', needed by `MyApp'. Stop.
I already built the lib so I am not sure why a make try is even needed.
Any help will be appreciated.

Because you use static library in your recipes, you can make a soft link to the library in your project source folder, i.e., hello-world-0.1, using following command to link to your static library
ln -s /home/xxx/workspace/MyApp/Encoding2/Debug/libEncoding2.a
and then edit your bb file, hello-world_0.1.bb, adding the source path to your URL
SRC_URI = " \
file://libEncoding2.a \
file://hello-world.c \
"
and in the do_compile block, using follow command to compile your project
do_compile() {
${CC} hello-world.c libEncoding.a -o hello-world
}
do_install() {
install -d ${D}${bindir}/Hello
install -m 0755 enet ${D}${bindir}/Hello
}
After you bitbake your project
bitbake hello-world
and run mkefidisk.sh, you can find the hello-world in /usr/bin/Hello/hello-world. Hope this hint can help you.
BTW, I am not familiar with autotools, I just use make to bitbake the recipes. And your static library should also be created in Yocto not in Eclipse I think. So I think your path for the static library maybe not correct, it should locate in ~/yocto/build/tmp/... or some where like this. In my case, it was located in ln -s ~/yocto/build/tmp/sysroots/intel-corei7-64/usr/lib/libEncoding.a depends on your target environment.

Depending on whether you're using libtool or not, you should have either a noinst_LTLIBRARIES or noinst_LIBRARIES list of targets, respectively. This should only include the name of your library (libEncoding2.la or libEncoding2.a.)
You should never use a full path for this, and you should not quote Make variables, so what you were looking for is
MyApp_CPPFLAGS = -I$LOCATION
MyApp_LDADD = libEncoding2.la # or .a
And that would work.
But on the other hand it seems like you should take some time to understand how autotools work, as it might not be what you're looking for. With a grain of salt you can take my Autotools Mythbuster as a starting point.

Related

Install an executable created by another recipe in Yocto

On Yocto, I have a recipe (application_1.0.0.bb) with a dependency to Poco package (poco_1.11.2.bb):
DEPENDS = "poco"
In the configure step of application_1.0.0.bb, I need to use arc.
This is an executable that the Poco recipe generates. In the poco/1.11.2-r0 workdir, I can see it under poco/1.11.2-r0/package/usr/bin/arc. However, it is not transfered to the application workdir.
I need a bbappend recipe but I cannot seem to make it work, poco_%.bbappend:
do_install:append() {
install -d ${D}${bindir}
install -m 0755 ${WORKDIR}/package/usr/bin/arc ${D}${bindir}
This gives an already stripped error, so I added INSANE_SKIP:${PN}:append = "already-stripped" but arc is still not present in application_1.0.0 WORKDIR.
do_install is a task where files are copied from build system to build target. Hence, it is mandatory to use variable FILES_PN to install files in your target.
Then, I advice you to add in your .bbappend:
FILES_PN += "/usr/bin/arc"
Note that do_install:append is a deprecated method. Use do_install_append instead. Also, you can remove this task if arc executable is already inside your workdir. You need to read documentation https://docs.yoctoproject.org/

How do I get a complex non-Yocto makefile-based project to cross-compile in a Yocto layer?

This follows on from
How do I strip and objcopy a built .so file in the Yocto bitbake compile step?
This leads back to considerable background information.
As mentioned in the previous question, I am seeking to build OCA, which I have
as a non-Yocto makefile-based project, in Yocto. The project, which builds
fine outside of Yocto, and even in Yocto, is quite complex. The issue is that it
is not cross-compiling for my target, which is aarch64 armv8-a. It is building
successfully, but for my host machine, which is x86-64. Then Yocto sensibly
refuses to package it, saying "Unable to recognise the format of the input
file".
I changed the compile flags in my makefile to -march=armv8-a, but got the error
"cc1plus: error: bad value ('armv8-a') for '-march=' switch" which seems to
mean that I can't use the host's installed gcc for cross-compiling, but rather a
cross-compiler is needed. I previously custom-added two additional layers, a
sample helloworld and mDNS (see previous questions for lots of background), and
they all cross-compiled fine, so I know that Yocto is basically set up to do it.
What is the method to get the cross-compilation to happen? Do I need to do a lot
of pervasive changes to my project's makefile system? It may not ever have been
designed with Yocto in mind.
I am looking into this: "cross-compile library recipe in yocto":
cross-compile library recipe in yocto
which seems to have some relevant information. Edit: it was only standard stuff that I had seen before; nothing about how cross-compilation gets invoked instead of the host machine's gcc.
Edit: My updated recipe, with the FILES_${PN} added and make changed to
oe_runmake.
DESCRIPTION = "OCA"
PRIORITY = "optional"
SECTION = "protocols"
LICENSE = "MIT"
LIC_FILES_CHKSUM = "file://${COMMON_LICENSE_DIR}/MIT;md5=0835ade698e0bcf8506ecda2f7b4f302"
SRC_URI = "file://oca-1.2.7"
S = "${WORKDIR}/oca-1.2.7/Src"
# Need to override S because BitBake expects the source to be in a dir called
# oca-1.2.7 in the work dir, but it's actually additionally under Src/.
# Need a do_compile, since OCA has a makefile with a non-standard name,
# makefileOCA. Also needs non-standard flags, -f and linuxRelease.
do_compile() {
export CAP_HOME="${WORKDIR}/oca-1.2.7"
oe_runmake -f makefileOCA linuxRelease
}
do_install() {
install -d ${D}${libdir}
cp ../Obj/linuxApp/Release/OcaProtoController.so ${D}${libdir}/OcaProtoController.so
chmod 0755 ${D}${libdir}/OcaProtoController.so
}
FILES_${PN} += "${libdir}/OcaProtoController.so"
Edit: I found some info:
https://www.yoctoproject.org/docs/1.8.1/adt-manual/adt-manual.html
https://www.yoctoproject.org/docs/1.8.1/adt-manual/adt-manual.html#setting-up-the-cross-development-environment
I commented-out the setting of CC and LD in makeOCA.inc.
I did the cleaning actions of deleting the tmp folder from my build-wayland
build dir, and did "bitbake -c cleansstate oca". Then I did "time bitbake oca".
Now it looks like it is using the cross compiler.
The first error I got now is:
~/Yocto/imx-yocto-bsp/build-wayland/tmp/work/aarch64-poky-linux/oca/1.2.7-r0/oca-1.2.7/Obj/linuxApp/Release/OcaAgentProxies.a
aarch64-poky-linux-ld: cannot find crus: No such file or directory
So this is the next question: Can you tell me what "crus" means in "LDFLAGS = crus $#"?

How to include irdadump into Yocto (Poky) irda-utils 0.9.18 package

Please excuse my lack of knowledge and incorrect use of terminology. I
am looking to include irdadump in my build image within Yocto.
I modified the
/poky/meta/recipes-connectivity/irda-utils/irda-utils_0.9.18.bb file to
include irdadump in the list of targets to be built.
INITSCRIPT_NAME = "irattach"
INITSCRIPT_PARAMS = "defaults 20"
TARGETS ??= "irattach irdaping irdadump"
do_compile () {
for t in ${TARGETS}; do
oe_runmake -C $t
done
}
However the bitbake process fails which comes down to the dependency of
pkg-config and glib 2.0 required for idradump.
I did a quick search online and noticed that there was a separate .bb
file for irdadump:
http://cgit.openembedded.org/openembedded/plain/recipes/irda-utils/
I tried to replicate this however was still faced with compiling issues.
Could anyone give me a helping hand on including irdadump to my
irda-utils package?
Thank you
To add irda-utils to your build image, just add IMAGE_INSTALL_append in your conf/local.conf file.Next time when you will run Bitbake,it will include irda-utlis package in your build image.
IMAGE_INSTALL_append = " irda-utils"

Adding new recipe to Yocto fails during generate root fs

I have been using Yocto to create Linux builds for an ARM board.
I had been cross compiling add on applications manually. Now we are in a place where we would like a nice integrated build so I started adding custom recipes to yocto.
I have been struggling with the ARM build (a x86 build with the same code seems fine).
Even a basic 'hello world' pretty much cut and paste from the development manual does not work (http://www.yoctoproject.org/docs/current/dev-manual/dev-manual.html#new-recipe-writing-a-new-recipe)
Here is the recipe:
SUMMARY = "Simple helloworld application"
SECTION = "examples"
LICENSE = "MIT"
LIC_FILES_CHKSUM = "file://${COMMON_LICENSE_DIR}/MIT;md5=0835ade698e0bcf8506ecda2f7b4f302"
RPROVIDES_${PN} = "helloworld"
FILES_${PN} += "${bindir}"
SRC_URI = "file://helloworld.c"
S = "${WORKDIR}"
do_compile() {
${CC} helloworld.c -o helloworld ${LDFLAGS}
}
do_install() {
install -d ${D}${bindir}
install -m 0755 helloworld ${D}${bindir}
}
Here is the error:
ERROR: helloworld not found in the base feeds (smarc_samx6i cortexa9t2hf-vfp-neon-mx6qdl cortexa9hf-vfp-neon-mx6qdl cortexa9t2hf-vfp-neon cortexa9t2hf-vfp cortexa9hf-vfp-neon cortexa9hf-vfp armv7at2hf-vfp-neon armv7ahf-vfp-neon armv7at2hf-vfp armv7ahf-vfp armv6thf-vfp armv6hf-vfp armv5tehf-vfp armv5ehf-vfp armv5thf-vfp armv5hf-vfp noarch any all).
ERROR: Function failed: do_rootfs
Any suggestions as to what would be causing this error?
The package does build properly; the problem seems to be isolated to finding it for the rootfs.
Thanks!
EDIT:
I have a solution that seems to work, although it is not ideal long term.
Changing the package name under IMAGE_INSTALL from helloworld to helloworld-0.0.1 resolves the issue. Obviously I would rather not hard code the version of each package in the top level recipe and other packages do not require this, so hopefully there is another solution.
EDIT 2:
Renaming the recipe and removing the version string also resolves the issue. Once again, this does not seem ideal long term.
OK, after some further testing I discovered this was a naming issue with the recipe.
It was named helloworld-0.0.1.bb (the same format with the other recipes I had put together driving me to try this simple test).
If anyone else encounters this simply replacing the '-' with a '_' resolves this.
1.Rename your recipe name e.g hello-0.1.bb to hello_0.1.bb
2.Add below line at last only:
FILES_${PN} = "${bindir}/*"
Abvoe line helps you copy your binary to rootfs.

Using Makefile to add new source code files to Postgresql

I'm working on adding some functionality to the storage manager module in Postgresql.
I have added few source files already to the smgr folder, and I was able to have the Make system includes them by adding their names to the OBJS list in the Makefile inside the smgr folder. (i.e. When I add A.c, I would add A.o to the OBJS list).
That was working fine. Now I'm trying to add a new file hdfs_test.c to the project. The problem with this file is that it requires some extra directives in its compilation command (-I and -L directives).
The gcc command is:
gcc hdfs_test.c -I/HDFS_HOME/hdfs/src/c++/libhdfs -I/usr/lib/jvm/default-java/include -L/HDFS_HOME/hdfs/src/c++/libhdfs -L/HDFS_HOME/build/c++/Linux-i386-32/lib -L/usr/lib/jvm/default-java/jre/lib/i386/server -ljvm -lhdfs -o hdfs_test
Therefore, simply adding hdfs_test.o to the OBJS list doesn't work.
I tried editing the Makefile to look like this:
OBJS = md.o smgr.o smgrtype.o A.o B.o hdfs_test.o
MyRule1 : hdfs_test.c
gcc tati.c -c -I/diskless/taljab1/Workspace/HDFS_Append/hdfs/src/c++/libhdfs -I/usr/lib/jvm/default-java/include -L/diskless/taljab1/Workspace/HDFS_Append/hdfs/src/c++/libhdfs -L/diskless/taljab1/Workspace/HDFS_Append/build/c++/Linux-i386-32/lib -L/usr/lib/jvm/default-java/jre/lib/i386/server -ljvm -lhdfs
but it didn't work out, and I kept getting errors message of the Make trying to compile hdfs_test.c without including the directives.
How do I enforce the Make to include my compilation directives for hdfs_test.c ?
Thanks
You don't need to pass -l and -L at compile time, only at link time. At compile time only -I (include path) directives are required to help the compiler find any extra headers.
You should compile your source file to a .o file, same as all the others. Then add the -L and -l directives to the link command line when the linker is invoked to create the postgres executable. That means all you need to edit in src/backend/storage/smgr/Makefile is the OBJS line to add your output object, as you've already done below. Remove your custom rule, it's unnecessary as well as incorrect.
Just add your extra libraries to the $(LIBS) make variable and add your -L paths to $(LDFLAGS) via src/Makefile.global. src/Makefile.global is generated by configure from src/Makefile.global.in so you actually need to modify configure's behavior to add your includes, library paths and libraries. Don't edit configure directly either; edit configure.in and re-generate it with autoconf.
Yes, GNU Autotools is sometimes referred to as autohell for a reason. It's a bit ... interesting ... to work with sometimes, and there can be a lot of indirection involved in doing simple things.