Did you know you can run recipe tasks without using bitbake? Keep reading to see how.
Each recipe has its own work directory where the source code is unpacked, patches are applied, the build is set up, and the source is compiled. These work directories are under build/tmp/work/…
and spread out from there. The easiest way to find a recipe’s work directory is to go to build/tmp/work/
and search for the recipe name.
find . -name "libmetal-xlnx"
./refdes_xu8_st1_xczu4cg-xilinx-linux/libmetal-xlnx
The name “temp” is a bit misleading because it’s usually the only directory left after a recipe is built (if rm_work
is on). You have to do a full cleanall
on the recipe to clear the temp
directory. But it will come back again.
So, what’s so special about this sticky temp directory? Well, recipes are made up of tasks. Each task is written in Python or Bash. The source code for all tasks is actually in the temp
directory. Files starting with run.do_*
are the task scripts.
Alongside these, you’ll find log.do_x files. These are logs from running the tasks. Each time bitbake runs a task, it creates new task and log files, but keeps the old ones too.
For example, run.do_compile
is the compile task, and log.do_compile
is its log.
Actually, these files are symbolic links.
ls -l *do_compile*
lrwxrwxrwx 1 mk users 21 Sep 16 14:01 log.do_compile -> log.do_compile.550001
-rw-r--r-- 1 mk users 453063 Sep 16 13:45 log.do_compile.481552
-rw-r--r-- 1 mk users 453063 Sep 16 14:01 log.do_compile.550001
lrwxrwxrwx 1 mk users 21 Sep 16 14:01 run.do_compile -> run.do_compile.550001
-rwxrwxr-x 1 mk users 16893 Sep 16 13:45 run.do_compile.481552
-rwxrwxr-x 1 mk users 16893 Sep 16 14:01 run.do_compile.550001
They always point to the latest task and log, which is handy when working in the command line.
There’s also a log file called log.task_order
. There’s only one of these. It lists all tasks in the order they ran. This file is only cleared by doing a cleanall
.
Here’s the cool part: Python tasks need bitbake to run, but Bash tasks can be run straight from the command line. You don’t even need to source the Yocto environment! Give running run.do_compile
a try.
Just remember, if you run a task directly, it won’t create log files. Instead, you’ll see the output right in the terminal.
There are a few handy uses for this.
The best use is for debugging. You can change the source code and quickly recompile without waiting for bitbake. No need to build and install a SDK either. If your source code is in git, you can try out different commits or branches.
If your recipe is based on your source code, you can make changes, commit, and push directly to your repo. You don’t have to clone, commit, push, pull and then rebuild with bitbake just to see if it works. This saves time, especially if your changes don’t pass the Yocto build.
Sometimes you just want to add a few debug prints and upload a binary to the target for more testing. This is a quick way to do that.
Another use is to debug the tasks themselves. You can see how your recipe changes actually affect the code that runs.
Being able to run Bash tasks directly from a recipe’s temp/
directory is a small trick with big payoff. Once you’ve located the work directory, you can execute run.do_*
scripts (e.g., run.do_compile
) to iterate on code and task logic without invoking BitBake or sourcing the environment. Just perfect for quick debug cycles, trying branches, or dropping in extra logs.
With a background in Embedded Systems development, Michal has worked on projects ranging from bare-metal applications to Embedded Linux platforms. In his role as a Principal Software Developer and System Architect, he has taken on responsibility for delivering robust technical solutions in cross-disciplinary teams. He is particularly focused on systems engineering and requirements handling, and is known for a detail-oriented and proactive approach to development.