blob: 66e423e999329c1cf06e22246e7d136ad3caef77 [file] [log] [blame]
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001#
2# Packaging process
3#
4# Executive summary: This class iterates over the functions listed in PACKAGEFUNCS
5# Taking D and splitting it up into the packages listed in PACKAGES, placing the
6# resulting output in PKGDEST.
7#
8# There are the following default steps but PACKAGEFUNCS can be extended:
9#
10# a) package_get_auto_pr - get PRAUTO from remote PR service
11#
12# b) perform_packagecopy - Copy D into PKGD
13#
14# c) package_do_split_locales - Split out the locale files, updates FILES and PACKAGES
15#
16# d) split_and_strip_files - split the files into runtime and debug and strip them.
17# Debug files include debug info split, and associated sources that end up in -dbg packages
18#
19# e) fixup_perms - Fix up permissions in the package before we split it.
20#
21# f) populate_packages - Split the files in PKGD into separate packages in PKGDEST/<pkgname>
22# Also triggers the binary stripping code to put files in -dbg packages.
23#
24# g) package_do_filedeps - Collect perfile run-time dependency metadata
25# The data is stores in FILER{PROVIDES,DEPENDS}_file_pkg variables with
26# a list of affected files in FILER{PROVIDES,DEPENDS}FLIST_pkg
27#
28# h) package_do_shlibs - Look at the shared libraries generated and autotmatically add any
Brad Bishop316dfdd2018-06-25 12:45:53 -040029# dependencies found. Also stores the package name so anyone else using this library
Patrick Williamsc124f4f2015-09-15 14:41:29 -050030# knows which package to depend on.
31#
32# i) package_do_pkgconfig - Keep track of which packages need and provide which .pc files
33#
34# j) read_shlibdeps - Reads the stored shlibs information into the metadata
35#
36# k) package_depchains - Adds automatic dependencies to -dbg and -dev packages
37#
38# l) emit_pkgdata - saves the packaging data into PKGDATA_DIR for use in later
39# packaging steps
40
41inherit packagedata
Patrick Williamsc124f4f2015-09-15 14:41:29 -050042inherit chrpath
43
44# Need the package_qa_handle_error() in insane.bbclass
45inherit insane
46
47PKGD = "${WORKDIR}/package"
48PKGDEST = "${WORKDIR}/packages-split"
49
50LOCALE_SECTION ?= ''
51
52ALL_MULTILIB_PACKAGE_ARCHS = "${@all_multilib_tune_values(d, 'PACKAGE_ARCHS')}"
53
54# rpm is used for the per-file dependency identification
Brad Bishop316dfdd2018-06-25 12:45:53 -040055# dwarfsrcfiles is used to determine the list of debug source files
56PACKAGE_DEPENDS += "rpm-native dwarfsrcfiles-native"
Patrick Williamsc124f4f2015-09-15 14:41:29 -050057
Brad Bishop6e60e8b2018-02-01 10:27:11 -050058
59# If your postinstall can execute at rootfs creation time rather than on
60# target but depends on a native/cross tool in order to execute, you need to
Brad Bishop1a4b7ee2018-12-16 17:11:34 -080061# list that tool in PACKAGE_WRITE_DEPS. Target package dependencies belong
Brad Bishop6e60e8b2018-02-01 10:27:11 -050062# in the package dependencies as normal, this is just for native/cross support
63# tools at rootfs build time.
64PACKAGE_WRITE_DEPS ??= ""
65
Patrick Williamsc124f4f2015-09-15 14:41:29 -050066def legitimize_package_name(s):
67 """
68 Make sure package names are legitimate strings
69 """
70 import re
71
72 def fixutf(m):
73 cp = m.group(1)
74 if cp:
Patrick Williamsc0f7c042017-02-23 20:41:17 -060075 return ('\\u%s' % cp).encode('latin-1').decode('unicode_escape')
Patrick Williamsc124f4f2015-09-15 14:41:29 -050076
77 # Handle unicode codepoints encoded as <U0123>, as in glibc locale files.
78 s = re.sub('<U([0-9A-Fa-f]{1,4})>', fixutf, s)
79
80 # Remaining package name validity fixes
81 return s.lower().replace('_', '-').replace('@', '+').replace(',', '+').replace('/', '-')
82
83def do_split_packages(d, root, file_regex, output_pattern, description, postinst=None, recursive=False, hook=None, extra_depends=None, aux_files_pattern=None, postrm=None, allow_dirs=False, prepend=False, match_path=False, aux_files_pattern_verbatim=None, allow_links=False, summary=None):
84 """
85 Used in .bb files to split up dynamically generated subpackages of a
86 given package, usually plugins or modules.
87
88 Arguments:
89 root -- the path in which to search
90 file_regex -- regular expression to match searched files. Use
91 parentheses () to mark the part of this expression
92 that should be used to derive the module name (to be
93 substituted where %s is used in other function
94 arguments as noted below)
95 output_pattern -- pattern to use for the package names. Must include %s.
96 description -- description to set for each package. Must include %s.
97 postinst -- postinstall script to use for all packages (as a
98 string)
99 recursive -- True to perform a recursive search - default False
100 hook -- a hook function to be called for every match. The
101 function will be called with the following arguments
102 (in the order listed):
103 f: full path to the file/directory match
104 pkg: the package name
105 file_regex: as above
106 output_pattern: as above
107 modulename: the module name derived using file_regex
108 extra_depends -- extra runtime dependencies (RDEPENDS) to be set for
109 all packages. The default value of None causes a
110 dependency on the main package (${PN}) - if you do
111 not want this, pass '' for this parameter.
112 aux_files_pattern -- extra item(s) to be added to FILES for each
113 package. Can be a single string item or a list of
114 strings for multiple items. Must include %s.
115 postrm -- postrm script to use for all packages (as a string)
116 allow_dirs -- True allow directories to be matched - default False
117 prepend -- if True, prepend created packages to PACKAGES instead
118 of the default False which appends them
119 match_path -- match file_regex on the whole relative path to the
120 root rather than just the file name
121 aux_files_pattern_verbatim -- extra item(s) to be added to FILES for
122 each package, using the actual derived module name
123 rather than converting it to something legal for a
124 package name. Can be a single string item or a list
125 of strings for multiple items. Must include %s.
126 allow_links -- True to allow symlinks to be matched - default False
127 summary -- Summary to set for each package. Must include %s;
128 defaults to description if not set.
129
130 """
131
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500132 dvar = d.getVar('PKGD')
Patrick Williamsd8c66bc2016-06-20 12:57:21 -0500133 root = d.expand(root)
134 output_pattern = d.expand(output_pattern)
135 extra_depends = d.expand(extra_depends)
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500136
137 # If the root directory doesn't exist, don't error out later but silently do
138 # no splitting.
139 if not os.path.exists(dvar + root):
140 return []
141
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500142 ml = d.getVar("MLPREFIX")
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500143 if ml:
144 if not output_pattern.startswith(ml):
145 output_pattern = ml + output_pattern
146
147 newdeps = []
148 for dep in (extra_depends or "").split():
149 if dep.startswith(ml):
150 newdeps.append(dep)
151 else:
152 newdeps.append(ml + dep)
153 if newdeps:
154 extra_depends = " ".join(newdeps)
155
156
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500157 packages = d.getVar('PACKAGES').split()
Patrick Williamsc0f7c042017-02-23 20:41:17 -0600158 split_packages = set()
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500159
160 if postinst:
161 postinst = '#!/bin/sh\n' + postinst + '\n'
162 if postrm:
163 postrm = '#!/bin/sh\n' + postrm + '\n'
164 if not recursive:
165 objs = os.listdir(dvar + root)
166 else:
167 objs = []
168 for walkroot, dirs, files in os.walk(dvar + root):
169 for file in files:
170 relpath = os.path.join(walkroot, file).replace(dvar + root + '/', '', 1)
171 if relpath:
172 objs.append(relpath)
173
174 if extra_depends == None:
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500175 extra_depends = d.getVar("PN")
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500176
177 if not summary:
178 summary = description
179
180 for o in sorted(objs):
181 import re, stat
182 if match_path:
183 m = re.match(file_regex, o)
184 else:
185 m = re.match(file_regex, os.path.basename(o))
186
187 if not m:
188 continue
189 f = os.path.join(dvar + root, o)
190 mode = os.lstat(f).st_mode
191 if not (stat.S_ISREG(mode) or (allow_links and stat.S_ISLNK(mode)) or (allow_dirs and stat.S_ISDIR(mode))):
192 continue
193 on = legitimize_package_name(m.group(1))
194 pkg = output_pattern % on
Patrick Williamsc0f7c042017-02-23 20:41:17 -0600195 split_packages.add(pkg)
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500196 if not pkg in packages:
197 if prepend:
198 packages = [pkg] + packages
199 else:
200 packages.append(pkg)
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500201 oldfiles = d.getVar('FILES_' + pkg)
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500202 newfile = os.path.join(root, o)
203 # These names will be passed through glob() so if the filename actually
204 # contains * or ? (rare, but possible) we need to handle that specially
205 newfile = newfile.replace('*', '[*]')
206 newfile = newfile.replace('?', '[?]')
207 if not oldfiles:
208 the_files = [newfile]
209 if aux_files_pattern:
210 if type(aux_files_pattern) is list:
211 for fp in aux_files_pattern:
212 the_files.append(fp % on)
213 else:
214 the_files.append(aux_files_pattern % on)
215 if aux_files_pattern_verbatim:
216 if type(aux_files_pattern_verbatim) is list:
217 for fp in aux_files_pattern_verbatim:
218 the_files.append(fp % m.group(1))
219 else:
220 the_files.append(aux_files_pattern_verbatim % m.group(1))
221 d.setVar('FILES_' + pkg, " ".join(the_files))
222 else:
223 d.setVar('FILES_' + pkg, oldfiles + " " + newfile)
224 if extra_depends != '':
225 d.appendVar('RDEPENDS_' + pkg, ' ' + extra_depends)
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500226 if not d.getVar('DESCRIPTION_' + pkg):
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500227 d.setVar('DESCRIPTION_' + pkg, description % on)
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500228 if not d.getVar('SUMMARY_' + pkg):
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500229 d.setVar('SUMMARY_' + pkg, summary % on)
230 if postinst:
231 d.setVar('pkg_postinst_' + pkg, postinst)
232 if postrm:
233 d.setVar('pkg_postrm_' + pkg, postrm)
234 if callable(hook):
235 hook(f, pkg, file_regex, output_pattern, m.group(1))
236
237 d.setVar('PACKAGES', ' '.join(packages))
Patrick Williamsc0f7c042017-02-23 20:41:17 -0600238 return list(split_packages)
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500239
240PACKAGE_DEPENDS += "file-native"
241
242python () {
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500243 if d.getVar('PACKAGES') != '':
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500244 deps = ""
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500245 for dep in (d.getVar('PACKAGE_DEPENDS') or "").split():
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500246 deps += " %s:do_populate_sysroot" % dep
247 d.appendVarFlag('do_package', 'depends', deps)
248
249 # shlibs requires any DEPENDS to have already packaged for the *.list files
250 d.appendVarFlag('do_package', 'deptask', " do_packagedata")
251}
252
253# Get a list of files from file vars by searching files under current working directory
254# The list contains symlinks, directories and normal files.
255def files_from_filevars(filevars):
256 import os,glob
257 cpath = oe.cachedpath.CachedPath()
258 files = []
259 for f in filevars:
260 if os.path.isabs(f):
261 f = '.' + f
262 if not f.startswith("./"):
263 f = './' + f
264 globbed = glob.glob(f)
265 if globbed:
266 if [ f ] != globbed:
267 files += globbed
268 continue
269 files.append(f)
270
Patrick Williamsc0f7c042017-02-23 20:41:17 -0600271 symlink_paths = []
272 for ind, f in enumerate(files):
273 # Handle directory symlinks. Truncate path to the lowest level symlink
274 parent = ''
275 for dirname in f.split('/')[:-1]:
276 parent = os.path.join(parent, dirname)
277 if dirname == '.':
278 continue
279 if cpath.islink(parent):
280 bb.warn("FILES contains file '%s' which resides under a "
281 "directory symlink. Please fix the recipe and use the "
282 "real path for the file." % f[1:])
283 symlink_paths.append(f)
284 files[ind] = parent
285 f = parent
286 break
287
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500288 if not cpath.islink(f):
289 if cpath.isdir(f):
290 newfiles = [ os.path.join(f,x) for x in os.listdir(f) ]
291 if newfiles:
292 files += newfiles
293
Patrick Williamsc0f7c042017-02-23 20:41:17 -0600294 return files, symlink_paths
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500295
296# Called in package_<rpm,ipk,deb>.bbclass to get the correct list of configuration files
297def get_conffiles(pkg, d):
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500298 pkgdest = d.getVar('PKGDEST')
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500299 root = os.path.join(pkgdest, pkg)
300 cwd = os.getcwd()
301 os.chdir(root)
302
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500303 conffiles = d.getVar('CONFFILES_%s' % pkg);
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500304 if conffiles == None:
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500305 conffiles = d.getVar('CONFFILES')
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500306 if conffiles == None:
307 conffiles = ""
308 conffiles = conffiles.split()
Patrick Williamsc0f7c042017-02-23 20:41:17 -0600309 conf_orig_list = files_from_filevars(conffiles)[0]
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500310
311 # Remove links and directories from conf_orig_list to get conf_list which only contains normal files
312 conf_list = []
313 for f in conf_orig_list:
314 if os.path.isdir(f):
315 continue
316 if os.path.islink(f):
317 continue
318 if not os.path.exists(f):
319 continue
320 conf_list.append(f)
321
322 # Remove the leading './'
323 for i in range(0, len(conf_list)):
324 conf_list[i] = conf_list[i][1:]
325
326 os.chdir(cwd)
327 return conf_list
328
Patrick Williamsd8c66bc2016-06-20 12:57:21 -0500329def checkbuildpath(file, d):
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500330 tmpdir = d.getVar('TMPDIR')
Patrick Williamsd8c66bc2016-06-20 12:57:21 -0500331 with open(file) as f:
332 file_content = f.read()
333 if tmpdir in file_content:
334 return True
335
336 return False
337
Brad Bishop316dfdd2018-06-25 12:45:53 -0400338def parse_debugsources_from_dwarfsrcfiles_output(dwarfsrcfiles_output):
339 debugfiles = {}
340
341 for line in dwarfsrcfiles_output.splitlines():
342 if line.startswith("\t"):
343 debugfiles[os.path.normpath(line.split()[0])] = ""
344
345 return debugfiles.keys()
346
347def append_source_info(file, sourcefile, d, fatal=True):
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800348 import subprocess
349
350 cmd = ["dwarfsrcfiles", file]
351 try:
352 output = subprocess.check_output(cmd, universal_newlines=True, stderr=subprocess.STDOUT)
353 retval = 0
354 except subprocess.CalledProcessError as exc:
355 output = exc.output
356 retval = exc.returncode
357
Brad Bishop316dfdd2018-06-25 12:45:53 -0400358 # 255 means a specific file wasn't fully parsed to get the debug file list, which is not a fatal failure
359 if retval != 0 and retval != 255:
360 msg = "dwarfsrcfiles failed with exit code %s (cmd was %s)%s" % (retval, cmd, ":\n%s" % output if output else "")
361 if fatal:
362 bb.fatal(msg)
363 bb.note(msg)
364
365 debugsources = parse_debugsources_from_dwarfsrcfiles_output(output)
366 # filenames are null-separated - this is an artefact of the previous use
367 # of rpm's debugedit, which was writing them out that way, and the code elsewhere
368 # is still assuming that.
369 debuglistoutput = '\0'.join(debugsources) + '\0'
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800370 lf = bb.utils.lockfile(sourcefile + ".lock")
Brad Bishop977dc1a2019-02-06 16:01:43 -0500371 with open(sourcefile, 'a') as sf:
372 sf.write(debuglistoutput)
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800373 bb.utils.unlockfile(lf)
Brad Bishop316dfdd2018-06-25 12:45:53 -0400374
375
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800376def splitdebuginfo(file, dvar, debugdir, debuglibdir, debugappend, debugsrcdir, sourcefile, d):
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500377 # Function to split a single file into two components, one is the stripped
378 # target system binary, the other contains any debugging information. The
379 # two files are linked to reference each other.
380 #
381 # sourcefile is also generated containing a list of debugsources
382
383 import stat
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800384 import subprocess
385
386 src = file[len(dvar):]
387 dest = debuglibdir + os.path.dirname(src) + debugdir + "/" + os.path.basename(src) + debugappend
388 debugfile = dvar + dest
389
390 # Split the file...
391 bb.utils.mkdirhier(os.path.dirname(debugfile))
392 #bb.note("Split %s -> %s" % (file, debugfile))
393 # Only store off the hard link reference if we successfully split!
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500394
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500395 dvar = d.getVar('PKGD')
396 objcopy = d.getVar("OBJCOPY")
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500397
398 # We ignore kernel modules, we don't generate debug info files.
399 if file.find("/lib/modules/") != -1 and file.endswith(".ko"):
400 return 1
401
402 newmode = None
403 if not os.access(file, os.W_OK) or os.access(file, os.R_OK):
404 origmode = os.stat(file)[stat.ST_MODE]
405 newmode = origmode | stat.S_IWRITE | stat.S_IREAD
406 os.chmod(file, newmode)
407
408 # We need to extract the debug src information here...
409 if debugsrcdir:
Brad Bishop316dfdd2018-06-25 12:45:53 -0400410 append_source_info(file, sourcefile, d)
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500411
412 bb.utils.mkdirhier(os.path.dirname(debugfile))
413
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800414 subprocess.check_output([objcopy, '--only-keep-debug', file, debugfile], stderr=subprocess.STDOUT)
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500415
416 # Set the debuglink to have the view of the file path on the target
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800417 subprocess.check_output([objcopy, '--add-gnu-debuglink', debugfile, file], stderr=subprocess.STDOUT)
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500418
419 if newmode:
420 os.chmod(file, origmode)
421
422 return 0
423
424def copydebugsources(debugsrcdir, d):
Brad Bishop316dfdd2018-06-25 12:45:53 -0400425 # The debug src information written out to sourcefile is further processed
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500426 # and copied to the destination here.
427
428 import stat
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800429 import subprocess
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500430
431 sourcefile = d.expand("${WORKDIR}/debugsources.list")
432 if debugsrcdir and os.path.isfile(sourcefile):
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500433 dvar = d.getVar('PKGD')
434 strip = d.getVar("STRIP")
435 objcopy = d.getVar("OBJCOPY")
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500436 workdir = d.getVar("WORKDIR")
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500437 workparentdir = os.path.dirname(os.path.dirname(workdir))
438 workbasedir = os.path.basename(os.path.dirname(workdir)) + "/" + os.path.basename(workdir)
439
Patrick Williamsd8c66bc2016-06-20 12:57:21 -0500440 # If build path exists in sourcefile, it means toolchain did not use
441 # -fdebug-prefix-map to compile
442 if checkbuildpath(sourcefile, d):
443 localsrc_prefix = workparentdir + "/"
444 else:
445 localsrc_prefix = "/usr/src/debug/"
446
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500447 nosuchdir = []
448 basepath = dvar
449 for p in debugsrcdir.split("/"):
450 basepath = basepath + "/" + p
451 if not cpath.exists(basepath):
452 nosuchdir.append(basepath)
453 bb.utils.mkdirhier(basepath)
454 cpath.updatecache(basepath)
455
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500456 # Ignore files from the recipe sysroots (target and native)
457 processdebugsrc = "LC_ALL=C ; sort -z -u '%s' | egrep -v -z '((<internal>|<built-in>)$|/.*recipe-sysroot.*/)' | "
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500458 # We need to ignore files that are not actually ours
459 # we do this by only paying attention to items from this package
460 processdebugsrc += "fgrep -zw '%s' | "
Patrick Williamsd8c66bc2016-06-20 12:57:21 -0500461 # Remove prefix in the source paths
462 processdebugsrc += "sed 's#%s##g' | "
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500463 processdebugsrc += "(cd '%s' ; cpio -pd0mlL --no-preserve-owner '%s%s' 2>/dev/null)"
464
Patrick Williamsd8c66bc2016-06-20 12:57:21 -0500465 cmd = processdebugsrc % (sourcefile, workbasedir, localsrc_prefix, workparentdir, dvar, debugsrcdir)
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800466 try:
467 subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT)
468 except subprocess.CalledProcessError:
469 # Can "fail" if internal headers/transient sources are attempted
470 pass
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500471
472 # cpio seems to have a bug with -lL together and symbolic links are just copied, not dereferenced.
473 # Work around this by manually finding and copying any symbolic links that made it through.
474 cmd = "find %s%s -type l -print0 -delete | sed s#%s%s/##g | (cd '%s' ; cpio -pd0mL --no-preserve-owner '%s%s' 2>/dev/null)" % (dvar, debugsrcdir, dvar, debugsrcdir, workparentdir, dvar, debugsrcdir)
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800475 subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT)
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500476
477 # The copy by cpio may have resulted in some empty directories! Remove these
478 cmd = "find %s%s -empty -type d -delete" % (dvar, debugsrcdir)
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800479 subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT)
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500480
481 # Also remove debugsrcdir if its empty
482 for p in nosuchdir[::-1]:
483 if os.path.exists(p) and not os.listdir(p):
484 os.rmdir(p)
485
486#
487# Package data handling routines
488#
489
490def get_package_mapping (pkg, basepkg, d):
491 import oe.packagedata
492
493 data = oe.packagedata.read_subpkgdata(pkg, d)
494 key = "PKG_%s" % pkg
495
496 if key in data:
497 # Have to avoid undoing the write_extra_pkgs(global_variants...)
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800498 if bb.data.inherits_class('allarch', d) and not d.getVar('MULTILIB_VARIANTS') \
499 and data[key] == basepkg:
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500500 return pkg
501 return data[key]
502
503 return pkg
504
505def get_package_additional_metadata (pkg_type, d):
506 base_key = "PACKAGE_ADD_METADATA"
507 for key in ("%s_%s" % (base_key, pkg_type.upper()), base_key):
508 if d.getVar(key, False) is None:
509 continue
510 d.setVarFlag(key, "type", "list")
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500511 if d.getVarFlag(key, "separator") is None:
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500512 d.setVarFlag(key, "separator", "\\n")
513 metadata_fields = [field.strip() for field in oe.data.typed_value(key, d)]
514 return "\n".join(metadata_fields).strip()
515
516def runtime_mapping_rename (varname, pkg, d):
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500517 #bb.note("%s before: %s" % (varname, d.getVar(varname)))
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500518
519 new_depends = {}
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500520 deps = bb.utils.explode_dep_versions2(d.getVar(varname) or "")
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500521 for depend in deps:
522 new_depend = get_package_mapping(depend, pkg, d)
523 new_depends[new_depend] = deps[depend]
524
525 d.setVar(varname, bb.utils.join_deps(new_depends, commasep=False))
526
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500527 #bb.note("%s after: %s" % (varname, d.getVar(varname)))
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500528
529#
530# Package functions suitable for inclusion in PACKAGEFUNCS
531#
532
533python package_get_auto_pr() {
534 import oe.prservice
535 import re
536
537 # Support per recipe PRSERV_HOST
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500538 pn = d.getVar('PN')
539 host = d.getVar("PRSERV_HOST_" + pn)
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500540 if not (host is None):
541 d.setVar("PRSERV_HOST", host)
542
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500543 pkgv = d.getVar("PKGV")
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500544
545 # PR Server not active, handle AUTOINC
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500546 if not d.getVar('PRSERV_HOST'):
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500547 if 'AUTOINC' in pkgv:
548 d.setVar("PKGV", pkgv.replace("AUTOINC", "0"))
549 return
550
551 auto_pr = None
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500552 pv = d.getVar("PV")
553 version = d.getVar("PRAUTOINX")
554 pkgarch = d.getVar("PACKAGE_ARCH")
555 checksum = d.getVar("BB_TASKHASH")
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500556
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500557 if d.getVar('PRSERV_LOCKDOWN'):
558 auto_pr = d.getVar('PRAUTO_' + version + '_' + pkgarch) or d.getVar('PRAUTO_' + version) or None
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500559 if auto_pr is None:
560 bb.fatal("Can NOT get PRAUTO from lockdown exported file")
561 d.setVar('PRAUTO',str(auto_pr))
562 return
563
564 try:
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500565 conn = d.getVar("__PRSERV_CONN")
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500566 if conn is None:
567 conn = oe.prservice.prserv_make_conn(d)
568 if conn is not None:
569 if "AUTOINC" in pkgv:
570 srcpv = bb.fetch2.get_srcrev(d)
571 base_ver = "AUTOINC-%s" % version[:version.find(srcpv)]
572 value = conn.getPR(base_ver, pkgarch, srcpv)
573 d.setVar("PKGV", pkgv.replace("AUTOINC", str(value)))
574
575 auto_pr = conn.getPR(version, pkgarch, checksum)
576 except Exception as e:
577 bb.fatal("Can NOT get PRAUTO, exception %s" % str(e))
578 if auto_pr is None:
579 bb.fatal("Can NOT get PRAUTO from remote PR service")
580 d.setVar('PRAUTO',str(auto_pr))
581}
582
583LOCALEBASEPN ??= "${PN}"
584
585python package_do_split_locales() {
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500586 if (d.getVar('PACKAGE_NO_LOCALE') == '1'):
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500587 bb.debug(1, "package requested not splitting locales")
588 return
589
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500590 packages = (d.getVar('PACKAGES') or "").split()
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500591
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500592 datadir = d.getVar('datadir')
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500593 if not datadir:
594 bb.note("datadir not defined")
595 return
596
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500597 dvar = d.getVar('PKGD')
598 pn = d.getVar('LOCALEBASEPN')
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500599
600 if pn + '-locale' in packages:
601 packages.remove(pn + '-locale')
602
603 localedir = os.path.join(dvar + datadir, 'locale')
604
605 if not cpath.isdir(localedir):
606 bb.debug(1, "No locale files in this package")
607 return
608
609 locales = os.listdir(localedir)
610
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500611 summary = d.getVar('SUMMARY') or pn
612 description = d.getVar('DESCRIPTION') or ""
613 locale_section = d.getVar('LOCALE_SECTION')
614 mlprefix = d.getVar('MLPREFIX') or ""
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500615 for l in sorted(locales):
616 ln = legitimize_package_name(l)
617 pkg = pn + '-locale-' + ln
618 packages.append(pkg)
619 d.setVar('FILES_' + pkg, os.path.join(datadir, 'locale', l))
620 d.setVar('RRECOMMENDS_' + pkg, '%svirtual-locale-%s' % (mlprefix, ln))
621 d.setVar('RPROVIDES_' + pkg, '%s-locale %s%s-translation' % (pn, mlprefix, ln))
622 d.setVar('SUMMARY_' + pkg, '%s - %s translations' % (summary, l))
623 d.setVar('DESCRIPTION_' + pkg, '%s This package contains language translation files for the %s locale.' % (description, l))
624 if locale_section:
625 d.setVar('SECTION_' + pkg, locale_section)
626
627 d.setVar('PACKAGES', ' '.join(packages))
628
629 # Disabled by RP 18/06/07
630 # Wildcards aren't supported in debian
631 # They break with ipkg since glibc-locale* will mean that
632 # glibc-localedata-translit* won't install as a dependency
633 # for some other package which breaks meta-toolchain
634 # Probably breaks since virtual-locale- isn't provided anywhere
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500635 #rdep = (d.getVar('RDEPENDS_%s' % pn) or "").split()
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500636 #rdep.append('%s-locale*' % pn)
637 #d.setVar('RDEPENDS_%s' % pn, ' '.join(rdep))
638}
639
640python perform_packagecopy () {
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800641 import subprocess
642
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500643 dest = d.getVar('D')
644 dvar = d.getVar('PKGD')
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500645
646 # Start by package population by taking a copy of the installed
647 # files to operate on
648 # Preserve sparse files and hard links
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800649 cmd = 'tar -cf - -C %s -p -S . | tar -xf - -C %s' % (dest, dvar)
650 subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT)
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500651
652 # replace RPATHs for the nativesdk binaries, to make them relocatable
653 if bb.data.inherits_class('nativesdk', d) or bb.data.inherits_class('cross-canadian', d):
654 rpath_replace (dvar, d)
655}
656perform_packagecopy[cleandirs] = "${PKGD}"
657perform_packagecopy[dirs] = "${PKGD}"
658
659# We generate a master list of directories to process, we start by
660# seeding this list with reasonable defaults, then load from
661# the fs-perms.txt files
662python fixup_perms () {
663 import pwd, grp
664
665 # init using a string with the same format as a line as documented in
666 # the fs-perms.txt file
667 # <path> <mode> <uid> <gid> <walk> <fmode> <fuid> <fgid>
668 # <path> link <link target>
669 #
670 # __str__ can be used to print out an entry in the input format
671 #
672 # if fs_perms_entry.path is None:
Brad Bishop316dfdd2018-06-25 12:45:53 -0400673 # an error occurred
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500674 # if fs_perms_entry.link, you can retrieve:
675 # fs_perms_entry.path = path
676 # fs_perms_entry.link = target of link
677 # if not fs_perms_entry.link, you can retrieve:
678 # fs_perms_entry.path = path
679 # fs_perms_entry.mode = expected dir mode or None
680 # fs_perms_entry.uid = expected uid or -1
681 # fs_perms_entry.gid = expected gid or -1
682 # fs_perms_entry.walk = 'true' or something else
683 # fs_perms_entry.fmode = expected file mode or None
684 # fs_perms_entry.fuid = expected file uid or -1
685 # fs_perms_entry_fgid = expected file gid or -1
686 class fs_perms_entry():
687 def __init__(self, line):
688 lsplit = line.split()
689 if len(lsplit) == 3 and lsplit[1].lower() == "link":
690 self._setlink(lsplit[0], lsplit[2])
691 elif len(lsplit) == 8:
692 self._setdir(lsplit[0], lsplit[1], lsplit[2], lsplit[3], lsplit[4], lsplit[5], lsplit[6], lsplit[7])
693 else:
694 msg = "Fixup Perms: invalid config line %s" % line
695 package_qa_handle_error("perm-config", msg, d)
696 self.path = None
697 self.link = None
698
699 def _setdir(self, path, mode, uid, gid, walk, fmode, fuid, fgid):
700 self.path = os.path.normpath(path)
701 self.link = None
702 self.mode = self._procmode(mode)
703 self.uid = self._procuid(uid)
704 self.gid = self._procgid(gid)
705 self.walk = walk.lower()
706 self.fmode = self._procmode(fmode)
707 self.fuid = self._procuid(fuid)
708 self.fgid = self._procgid(fgid)
709
710 def _setlink(self, path, link):
711 self.path = os.path.normpath(path)
712 self.link = link
713
714 def _procmode(self, mode):
715 if not mode or (mode and mode == "-"):
716 return None
717 else:
718 return int(mode,8)
719
720 # Note uid/gid -1 has special significance in os.lchown
721 def _procuid(self, uid):
722 if uid is None or uid == "-":
723 return -1
724 elif uid.isdigit():
725 return int(uid)
726 else:
727 return pwd.getpwnam(uid).pw_uid
728
729 def _procgid(self, gid):
730 if gid is None or gid == "-":
731 return -1
732 elif gid.isdigit():
733 return int(gid)
734 else:
735 return grp.getgrnam(gid).gr_gid
736
737 # Use for debugging the entries
738 def __str__(self):
739 if self.link:
740 return "%s link %s" % (self.path, self.link)
741 else:
742 mode = "-"
743 if self.mode:
744 mode = "0%o" % self.mode
745 fmode = "-"
746 if self.fmode:
747 fmode = "0%o" % self.fmode
748 uid = self._mapugid(self.uid)
749 gid = self._mapugid(self.gid)
750 fuid = self._mapugid(self.fuid)
751 fgid = self._mapugid(self.fgid)
752 return "%s %s %s %s %s %s %s %s" % (self.path, mode, uid, gid, self.walk, fmode, fuid, fgid)
753
754 def _mapugid(self, id):
755 if id is None or id == -1:
756 return "-"
757 else:
758 return "%d" % id
759
760 # Fix the permission, owner and group of path
761 def fix_perms(path, mode, uid, gid, dir):
762 if mode and not os.path.islink(path):
763 #bb.note("Fixup Perms: chmod 0%o %s" % (mode, dir))
764 os.chmod(path, mode)
765 # -1 is a special value that means don't change the uid/gid
766 # if they are BOTH -1, don't bother to lchown
767 if not (uid == -1 and gid == -1):
768 #bb.note("Fixup Perms: lchown %d:%d %s" % (uid, gid, dir))
769 os.lchown(path, uid, gid)
770
771 # Return a list of configuration files based on either the default
772 # files/fs-perms.txt or the contents of FILESYSTEM_PERMS_TABLES
773 # paths are resolved via BBPATH
774 def get_fs_perms_list(d):
775 str = ""
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500776 bbpath = d.getVar('BBPATH')
Brad Bishopd7bf8c12018-02-25 22:55:05 -0500777 fs_perms_tables = d.getVar('FILESYSTEM_PERMS_TABLES') or ""
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500778 for conf_file in fs_perms_tables.split():
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800779 confpath = bb.utils.which(bbpath, conf_file)
780 if confpath:
781 str += " %s" % bb.utils.which(bbpath, conf_file)
782 else:
783 bb.warn("cannot find %s specified in FILESYSTEM_PERMS_TABLES" % conf_file)
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500784 return str
785
786
787
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500788 dvar = d.getVar('PKGD')
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500789
790 fs_perms_table = {}
Patrick Williamsd8c66bc2016-06-20 12:57:21 -0500791 fs_link_table = {}
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500792
793 # By default all of the standard directories specified in
794 # bitbake.conf will get 0755 root:root.
795 target_path_vars = [ 'base_prefix',
796 'prefix',
797 'exec_prefix',
798 'base_bindir',
799 'base_sbindir',
800 'base_libdir',
801 'datadir',
802 'sysconfdir',
803 'servicedir',
804 'sharedstatedir',
805 'localstatedir',
806 'infodir',
807 'mandir',
808 'docdir',
809 'bindir',
810 'sbindir',
811 'libexecdir',
812 'libdir',
813 'includedir',
814 'oldincludedir' ]
815
816 for path in target_path_vars:
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500817 dir = d.getVar(path) or ""
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500818 if dir == "":
819 continue
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500820 fs_perms_table[dir] = fs_perms_entry(d.expand("%s 0755 root root false - - -" % (dir)))
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500821
822 # Now we actually load from the configuration files
823 for conf in get_fs_perms_list(d).split():
824 if os.path.exists(conf):
825 f = open(conf)
826 for line in f:
827 if line.startswith('#'):
828 continue
829 lsplit = line.split()
830 if len(lsplit) == 0:
831 continue
832 if len(lsplit) != 8 and not (len(lsplit) == 3 and lsplit[1].lower() == "link"):
833 msg = "Fixup perms: %s invalid line: %s" % (conf, line)
834 package_qa_handle_error("perm-line", msg, d)
835 continue
836 entry = fs_perms_entry(d.expand(line))
837 if entry and entry.path:
Patrick Williamsd8c66bc2016-06-20 12:57:21 -0500838 if entry.link:
839 fs_link_table[entry.path] = entry
840 if entry.path in fs_perms_table:
841 fs_perms_table.pop(entry.path)
842 else:
843 fs_perms_table[entry.path] = entry
844 if entry.path in fs_link_table:
845 fs_link_table.pop(entry.path)
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500846 f.close()
847
848 # Debug -- list out in-memory table
849 #for dir in fs_perms_table:
850 # bb.note("Fixup Perms: %s: %s" % (dir, str(fs_perms_table[dir])))
Patrick Williamsd8c66bc2016-06-20 12:57:21 -0500851 #for link in fs_link_table:
852 # bb.note("Fixup Perms: %s: %s" % (link, str(fs_link_table[link])))
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500853
854 # We process links first, so we can go back and fixup directory ownership
855 # for any newly created directories
Patrick Williamsd8c66bc2016-06-20 12:57:21 -0500856 # Process in sorted order so /run gets created before /run/lock, etc.
857 for entry in sorted(fs_link_table.values(), key=lambda x: x.link):
858 link = entry.link
859 dir = entry.path
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500860 origin = dvar + dir
861 if not (cpath.exists(origin) and cpath.isdir(origin) and not cpath.islink(origin)):
862 continue
863
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500864 if link[0] == "/":
865 target = dvar + link
866 ptarget = link
867 else:
868 target = os.path.join(os.path.dirname(origin), link)
869 ptarget = os.path.join(os.path.dirname(dir), link)
870 if os.path.exists(target):
871 msg = "Fixup Perms: Unable to correct directory link, target already exists: %s -> %s" % (dir, ptarget)
872 package_qa_handle_error("perm-link", msg, d)
873 continue
874
875 # Create path to move directory to, move it, and then setup the symlink
876 bb.utils.mkdirhier(os.path.dirname(target))
877 #bb.note("Fixup Perms: Rename %s -> %s" % (dir, ptarget))
878 os.rename(origin, target)
879 #bb.note("Fixup Perms: Link %s -> %s" % (dir, link))
880 os.symlink(link, origin)
881
882 for dir in fs_perms_table:
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500883 origin = dvar + dir
884 if not (cpath.exists(origin) and cpath.isdir(origin)):
885 continue
886
887 fix_perms(origin, fs_perms_table[dir].mode, fs_perms_table[dir].uid, fs_perms_table[dir].gid, dir)
888
889 if fs_perms_table[dir].walk == 'true':
890 for root, dirs, files in os.walk(origin):
891 for dr in dirs:
892 each_dir = os.path.join(root, dr)
893 fix_perms(each_dir, fs_perms_table[dir].mode, fs_perms_table[dir].uid, fs_perms_table[dir].gid, dir)
894 for f in files:
895 each_file = os.path.join(root, f)
896 fix_perms(each_file, fs_perms_table[dir].fmode, fs_perms_table[dir].fuid, fs_perms_table[dir].fgid, dir)
897}
898
899python split_and_strip_files () {
900 import stat, errno
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800901 import subprocess
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500902
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500903 dvar = d.getVar('PKGD')
904 pn = d.getVar('PN')
Brad Bishop316dfdd2018-06-25 12:45:53 -0400905 targetos = d.getVar('TARGET_OS')
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500906
Patrick Williamsc0f7c042017-02-23 20:41:17 -0600907 oldcwd = os.getcwd()
908 os.chdir(dvar)
909
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500910 # We default to '.debug' style
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500911 if d.getVar('PACKAGE_DEBUG_SPLIT_STYLE') == 'debug-file-directory':
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500912 # Single debug-file-directory style debug info
913 debugappend = ".debug"
914 debugdir = ""
915 debuglibdir = "/usr/lib/debug"
916 debugsrcdir = "/usr/src/debug"
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500917 elif d.getVar('PACKAGE_DEBUG_SPLIT_STYLE') == 'debug-without-src':
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500918 # Original OE-core, a.k.a. ".debug", style debug info, but without sources in /usr/src/debug
919 debugappend = ""
920 debugdir = "/.debug"
921 debuglibdir = ""
922 debugsrcdir = ""
Brad Bishopd7bf8c12018-02-25 22:55:05 -0500923 elif d.getVar('PACKAGE_DEBUG_SPLIT_STYLE') == 'debug-with-srcpkg':
924 debugappend = ""
925 debugdir = "/.debug"
926 debuglibdir = ""
927 debugsrcdir = "/usr/src/debug"
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500928 else:
929 # Original OE-core, a.k.a. ".debug", style debug info
930 debugappend = ""
931 debugdir = "/.debug"
932 debuglibdir = ""
933 debugsrcdir = "/usr/src/debug"
934
935 sourcefile = d.expand("${WORKDIR}/debugsources.list")
936 bb.utils.remove(sourcefile)
937
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500938 #
939 # First lets figure out all of the files we may have to process ... do this only once!
940 #
941 elffiles = {}
942 symlinks = {}
943 kernmods = []
Brad Bishop316dfdd2018-06-25 12:45:53 -0400944 staticlibs = []
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500945 inodes = {}
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500946 libdir = os.path.abspath(dvar + os.sep + d.getVar("libdir"))
947 baselibdir = os.path.abspath(dvar + os.sep + d.getVar("base_libdir"))
Brad Bishop316dfdd2018-06-25 12:45:53 -0400948 skipfiles = (d.getVar("INHIBIT_PACKAGE_STRIP_FILES") or "").split()
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500949 if (d.getVar('INHIBIT_PACKAGE_STRIP') != '1' or \
950 d.getVar('INHIBIT_PACKAGE_DEBUG_SPLIT') != '1'):
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800951 checkelf = {}
952 checkelflinks = {}
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500953 for root, dirs, files in cpath.walk(dvar):
954 for f in files:
955 file = os.path.join(root, f)
956 if file.endswith(".ko") and file.find("/lib/modules/") != -1:
957 kernmods.append(file)
958 continue
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800959 if oe.package.is_static_lib(file):
Brad Bishop316dfdd2018-06-25 12:45:53 -0400960 staticlibs.append(file)
961 continue
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500962
963 # Skip debug files
964 if debugappend and file.endswith(debugappend):
965 continue
966 if debugdir and debugdir in os.path.dirname(file[len(dvar):]):
967 continue
968
Brad Bishop316dfdd2018-06-25 12:45:53 -0400969 if file in skipfiles:
970 continue
971
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500972 try:
973 ltarget = cpath.realpath(file, dvar, False)
974 s = cpath.lstat(ltarget)
975 except OSError as e:
976 (err, strerror) = e.args
977 if err != errno.ENOENT:
978 raise
979 # Skip broken symlinks
980 continue
981 if not s:
982 continue
Brad Bishop316dfdd2018-06-25 12:45:53 -0400983 # Check its an executable
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500984 if (s[stat.ST_MODE] & stat.S_IXUSR) or (s[stat.ST_MODE] & stat.S_IXGRP) or (s[stat.ST_MODE] & stat.S_IXOTH) \
Patrick Williamsd8c66bc2016-06-20 12:57:21 -0500985 or ((file.startswith(libdir) or file.startswith(baselibdir)) and (".so" in f or ".node" in f)):
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800986
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500987 if cpath.islink(file):
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800988 checkelflinks[file] = ltarget
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500989 continue
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800990 # Use a reference of device ID and inode number to identify files
991 file_reference = "%d_%d" % (s.st_dev, s.st_ino)
992 checkelf[file] = (file, file_reference)
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500993
Brad Bishop1a4b7ee2018-12-16 17:11:34 -0800994 results = oe.utils.multiprocess_launch(oe.package.is_elf, checkelflinks.values(), d)
995 results_map = {}
996 for (ltarget, elf_file) in results:
997 results_map[ltarget] = elf_file
998 for file in checkelflinks:
999 ltarget = checkelflinks[file]
1000 # If it's a symlink, and points to an ELF file, we capture the readlink target
1001 if results_map[ltarget]:
1002 target = os.readlink(file)
1003 #bb.note("Sym: %s (%d)" % (ltarget, results_map[ltarget]))
1004 symlinks[file] = target
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001005
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001006 results = oe.utils.multiprocess_launch(oe.package.is_elf, checkelf.keys(), d)
1007 for (file, elf_file) in results:
1008 # It's a file (or hardlink), not a link
1009 # ...but is it ELF, and is it already stripped?
1010 if elf_file & 1:
1011 if elf_file & 2:
1012 if 'already-stripped' in (d.getVar('INSANE_SKIP_' + pn) or "").split():
1013 bb.note("Skipping file %s from %s for already-stripped QA test" % (file[len(dvar):], pn))
1014 else:
1015 msg = "File '%s' from %s was already stripped, this will prevent future debugging!" % (file[len(dvar):], pn)
1016 package_qa_handle_error("already-stripped", msg, d)
1017 continue
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001018
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001019 # At this point we have an unstripped elf file. We need to:
1020 # a) Make sure any file we strip is not hardlinked to anything else outside this tree
1021 # b) Only strip any hardlinked file once (no races)
1022 # c) Track any hardlinks between files so that we can reconstruct matching debug file hardlinks
1023
1024 # Use a reference of device ID and inode number to identify files
1025 file_reference = checkelf[file][1]
1026 if file_reference in inodes:
1027 os.unlink(file)
1028 os.link(inodes[file_reference][0], file)
1029 inodes[file_reference].append(file)
1030 else:
1031 inodes[file_reference] = [file]
1032 # break hardlink
1033 bb.utils.break_hardlinks(file)
1034 elffiles[file] = elf_file
1035 # Modified the file so clear the cache
1036 cpath.updatecache(file)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001037
1038 #
1039 # First lets process debug splitting
1040 #
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001041 if (d.getVar('INHIBIT_PACKAGE_DEBUG_SPLIT') != '1'):
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001042 oe.utils.multiprocess_launch(splitdebuginfo, list(elffiles), d, extraargs=(dvar, debugdir, debuglibdir, debugappend, debugsrcdir, sourcefile, d))
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001043
Brad Bishop316dfdd2018-06-25 12:45:53 -04001044 if debugsrcdir and not targetos.startswith("mingw"):
1045 for file in staticlibs:
1046 append_source_info(file, sourcefile, d, fatal=False)
1047
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001048 # Hardlink our debug symbols to the other hardlink copies
1049 for ref in inodes:
1050 if len(inodes[ref]) == 1:
1051 continue
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001052
1053 target = inodes[ref][0][len(dvar):]
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001054 for file in inodes[ref][1:]:
1055 src = file[len(dvar):]
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001056 dest = debuglibdir + os.path.dirname(src) + debugdir + "/" + os.path.basename(target) + debugappend
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001057 fpath = dvar + dest
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001058 ftarget = dvar + debuglibdir + os.path.dirname(target) + debugdir + "/" + os.path.basename(target) + debugappend
1059 bb.utils.mkdirhier(os.path.dirname(fpath))
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001060 # Only one hardlink of separated debug info file in each directory
1061 if not os.access(fpath, os.R_OK):
1062 #bb.note("Link %s -> %s" % (fpath, ftarget))
1063 os.link(ftarget, fpath)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001064
1065 # Create symlinks for all cases we were able to split symbols
1066 for file in symlinks:
1067 src = file[len(dvar):]
1068 dest = debuglibdir + os.path.dirname(src) + debugdir + "/" + os.path.basename(src) + debugappend
1069 fpath = dvar + dest
1070 # Skip it if the target doesn't exist
1071 try:
1072 s = os.stat(fpath)
1073 except OSError as e:
1074 (err, strerror) = e.args
1075 if err != errno.ENOENT:
1076 raise
1077 continue
1078
1079 ltarget = symlinks[file]
1080 lpath = os.path.dirname(ltarget)
1081 lbase = os.path.basename(ltarget)
1082 ftarget = ""
1083 if lpath and lpath != ".":
1084 ftarget += lpath + debugdir + "/"
1085 ftarget += lbase + debugappend
1086 if lpath.startswith(".."):
1087 ftarget = os.path.join("..", ftarget)
1088 bb.utils.mkdirhier(os.path.dirname(fpath))
1089 #bb.note("Symlink %s -> %s" % (fpath, ftarget))
1090 os.symlink(ftarget, fpath)
1091
1092 # Process the debugsrcdir if requested...
1093 # This copies and places the referenced sources for later debugging...
1094 copydebugsources(debugsrcdir, d)
1095 #
1096 # End of debug splitting
1097 #
1098
1099 #
1100 # Now lets go back over things and strip them
1101 #
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001102 if (d.getVar('INHIBIT_PACKAGE_STRIP') != '1'):
1103 strip = d.getVar("STRIP")
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001104 sfiles = []
1105 for file in elffiles:
1106 elf_file = int(elffiles[file])
1107 #bb.note("Strip %s" % file)
1108 sfiles.append((file, elf_file, strip))
1109 for f in kernmods:
1110 sfiles.append((f, 16, strip))
1111
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001112 oe.utils.multiprocess_launch(oe.package.runstrip, sfiles, d)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001113
1114 #
1115 # End of strip
1116 #
Patrick Williamsc0f7c042017-02-23 20:41:17 -06001117 os.chdir(oldcwd)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001118}
1119
1120python populate_packages () {
1121 import glob, re
1122
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001123 workdir = d.getVar('WORKDIR')
1124 outdir = d.getVar('DEPLOY_DIR')
1125 dvar = d.getVar('PKGD')
1126 packages = d.getVar('PACKAGES')
1127 pn = d.getVar('PN')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001128
1129 bb.utils.mkdirhier(outdir)
1130 os.chdir(dvar)
Patrick Williamsd8c66bc2016-06-20 12:57:21 -05001131
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001132 autodebug = not (d.getVar("NOAUTOPACKAGEDEBUG") or False)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001133
Brad Bishopd7bf8c12018-02-25 22:55:05 -05001134 split_source_package = (d.getVar('PACKAGE_DEBUG_SPLIT_STYLE') == 'debug-with-srcpkg')
1135
1136 # If debug-with-srcpkg mode is enabled then the src package is added
1137 # into the package list and the source directory as its main content
1138 if split_source_package:
1139 src_package_name = ('%s-src' % d.getVar('PN'))
1140 packages += (' ' + src_package_name)
1141 d.setVar('FILES_%s' % src_package_name, '/usr/src/debug')
1142
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001143 # Sanity check PACKAGES for duplicates
Brad Bishop316dfdd2018-06-25 12:45:53 -04001144 # Sanity should be moved to sanity.bbclass once we have the infrastructure
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001145 package_dict = {}
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001146
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001147 for i, pkg in enumerate(packages.split()):
1148 if pkg in package_dict:
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001149 msg = "%s is listed in PACKAGES multiple times, this leads to packaging errors." % pkg
1150 package_qa_handle_error("packages-list", msg, d)
Brad Bishopd7bf8c12018-02-25 22:55:05 -05001151 # If debug-with-srcpkg mode is enabled then the src package will have
1152 # priority over dbg package when assigning the files.
1153 # This allows src package to include source files and remove them from dbg.
1154 elif split_source_package and pkg.endswith("-src"):
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001155 package_dict[pkg] = (10, i)
1156 elif autodebug and pkg.endswith("-dbg"):
1157 package_dict[pkg] = (30, i)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001158 else:
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001159 package_dict[pkg] = (50, i)
1160 package_list = sorted(package_dict.keys(), key=package_dict.get)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001161 d.setVar('PACKAGES', ' '.join(package_list))
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001162 pkgdest = d.getVar('PKGDEST')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001163
1164 seen = []
1165
1166 # os.mkdir masks the permissions with umask so we have to unset it first
1167 oldumask = os.umask(0)
1168
Patrick Williamsd8c66bc2016-06-20 12:57:21 -05001169 debug = []
1170 for root, dirs, files in cpath.walk(dvar):
1171 dir = root[len(dvar):]
1172 if not dir:
1173 dir = os.sep
1174 for f in (files + dirs):
1175 path = "." + os.path.join(dir, f)
1176 if "/.debug/" in path or path.endswith("/.debug"):
1177 debug.append(path)
1178
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001179 for pkg in package_list:
1180 root = os.path.join(pkgdest, pkg)
1181 bb.utils.mkdirhier(root)
1182
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001183 filesvar = d.getVar('FILES_%s' % pkg) or ""
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001184 if "//" in filesvar:
1185 msg = "FILES variable for package %s contains '//' which is invalid. Attempting to fix this but you should correct the metadata.\n" % pkg
1186 package_qa_handle_error("files-invalid", msg, d)
1187 filesvar.replace("//", "/")
1188
1189 origfiles = filesvar.split()
Patrick Williamsc0f7c042017-02-23 20:41:17 -06001190 files, symlink_paths = files_from_filevars(origfiles)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001191
Patrick Williamsd8c66bc2016-06-20 12:57:21 -05001192 if autodebug and pkg.endswith("-dbg"):
1193 files.extend(debug)
1194
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001195 for file in files:
1196 if (not cpath.islink(file)) and (not cpath.exists(file)):
1197 continue
1198 if file in seen:
1199 continue
1200 seen.append(file)
1201
1202 def mkdir(src, dest, p):
1203 src = os.path.join(src, p)
1204 dest = os.path.join(dest, p)
1205 fstat = cpath.stat(src)
1206 os.mkdir(dest, fstat.st_mode)
1207 os.chown(dest, fstat.st_uid, fstat.st_gid)
1208 if p not in seen:
1209 seen.append(p)
1210 cpath.updatecache(dest)
1211
1212 def mkdir_recurse(src, dest, paths):
1213 if cpath.exists(dest + '/' + paths):
1214 return
1215 while paths.startswith("./"):
1216 paths = paths[2:]
1217 p = "."
1218 for c in paths.split("/"):
1219 p = os.path.join(p, c)
1220 if not cpath.exists(os.path.join(dest, p)):
1221 mkdir(src, dest, p)
1222
1223 if cpath.isdir(file) and not cpath.islink(file):
1224 mkdir_recurse(dvar, root, file)
1225 continue
1226
1227 mkdir_recurse(dvar, root, os.path.dirname(file))
1228 fpath = os.path.join(root,file)
1229 if not cpath.islink(file):
1230 os.link(file, fpath)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001231 continue
1232 ret = bb.utils.copyfile(file, fpath)
1233 if ret is False or ret == 0:
Patrick Williamsc0f7c042017-02-23 20:41:17 -06001234 bb.fatal("File population failed")
1235
1236 # Check if symlink paths exist
1237 for file in symlink_paths:
1238 if not os.path.exists(os.path.join(root,file)):
1239 bb.fatal("File '%s' cannot be packaged into '%s' because its "
1240 "parent directory structure does not exist. One of "
1241 "its parent directories is a symlink whose target "
1242 "directory is not included in the package." %
1243 (file, pkg))
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001244
1245 os.umask(oldumask)
1246 os.chdir(workdir)
1247
1248 # Handle LICENSE_EXCLUSION
1249 package_list = []
1250 for pkg in packages.split():
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001251 if d.getVar('LICENSE_EXCLUSION-' + pkg):
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001252 msg = "%s has an incompatible license. Excluding from packaging." % pkg
1253 package_qa_handle_error("incompatible-license", msg, d)
1254 else:
1255 package_list.append(pkg)
1256 d.setVar('PACKAGES', ' '.join(package_list))
1257
1258 unshipped = []
1259 for root, dirs, files in cpath.walk(dvar):
1260 dir = root[len(dvar):]
1261 if not dir:
1262 dir = os.sep
1263 for f in (files + dirs):
1264 path = os.path.join(dir, f)
1265 if ('.' + path) not in seen:
1266 unshipped.append(path)
1267
1268 if unshipped != []:
1269 msg = pn + ": Files/directories were installed but not shipped in any package:"
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001270 if "installed-vs-shipped" in (d.getVar('INSANE_SKIP_' + pn) or "").split():
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001271 bb.note("Package %s skipping QA tests: installed-vs-shipped" % pn)
1272 else:
1273 for f in unshipped:
1274 msg = msg + "\n " + f
Patrick Williamsf1e5d692016-03-30 15:21:19 -05001275 msg = msg + "\nPlease set FILES such that these items are packaged. Alternatively if they are unneeded, avoid installing them or delete them within do_install.\n"
1276 msg = msg + "%s: %d installed and not shipped files." % (pn, len(unshipped))
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001277 package_qa_handle_error("installed-vs-shipped", msg, d)
1278}
1279populate_packages[dirs] = "${D}"
1280
1281python package_fixsymlinks () {
1282 import errno
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001283 pkgdest = d.getVar('PKGDEST')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001284 packages = d.getVar("PACKAGES", False).split()
1285
1286 dangling_links = {}
1287 pkg_files = {}
1288 for pkg in packages:
1289 dangling_links[pkg] = []
1290 pkg_files[pkg] = []
1291 inst_root = os.path.join(pkgdest, pkg)
1292 for path in pkgfiles[pkg]:
1293 rpath = path[len(inst_root):]
1294 pkg_files[pkg].append(rpath)
1295 rtarget = cpath.realpath(path, inst_root, True, assume_dir = True)
1296 if not cpath.lexists(rtarget):
1297 dangling_links[pkg].append(os.path.normpath(rtarget[len(inst_root):]))
1298
1299 newrdepends = {}
1300 for pkg in dangling_links:
1301 for l in dangling_links[pkg]:
1302 found = False
1303 bb.debug(1, "%s contains dangling link %s" % (pkg, l))
1304 for p in packages:
1305 if l in pkg_files[p]:
1306 found = True
1307 bb.debug(1, "target found in %s" % p)
1308 if p == pkg:
1309 break
1310 if pkg not in newrdepends:
1311 newrdepends[pkg] = []
1312 newrdepends[pkg].append(p)
1313 break
1314 if found == False:
1315 bb.note("%s contains dangling symlink to %s" % (pkg, l))
1316
1317 for pkg in newrdepends:
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001318 rdepends = bb.utils.explode_dep_versions2(d.getVar('RDEPENDS_' + pkg) or "")
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001319 for p in newrdepends[pkg]:
1320 if p not in rdepends:
1321 rdepends[p] = []
1322 d.setVar('RDEPENDS_' + pkg, bb.utils.join_deps(rdepends, commasep=False))
1323}
1324
1325
1326python package_package_name_hook() {
1327 """
1328 A package_name_hook function can be used to rewrite the package names by
1329 changing PKG. For an example, see debian.bbclass.
1330 """
1331 pass
1332}
1333
1334EXPORT_FUNCTIONS package_name_hook
1335
1336
1337PKGDESTWORK = "${WORKDIR}/pkgdata"
1338
1339python emit_pkgdata() {
1340 from glob import glob
1341 import json
1342
Brad Bishop316dfdd2018-06-25 12:45:53 -04001343 def process_postinst_on_target(pkg, mlprefix):
1344 defer_fragment = """
1345if [ -n "$D" ]; then
1346 $INTERCEPT_DIR/postinst_intercept delay_to_first_boot %s mlprefix=%s
1347 exit 0
1348fi
1349""" % (pkg, mlprefix)
1350
1351 postinst = d.getVar('pkg_postinst_%s' % pkg)
1352 postinst_ontarget = d.getVar('pkg_postinst_ontarget_%s' % pkg)
1353
1354 if postinst_ontarget:
1355 bb.debug(1, 'adding deferred pkg_postinst_ontarget() to pkg_postinst() for %s' % pkg)
1356 if not postinst:
1357 postinst = '#!/bin/sh\n'
1358 postinst += defer_fragment
1359 postinst += postinst_ontarget
1360 d.setVar('pkg_postinst_%s' % pkg, postinst)
1361
1362 def add_set_e_to_scriptlets(pkg):
1363 for scriptlet_name in ('pkg_preinst', 'pkg_postinst', 'pkg_prerm', 'pkg_postrm'):
1364 scriptlet = d.getVar('%s_%s' % (scriptlet_name, pkg))
1365 if scriptlet:
1366 scriptlet_split = scriptlet.split('\n')
1367 if scriptlet_split[0].startswith("#!"):
1368 scriptlet = scriptlet_split[0] + "\nset -e\n" + "\n".join(scriptlet_split[1:])
1369 else:
1370 scriptlet = "set -e\n" + "\n".join(scriptlet_split[0:])
1371 d.setVar('%s_%s' % (scriptlet_name, pkg), scriptlet)
1372
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001373 def write_if_exists(f, pkg, var):
1374 def encode(str):
1375 import codecs
Patrick Williamsc0f7c042017-02-23 20:41:17 -06001376 c = codecs.getencoder("unicode_escape")
1377 return c(str)[0].decode("latin1")
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001378
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001379 val = d.getVar('%s_%s' % (var, pkg))
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001380 if val:
1381 f.write('%s_%s: %s\n' % (var, pkg, encode(val)))
1382 return val
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001383 val = d.getVar('%s' % (var))
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001384 if val:
1385 f.write('%s: %s\n' % (var, encode(val)))
1386 return val
1387
1388 def write_extra_pkgs(variants, pn, packages, pkgdatadir):
1389 for variant in variants:
1390 with open("%s/%s-%s" % (pkgdatadir, variant, pn), 'w') as fd:
1391 fd.write("PACKAGES: %s\n" % ' '.join(
1392 map(lambda pkg: '%s-%s' % (variant, pkg), packages.split())))
1393
1394 def write_extra_runtime_pkgs(variants, packages, pkgdatadir):
1395 for variant in variants:
1396 for pkg in packages.split():
1397 ml_pkg = "%s-%s" % (variant, pkg)
1398 subdata_file = "%s/runtime/%s" % (pkgdatadir, ml_pkg)
1399 with open(subdata_file, 'w') as fd:
1400 fd.write("PKG_%s: %s" % (ml_pkg, pkg))
1401
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001402 packages = d.getVar('PACKAGES')
1403 pkgdest = d.getVar('PKGDEST')
1404 pkgdatadir = d.getVar('PKGDESTWORK')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001405
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001406 data_file = pkgdatadir + d.expand("/${PN}" )
1407 f = open(data_file, 'w')
1408 f.write("PACKAGES: %s\n" % packages)
1409 f.close()
1410
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001411 pn = d.getVar('PN')
1412 global_variants = (d.getVar('MULTILIB_GLOBAL_VARIANTS') or "").split()
1413 variants = (d.getVar('MULTILIB_VARIANTS') or "").split()
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001414
1415 if bb.data.inherits_class('kernel', d) or bb.data.inherits_class('module-base', d):
1416 write_extra_pkgs(variants, pn, packages, pkgdatadir)
1417
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001418 if bb.data.inherits_class('allarch', d) and not variants \
1419 and not bb.data.inherits_class('packagegroup', d):
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001420 write_extra_pkgs(global_variants, pn, packages, pkgdatadir)
1421
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001422 workdir = d.getVar('WORKDIR')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001423
1424 for pkg in packages.split():
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001425 pkgval = d.getVar('PKG_%s' % pkg)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001426 if pkgval is None:
1427 pkgval = pkg
1428 d.setVar('PKG_%s' % pkg, pkg)
1429
1430 pkgdestpkg = os.path.join(pkgdest, pkg)
1431 files = {}
1432 total_size = 0
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001433 seen = set()
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001434 for f in pkgfiles[pkg]:
1435 relpth = os.path.relpath(f, pkgdestpkg)
1436 fstat = os.lstat(f)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001437 files[os.sep + relpth] = fstat.st_size
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001438 if fstat.st_ino not in seen:
1439 seen.add(fstat.st_ino)
1440 total_size += fstat.st_size
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001441 d.setVar('FILES_INFO', json.dumps(files))
1442
1443 subdata_file = pkgdatadir + "/runtime/%s" % pkg
1444 sf = open(subdata_file, 'w')
1445 write_if_exists(sf, pkg, 'PN')
1446 write_if_exists(sf, pkg, 'PE')
1447 write_if_exists(sf, pkg, 'PV')
1448 write_if_exists(sf, pkg, 'PR')
1449 write_if_exists(sf, pkg, 'PKGE')
1450 write_if_exists(sf, pkg, 'PKGV')
1451 write_if_exists(sf, pkg, 'PKGR')
1452 write_if_exists(sf, pkg, 'LICENSE')
1453 write_if_exists(sf, pkg, 'DESCRIPTION')
1454 write_if_exists(sf, pkg, 'SUMMARY')
1455 write_if_exists(sf, pkg, 'RDEPENDS')
1456 rprov = write_if_exists(sf, pkg, 'RPROVIDES')
1457 write_if_exists(sf, pkg, 'RRECOMMENDS')
1458 write_if_exists(sf, pkg, 'RSUGGESTS')
1459 write_if_exists(sf, pkg, 'RREPLACES')
1460 write_if_exists(sf, pkg, 'RCONFLICTS')
1461 write_if_exists(sf, pkg, 'SECTION')
1462 write_if_exists(sf, pkg, 'PKG')
1463 write_if_exists(sf, pkg, 'ALLOW_EMPTY')
1464 write_if_exists(sf, pkg, 'FILES')
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001465 write_if_exists(sf, pkg, 'CONFFILES')
Brad Bishop316dfdd2018-06-25 12:45:53 -04001466 process_postinst_on_target(pkg, d.getVar("MLPREFIX"))
1467 add_set_e_to_scriptlets(pkg)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001468 write_if_exists(sf, pkg, 'pkg_postinst')
1469 write_if_exists(sf, pkg, 'pkg_postrm')
1470 write_if_exists(sf, pkg, 'pkg_preinst')
1471 write_if_exists(sf, pkg, 'pkg_prerm')
1472 write_if_exists(sf, pkg, 'FILERPROVIDESFLIST')
1473 write_if_exists(sf, pkg, 'FILES_INFO')
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001474 for dfile in (d.getVar('FILERPROVIDESFLIST_' + pkg) or "").split():
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001475 write_if_exists(sf, pkg, 'FILERPROVIDES_' + dfile)
1476
1477 write_if_exists(sf, pkg, 'FILERDEPENDSFLIST')
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001478 for dfile in (d.getVar('FILERDEPENDSFLIST_' + pkg) or "").split():
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001479 write_if_exists(sf, pkg, 'FILERDEPENDS_' + dfile)
1480
1481 sf.write('%s_%s: %d\n' % ('PKGSIZE', pkg, total_size))
1482 sf.close()
1483
1484 # Symlinks needed for rprovides lookup
1485 if rprov:
1486 for p in rprov.strip().split():
1487 subdata_sym = pkgdatadir + "/runtime-rprovides/%s/%s" % (p, pkg)
1488 bb.utils.mkdirhier(os.path.dirname(subdata_sym))
1489 oe.path.symlink("../../runtime/%s" % pkg, subdata_sym, True)
1490
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001491 allow_empty = d.getVar('ALLOW_EMPTY_%s' % pkg)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001492 if not allow_empty:
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001493 allow_empty = d.getVar('ALLOW_EMPTY')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001494 root = "%s/%s" % (pkgdest, pkg)
1495 os.chdir(root)
1496 g = glob('*')
1497 if g or allow_empty == "1":
1498 # Symlinks needed for reverse lookups (from the final package name)
1499 subdata_sym = pkgdatadir + "/runtime-reverse/%s" % pkgval
1500 oe.path.symlink("../runtime/%s" % pkg, subdata_sym, True)
1501
1502 packagedfile = pkgdatadir + '/runtime/%s.packaged' % pkg
1503 open(packagedfile, 'w').close()
1504
1505 if bb.data.inherits_class('kernel', d) or bb.data.inherits_class('module-base', d):
1506 write_extra_runtime_pkgs(variants, packages, pkgdatadir)
1507
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001508 if bb.data.inherits_class('allarch', d) and not variants \
1509 and not bb.data.inherits_class('packagegroup', d):
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001510 write_extra_runtime_pkgs(global_variants, packages, pkgdatadir)
1511
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001512}
1513emit_pkgdata[dirs] = "${PKGDESTWORK}/runtime ${PKGDESTWORK}/runtime-reverse ${PKGDESTWORK}/runtime-rprovides"
1514
1515ldconfig_postinst_fragment() {
1516if [ x"$D" = "x" ]; then
1517 if [ -x /sbin/ldconfig ]; then /sbin/ldconfig ; fi
1518fi
1519}
1520
Brad Bishopd7bf8c12018-02-25 22:55:05 -05001521RPMDEPS = "${STAGING_LIBDIR_NATIVE}/rpm/rpmdeps --alldeps"
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001522
1523# Collect perfile run-time dependency metadata
1524# Output:
1525# FILERPROVIDESFLIST_pkg - list of all files w/ deps
1526# FILERPROVIDES_filepath_pkg - per file dep
1527#
1528# FILERDEPENDSFLIST_pkg - list of all files w/ deps
1529# FILERDEPENDS_filepath_pkg - per file dep
1530
1531python package_do_filedeps() {
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001532 if d.getVar('SKIP_FILEDEPS') == '1':
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001533 return
1534
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001535 pkgdest = d.getVar('PKGDEST')
1536 packages = d.getVar('PACKAGES')
1537 rpmdeps = d.getVar('RPMDEPS')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001538
1539 def chunks(files, n):
1540 return [files[i:i+n] for i in range(0, len(files), n)]
1541
1542 pkglist = []
1543 for pkg in packages.split():
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001544 if d.getVar('SKIP_FILEDEPS_' + pkg) == '1':
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001545 continue
Brad Bishopd7bf8c12018-02-25 22:55:05 -05001546 if pkg.endswith('-dbg') or pkg.endswith('-doc') or pkg.find('-locale-') != -1 or pkg.find('-localedata-') != -1 or pkg.find('-gconv-') != -1 or pkg.find('-charmap-') != -1 or pkg.startswith('kernel-module-') or pkg.endswith('-src'):
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001547 continue
1548 for files in chunks(pkgfiles[pkg], 100):
1549 pkglist.append((pkg, files, rpmdeps, pkgdest))
1550
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001551 processed = oe.utils.multiprocess_launch(oe.package.filedeprunner, pkglist, d)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001552
1553 provides_files = {}
1554 requires_files = {}
1555
1556 for result in processed:
1557 (pkg, provides, requires) = result
1558
1559 if pkg not in provides_files:
1560 provides_files[pkg] = []
1561 if pkg not in requires_files:
1562 requires_files[pkg] = []
1563
1564 for file in provides:
1565 provides_files[pkg].append(file)
1566 key = "FILERPROVIDES_" + file + "_" + pkg
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001567 d.appendVar(key, " " + " ".join(provides[file]))
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001568
1569 for file in requires:
1570 requires_files[pkg].append(file)
1571 key = "FILERDEPENDS_" + file + "_" + pkg
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001572 d.appendVar(key, " " + " ".join(requires[file]))
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001573
1574 for pkg in requires_files:
1575 d.setVar("FILERDEPENDSFLIST_" + pkg, " ".join(requires_files[pkg]))
1576 for pkg in provides_files:
1577 d.setVar("FILERPROVIDESFLIST_" + pkg, " ".join(provides_files[pkg]))
1578}
1579
1580SHLIBSDIRS = "${PKGDATA_DIR}/${MLPREFIX}shlibs2"
1581SHLIBSWORKDIR = "${PKGDESTWORK}/${MLPREFIX}shlibs2"
1582
1583python package_do_shlibs() {
1584 import re, pipes
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001585 import subprocess
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001586
Patrick Williamsc0f7c042017-02-23 20:41:17 -06001587 exclude_shlibs = d.getVar('EXCLUDE_FROM_SHLIBS', False)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001588 if exclude_shlibs:
1589 bb.note("not generating shlibs")
1590 return
1591
1592 lib_re = re.compile("^.*\.so")
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001593 libdir_re = re.compile(".*/%s$" % d.getVar('baselib'))
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001594
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001595 packages = d.getVar('PACKAGES')
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001596
1597 shlib_pkgs = []
1598 exclusion_list = d.getVar("EXCLUDE_PACKAGES_FROM_SHLIBS")
1599 if exclusion_list:
1600 for pkg in packages.split():
1601 if pkg not in exclusion_list.split():
1602 shlib_pkgs.append(pkg)
1603 else:
1604 bb.note("not generating shlibs for %s" % pkg)
1605 else:
1606 shlib_pkgs = packages.split()
1607
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001608 targetos = d.getVar('TARGET_OS')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001609
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001610 workdir = d.getVar('WORKDIR')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001611
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001612 ver = d.getVar('PKGV')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001613 if not ver:
1614 msg = "PKGV not defined"
1615 package_qa_handle_error("pkgv-undefined", msg, d)
1616 return
1617
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001618 pkgdest = d.getVar('PKGDEST')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001619
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001620 shlibswork_dir = d.getVar('SHLIBSWORKDIR')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001621
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001622 def linux_so(file, pkg, pkgver, d):
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001623 needs_ldconfig = False
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001624 needed = set()
1625 sonames = set()
1626 renames = []
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001627 ldir = os.path.dirname(file).replace(pkgdest + "/" + pkg, '')
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001628 cmd = d.getVar('OBJDUMP') + " -p " + pipes.quote(file) + " 2>/dev/null"
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001629 fd = os.popen(cmd)
1630 lines = fd.readlines()
1631 fd.close()
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001632 rpath = tuple()
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001633 for l in lines:
1634 m = re.match("\s+RPATH\s+([^\s]*)", l)
1635 if m:
1636 rpaths = m.group(1).replace("$ORIGIN", ldir).split(":")
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001637 rpath = tuple(map(os.path.normpath, rpaths))
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001638 for l in lines:
1639 m = re.match("\s+NEEDED\s+([^\s]*)", l)
1640 if m:
1641 dep = m.group(1)
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001642 if dep not in needed:
1643 needed.add((dep, file, rpath))
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001644 m = re.match("\s+SONAME\s+([^\s]*)", l)
1645 if m:
1646 this_soname = m.group(1)
1647 prov = (this_soname, ldir, pkgver)
1648 if not prov in sonames:
1649 # if library is private (only used by package) then do not build shlib for it
1650 if not private_libs or this_soname not in private_libs:
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001651 sonames.add(prov)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001652 if libdir_re.match(os.path.dirname(file)):
1653 needs_ldconfig = True
1654 if snap_symlinks and (os.path.basename(file) != this_soname):
1655 renames.append((file, os.path.join(os.path.dirname(file), this_soname)))
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001656 return (needs_ldconfig, needed, sonames, renames)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001657
1658 def darwin_so(file, needed, sonames, renames, pkgver):
1659 if not os.path.exists(file):
1660 return
1661 ldir = os.path.dirname(file).replace(pkgdest + "/" + pkg, '')
1662
1663 def get_combinations(base):
1664 #
1665 # Given a base library name, find all combinations of this split by "." and "-"
1666 #
1667 combos = []
1668 options = base.split(".")
1669 for i in range(1, len(options) + 1):
1670 combos.append(".".join(options[0:i]))
1671 options = base.split("-")
1672 for i in range(1, len(options) + 1):
1673 combos.append("-".join(options[0:i]))
1674 return combos
1675
Brad Bishopd7bf8c12018-02-25 22:55:05 -05001676 if (file.endswith('.dylib') or file.endswith('.so')) and not pkg.endswith('-dev') and not pkg.endswith('-dbg') and not pkg.endswith('-src'):
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001677 # Drop suffix
1678 name = os.path.basename(file).rsplit(".",1)[0]
1679 # Find all combinations
1680 combos = get_combinations(name)
1681 for combo in combos:
1682 if not combo in sonames:
1683 prov = (combo, ldir, pkgver)
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001684 sonames.add(prov)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001685 if file.endswith('.dylib') or file.endswith('.so'):
1686 rpath = []
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001687 p = subprocess.Popen([d.expand("${HOST_PREFIX}otool"), '-l', file], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
Patrick Williamsc0f7c042017-02-23 20:41:17 -06001688 out, err = p.communicate()
1689 # If returned successfully, process stdout for results
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001690 if p.returncode == 0:
Patrick Williamsc0f7c042017-02-23 20:41:17 -06001691 for l in out.split("\n"):
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001692 l = l.strip()
1693 if l.startswith('path '):
1694 rpath.append(l.split()[1])
1695
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001696 p = subprocess.Popen([d.expand("${HOST_PREFIX}otool"), '-L', file], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
Patrick Williamsc0f7c042017-02-23 20:41:17 -06001697 out, err = p.communicate()
1698 # If returned successfully, process stdout for results
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001699 if p.returncode == 0:
Patrick Williamsc0f7c042017-02-23 20:41:17 -06001700 for l in out.split("\n"):
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001701 l = l.strip()
1702 if not l or l.endswith(":"):
1703 continue
1704 if "is not an object file" in l:
1705 continue
1706 name = os.path.basename(l.split()[0]).rsplit(".", 1)[0]
1707 if name and name not in needed[pkg]:
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001708 needed[pkg].add((name, file, tuple()))
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001709
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001710 def mingw_dll(file, needed, sonames, renames, pkgver):
1711 if not os.path.exists(file):
1712 return
1713
1714 if file.endswith(".dll"):
1715 # assume all dlls are shared objects provided by the package
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001716 sonames.add((os.path.basename(file), os.path.dirname(file).replace(pkgdest + "/" + pkg, ''), pkgver))
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001717
1718 if (file.endswith(".dll") or file.endswith(".exe")):
1719 # use objdump to search for "DLL Name: .*\.dll"
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001720 p = subprocess.Popen([d.expand("${HOST_PREFIX}objdump"), "-p", file], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001721 out, err = p.communicate()
1722 # process the output, grabbing all .dll names
1723 if p.returncode == 0:
1724 for m in re.finditer("DLL Name: (.*?\.dll)$", out.decode(), re.MULTILINE | re.IGNORECASE):
1725 dllname = m.group(1)
1726 if dllname:
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001727 needed[pkg].add((dllname, file, tuple()))
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001728
1729 if d.getVar('PACKAGE_SNAP_LIB_SYMLINKS') == "1":
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001730 snap_symlinks = True
1731 else:
1732 snap_symlinks = False
1733
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001734 use_ldconfig = bb.utils.contains('DISTRO_FEATURES', 'ldconfig', True, False, d)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001735
1736 needed = {}
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001737
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001738 # Take shared lock since we're only reading, not writing
1739 lf = bb.utils.lockfile(d.expand("${PACKAGELOCK}"), True)
1740 shlib_provider = oe.package.read_shlib_providers(d)
1741 bb.utils.unlockfile(lf)
1742
1743 for pkg in shlib_pkgs:
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001744 private_libs = d.getVar('PRIVATE_LIBS_' + pkg) or d.getVar('PRIVATE_LIBS') or ""
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001745 private_libs = private_libs.split()
1746 needs_ldconfig = False
1747 bb.debug(2, "calculating shlib provides for %s" % pkg)
1748
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001749 pkgver = d.getVar('PKGV_' + pkg)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001750 if not pkgver:
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001751 pkgver = d.getVar('PV_' + pkg)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001752 if not pkgver:
1753 pkgver = ver
1754
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001755 needed[pkg] = set()
1756 sonames = set()
1757 renames = []
1758 linuxlist = []
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001759 for file in pkgfiles[pkg]:
1760 soname = None
1761 if cpath.islink(file):
1762 continue
1763 if targetos == "darwin" or targetos == "darwin8":
1764 darwin_so(file, needed, sonames, renames, pkgver)
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001765 elif targetos.startswith("mingw"):
1766 mingw_dll(file, needed, sonames, renames, pkgver)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001767 elif os.access(file, os.X_OK) or lib_re.match(file):
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001768 linuxlist.append(file)
1769
1770 if linuxlist:
1771 results = oe.utils.multiprocess_launch(linux_so, linuxlist, d, extraargs=(pkg, pkgver, d))
1772 for r in results:
1773 ldconfig = r[0]
1774 needed[pkg] |= r[1]
1775 sonames |= r[2]
1776 renames.extend(r[3])
1777 needs_ldconfig = needs_ldconfig or ldconfig
1778
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001779 for (old, new) in renames:
1780 bb.note("Renaming %s to %s" % (old, new))
1781 os.rename(old, new)
1782 pkgfiles[pkg].remove(old)
1783
1784 shlibs_file = os.path.join(shlibswork_dir, pkg + ".list")
1785 if len(sonames):
1786 fd = open(shlibs_file, 'w')
1787 for s in sonames:
1788 if s[0] in shlib_provider and s[1] in shlib_provider[s[0]]:
1789 (old_pkg, old_pkgver) = shlib_provider[s[0]][s[1]]
1790 if old_pkg != pkg:
1791 bb.warn('%s-%s was registered as shlib provider for %s, changing it to %s-%s because it was built later' % (old_pkg, old_pkgver, s[0], pkg, pkgver))
1792 bb.debug(1, 'registering %s-%s as shlib provider for %s' % (pkg, pkgver, s[0]))
1793 fd.write(s[0] + ':' + s[1] + ':' + s[2] + '\n')
1794 if s[0] not in shlib_provider:
1795 shlib_provider[s[0]] = {}
1796 shlib_provider[s[0]][s[1]] = (pkg, pkgver)
1797 fd.close()
1798 if needs_ldconfig and use_ldconfig:
1799 bb.debug(1, 'adding ldconfig call to postinst for %s' % pkg)
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001800 postinst = d.getVar('pkg_postinst_%s' % pkg)
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001801 if not postinst:
1802 postinst = '#!/bin/sh\n'
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001803 postinst += d.getVar('ldconfig_postinst_fragment')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001804 d.setVar('pkg_postinst_%s' % pkg, postinst)
1805 bb.debug(1, 'LIBNAMES: pkg %s sonames %s' % (pkg, sonames))
1806
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001807 assumed_libs = d.getVar('ASSUME_SHLIBS')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001808 if assumed_libs:
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001809 libdir = d.getVar("libdir")
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001810 for e in assumed_libs.split():
1811 l, dep_pkg = e.split(":")
1812 lib_ver = None
1813 dep_pkg = dep_pkg.rsplit("_", 1)
1814 if len(dep_pkg) == 2:
1815 lib_ver = dep_pkg[1]
1816 dep_pkg = dep_pkg[0]
1817 if l not in shlib_provider:
1818 shlib_provider[l] = {}
1819 shlib_provider[l][libdir] = (dep_pkg, lib_ver)
1820
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001821 libsearchpath = [d.getVar('libdir'), d.getVar('base_libdir')]
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001822
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001823 for pkg in shlib_pkgs:
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001824 bb.debug(2, "calculating shlib requirements for %s" % pkg)
1825
Brad Bishop316dfdd2018-06-25 12:45:53 -04001826 private_libs = d.getVar('PRIVATE_LIBS_' + pkg) or d.getVar('PRIVATE_LIBS') or ""
1827 private_libs = private_libs.split()
1828
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001829 deps = list()
1830 for n in needed[pkg]:
1831 # if n is in private libraries, don't try to search provider for it
1832 # this could cause problem in case some abc.bb provides private
1833 # /opt/abc/lib/libfoo.so.1 and contains /usr/bin/abc depending on system library libfoo.so.1
1834 # but skipping it is still better alternative than providing own
1835 # version and then adding runtime dependency for the same system library
1836 if private_libs and n[0] in private_libs:
1837 bb.debug(2, '%s: Dependency %s covered by PRIVATE_LIBS' % (pkg, n[0]))
1838 continue
1839 if n[0] in shlib_provider.keys():
Patrick Williamsc0f7c042017-02-23 20:41:17 -06001840 shlib_provider_path = []
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001841 for k in shlib_provider[n[0]].keys():
1842 shlib_provider_path.append(k)
1843 match = None
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001844 for p in list(n[2]) + shlib_provider_path + libsearchpath:
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001845 if p in shlib_provider[n[0]]:
1846 match = p
1847 break
1848 if match:
1849 (dep_pkg, ver_needed) = shlib_provider[n[0]][match]
1850
1851 bb.debug(2, '%s: Dependency %s requires package %s (used by files: %s)' % (pkg, n[0], dep_pkg, n[1]))
1852
1853 if dep_pkg == pkg:
1854 continue
1855
1856 if ver_needed:
1857 dep = "%s (>= %s)" % (dep_pkg, ver_needed)
1858 else:
1859 dep = dep_pkg
1860 if not dep in deps:
1861 deps.append(dep)
1862 continue
1863 bb.note("Couldn't find shared library provider for %s, used by files: %s" % (n[0], n[1]))
1864
1865 deps_file = os.path.join(pkgdest, pkg + ".shlibdeps")
1866 if os.path.exists(deps_file):
1867 os.remove(deps_file)
1868 if len(deps):
1869 fd = open(deps_file, 'w')
1870 for dep in deps:
1871 fd.write(dep + '\n')
1872 fd.close()
1873}
1874
1875python package_do_pkgconfig () {
1876 import re
1877
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001878 packages = d.getVar('PACKAGES')
1879 workdir = d.getVar('WORKDIR')
1880 pkgdest = d.getVar('PKGDEST')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001881
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001882 shlibs_dirs = d.getVar('SHLIBSDIRS').split()
1883 shlibswork_dir = d.getVar('SHLIBSWORKDIR')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001884
1885 pc_re = re.compile('(.*)\.pc$')
1886 var_re = re.compile('(.*)=(.*)')
1887 field_re = re.compile('(.*): (.*)')
1888
1889 pkgconfig_provided = {}
1890 pkgconfig_needed = {}
1891 for pkg in packages.split():
1892 pkgconfig_provided[pkg] = []
1893 pkgconfig_needed[pkg] = []
1894 for file in pkgfiles[pkg]:
1895 m = pc_re.match(file)
1896 if m:
1897 pd = bb.data.init()
1898 name = m.group(1)
1899 pkgconfig_provided[pkg].append(name)
1900 if not os.access(file, os.R_OK):
1901 continue
1902 f = open(file, 'r')
1903 lines = f.readlines()
1904 f.close()
1905 for l in lines:
1906 m = var_re.match(l)
1907 if m:
1908 name = m.group(1)
1909 val = m.group(2)
1910 pd.setVar(name, pd.expand(val))
1911 continue
1912 m = field_re.match(l)
1913 if m:
1914 hdr = m.group(1)
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001915 exp = pd.expand(m.group(2))
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001916 if hdr == 'Requires':
1917 pkgconfig_needed[pkg] += exp.replace(',', ' ').split()
1918
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001919 for pkg in packages.split():
1920 pkgs_file = os.path.join(shlibswork_dir, pkg + ".pclist")
1921 if pkgconfig_provided[pkg] != []:
1922 f = open(pkgs_file, 'w')
1923 for p in pkgconfig_provided[pkg]:
1924 f.write('%s\n' % p)
1925 f.close()
1926
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001927 # Take shared lock since we're only reading, not writing
1928 lf = bb.utils.lockfile(d.expand("${PACKAGELOCK}"), True)
1929
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001930 # Go from least to most specific since the last one found wins
1931 for dir in reversed(shlibs_dirs):
1932 if not os.path.exists(dir):
1933 continue
1934 for file in os.listdir(dir):
1935 m = re.match('^(.*)\.pclist$', file)
1936 if m:
1937 pkg = m.group(1)
1938 fd = open(os.path.join(dir, file))
1939 lines = fd.readlines()
1940 fd.close()
1941 pkgconfig_provided[pkg] = []
1942 for l in lines:
1943 pkgconfig_provided[pkg].append(l.rstrip())
1944
Brad Bishop1a4b7ee2018-12-16 17:11:34 -08001945 bb.utils.unlockfile(lf)
1946
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001947 for pkg in packages.split():
1948 deps = []
1949 for n in pkgconfig_needed[pkg]:
1950 found = False
1951 for k in pkgconfig_provided.keys():
1952 if n in pkgconfig_provided[k]:
1953 if k != pkg and not (k in deps):
1954 deps.append(k)
1955 found = True
1956 if found == False:
1957 bb.note("couldn't find pkgconfig module '%s' in any package" % n)
1958 deps_file = os.path.join(pkgdest, pkg + ".pcdeps")
1959 if len(deps):
1960 fd = open(deps_file, 'w')
1961 for dep in deps:
1962 fd.write(dep + '\n')
1963 fd.close()
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001964}
1965
1966def read_libdep_files(d):
1967 pkglibdeps = {}
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001968 packages = d.getVar('PACKAGES').split()
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001969 for pkg in packages:
1970 pkglibdeps[pkg] = {}
1971 for extension in ".shlibdeps", ".pcdeps", ".clilibdeps":
1972 depsfile = d.expand("${PKGDEST}/" + pkg + extension)
1973 if os.access(depsfile, os.R_OK):
1974 fd = open(depsfile)
1975 lines = fd.readlines()
1976 fd.close()
1977 for l in lines:
1978 l.rstrip()
1979 deps = bb.utils.explode_dep_versions2(l)
1980 for dep in deps:
1981 if not dep in pkglibdeps[pkg]:
1982 pkglibdeps[pkg][dep] = deps[dep]
1983 return pkglibdeps
1984
1985python read_shlibdeps () {
1986 pkglibdeps = read_libdep_files(d)
1987
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001988 packages = d.getVar('PACKAGES').split()
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001989 for pkg in packages:
Brad Bishop6e60e8b2018-02-01 10:27:11 -05001990 rdepends = bb.utils.explode_dep_versions2(d.getVar('RDEPENDS_' + pkg) or "")
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001991 for dep in pkglibdeps[pkg]:
1992 # Add the dep if it's not already there, or if no comparison is set
1993 if dep not in rdepends:
1994 rdepends[dep] = []
1995 for v in pkglibdeps[pkg][dep]:
1996 if v not in rdepends[dep]:
1997 rdepends[dep].append(v)
1998 d.setVar('RDEPENDS_' + pkg, bb.utils.join_deps(rdepends, commasep=False))
1999}
2000
2001python package_depchains() {
2002 """
2003 For a given set of prefix and postfix modifiers, make those packages
2004 RRECOMMENDS on the corresponding packages for its RDEPENDS.
2005
2006 Example: If package A depends upon package B, and A's .bb emits an
2007 A-dev package, this would make A-dev Recommends: B-dev.
2008
2009 If only one of a given suffix is specified, it will take the RRECOMMENDS
2010 based on the RDEPENDS of *all* other packages. If more than one of a given
2011 suffix is specified, its will only use the RDEPENDS of the single parent
2012 package.
2013 """
2014
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002015 packages = d.getVar('PACKAGES')
2016 postfixes = (d.getVar('DEPCHAIN_POST') or '').split()
2017 prefixes = (d.getVar('DEPCHAIN_PRE') or '').split()
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002018
2019 def pkg_adddeprrecs(pkg, base, suffix, getname, depends, d):
2020
2021 #bb.note('depends for %s is %s' % (base, depends))
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002022 rreclist = bb.utils.explode_dep_versions2(d.getVar('RRECOMMENDS_' + pkg) or "")
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002023
2024 for depend in depends:
2025 if depend.find('-native') != -1 or depend.find('-cross') != -1 or depend.startswith('virtual/'):
2026 #bb.note("Skipping %s" % depend)
2027 continue
2028 if depend.endswith('-dev'):
2029 depend = depend[:-4]
2030 if depend.endswith('-dbg'):
2031 depend = depend[:-4]
2032 pkgname = getname(depend, suffix)
2033 #bb.note("Adding %s for %s" % (pkgname, depend))
2034 if pkgname not in rreclist and pkgname != pkg:
2035 rreclist[pkgname] = []
2036
2037 #bb.note('setting: RRECOMMENDS_%s=%s' % (pkg, ' '.join(rreclist)))
2038 d.setVar('RRECOMMENDS_%s' % pkg, bb.utils.join_deps(rreclist, commasep=False))
2039
2040 def pkg_addrrecs(pkg, base, suffix, getname, rdepends, d):
2041
2042 #bb.note('rdepends for %s is %s' % (base, rdepends))
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002043 rreclist = bb.utils.explode_dep_versions2(d.getVar('RRECOMMENDS_' + pkg) or "")
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002044
2045 for depend in rdepends:
2046 if depend.find('virtual-locale-') != -1:
2047 #bb.note("Skipping %s" % depend)
2048 continue
2049 if depend.endswith('-dev'):
2050 depend = depend[:-4]
2051 if depend.endswith('-dbg'):
2052 depend = depend[:-4]
2053 pkgname = getname(depend, suffix)
2054 #bb.note("Adding %s for %s" % (pkgname, depend))
2055 if pkgname not in rreclist and pkgname != pkg:
2056 rreclist[pkgname] = []
2057
2058 #bb.note('setting: RRECOMMENDS_%s=%s' % (pkg, ' '.join(rreclist)))
2059 d.setVar('RRECOMMENDS_%s' % pkg, bb.utils.join_deps(rreclist, commasep=False))
2060
2061 def add_dep(list, dep):
2062 if dep not in list:
2063 list.append(dep)
2064
2065 depends = []
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002066 for dep in bb.utils.explode_deps(d.getVar('DEPENDS') or ""):
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002067 add_dep(depends, dep)
2068
2069 rdepends = []
2070 for pkg in packages.split():
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002071 for dep in bb.utils.explode_deps(d.getVar('RDEPENDS_' + pkg) or ""):
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002072 add_dep(rdepends, dep)
2073
2074 #bb.note('rdepends is %s' % rdepends)
2075
2076 def post_getname(name, suffix):
2077 return '%s%s' % (name, suffix)
2078 def pre_getname(name, suffix):
2079 return '%s%s' % (suffix, name)
2080
2081 pkgs = {}
2082 for pkg in packages.split():
2083 for postfix in postfixes:
2084 if pkg.endswith(postfix):
2085 if not postfix in pkgs:
2086 pkgs[postfix] = {}
2087 pkgs[postfix][pkg] = (pkg[:-len(postfix)], post_getname)
2088
2089 for prefix in prefixes:
2090 if pkg.startswith(prefix):
2091 if not prefix in pkgs:
2092 pkgs[prefix] = {}
2093 pkgs[prefix][pkg] = (pkg[:-len(prefix)], pre_getname)
2094
2095 if "-dbg" in pkgs:
2096 pkglibdeps = read_libdep_files(d)
2097 pkglibdeplist = []
2098 for pkg in pkglibdeps:
2099 for k in pkglibdeps[pkg]:
2100 add_dep(pkglibdeplist, k)
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002101 dbgdefaultdeps = ((d.getVar('DEPCHAIN_DBGDEFAULTDEPS') == '1') or (bb.data.inherits_class('packagegroup', d)))
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002102
2103 for suffix in pkgs:
2104 for pkg in pkgs[suffix]:
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002105 if d.getVarFlag('RRECOMMENDS_' + pkg, 'nodeprrecs'):
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002106 continue
2107 (base, func) = pkgs[suffix][pkg]
2108 if suffix == "-dev":
2109 pkg_adddeprrecs(pkg, base, suffix, func, depends, d)
2110 elif suffix == "-dbg":
2111 if not dbgdefaultdeps:
2112 pkg_addrrecs(pkg, base, suffix, func, pkglibdeplist, d)
2113 continue
2114 if len(pkgs[suffix]) == 1:
2115 pkg_addrrecs(pkg, base, suffix, func, rdepends, d)
2116 else:
2117 rdeps = []
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002118 for dep in bb.utils.explode_deps(d.getVar('RDEPENDS_' + base) or ""):
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002119 add_dep(rdeps, dep)
2120 pkg_addrrecs(pkg, base, suffix, func, rdeps, d)
2121}
2122
2123# Since bitbake can't determine which variables are accessed during package
2124# iteration, we need to list them here:
Andrew Geissler99467da2019-02-25 18:54:23 -06002125PACKAGEVARS = "FILES RDEPENDS RRECOMMENDS SUMMARY DESCRIPTION RSUGGESTS RPROVIDES RCONFLICTS PKG ALLOW_EMPTY pkg_postinst pkg_postrm pkg_postinst_ontarget INITSCRIPT_NAME INITSCRIPT_PARAMS DEBIAN_NOAUTONAME ALTERNATIVE PKGE PKGV PKGR USERADD_PARAM GROUPADD_PARAM CONFFILES SYSTEMD_SERVICE LICENSE SECTION pkg_preinst pkg_prerm RREPLACES GROUPMEMS_PARAM SYSTEMD_AUTO_ENABLE SKIP_FILEDEPS PRIVATE_LIBS"
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002126
2127def gen_packagevar(d):
2128 ret = []
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002129 pkgs = (d.getVar("PACKAGES") or "").split()
2130 vars = (d.getVar("PACKAGEVARS") or "").split()
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002131 for p in pkgs:
2132 for v in vars:
2133 ret.append(v + "_" + p)
2134
2135 # Ensure that changes to INCOMPATIBLE_LICENSE re-run do_package for
2136 # affected recipes.
2137 ret.append('LICENSE_EXCLUSION-%s' % p)
2138 return " ".join(ret)
2139
2140PACKAGE_PREPROCESS_FUNCS ?= ""
2141# Functions for setting up PKGD
2142PACKAGEBUILDPKGD ?= " \
2143 perform_packagecopy \
2144 ${PACKAGE_PREPROCESS_FUNCS} \
2145 split_and_strip_files \
2146 fixup_perms \
2147 "
2148# Functions which split PKGD up into separate packages
2149PACKAGESPLITFUNCS ?= " \
2150 package_do_split_locales \
2151 populate_packages"
2152# Functions which process metadata based on split packages
2153PACKAGEFUNCS += " \
2154 package_fixsymlinks \
2155 package_name_hook \
2156 package_do_filedeps \
2157 package_do_shlibs \
2158 package_do_pkgconfig \
2159 read_shlibdeps \
2160 package_depchains \
2161 emit_pkgdata"
2162
2163python do_package () {
2164 # Change the following version to cause sstate to invalidate the package
2165 # cache. This is useful if an item this class depends on changes in a
2166 # way that the output of this class changes. rpmdeps is a good example
2167 # as any change to rpmdeps requires this to be rerun.
Brad Bishopd7bf8c12018-02-25 22:55:05 -05002168 # PACKAGE_BBCLASS_VERSION = "2"
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002169
2170 # Init cachedpath
2171 global cpath
2172 cpath = oe.cachedpath.CachedPath()
2173
2174 ###########################################################################
2175 # Sanity test the setup
2176 ###########################################################################
2177
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002178 packages = (d.getVar('PACKAGES') or "").split()
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002179 if len(packages) < 1:
2180 bb.debug(1, "No packages to build, skipping do_package")
2181 return
2182
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002183 workdir = d.getVar('WORKDIR')
2184 outdir = d.getVar('DEPLOY_DIR')
2185 dest = d.getVar('D')
2186 dvar = d.getVar('PKGD')
2187 pn = d.getVar('PN')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002188
2189 if not workdir or not outdir or not dest or not dvar or not pn:
2190 msg = "WORKDIR, DEPLOY_DIR, D, PN and PKGD all must be defined, unable to package"
2191 package_qa_handle_error("var-undefined", msg, d)
2192 return
2193
2194 bb.build.exec_func("package_get_auto_pr", d)
2195
2196 ###########################################################################
2197 # Optimisations
2198 ###########################################################################
2199
2200 # Continually expanding complex expressions is inefficient, particularly
2201 # when we write to the datastore and invalidate the expansion cache. This
2202 # code pre-expands some frequently used variables
2203
2204 def expandVar(x, d):
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002205 d.setVar(x, d.getVar(x))
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002206
2207 for x in 'PN', 'PV', 'BPN', 'TARGET_SYS', 'EXTENDPRAUTO':
2208 expandVar(x, d)
2209
2210 ###########################################################################
2211 # Setup PKGD (from D)
2212 ###########################################################################
2213
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002214 for f in (d.getVar('PACKAGEBUILDPKGD') or '').split():
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002215 bb.build.exec_func(f, d)
2216
2217 ###########################################################################
2218 # Split up PKGD into PKGDEST
2219 ###########################################################################
2220
2221 cpath = oe.cachedpath.CachedPath()
2222
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002223 for f in (d.getVar('PACKAGESPLITFUNCS') or '').split():
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002224 bb.build.exec_func(f, d)
2225
2226 ###########################################################################
2227 # Process PKGDEST
2228 ###########################################################################
2229
2230 # Build global list of files in each split package
2231 global pkgfiles
2232 pkgfiles = {}
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002233 packages = d.getVar('PACKAGES').split()
2234 pkgdest = d.getVar('PKGDEST')
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002235 for pkg in packages:
2236 pkgfiles[pkg] = []
2237 for walkroot, dirs, files in cpath.walk(pkgdest + "/" + pkg):
2238 for file in files:
2239 pkgfiles[pkg].append(walkroot + os.sep + file)
2240
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002241 for f in (d.getVar('PACKAGEFUNCS') or '').split():
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002242 bb.build.exec_func(f, d)
Patrick Williamsd8c66bc2016-06-20 12:57:21 -05002243
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002244 qa_sane = d.getVar("QA_SANE")
Patrick Williamsd8c66bc2016-06-20 12:57:21 -05002245 if not qa_sane:
2246 bb.fatal("Fatal QA errors found, failing task.")
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002247}
2248
2249do_package[dirs] = "${SHLIBSWORKDIR} ${PKGDESTWORK} ${D}"
2250do_package[vardeps] += "${PACKAGEBUILDPKGD} ${PACKAGESPLITFUNCS} ${PACKAGEFUNCS} ${@gen_packagevar(d)}"
2251addtask package after do_install
2252
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002253SSTATETASKS += "do_package"
2254do_package[cleandirs] = "${PKGDEST} ${PKGDESTWORK}"
2255do_package[sstate-plaindirs] = "${PKGD} ${PKGDEST} ${PKGDESTWORK}"
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002256do_package_setscene[dirs] = "${STAGING_DIR}"
2257
2258python do_package_setscene () {
2259 sstate_setscene(d)
2260}
2261addtask do_package_setscene
2262
2263do_packagedata () {
2264 :
2265}
2266
2267addtask packagedata before do_build after do_package
2268
2269SSTATETASKS += "do_packagedata"
Brad Bishop316dfdd2018-06-25 12:45:53 -04002270# PACKAGELOCK protects readers of PKGDATA_DIR against writes
2271# whilst code is reading in do_package
2272PACKAGELOCK = "${STAGING_DIR}/package-output.lock"
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002273do_packagedata[sstate-inputdirs] = "${PKGDESTWORK}"
2274do_packagedata[sstate-outputdirs] = "${PKGDATA_DIR}"
Brad Bishop316dfdd2018-06-25 12:45:53 -04002275do_packagedata[sstate-lockfile] = "${PACKAGELOCK}"
2276do_packagedata[stamp-extra-info] = "${MACHINE_ARCH}"
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002277
2278python do_packagedata_setscene () {
2279 sstate_setscene(d)
2280}
2281addtask do_packagedata_setscene
2282
2283#
2284# Helper functions for the package writing classes
2285#
2286
2287def mapping_rename_hook(d):
2288 """
2289 Rewrite variables to account for package renaming in things
2290 like debian.bbclass or manual PKG variable name changes
2291 """
Brad Bishop6e60e8b2018-02-01 10:27:11 -05002292 pkg = d.getVar("PKG")
Patrick Williamsc124f4f2015-09-15 14:41:29 -05002293 runtime_mapping_rename("RDEPENDS", pkg, d)
2294 runtime_mapping_rename("RRECOMMENDS", pkg, d)
2295 runtime_mapping_rename("RSUGGESTS", pkg, d)