-
Notifications
You must be signed in to change notification settings - Fork 620
Skip RPATH patching on Schema v1 builds #5318
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: master
Are you sure you want to change the base?
Changes from all commits
64ea4e8
4bb44a1
e590264
cef212a
0691dd8
e680bc4
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -16,6 +16,7 @@ | |
| from collections import namedtuple | ||
| import contextlib | ||
| import datetime | ||
| import json | ||
| import os | ||
| import re | ||
| import shutil | ||
|
|
@@ -378,6 +379,19 @@ def _pre_setup(self): | |
| environment.set_value(self.env_prefix + 'APP_PATH', '') | ||
| environment.set_value(self.env_prefix + 'APP_PATH_DEBUG', '') | ||
|
|
||
| def _read_schema_version_from_manifest(self, build_dir: str) -> int: | ||
| """Reads archive_schema_version from clusterfuzz_manifest.json.""" | ||
| manifest_path = os.path.join(build_dir, 'clusterfuzz_manifest.json') | ||
| if not os.path.exists(manifest_path): | ||
| return 0 | ||
| try: | ||
| with open(manifest_path) as f: | ||
| manifest = json.load(f) | ||
| return int(manifest.get('archive_schema_version') or 0) | ||
| except Exception as e: | ||
| logs.warning(f'Failed to read schema version from {manifest_path}: {e}') | ||
| return 0 | ||
|
|
||
| def _patch_rpath(self, binary_path, instrumented_library_paths): | ||
| """Patch rpaths of a binary to point to instrumented libraries""" | ||
| rpaths = get_rpaths(binary_path) | ||
|
|
@@ -390,22 +404,39 @@ def _patch_rpath(self, binary_path, instrumented_library_paths): | |
|
|
||
| set_rpaths(binary_path, rpaths) | ||
|
|
||
| def _patch_rpaths(self, instrumented_library_paths): | ||
| def _patch_rpaths(self, | ||
| build_dir: str | None = None, | ||
| app_path_env: str | None = None): | ||
|
Comment on lines
+407
to
+409
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think it would be a bit easier to follow if def _patch_rpaths(build_dir: str, app_path_env: str):
...
if environment.is_engine_fuzzer_job():
...
assert app_path_env
... |
||
| """Patch rpaths of builds to point to instrumented libraries.""" | ||
| instrumented_library_paths = environment.get_instrumented_libraries_paths() | ||
| if not instrumented_library_paths: | ||
| return | ||
|
|
||
| if not build_dir: | ||
| build_dir = self.build_dir | ||
|
|
||
| schema_version = self._read_schema_version_from_manifest(build_dir) | ||
| if schema_version > 0: | ||
| logs.info('Skipping RPATH patching for schema v1+ build.') | ||
| return | ||
|
|
||
| if environment.is_engine_fuzzer_job(): | ||
| # Import here as this path is not available in App Engine context. | ||
| from clusterfuzz._internal.bot.fuzzers import utils as fuzzer_utils | ||
|
|
||
| for target_path in fuzzer_utils.get_fuzz_targets(self.build_dir): | ||
| for target_path in fuzzer_utils.get_fuzz_targets(build_dir): | ||
| self._patch_rpath(target_path, instrumented_library_paths) | ||
| else: | ||
|
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Consider an early return here to reduce nesting. |
||
| app_path = environment.get_value('APP_PATH') | ||
| if app_path: | ||
| self._patch_rpath(app_path, instrumented_library_paths) | ||
|
|
||
| app_path_debug = environment.get_value('APP_PATH_DEBUG') | ||
| if app_path_debug: | ||
| self._patch_rpath(app_path_debug, instrumented_library_paths) | ||
| if app_path_env: | ||
| app_paths = [environment.get_value(app_path_env)] | ||
| else: | ||
| app_paths = [ | ||
| environment.get_value('APP_PATH'), | ||
| environment.get_value('APP_PATH_DEBUG') | ||
| ] | ||
|
Comment on lines
+433
to
+436
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I don't think we ever want to fix both at once now that we're calling this method twice for symbolized builds. See also my comment above. |
||
| for app_path in app_paths: | ||
| if app_path: | ||
| self._patch_rpath(app_path, instrumented_library_paths) | ||
|
|
||
| def _post_setup_success(self, update_revision=True): | ||
| """Common post-setup.""" | ||
|
|
@@ -417,11 +448,6 @@ def _post_setup_success(self, update_revision=True): | |
| timestamp_file_path = os.path.join(self.base_build_dir, TIMESTAMP_FILE) | ||
| utils.write_data_to_file(time.time(), timestamp_file_path) | ||
|
|
||
| # Update rpaths if necessary (for e.g. instrumented libraries). | ||
| instrumented_library_paths = environment.get_instrumented_libraries_paths() | ||
| if instrumented_library_paths: | ||
| self._patch_rpaths(instrumented_library_paths) | ||
|
|
||
| @contextlib.contextmanager | ||
| def _download_and_open_build_archive(self, base_build_dir: str, | ||
| build_dir: str, build_url: str): | ||
|
|
@@ -769,6 +795,7 @@ def setup(self): | |
|
|
||
| self._setup_application_path(build_update=build_update) | ||
| self._post_setup_success(update_revision=build_update) | ||
| self._patch_rpaths() | ||
|
Comment on lines
796
to
+798
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
_patch_rpaths(self.build_dir, 'APP_PATH') |
||
| return True | ||
|
|
||
|
|
||
|
|
@@ -879,12 +906,16 @@ def setup(self): | |
| self._setup_application_path( | ||
| self.release_build_dir, build_update=build_update) | ||
| environment.set_value('BUILD_URL', self.release_build_url) | ||
| self._patch_rpaths( | ||
| build_dir=self.release_build_dir, app_path_env='APP_PATH') | ||
|
|
||
| if self.debug_build_url: | ||
| # Note: this will override LLVM_SYMBOLIZER_PATH, APP_DIR etc from the | ||
| # previous release setup, which may not be desirable behaviour. | ||
| self._setup_application_path( | ||
| self.debug_build_dir, 'APP_PATH_DEBUG', build_update=build_update) | ||
| self._patch_rpaths( | ||
| build_dir=self.debug_build_dir, app_path_env='APP_PATH_DEBUG') | ||
|
|
||
| self._post_setup_success(update_revision=build_update) | ||
| return True | ||
|
|
@@ -989,6 +1020,7 @@ def setup(self): | |
| self._fuzz_targets = list(self._get_fuzz_targets_from_dir(self.build_dir)) | ||
| self._setup_application_path(build_update=build_update) | ||
| self._post_setup_success(update_revision=build_update) | ||
| self._patch_rpaths() | ||
| return True | ||
|
|
||
|
|
||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
AFAICT this method does not use
self. Move it to a helper outside the class, or annotate it as@staticmethod.