diff options
Diffstat (limited to 'bitbake/lib')
-rw-r--r-- | bitbake/lib/bb/command.py | 8 | ||||
-rw-r--r-- | bitbake/lib/bb/cooker.py | 179 | ||||
-rw-r--r-- | bitbake/lib/bb/parse/__init__.py | 8 | ||||
-rw-r--r-- | bitbake/lib/bb/server/process.py | 6 | ||||
-rw-r--r-- | bitbake/lib/bb/tinfoil.py | 6 | ||||
-rw-r--r-- | bitbake/lib/bblayers/action.py | 6 |
6 files changed, 65 insertions, 148 deletions
diff --git a/bitbake/lib/bb/command.py b/bitbake/lib/bb/command.py index b494f84a0a..8663eed933 100644 --- a/bitbake/lib/bb/command.py +++ b/bitbake/lib/bb/command.py | |||
@@ -85,8 +85,6 @@ class Command: | |||
85 | if not hasattr(command_method, 'readonly') or not getattr(command_method, 'readonly'): | 85 | if not hasattr(command_method, 'readonly') or not getattr(command_method, 'readonly'): |
86 | return None, "Not able to execute not readonly commands in readonly mode" | 86 | return None, "Not able to execute not readonly commands in readonly mode" |
87 | try: | 87 | try: |
88 | if command != "ping": | ||
89 | self.cooker.process_inotify_updates_apply() | ||
90 | if getattr(command_method, 'needconfig', True): | 88 | if getattr(command_method, 'needconfig', True): |
91 | self.cooker.updateCacheSync() | 89 | self.cooker.updateCacheSync() |
92 | result = command_method(self, commandline) | 90 | result = command_method(self, commandline) |
@@ -110,7 +108,6 @@ class Command: | |||
110 | 108 | ||
111 | def runAsyncCommand(self, _, process_server, halt): | 109 | def runAsyncCommand(self, _, process_server, halt): |
112 | try: | 110 | try: |
113 | self.cooker.process_inotify_updates_apply() | ||
114 | if self.cooker.state in (bb.cooker.state.error, bb.cooker.state.shutdown, bb.cooker.state.forceshutdown): | 111 | if self.cooker.state in (bb.cooker.state.error, bb.cooker.state.shutdown, bb.cooker.state.forceshutdown): |
115 | # updateCache will trigger a shutdown of the parser | 112 | # updateCache will trigger a shutdown of the parser |
116 | # and then raise BBHandledException triggering an exit | 113 | # and then raise BBHandledException triggering an exit |
@@ -310,6 +307,11 @@ class CommandsSync: | |||
310 | return ret | 307 | return ret |
311 | getLayerPriorities.readonly = True | 308 | getLayerPriorities.readonly = True |
312 | 309 | ||
310 | def revalidateCaches(self, command, params): | ||
311 | """Called by UI clients when metadata may have changed""" | ||
312 | command.cooker.revalidateCaches() | ||
313 | parseConfiguration.needconfig = False | ||
314 | |||
313 | def getRecipes(self, command, params): | 315 | def getRecipes(self, command, params): |
314 | try: | 316 | try: |
315 | mc = params[0] | 317 | mc = params[0] |
diff --git a/bitbake/lib/bb/cooker.py b/bitbake/lib/bb/cooker.py index 064e3cae6e..4089d003bb 100644 --- a/bitbake/lib/bb/cooker.py +++ b/bitbake/lib/bb/cooker.py | |||
@@ -22,7 +22,6 @@ from bb import utils, data, parse, event, cache, providers, taskdata, runqueue, | |||
22 | import queue | 22 | import queue |
23 | import signal | 23 | import signal |
24 | import prserv.serv | 24 | import prserv.serv |
25 | import pyinotify | ||
26 | import json | 25 | import json |
27 | import pickle | 26 | import pickle |
28 | import codecs | 27 | import codecs |
@@ -175,15 +174,8 @@ class BBCooker: | |||
175 | bb.debug(1, "BBCooker starting %s" % time.time()) | 174 | bb.debug(1, "BBCooker starting %s" % time.time()) |
176 | sys.stdout.flush() | 175 | sys.stdout.flush() |
177 | 176 | ||
178 | self.configwatcher = None | 177 | self.configwatched = {} |
179 | self.confignotifier = None | 178 | self.parsewatched = {} |
180 | |||
181 | self.watchmask = pyinotify.IN_CLOSE_WRITE | pyinotify.IN_CREATE | pyinotify.IN_DELETE | \ | ||
182 | pyinotify.IN_DELETE_SELF | pyinotify.IN_MODIFY | pyinotify.IN_MOVE_SELF | \ | ||
183 | pyinotify.IN_MOVED_FROM | pyinotify.IN_MOVED_TO | ||
184 | |||
185 | self.watcher = None | ||
186 | self.notifier = None | ||
187 | 179 | ||
188 | # If being called by something like tinfoil, we need to clean cached data | 180 | # If being called by something like tinfoil, we need to clean cached data |
189 | # which may now be invalid | 181 | # which may now be invalid |
@@ -194,8 +186,6 @@ class BBCooker: | |||
194 | self.hashserv = None | 186 | self.hashserv = None |
195 | self.hashservaddr = None | 187 | self.hashservaddr = None |
196 | 188 | ||
197 | self.inotify_modified_files = [] | ||
198 | |||
199 | # TOSTOP must not be set or our children will hang when they output | 189 | # TOSTOP must not be set or our children will hang when they output |
200 | try: | 190 | try: |
201 | fd = sys.stdout.fileno() | 191 | fd = sys.stdout.fileno() |
@@ -221,8 +211,6 @@ class BBCooker: | |||
221 | bb.debug(1, "BBCooker startup complete %s" % time.time()) | 211 | bb.debug(1, "BBCooker startup complete %s" % time.time()) |
222 | sys.stdout.flush() | 212 | sys.stdout.flush() |
223 | 213 | ||
224 | self.inotify_threadlock = threading.Lock() | ||
225 | |||
226 | def init_configdata(self): | 214 | def init_configdata(self): |
227 | if not hasattr(self, "data"): | 215 | if not hasattr(self, "data"): |
228 | self.initConfigurationData() | 216 | self.initConfigurationData() |
@@ -230,42 +218,6 @@ class BBCooker: | |||
230 | sys.stdout.flush() | 218 | sys.stdout.flush() |
231 | self.handlePRServ() | 219 | self.handlePRServ() |
232 | 220 | ||
233 | def setupConfigWatcher(self): | ||
234 | with bb.utils.lock_timeout(self.inotify_threadlock): | ||
235 | if self.configwatcher: | ||
236 | self.configwatcher.close() | ||
237 | self.confignotifier = None | ||
238 | self.configwatcher = None | ||
239 | self.configwatcher = pyinotify.WatchManager() | ||
240 | self.configwatcher.bbseen = set() | ||
241 | self.configwatcher.bbwatchedfiles = set() | ||
242 | self.confignotifier = pyinotify.Notifier(self.configwatcher, self.config_notifications) | ||
243 | |||
244 | def setupParserWatcher(self): | ||
245 | with bb.utils.lock_timeout(self.inotify_threadlock): | ||
246 | if self.watcher: | ||
247 | self.watcher.close() | ||
248 | self.notifier = None | ||
249 | self.watcher = None | ||
250 | self.watcher = pyinotify.WatchManager() | ||
251 | self.watcher.bbseen = set() | ||
252 | self.watcher.bbwatchedfiles = set() | ||
253 | self.notifier = pyinotify.Notifier(self.watcher, self.notifications) | ||
254 | |||
255 | def process_inotify_updates(self): | ||
256 | with bb.utils.lock_timeout(self.inotify_threadlock): | ||
257 | for n in [self.confignotifier, self.notifier]: | ||
258 | if n and n.check_events(timeout=0): | ||
259 | # read notified events and enqueue them | ||
260 | n.read_events() | ||
261 | |||
262 | def process_inotify_updates_apply(self): | ||
263 | with bb.utils.lock_timeout(self.inotify_threadlock): | ||
264 | for n in [self.confignotifier, self.notifier]: | ||
265 | if n and n.check_events(timeout=0): | ||
266 | n.read_events() | ||
267 | n.process_events() | ||
268 | |||
269 | def _baseconfig_set(self, value): | 221 | def _baseconfig_set(self, value): |
270 | if value and not self.baseconfig_valid: | 222 | if value and not self.baseconfig_valid: |
271 | bb.server.process.serverlog("Base config valid") | 223 | bb.server.process.serverlog("Base config valid") |
@@ -280,88 +232,16 @@ class BBCooker: | |||
280 | bb.server.process.serverlog("Parse cache invalidated") | 232 | bb.server.process.serverlog("Parse cache invalidated") |
281 | self.parsecache_valid = value | 233 | self.parsecache_valid = value |
282 | 234 | ||
283 | def config_notifications(self, event): | 235 | def add_filewatch(self, deps, configwatcher=False): |
284 | if event.maskname == "IN_Q_OVERFLOW": | 236 | if configwatcher: |
285 | bb.warn("inotify event queue overflowed, invalidating caches.") | 237 | watcher = self.configwatched |
286 | self._parsecache_set(False) | 238 | else: |
287 | self._baseconfig_set(False) | 239 | watcher = self.parsewatched |
288 | bb.parse.clear_cache() | ||
289 | return | ||
290 | if not event.pathname in self.configwatcher.bbwatchedfiles: | ||
291 | return | ||
292 | if "IN_ISDIR" in event.maskname: | ||
293 | if "IN_CREATE" in event.maskname or "IN_DELETE" in event.maskname: | ||
294 | if event.pathname in self.configwatcher.bbseen: | ||
295 | self.configwatcher.bbseen.remove(event.pathname) | ||
296 | # Could remove all entries starting with the directory but for now... | ||
297 | bb.parse.clear_cache() | ||
298 | if not event.pathname in self.inotify_modified_files: | ||
299 | self.inotify_modified_files.append(event.pathname) | ||
300 | self._baseconfig_set(False) | ||
301 | |||
302 | def notifications(self, event): | ||
303 | if event.maskname == "IN_Q_OVERFLOW": | ||
304 | bb.warn("inotify event queue overflowed, invalidating caches.") | ||
305 | self._parsecache_set(False) | ||
306 | bb.parse.clear_cache() | ||
307 | return | ||
308 | if event.pathname.endswith("bitbake-cookerdaemon.log") \ | ||
309 | or event.pathname.endswith("bitbake.lock"): | ||
310 | return | ||
311 | if "IN_ISDIR" in event.maskname: | ||
312 | if "IN_CREATE" in event.maskname or "IN_DELETE" in event.maskname: | ||
313 | if event.pathname in self.watcher.bbseen: | ||
314 | self.watcher.bbseen.remove(event.pathname) | ||
315 | # Could remove all entries starting with the directory but for now... | ||
316 | bb.parse.clear_cache() | ||
317 | if not event.pathname in self.inotify_modified_files: | ||
318 | self.inotify_modified_files.append(event.pathname) | ||
319 | self._parsecache_set(False) | ||
320 | 240 | ||
321 | def add_filewatch(self, deps, watcher=None, dirs=False): | ||
322 | if not watcher: | ||
323 | watcher = self.watcher | ||
324 | for i in deps: | 241 | for i in deps: |
325 | watcher.bbwatchedfiles.add(i[0]) | 242 | f = i[0] |
326 | if dirs: | 243 | mtime = i[1] |
327 | f = i[0] | 244 | watcher[f] = mtime |
328 | else: | ||
329 | f = os.path.dirname(i[0]) | ||
330 | if f in watcher.bbseen: | ||
331 | continue | ||
332 | watcher.bbseen.add(f) | ||
333 | watchtarget = None | ||
334 | while True: | ||
335 | # We try and add watches for files that don't exist but if they did, would influence | ||
336 | # the parser. The parent directory of these files may not exist, in which case we need | ||
337 | # to watch any parent that does exist for changes. | ||
338 | try: | ||
339 | watcher.add_watch(f, self.watchmask, quiet=False) | ||
340 | if watchtarget: | ||
341 | watcher.bbwatchedfiles.add(watchtarget) | ||
342 | break | ||
343 | except pyinotify.WatchManagerError as e: | ||
344 | if 'ENOENT' in str(e): | ||
345 | watchtarget = f | ||
346 | f = os.path.dirname(f) | ||
347 | if f in watcher.bbseen: | ||
348 | break | ||
349 | watcher.bbseen.add(f) | ||
350 | continue | ||
351 | if 'ENOSPC' in str(e): | ||
352 | providerlog.error("No space left on device or exceeds fs.inotify.max_user_watches?") | ||
353 | providerlog.error("To check max_user_watches: sysctl -n fs.inotify.max_user_watches.") | ||
354 | providerlog.error("To modify max_user_watches: sysctl -n -w fs.inotify.max_user_watches=<value>.") | ||
355 | providerlog.error("Root privilege is required to modify max_user_watches.") | ||
356 | raise | ||
357 | |||
358 | def handle_inotify_updates(self): | ||
359 | # reload files for which we got notifications | ||
360 | for p in self.inotify_modified_files: | ||
361 | bb.parse.update_cache(p) | ||
362 | if p in bb.parse.BBHandler.cached_statements: | ||
363 | del bb.parse.BBHandler.cached_statements[p] | ||
364 | self.inotify_modified_files = [] | ||
365 | 245 | ||
366 | def sigterm_exception(self, signum, stackframe): | 246 | def sigterm_exception(self, signum, stackframe): |
367 | if signum == signal.SIGTERM: | 247 | if signum == signal.SIGTERM: |
@@ -392,8 +272,7 @@ class BBCooker: | |||
392 | if mod not in self.orig_sysmodules: | 272 | if mod not in self.orig_sysmodules: |
393 | del sys.modules[mod] | 273 | del sys.modules[mod] |
394 | 274 | ||
395 | self.handle_inotify_updates() | 275 | self.configwatched = {} |
396 | self.setupConfigWatcher() | ||
397 | 276 | ||
398 | # Need to preserve BB_CONSOLELOG over resets | 277 | # Need to preserve BB_CONSOLELOG over resets |
399 | consolelog = None | 278 | consolelog = None |
@@ -436,7 +315,7 @@ class BBCooker: | |||
436 | self.disableDataTracking() | 315 | self.disableDataTracking() |
437 | 316 | ||
438 | for mc in self.databuilder.mcdata.values(): | 317 | for mc in self.databuilder.mcdata.values(): |
439 | self.add_filewatch(mc.getVar("__base_depends", False), self.configwatcher) | 318 | self.add_filewatch(mc.getVar("__base_depends", False), configwatcher=True) |
440 | 319 | ||
441 | self._baseconfig_set(True) | 320 | self._baseconfig_set(True) |
442 | self._parsecache_set(False) | 321 | self._parsecache_set(False) |
@@ -486,6 +365,29 @@ class BBCooker: | |||
486 | if hasattr(self, "data"): | 365 | if hasattr(self, "data"): |
487 | self.data.disableTracking() | 366 | self.data.disableTracking() |
488 | 367 | ||
368 | def revalidateCaches(self): | ||
369 | bb.parse.clear_cache() | ||
370 | |||
371 | clean = True | ||
372 | for f in self.configwatched: | ||
373 | if not bb.parse.check_mtime(f, self.configwatched[f]): | ||
374 | bb.server.process.serverlog("Found %s changed, invalid cache" % f) | ||
375 | self._baseconfig_set(False) | ||
376 | self._parsecache_set(False) | ||
377 | clean = False | ||
378 | break | ||
379 | |||
380 | if clean: | ||
381 | for f in self.parsewatched: | ||
382 | if not bb.parse.check_mtime(f, self.parsewatched[f]): | ||
383 | bb.server.process.serverlog("Found %s changed, invalid cache" % f) | ||
384 | self._parsecache_set(False) | ||
385 | clean = False | ||
386 | break | ||
387 | |||
388 | if not clean: | ||
389 | bb.parse.BBHandler.cached_statements = {} | ||
390 | |||
489 | def parseConfiguration(self): | 391 | def parseConfiguration(self): |
490 | self.updateCacheSync() | 392 | self.updateCacheSync() |
491 | 393 | ||
@@ -566,6 +468,7 @@ class BBCooker: | |||
566 | # Now update all the variables not in the datastore to match | 468 | # Now update all the variables not in the datastore to match |
567 | self.configuration.env = environment | 469 | self.configuration.env = environment |
568 | 470 | ||
471 | self.revalidateCaches() | ||
569 | if not clean: | 472 | if not clean: |
570 | logger.debug("Base environment change, triggering reparse") | 473 | logger.debug("Base environment change, triggering reparse") |
571 | self.reset() | 474 | self.reset() |
@@ -1644,8 +1547,6 @@ class BBCooker: | |||
1644 | if self.state == state.running: | 1547 | if self.state == state.running: |
1645 | return | 1548 | return |
1646 | 1549 | ||
1647 | self.handle_inotify_updates() | ||
1648 | |||
1649 | if not self.baseconfig_valid: | 1550 | if not self.baseconfig_valid: |
1650 | logger.debug("Reloading base configuration data") | 1551 | logger.debug("Reloading base configuration data") |
1651 | self.initConfigurationData() | 1552 | self.initConfigurationData() |
@@ -1667,7 +1568,7 @@ class BBCooker: | |||
1667 | 1568 | ||
1668 | if self.state != state.parsing and not self.parsecache_valid: | 1569 | if self.state != state.parsing and not self.parsecache_valid: |
1669 | bb.server.process.serverlog("Parsing started") | 1570 | bb.server.process.serverlog("Parsing started") |
1670 | self.setupParserWatcher() | 1571 | self.parsewatched = {} |
1671 | 1572 | ||
1672 | bb.parse.siggen.reset(self.data) | 1573 | bb.parse.siggen.reset(self.data) |
1673 | self.parseConfiguration () | 1574 | self.parseConfiguration () |
@@ -1692,9 +1593,9 @@ class BBCooker: | |||
1692 | total_masked += masked | 1593 | total_masked += masked |
1693 | searchdirs |= set(search) | 1594 | searchdirs |= set(search) |
1694 | 1595 | ||
1695 | # Add inotify watches for directories searched for bb/bbappend files | 1596 | # Add mtimes for directories searched for bb/bbappend files |
1696 | for dirent in searchdirs: | 1597 | for dirent in searchdirs: |
1697 | self.add_filewatch([[dirent]], dirs=True) | 1598 | self.add_filewatch([(dirent, bb.parse.cached_mtime_noerror(dirent))]) |
1698 | 1599 | ||
1699 | self.parser = CookerParser(self, mcfilelist, total_masked) | 1600 | self.parser = CookerParser(self, mcfilelist, total_masked) |
1700 | self._parsecache_set(True) | 1601 | self._parsecache_set(True) |
@@ -1881,7 +1782,7 @@ class CookerCollectFiles(object): | |||
1881 | collectlog.error("no recipe files to build, check your BBPATH and BBFILES?") | 1782 | collectlog.error("no recipe files to build, check your BBPATH and BBFILES?") |
1882 | bb.event.fire(CookerExit(), eventdata) | 1783 | bb.event.fire(CookerExit(), eventdata) |
1883 | 1784 | ||
1884 | # We need to track where we look so that we can add inotify watches. There | 1785 | # We need to track where we look so that we can know when the cache is invalid. There |
1885 | # is no nice way to do this, this is horrid. We intercept the os.listdir() | 1786 | # is no nice way to do this, this is horrid. We intercept the os.listdir() |
1886 | # (or os.scandir() for python 3.6+) calls while we run glob(). | 1787 | # (or os.scandir() for python 3.6+) calls while we run glob(). |
1887 | origlistdir = os.listdir | 1788 | origlistdir = os.listdir |
diff --git a/bitbake/lib/bb/parse/__init__.py b/bitbake/lib/bb/parse/__init__.py index 4cd82f115b..a4358f1374 100644 --- a/bitbake/lib/bb/parse/__init__.py +++ b/bitbake/lib/bb/parse/__init__.py | |||
@@ -60,6 +60,14 @@ def cached_mtime_noerror(f): | |||
60 | return 0 | 60 | return 0 |
61 | return __mtime_cache[f] | 61 | return __mtime_cache[f] |
62 | 62 | ||
63 | def check_mtime(f, mtime): | ||
64 | try: | ||
65 | current_mtime = os.stat(f)[stat.ST_MTIME] | ||
66 | __mtime_cache[f] = current_mtime | ||
67 | except OSError: | ||
68 | current_mtime = 0 | ||
69 | return current_mtime == mtime | ||
70 | |||
63 | def update_mtime(f): | 71 | def update_mtime(f): |
64 | try: | 72 | try: |
65 | __mtime_cache[f] = os.stat(f)[stat.ST_MTIME] | 73 | __mtime_cache[f] = os.stat(f)[stat.ST_MTIME] |
diff --git a/bitbake/lib/bb/server/process.py b/bitbake/lib/bb/server/process.py index 40cb99bc97..993ae66279 100644 --- a/bitbake/lib/bb/server/process.py +++ b/bitbake/lib/bb/server/process.py | |||
@@ -410,12 +410,6 @@ class ProcessServer(): | |||
410 | nextsleep = 0.1 | 410 | nextsleep = 0.1 |
411 | fds = [] | 411 | fds = [] |
412 | 412 | ||
413 | try: | ||
414 | self.cooker.process_inotify_updates() | ||
415 | except Exception as exc: | ||
416 | serverlog("Exception %s in inofify updates broke the idle_thread, exiting" % traceback.format_exc()) | ||
417 | self.quit = True | ||
418 | |||
419 | with bb.utils.lock_timeout(self._idlefuncsLock): | 413 | with bb.utils.lock_timeout(self._idlefuncsLock): |
420 | items = list(self._idlefuns.items()) | 414 | items = list(self._idlefuns.items()) |
421 | 415 | ||
diff --git a/bitbake/lib/bb/tinfoil.py b/bitbake/lib/bb/tinfoil.py index 91fbf1b13e..2200caa54c 100644 --- a/bitbake/lib/bb/tinfoil.py +++ b/bitbake/lib/bb/tinfoil.py | |||
@@ -449,6 +449,12 @@ class Tinfoil: | |||
449 | self.run_actions(config_params) | 449 | self.run_actions(config_params) |
450 | self.recipes_parsed = True | 450 | self.recipes_parsed = True |
451 | 451 | ||
452 | def modified_files(self): | ||
453 | """ | ||
454 | Notify the server it needs to revalidate it's caches since the client has modified files | ||
455 | """ | ||
456 | self.run_command("revalidateCaches") | ||
457 | |||
452 | def run_command(self, command, *params, handle_events=True): | 458 | def run_command(self, command, *params, handle_events=True): |
453 | """ | 459 | """ |
454 | Run a command on the server (as implemented in bb.command). | 460 | Run a command on the server (as implemented in bb.command). |
diff --git a/bitbake/lib/bblayers/action.py b/bitbake/lib/bblayers/action.py index 0d7fd6edd1..a8f2699335 100644 --- a/bitbake/lib/bblayers/action.py +++ b/bitbake/lib/bblayers/action.py | |||
@@ -50,12 +50,14 @@ class ActionPlugin(LayerPlugin): | |||
50 | 50 | ||
51 | try: | 51 | try: |
52 | notadded, _ = bb.utils.edit_bblayers_conf(bblayers_conf, layerdirs, None) | 52 | notadded, _ = bb.utils.edit_bblayers_conf(bblayers_conf, layerdirs, None) |
53 | self.tinfoil.modified_files() | ||
53 | if not (args.force or notadded): | 54 | if not (args.force or notadded): |
54 | try: | 55 | try: |
55 | self.tinfoil.run_command('parseConfiguration') | 56 | self.tinfoil.run_command('parseConfiguration') |
56 | except (bb.tinfoil.TinfoilUIException, bb.BBHandledException): | 57 | except (bb.tinfoil.TinfoilUIException, bb.BBHandledException): |
57 | # Restore the back up copy of bblayers.conf | 58 | # Restore the back up copy of bblayers.conf |
58 | shutil.copy2(backup, bblayers_conf) | 59 | shutil.copy2(backup, bblayers_conf) |
60 | self.tinfoil.modified_files() | ||
59 | bb.fatal("Parse failure with the specified layer added, exiting.") | 61 | bb.fatal("Parse failure with the specified layer added, exiting.") |
60 | else: | 62 | else: |
61 | for item in notadded: | 63 | for item in notadded: |
@@ -81,6 +83,7 @@ class ActionPlugin(LayerPlugin): | |||
81 | layerdir = os.path.abspath(item) | 83 | layerdir = os.path.abspath(item) |
82 | layerdirs.append(layerdir) | 84 | layerdirs.append(layerdir) |
83 | (_, notremoved) = bb.utils.edit_bblayers_conf(bblayers_conf, None, layerdirs) | 85 | (_, notremoved) = bb.utils.edit_bblayers_conf(bblayers_conf, None, layerdirs) |
86 | self.tinfoil.modified_files() | ||
84 | if notremoved: | 87 | if notremoved: |
85 | for item in notremoved: | 88 | for item in notremoved: |
86 | sys.stderr.write("No layers matching %s found in BBLAYERS\n" % item) | 89 | sys.stderr.write("No layers matching %s found in BBLAYERS\n" % item) |
@@ -240,6 +243,9 @@ build results (as the layer priority order has effectively changed). | |||
240 | if not entry_found: | 243 | if not entry_found: |
241 | logger.warning("File %s does not match the flattened layer's BBFILES setting, you may need to edit conf/layer.conf or move the file elsewhere" % f1full) | 244 | logger.warning("File %s does not match the flattened layer's BBFILES setting, you may need to edit conf/layer.conf or move the file elsewhere" % f1full) |
242 | 245 | ||
246 | self.tinfoil.modified_files() | ||
247 | |||
248 | |||
243 | def get_file_layer(self, filename): | 249 | def get_file_layer(self, filename): |
244 | layerdir = self.get_file_layerdir(filename) | 250 | layerdir = self.get_file_layerdir(filename) |
245 | if layerdir: | 251 | if layerdir: |