summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChris Larson <clarson@kergoth.com>2009-08-27 11:04:07 -0700
committerChris Larson <clarson@mvista.com>2009-08-27 11:08:54 -0700
commit42dc52e38db1fd2c57dadec26ca54a9f4a6db1aa (patch)
tree200ae8f1417e03ba0e3273cac892035bd40ee8e1
parent4923ae44c9e97a91deef41ecfec06227996c85fa (diff)
Add task-metadata-track.bbclass, for tracking task changes to metadata.
This class uses events to capture the state of the datastore when the task starts, and after it completes. It diffs those captured states, and emits messages showing which variables changed, and what their values were changed to. It provides a mechanism to blacklist variables you expect to change, both globally and on a per-task basis. Signed-off-by: Chris Larson <clarson@kergoth.com>
-rw-r--r--classes/task-metadata-track.bbclass96
1 files changed, 96 insertions, 0 deletions
diff --git a/classes/task-metadata-track.bbclass b/classes/task-metadata-track.bbclass
new file mode 100644
index 0000000000..d3622aef68
--- /dev/null
+++ b/classes/task-metadata-track.bbclass
@@ -0,0 +1,96 @@
+# Copyright (C) 2009 Chris Larson <clarson@kergoth.com>
+# Released under the MIT license (see COPYING.MIT for the terms)
+#
+# This class uses events to capture the state of the datastore when the task
+# starts, and after it completes. It diffs those captured states, and emits
+# messages showing which variables changed, and what their values were changed
+# to.
+#
+# It provides a mechanism to blacklist variables you expect to change, both
+# globally and on a per-task basis.
+#
+# Known instances of tasks changing metadata:
+#
+# PSTAGE_PKGMANAGER changes by calls to pstage_set_pkgmanager in:
+# do_clean, do_setscene, do_package_stage
+#
+# Subpackage metadata, read by the pkgdata functions in base.bbclass, in:
+# do_package, do_package_stage, do_package_write_*
+
+
+TASK_METADATA_BLACKLIST = "\
+ __RUNQUEUE_DO_NOT_USE_EXTERNALLY \
+"
+
+#TASK_METADATA_BLACKLIST_do_clean = "\
+# PSTAGE_PKGMANAGER \
+#"
+
+
+def dict_diff(olddict, newdict):
+ diff = {}
+ for key in set(olddict).union(set(newdict)):
+ old = olddict.get(key)
+ new = newdict.get(key)
+ if old != new:
+ diff[key] = (old, new)
+
+ return diff
+
+def dict_for_data(data):
+ newdict = {}
+ for key in data.keys():
+ newdict[key] = data.getVar(key, False)
+ return newdict
+
+def task_metadata_track_start(task, data):
+ originaldata = dict_for_data(data)
+ data.setVar("__originaldata_%s" % task, originaldata)
+
+def task_metadata_track_stop(task, data):
+ from bb import note
+
+ pf = data.getVar("PF", True)
+ def emit(msg):
+ note("%s: %s" % (pf, msg))
+
+ originaldata = data.getVar("__originaldata_%s" % task, False)
+ newdata = dict_for_data(data)
+ blacklist = data.getVar("TASK_METADATA_BLACKLIST", True).split() + \
+ (data.getVar("TASK_METADATA_BLACKLIST_%s" % task, True) or "").split()
+
+ diff = dict_diff(originaldata, newdata)
+ diff_clean = [key for key in diff \
+ if not key in blacklist and \
+ not key.startswith("__originaldata_")]
+
+ if diff_clean:
+ emit("Variables changed by %s:" % task)
+ for key in diff_clean:
+ (old, new) = diff[key]
+ emit(" %s:" % key)
+ emit(" '%s' -> '%s'" % (old, new))
+
+python __task_metadata_track_eh () {
+ from bb.build import TaskStarted, TaskSucceeded
+
+ if isinstance(e, TaskStarted):
+ if e.data is None:
+ from bb import fatal
+ fatal("e.data is none for %s" % e)
+ task_metadata_track_start(e.task, e.data)
+ elif isinstance(e, TaskSucceeded):
+ task_metadata_track_stop(e.task, e.data)
+}
+addhandler __task_metadata_track_eh
+
+addtask py_listtasks
+do_py_listtasks[nostamp] = "1"
+do_py_listtasks[recrdeptask] = "do_py_listtasks"
+python do_py_listtasks() {
+ import sys
+ for e in d.keys():
+ if d.getVarFlag(e, "task") and \
+ d.getVarFlag(e, "python"):
+ sys.stdout.write("%s\n" % e)
+}