diff options
Diffstat (limited to 'documentation/dev-manual/build-quality.rst')
-rw-r--r-- | documentation/dev-manual/build-quality.rst | 411 |
1 files changed, 411 insertions, 0 deletions
diff --git a/documentation/dev-manual/build-quality.rst b/documentation/dev-manual/build-quality.rst new file mode 100644 index 0000000000..03eee12bef --- /dev/null +++ b/documentation/dev-manual/build-quality.rst | |||
@@ -0,0 +1,411 @@ | |||
1 | .. SPDX-License-Identifier: CC-BY-SA-2.0-UK | ||
2 | |||
3 | Maintaining Build Output Quality | ||
4 | ******************************** | ||
5 | |||
6 | Many factors can influence the quality of a build. For example, if you | ||
7 | upgrade a recipe to use a new version of an upstream software package or | ||
8 | you experiment with some new configuration options, subtle changes can | ||
9 | occur that you might not detect until later. Consider the case where | ||
10 | your recipe is using a newer version of an upstream package. In this | ||
11 | case, a new version of a piece of software might introduce an optional | ||
12 | dependency on another library, which is auto-detected. If that library | ||
13 | has already been built when the software is building, the software will | ||
14 | link to the built library and that library will be pulled into your | ||
15 | image along with the new software even if you did not want the library. | ||
16 | |||
17 | The :ref:`buildhistory <ref-classes-buildhistory>` | ||
18 | class helps you maintain the quality of your build output. You | ||
19 | can use the class to highlight unexpected and possibly unwanted changes | ||
20 | in the build output. When you enable build history, it records | ||
21 | information about the contents of each package and image and then | ||
22 | commits that information to a local Git repository where you can examine | ||
23 | the information. | ||
24 | |||
25 | The remainder of this section describes the following: | ||
26 | |||
27 | - :ref:`How you can enable and disable build history <dev-manual/build-quality:enabling and disabling build history>` | ||
28 | |||
29 | - :ref:`How to understand what the build history contains <dev-manual/build-quality:understanding what the build history contains>` | ||
30 | |||
31 | - :ref:`How to limit the information used for build history <dev-manual/build-quality:using build history to gather image information only>` | ||
32 | |||
33 | - :ref:`How to examine the build history from both a command-line and web interface <dev-manual/build-quality:examining build history information>` | ||
34 | |||
35 | Enabling and Disabling Build History | ||
36 | ==================================== | ||
37 | |||
38 | Build history is disabled by default. To enable it, add the following | ||
39 | :term:`INHERIT` statement and set the :term:`BUILDHISTORY_COMMIT` variable to | ||
40 | "1" at the end of your ``conf/local.conf`` file found in the | ||
41 | :term:`Build Directory`:: | ||
42 | |||
43 | INHERIT += "buildhistory" | ||
44 | BUILDHISTORY_COMMIT = "1" | ||
45 | |||
46 | Enabling build history as | ||
47 | previously described causes the OpenEmbedded build system to collect | ||
48 | build output information and commit it as a single commit to a local | ||
49 | :ref:`overview-manual/development-environment:git` repository. | ||
50 | |||
51 | .. note:: | ||
52 | |||
53 | Enabling build history increases your build times slightly, | ||
54 | particularly for images, and increases the amount of disk space used | ||
55 | during the build. | ||
56 | |||
57 | You can disable build history by removing the previous statements from | ||
58 | your ``conf/local.conf`` file. | ||
59 | |||
60 | Understanding What the Build History Contains | ||
61 | ============================================= | ||
62 | |||
63 | Build history information is kept in ``${``\ :term:`TOPDIR`\ ``}/buildhistory`` | ||
64 | in the :term:`Build Directory` as defined by the :term:`BUILDHISTORY_DIR` | ||
65 | variable. Here is an example abbreviated listing: | ||
66 | |||
67 | .. image:: figures/buildhistory.png | ||
68 | :align: center | ||
69 | :width: 50% | ||
70 | |||
71 | At the top level, there is a ``metadata-revs`` file that lists the | ||
72 | revisions of the repositories for the enabled layers when the build was | ||
73 | produced. The rest of the data splits into separate ``packages``, | ||
74 | ``images`` and ``sdk`` directories, the contents of which are described | ||
75 | as follows. | ||
76 | |||
77 | Build History Package Information | ||
78 | --------------------------------- | ||
79 | |||
80 | The history for each package contains a text file that has name-value | ||
81 | pairs with information about the package. For example, | ||
82 | ``buildhistory/packages/i586-poky-linux/busybox/busybox/latest`` | ||
83 | contains the following: | ||
84 | |||
85 | .. code-block:: none | ||
86 | |||
87 | PV = 1.22.1 | ||
88 | PR = r32 | ||
89 | RPROVIDES = | ||
90 | RDEPENDS = glibc (>= 2.20) update-alternatives-opkg | ||
91 | RRECOMMENDS = busybox-syslog busybox-udhcpc update-rc.d | ||
92 | PKGSIZE = 540168 | ||
93 | FILES = /usr/bin/* /usr/sbin/* /usr/lib/busybox/* /usr/lib/lib*.so.* \ | ||
94 | /etc /com /var /bin/* /sbin/* /lib/*.so.* /lib/udev/rules.d \ | ||
95 | /usr/lib/udev/rules.d /usr/share/busybox /usr/lib/busybox/* \ | ||
96 | /usr/share/pixmaps /usr/share/applications /usr/share/idl \ | ||
97 | /usr/share/omf /usr/share/sounds /usr/lib/bonobo/servers | ||
98 | FILELIST = /bin/busybox /bin/busybox.nosuid /bin/busybox.suid /bin/sh \ | ||
99 | /etc/busybox.links.nosuid /etc/busybox.links.suid | ||
100 | |||
101 | Most of these | ||
102 | name-value pairs correspond to variables used to produce the package. | ||
103 | The exceptions are ``FILELIST``, which is the actual list of files in | ||
104 | the package, and ``PKGSIZE``, which is the total size of files in the | ||
105 | package in bytes. | ||
106 | |||
107 | There is also a file that corresponds to the recipe from which the package | ||
108 | came (e.g. ``buildhistory/packages/i586-poky-linux/busybox/latest``): | ||
109 | |||
110 | .. code-block:: none | ||
111 | |||
112 | PV = 1.22.1 | ||
113 | PR = r32 | ||
114 | DEPENDS = initscripts kern-tools-native update-rc.d-native \ | ||
115 | virtual/i586-poky-linux-compilerlibs virtual/i586-poky-linux-gcc \ | ||
116 | virtual/libc virtual/update-alternatives | ||
117 | PACKAGES = busybox-ptest busybox-httpd busybox-udhcpd busybox-udhcpc \ | ||
118 | busybox-syslog busybox-mdev busybox-hwclock busybox-dbg \ | ||
119 | busybox-staticdev busybox-dev busybox-doc busybox-locale busybox | ||
120 | |||
121 | Finally, for those recipes fetched from a version control system (e.g., | ||
122 | Git), there is a file that lists source revisions that are specified in | ||
123 | the recipe and the actual revisions used during the build. Listed | ||
124 | and actual revisions might differ when | ||
125 | :term:`SRCREV` is set to | ||
126 | ${:term:`AUTOREV`}. Here is an | ||
127 | example assuming | ||
128 | ``buildhistory/packages/qemux86-poky-linux/linux-yocto/latest_srcrev``):: | ||
129 | |||
130 | # SRCREV_machine = "38cd560d5022ed2dbd1ab0dca9642e47c98a0aa1" | ||
131 | SRCREV_machine = "38cd560d5022ed2dbd1ab0dca9642e47c98a0aa1" | ||
132 | # SRCREV_meta = "a227f20eff056e511d504b2e490f3774ab260d6f" | ||
133 | SRCREV_meta ="a227f20eff056e511d504b2e490f3774ab260d6f" | ||
134 | |||
135 | You can use the | ||
136 | ``buildhistory-collect-srcrevs`` command with the ``-a`` option to | ||
137 | collect the stored :term:`SRCREV` values from build history and report them | ||
138 | in a format suitable for use in global configuration (e.g., | ||
139 | ``local.conf`` or a distro include file) to override floating | ||
140 | :term:`AUTOREV` values to a fixed set of revisions. Here is some example | ||
141 | output from this command:: | ||
142 | |||
143 | $ buildhistory-collect-srcrevs -a | ||
144 | # all-poky-linux | ||
145 | SRCREV:pn-ca-certificates = "07de54fdcc5806bde549e1edf60738c6bccf50e8" | ||
146 | SRCREV:pn-update-rc.d = "8636cf478d426b568c1be11dbd9346f67e03adac" | ||
147 | # core2-64-poky-linux | ||
148 | SRCREV:pn-binutils = "87d4632d36323091e731eb07b8aa65f90293da66" | ||
149 | SRCREV:pn-btrfs-tools = "8ad326b2f28c044cb6ed9016d7c3285e23b673c8" | ||
150 | SRCREV_bzip2-tests:pn-bzip2 = "f9061c030a25de5b6829e1abf373057309c734c0" | ||
151 | SRCREV:pn-e2fsprogs = "02540dedd3ddc52c6ae8aaa8a95ce75c3f8be1c0" | ||
152 | SRCREV:pn-file = "504206e53a89fd6eed71aeaf878aa3512418eab1" | ||
153 | SRCREV_glibc:pn-glibc = "24962427071fa532c3c48c918e9d64d719cc8a6c" | ||
154 | SRCREV:pn-gnome-desktop-testing = "e346cd4ed2e2102c9b195b614f3c642d23f5f6e7" | ||
155 | SRCREV:pn-init-system-helpers = "dbd9197569c0935029acd5c9b02b84c68fd937ee" | ||
156 | SRCREV:pn-kmod = "b6ecfc916a17eab8f93be5b09f4e4f845aabd3d1" | ||
157 | SRCREV:pn-libnsl2 = "82245c0c58add79a8e34ab0917358217a70e5100" | ||
158 | SRCREV:pn-libseccomp = "57357d2741a3b3d3e8425889a6b79a130e0fa2f3" | ||
159 | SRCREV:pn-libxcrypt = "50cf2b6dd4fdf04309445f2eec8de7051d953abf" | ||
160 | SRCREV:pn-ncurses = "51d0fd9cc3edb975f04224f29f777f8f448e8ced" | ||
161 | SRCREV:pn-procps = "19a508ea121c0c4ac6d0224575a036de745eaaf8" | ||
162 | SRCREV:pn-psmisc = "5fab6b7ab385080f1db725d6803136ec1841a15f" | ||
163 | SRCREV:pn-ptest-runner = "bcb82804daa8f725b6add259dcef2067e61a75aa" | ||
164 | SRCREV:pn-shared-mime-info = "18e558fa1c8b90b86757ade09a4ba4d6a6cf8f70" | ||
165 | SRCREV:pn-zstd = "e47e674cd09583ff0503f0f6defd6d23d8b718d3" | ||
166 | # qemux86_64-poky-linux | ||
167 | SRCREV_machine:pn-linux-yocto = "20301aeb1a64164b72bc72af58802b315e025c9c" | ||
168 | SRCREV_meta:pn-linux-yocto = "2d38a472b21ae343707c8bd64ac68a9eaca066a0" | ||
169 | # x86_64-linux | ||
170 | SRCREV:pn-binutils-cross-x86_64 = "87d4632d36323091e731eb07b8aa65f90293da66" | ||
171 | SRCREV_glibc:pn-cross-localedef-native = "24962427071fa532c3c48c918e9d64d719cc8a6c" | ||
172 | SRCREV_localedef:pn-cross-localedef-native = "794da69788cbf9bf57b59a852f9f11307663fa87" | ||
173 | SRCREV:pn-debianutils-native = "de14223e5bffe15e374a441302c528ffc1cbed57" | ||
174 | SRCREV:pn-libmodulemd-native = "ee80309bc766d781a144e6879419b29f444d94eb" | ||
175 | SRCREV:pn-virglrenderer-native = "363915595e05fb252e70d6514be2f0c0b5ca312b" | ||
176 | SRCREV:pn-zstd-native = "e47e674cd09583ff0503f0f6defd6d23d8b718d3" | ||
177 | |||
178 | .. note:: | ||
179 | |||
180 | Here are some notes on using the ``buildhistory-collect-srcrevs`` command: | ||
181 | |||
182 | - By default, only values where the :term:`SRCREV` was not hardcoded | ||
183 | (usually when :term:`AUTOREV` is used) are reported. Use the ``-a`` | ||
184 | option to see all :term:`SRCREV` values. | ||
185 | |||
186 | - The output statements might not have any effect if overrides are | ||
187 | applied elsewhere in the build system configuration. Use the | ||
188 | ``-f`` option to add the ``forcevariable`` override to each output | ||
189 | line if you need to work around this restriction. | ||
190 | |||
191 | - The script does apply special handling when building for multiple | ||
192 | machines. However, the script does place a comment before each set | ||
193 | of values that specifies which triplet to which they belong as | ||
194 | previously shown (e.g., ``i586-poky-linux``). | ||
195 | |||
196 | Build History Image Information | ||
197 | ------------------------------- | ||
198 | |||
199 | The files produced for each image are as follows: | ||
200 | |||
201 | - ``image-files:`` A directory containing selected files from the root | ||
202 | filesystem. The files are defined by | ||
203 | :term:`BUILDHISTORY_IMAGE_FILES`. | ||
204 | |||
205 | - ``build-id.txt:`` Human-readable information about the build | ||
206 | configuration and metadata source revisions. This file contains the | ||
207 | full build header as printed by BitBake. | ||
208 | |||
209 | - ``*.dot:`` Dependency graphs for the image that are compatible with | ||
210 | ``graphviz``. | ||
211 | |||
212 | - ``files-in-image.txt:`` A list of files in the image with | ||
213 | permissions, owner, group, size, and symlink information. | ||
214 | |||
215 | - ``image-info.txt:`` A text file containing name-value pairs with | ||
216 | information about the image. See the following listing example for | ||
217 | more information. | ||
218 | |||
219 | - ``installed-package-names.txt:`` A list of installed packages by name | ||
220 | only. | ||
221 | |||
222 | - ``installed-package-sizes.txt:`` A list of installed packages ordered | ||
223 | by size. | ||
224 | |||
225 | - ``installed-packages.txt:`` A list of installed packages with full | ||
226 | package filenames. | ||
227 | |||
228 | .. note:: | ||
229 | |||
230 | Installed package information is able to be gathered and produced | ||
231 | even if package management is disabled for the final image. | ||
232 | |||
233 | Here is an example of ``image-info.txt``: | ||
234 | |||
235 | .. code-block:: none | ||
236 | |||
237 | DISTRO = poky | ||
238 | DISTRO_VERSION = 3.4+snapshot-a0245d7be08f3d24ea1875e9f8872aa6bbff93be | ||
239 | USER_CLASSES = buildstats | ||
240 | IMAGE_CLASSES = qemuboot qemuboot license_image | ||
241 | IMAGE_FEATURES = debug-tweaks | ||
242 | IMAGE_LINGUAS = | ||
243 | IMAGE_INSTALL = packagegroup-core-boot speex speexdsp | ||
244 | BAD_RECOMMENDATIONS = | ||
245 | NO_RECOMMENDATIONS = | ||
246 | PACKAGE_EXCLUDE = | ||
247 | ROOTFS_POSTPROCESS_COMMAND = write_package_manifest; license_create_manifest; cve_check_write_rootfs_manifest; ssh_allow_empty_password; ssh_allow_root_login; postinst_enable_logging; rootfs_update_timestamp; write_image_test_data; empty_var_volatile; sort_passwd; rootfs_reproducible; | ||
248 | IMAGE_POSTPROCESS_COMMAND = buildhistory_get_imageinfo ; | ||
249 | IMAGESIZE = 9265 | ||
250 | |||
251 | Other than ``IMAGESIZE``, | ||
252 | which is the total size of the files in the image in Kbytes, the | ||
253 | name-value pairs are variables that may have influenced the content of | ||
254 | the image. This information is often useful when you are trying to | ||
255 | determine why a change in the package or file listings has occurred. | ||
256 | |||
257 | Using Build History to Gather Image Information Only | ||
258 | ---------------------------------------------------- | ||
259 | |||
260 | As you can see, build history produces image information, including | ||
261 | dependency graphs, so you can see why something was pulled into the | ||
262 | image. If you are just interested in this information and not interested | ||
263 | in collecting specific package or SDK information, you can enable | ||
264 | writing only image information without any history by adding the | ||
265 | following to your ``conf/local.conf`` file found in the | ||
266 | :term:`Build Directory`:: | ||
267 | |||
268 | INHERIT += "buildhistory" | ||
269 | BUILDHISTORY_COMMIT = "0" | ||
270 | BUILDHISTORY_FEATURES = "image" | ||
271 | |||
272 | Here, you set the | ||
273 | :term:`BUILDHISTORY_FEATURES` | ||
274 | variable to use the image feature only. | ||
275 | |||
276 | Build History SDK Information | ||
277 | ----------------------------- | ||
278 | |||
279 | Build history collects similar information on the contents of SDKs (e.g. | ||
280 | ``bitbake -c populate_sdk imagename``) as compared to information it | ||
281 | collects for images. Furthermore, this information differs depending on | ||
282 | whether an extensible or standard SDK is being produced. | ||
283 | |||
284 | The following list shows the files produced for SDKs: | ||
285 | |||
286 | - ``files-in-sdk.txt:`` A list of files in the SDK with permissions, | ||
287 | owner, group, size, and symlink information. This list includes both | ||
288 | the host and target parts of the SDK. | ||
289 | |||
290 | - ``sdk-info.txt:`` A text file containing name-value pairs with | ||
291 | information about the SDK. See the following listing example for more | ||
292 | information. | ||
293 | |||
294 | - ``sstate-task-sizes.txt:`` A text file containing name-value pairs | ||
295 | with information about task group sizes (e.g. :ref:`ref-tasks-populate_sysroot` | ||
296 | tasks have a total size). The ``sstate-task-sizes.txt`` file exists | ||
297 | only when an extensible SDK is created. | ||
298 | |||
299 | - ``sstate-package-sizes.txt:`` A text file containing name-value pairs | ||
300 | with information for the shared-state packages and sizes in the SDK. | ||
301 | The ``sstate-package-sizes.txt`` file exists only when an extensible | ||
302 | SDK is created. | ||
303 | |||
304 | - ``sdk-files:`` A folder that contains copies of the files mentioned | ||
305 | in ``BUILDHISTORY_SDK_FILES`` if the files are present in the output. | ||
306 | Additionally, the default value of ``BUILDHISTORY_SDK_FILES`` is | ||
307 | specific to the extensible SDK although you can set it differently if | ||
308 | you would like to pull in specific files from the standard SDK. | ||
309 | |||
310 | The default files are ``conf/local.conf``, ``conf/bblayers.conf``, | ||
311 | ``conf/auto.conf``, ``conf/locked-sigs.inc``, and | ||
312 | ``conf/devtool.conf``. Thus, for an extensible SDK, these files get | ||
313 | copied into the ``sdk-files`` directory. | ||
314 | |||
315 | - The following information appears under each of the ``host`` and | ||
316 | ``target`` directories for the portions of the SDK that run on the | ||
317 | host and on the target, respectively: | ||
318 | |||
319 | .. note:: | ||
320 | |||
321 | The following files for the most part are empty when producing an | ||
322 | extensible SDK because this type of SDK is not constructed from | ||
323 | packages as is the standard SDK. | ||
324 | |||
325 | - ``depends.dot:`` Dependency graph for the SDK that is compatible | ||
326 | with ``graphviz``. | ||
327 | |||
328 | - ``installed-package-names.txt:`` A list of installed packages by | ||
329 | name only. | ||
330 | |||
331 | - ``installed-package-sizes.txt:`` A list of installed packages | ||
332 | ordered by size. | ||
333 | |||
334 | - ``installed-packages.txt:`` A list of installed packages with full | ||
335 | package filenames. | ||
336 | |||
337 | Here is an example of ``sdk-info.txt``: | ||
338 | |||
339 | .. code-block:: none | ||
340 | |||
341 | DISTRO = poky | ||
342 | DISTRO_VERSION = 1.3+snapshot-20130327 | ||
343 | SDK_NAME = poky-glibc-i686-arm | ||
344 | SDK_VERSION = 1.3+snapshot | ||
345 | SDKMACHINE = | ||
346 | SDKIMAGE_FEATURES = dev-pkgs dbg-pkgs | ||
347 | BAD_RECOMMENDATIONS = | ||
348 | SDKSIZE = 352712 | ||
349 | |||
350 | Other than ``SDKSIZE``, which is | ||
351 | the total size of the files in the SDK in Kbytes, the name-value pairs | ||
352 | are variables that might have influenced the content of the SDK. This | ||
353 | information is often useful when you are trying to determine why a | ||
354 | change in the package or file listings has occurred. | ||
355 | |||
356 | Examining Build History Information | ||
357 | ----------------------------------- | ||
358 | |||
359 | You can examine build history output from the command line or from a web | ||
360 | interface. | ||
361 | |||
362 | To see any changes that have occurred (assuming you have | ||
363 | :term:`BUILDHISTORY_COMMIT` = "1"), | ||
364 | you can simply use any Git command that allows you to view the history | ||
365 | of a repository. Here is one method:: | ||
366 | |||
367 | $ git log -p | ||
368 | |||
369 | You need to realize, | ||
370 | however, that this method does show changes that are not significant | ||
371 | (e.g. a package's size changing by a few bytes). | ||
372 | |||
373 | There is a command-line tool called ``buildhistory-diff``, though, | ||
374 | that queries the Git repository and prints just the differences that | ||
375 | might be significant in human-readable form. Here is an example:: | ||
376 | |||
377 | $ poky/poky/scripts/buildhistory-diff . HEAD^ | ||
378 | Changes to images/qemux86_64/glibc/core-image-minimal (files-in-image.txt): | ||
379 | /etc/anotherpkg.conf was added | ||
380 | /sbin/anotherpkg was added | ||
381 | * (installed-package-names.txt): | ||
382 | * anotherpkg was added | ||
383 | Changes to images/qemux86_64/glibc/core-image-minimal (installed-package-names.txt): | ||
384 | anotherpkg was added | ||
385 | packages/qemux86_64-poky-linux/v86d: PACKAGES: added "v86d-extras" | ||
386 | * PR changed from "r0" to "r1" | ||
387 | * PV changed from "0.1.10" to "0.1.12" | ||
388 | packages/qemux86_64-poky-linux/v86d/v86d: PKGSIZE changed from 110579 to 144381 (+30%) | ||
389 | * PR changed from "r0" to "r1" | ||
390 | * PV changed from "0.1.10" to "0.1.12" | ||
391 | |||
392 | .. note:: | ||
393 | |||
394 | The ``buildhistory-diff`` tool requires the ``GitPython`` | ||
395 | package. Be sure to install it using Pip3 as follows:: | ||
396 | |||
397 | $ pip3 install GitPython --user | ||
398 | |||
399 | |||
400 | Alternatively, you can install ``python3-git`` using the appropriate | ||
401 | distribution package manager (e.g. ``apt``, ``dnf``, or ``zipper``). | ||
402 | |||
403 | To see changes to the build history using a web interface, follow the | ||
404 | instruction in the ``README`` file | ||
405 | :yocto_git:`here </buildhistory-web/>`. | ||
406 | |||
407 | Here is a sample screenshot of the interface: | ||
408 | |||
409 | .. image:: figures/buildhistory-web.png | ||
410 | :width: 100% | ||
411 | |||