Yocto Project Expert Tips: Debugging Variables

Reading Time: 3 minutes

Introduction

Over my many years of working with the Yocto project, I have acquired many methods and tricks along the way that help me do things such as debug issues, accelerate development, create more efficient code and gain a better overall understanding of the project to design things right the first time.

The Yocto project is complex and during my tenure with the project, I have walked with many customers through various issues. As such, I have been working recently to identify particular items that I find valuable in an attempt to educate others and help flatten the learning curve in using the Yocto project.

The Challenge With Variables

One particular challenge in the Yocto project is manipulating variables. While making a variable assignment is fairly straightforward, because Yocto (bitbake) relies on various classes, appends, python functions and other methods to manipulate variables, users will often encounter situations where a variable is not taking on the value they think it should be.

See the official bitbake documentation on a more extensive explanation of variable assignment below:
https://docs.yoctoproject.org/bitbake/2.2/bitbake-user-manual/bitbake-user-manual-metadata.html

Debugging Variables

The often simple and straight forward approach might be to use bbdebug or other similar print statements to print the variables to the log or console. While this can work in many situations, when there is a need to obtain the value of multiple variables, this process can quickly become tedious. Additionally, using print statements does not necessarily immediately indicate how and why a variable is set, especially since many assignments happen at parsing time (declaratively) and not necessarily “inline” in a task call for example.

One potential solution is the bitbake “environment” argument. From the docs and help dialog of Bitbake:

-e, --environment Show the global or per-recipe environment complete
    with information about where variables were
    set/changed.

This is extremely useful in debugging variables in recipes or in the build environment. If for some reason a variable is not getting set the way you think it is, or it is getting set to some other value and you are not sure what is setting it, bitbake -e can help you determine this.

The usage of the environment arg is as follows:

bitbake <recipe-name> -e

<recipe-name> can also be omitted to print a default global view of the environment.

Warning: The output of this command is quite lengthy, so I often recommend redirecting the output to a file so that you can better examine it and save for reference:

bitbake <recipe-name> -e > yocto_env.log

Example

I think it is always helpful to lay out a real world example to help others understand the concepts being presented. Say we have a variable MY_GLOBAL_VAR. Let’s design a simple system where this variable gets set and appended in a few places:

# local.conf
MY_GLOBAL_VAR = "hello"

# my-recipe.bb
MY_GLOBAL_VAR = "hello recipe"

# my-recipe.bbappend
MY_GLOBAL_VAR:append = " world"

Now, let’s put bitbake to the test and see if the environment arg can help us determine the value of the variable and where it is set:

bitbake -e my-recipe > my-recipe-env.log

Now if we sort through the output in my-recipe-env.log we find the below:

# $MY_GLOBAL_VAR [3 operations]
# set /home/ksloat-engineering/engineering/cornersoft/yocto-env/poky/build/conf/local.conf:290
# "hello"
# set /home/ksloat-engineering/engineering/cornersoft/yocto-env/poky/meta-cornersoft/recipes-example/my-recipe/my-recipe.bb:4
# "hello recipe"
# :append /home/ksloat-engineering/engineering/cornersoft/yocto-env/poky/meta-cornersoft/recipes-example/my-recipe/my-recipe.bbappend:2
# " world"
# pre-expansion value:
# "hello recipe world"
MY_GLOBAL_VAR="hello recipe world"

We can see the final value is “hello recipe world” but we have insight into how and why it got set this way. Bitbake lays out the individual files and lines even where the values were set, whether they were ultimately discarded or not. This can become extremely useful in more complex situations where OVERRIDES are involved.

Note: In this example, this is the value in the case that the target of bitbake is “my-recipe” i.e. you are trying to build “my-recipe.” In cases where common variables are used in different recipes that are part of an image, it is often more appropriate to pass your image recipe with -e in those cases.

Conclusion

The Yocto Project can be a complex and challenging endeavor, but there are strategies and tools that can simplify the process. By providing clear explanations and free practical guidance, we hope to equip you with valuable knowledge that will smooth your Yocto journey. Remember that you don’t have to navigate the complexities of Yocto alone.

Partnering with a seasoned Yocto project expert, like Cornersoft Solutions, can provide invaluable support and expertise. Our organization can guide you through the intricacies of the project, helping you avoid costly mistakes and time-consuming setbacks. Engaging a partner like Cornersoft Solutions can allow you to confidently tackle the challenges of the Yocto Project and achieve your embedded Linux development goals.

Contact sales@cornersoftsolutions.com to learn how our Yocto expertise, development ability, coaching and guidance can benefit your organization.