build_packages: Always rebuild consumers of active cros_workon packages

The first time a user installs a workon package the rebuild logic would
work correctly as the new 9999 version is enough information for Portage
to correctly rebuild the packages that consume the workon package, but
subsequent rebuilds would not be handled correctly as they would already
see the 9999 version as being installed.

Change this logic to always recompile anything that directly depends on
an active cros_workon package in order to ensure that a user's local
changes to the package are always correctly reflected in the contents of
the overall build.

BUG=chromium:1071530, chromium:1017842
TEST=`build_packages`
TEST=CQ

Change-Id: I37b6752541f9481667983b12d7f79e143dd3b1c9
Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform/crosutils/+/2250552
Commit-Queue: Chris McDonald <cjmcdonald@chromium.org>
Tested-by: Chris McDonald <cjmcdonald@chromium.org>
Reviewed-by: Mike Frysinger <vapier@chromium.org>
diff --git a/build_packages b/build_packages
index fe1477a..6a9f5f9 100755
--- a/build_packages
+++ b/build_packages
@@ -304,6 +304,31 @@
 # cros_workon packages always have to be rebuilt.
 FORCE_LOCAL_BUILD_PKGS+=( "${CROS_WORKON_PKGS[@]}" )
 
+# Any package that directly depends on an active cros_workon package also needs
+# to be rebuilt in order to be correctly built against the current set of
+# changes a user may have made to the cros_workon package.
+if [[ ${#CROS_WORKON_PKGS[@]} -gt 0 ]]; then
+  # Collect all installed packages that depend on active cros_workon packages.
+  WORKON_PKG_CONSUMERS=()
+  mapfile -t WORKON_PKG_CONSUMERS < <( \
+    equery-${FLAGS_board} -q depends "${CROS_WORKON_PKGS[@]}" | sort -u )
+
+  # Transform this list of packages with versions in to a list of just
+  # $CATEGORY/$NAME entries, since we don't want to pass packages with explicit
+  # version numbers as arguments to `emerge`.
+  if [[ ${#WORKON_PKG_CONSUMERS[@]} -gt 0 ]]; then
+    WORKON_REBUILD_PKGS=()
+    mapfile -t WORKON_REBUILD_PKGS < <( \
+      equery-${FLAGS_board} list -p -o --format='$category/$name' \
+        "${WORKON_PKG_CONSUMERS[@]}" | sort -u )
+
+    info "The following packages depend directly on an active" \
+      "cros_workon package and will be rebuilt: ${WORKON_REBUILD_PKGS[*]}"
+
+    FORCE_LOCAL_BUILD_PKGS+=( "${WORKON_REBUILD_PKGS[@]}" )
+  fi
+fi
+
 if [[ -n "${FLAGS_board_root}" ]]; then
   export ROOT="${FLAGS_board_root}"
   export PORTAGE_CONFIGROOT="${ROOT}"