{"id":13732357,"url":"https://github.com/aras-p/ClangBuildAnalyzer","last_synced_at":"2025-05-08T06:32:01.521Z","repository":{"id":37431627,"uuid":"202865539","full_name":"aras-p/ClangBuildAnalyzer","owner":"aras-p","description":"Clang build analysis tool using -ftime-trace","archived":false,"fork":false,"pushed_at":"2025-03-21T04:55:04.000Z","size":2415,"stargazers_count":1091,"open_issues_count":16,"forks_count":69,"subscribers_count":23,"default_branch":"main","last_synced_at":"2025-05-03T11:07:15.879Z","etag":null,"topics":["build-analysis","clang"],"latest_commit_sha":null,"homepage":null,"language":"C++","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"unlicense","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/aras-p.png","metadata":{"files":{"readme":"readme.md","changelog":null,"contributing":null,"funding":null,"license":"license.md","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null}},"created_at":"2019-08-17T10:13:22.000Z","updated_at":"2025-05-01T19:19:48.000Z","dependencies_parsed_at":"2022-08-03T03:46:07.126Z","dependency_job_id":"c24246e5-c413-463d-98da-7e048b05889f","html_url":"https://github.com/aras-p/ClangBuildAnalyzer","commit_stats":{"total_commits":199,"total_committers":27,"mean_commits":7.37037037037037,"dds":"0.29145728643216084","last_synced_commit":"bae0cb488cce944bfc3da9850a69ad621701ebef"},"previous_names":[],"tags_count":8,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/aras-p%2FClangBuildAnalyzer","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/aras-p%2FClangBuildAnalyzer/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/aras-p%2FClangBuildAnalyzer/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/aras-p%2FClangBuildAnalyzer/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/aras-p","download_url":"https://codeload.github.com/aras-p/ClangBuildAnalyzer/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":252180036,"owners_count":21707120,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["build-analysis","clang"],"created_at":"2024-08-03T02:01:54.062Z","updated_at":"2025-05-08T06:31:56.513Z","avatar_url":"https://github.com/aras-p.png","language":"C++","readme":"# Clang Build Analyzer [![Build Status](https://github.com/aras-p/ClangBuildAnalyzer/workflows/build_and_test/badge.svg)](https://github.com/aras-p/ClangBuildAnalyzer/actions)\n\nClang C/C++ build analysis tool when using Clang 9+ `-ftime-trace`. The `-ftime-trace` compiler flag\n(see [blog post](https://aras-p.info/blog/2019/01/16/time-trace-timeline-flame-chart-profiler-for-Clang/) or\n[Clang 9 release notes](https://releases.llvm.org/9.0.0/tools/clang/docs/ReleaseNotes.html#new-compiler-flags)) can be useful\nto figure out what takes time during compilation of *one* source file. This tool helps to aggregate time trace\nreports from multiple compilations, and output \"what took the most time\" summary:\n\n- Which files are slowest to parse? i.e. spend time in compiler lexer/parser front-end\n- Which C++ templates took the most time to instantiate?\n- Which files are slowest to generate code for? i.e. spend time in compiler backend doing codegen and optimizations\n- Which functions are slowest to generate code for?\n- Which header files are included the most in the whole build, how much time is spent parsing them, and what are the include chains of them?\n\n\n### Usage\n\n1. **Start the build capture**: `ClangBuildAnalyzer --start \u003cartifacts_folder\u003e`\u003cbr/\u003e\n   This will write current timestamp in a `ClangBuildAnalyzerSession.txt` file under the given `artifacts_folder`. The artifacts\n   folder is where the compiled object files (and time trace report files) are expected to be produced by your build.\n1. **Do your build**. Does not matter how; an IDE build, a makefile, a shell script, whatever. As long as it invokes\n   Clang and passes `-ftime-trace` flag to the compiler (**Clang 9.0 or later is required** for this).\n1. **Stop the build capture**: `ClangBuildAnalyzer --stop \u003cartifacts_folder\u003e \u003ccapture_file\u003e`\u003cbr/\u003e\n   This will load all Clang time trace compatible `*.json` files under the given `artifacts_folder` that were modified after\n   `--start` step was done (Clang `-ftime-trace` produces one JSON file next to each object file), process them and store data file into\n   a binary `capture_file`.\n1. **Run the build analysis**: `ClangBuildAnalyzer --analyze \u003ccapture_file\u003e`\u003cbr/\u003e\n   This will read the `capture_file` produced by `--stop` step, calculate the slowest things and print them. If a\n   `ClangBuildAnalyzer.ini` file exists in the current folder, it will be read to control how many of various things to print.\n\nAternatively, instead of doing `--start` and `--stop` steps, you can do `ClangBuildAnalyzer --all \u003cartifacts_folder\u003e \u003ccapture_file\u003e` after your build; that will\ninclude all the compatible `*.json` files for analysis, no matter when they were produced.\n\n\n### Analysis Output\n\nThe analysis output will look something like this:\n\n```\nAnalyzing build trace from 'artifacts/FullCapture.bin'...\n**** Time summary:\nCompilation (7664 times):\n  Parsing (frontend):         2118.9 s\n  Codegen \u0026 opts (backend):   1204.1 s\n\n**** Files that took longest to parse (compiler frontend):\n  5084 ms: cycles_scene.build/RelWithDebInfo/volume.o\n  4471 ms: extern_ceres.build/RelWithDebInfo/covariance_impl.o\n  4225 ms: bf_intern_libmv.build/RelWithDebInfo/resect.o\n  4121 ms: bf_blenkernel.build/RelWithDebInfo/volume_to_mesh.o\n \n**** Files that took longest to codegen (compiler backend):\n 47123 ms: bf_blenkernel.build/RelWithDebInfo/volume.o\n 39617 ms: bf_blenkernel.build/RelWithDebInfo/volume_to_mesh.o\n 37488 ms: bf_modifiers.build/RelWithDebInfo/MOD_volume_displace.o\n 30676 ms: bf_gpu.build/RelWithDebInfo/gpu_shader_create_info.o\n\n**** Templates that took longest to instantiate:\n 11172 ms: fmt::detail::vformat_to\u003cchar\u003e (142 times, avg 78 ms)\n  6662 ms: std::__scalar_hash\u003cstd::_PairT, 2\u003e::operator() (3549 times, avg 1 ms)\n  6281 ms: std::__murmur2_or_cityhash\u003cunsigned long, 64\u003e::operator() (3549 times, avg 1 ms)\n  5757 ms: std::basic_string\u003cchar\u003e::basic_string (3597 times, avg 1 ms)\n  5541 ms: blender::CPPType::to_static_type_tag\u003cfloat, blender::VecBase\u003cfloat, ... (70 times, avg 79 ms)\n\n**** Template sets that took longest to instantiate:\n 32421 ms: std::unique_ptr\u003c$\u003e (30461 times, avg 1 ms)\n 30098 ms: Eigen::MatrixBase\u003c$\u003e (8639 times, avg 3 ms)\n 27524 ms: Eigen::internal::call_assignment_no_alias\u003c$\u003e (2397 times, avg 11 ms)\n\n**** Functions that took longest to compile:\n 28359 ms: gpu_shader_create_info_init (source/blender/gpu/intern/gpu_shader_create_info.cc)\n  4090 ms: ccl::GetConstantValues(ccl::KernelData const*) (intern/cycles/device/metal/kernel.mm)\n  3996 ms: gpu_shader_dependency_init (source/blender/gpu/intern/gpu_shader_dependency.cc)\n\n**** Function sets that took longest to compile / optimize:\n 10606 ms: bool openvdb::v10_0::tree::NodeList\u003c$\u003e::initNodeChildren\u003c$\u003e(openvdb:... (470 times, avg 22 ms)\n  9640 ms: void tbb::interface9::internal::dynamic_grainsize_mode\u003c$\u003e::work_bala... (919 times, avg 10 ms)\n  9459 ms: void tbb::interface9::internal::dynamic_grainsize_mode\u003c$\u003e::work_bala... (715 times, avg 13 ms)\n  7279 ms: blender::Vector\u003c$\u003e::realloc_to_at_least(long long) (1840 times, avg 3 ms)\n \n**** Expensive headers:\n261580 ms: /Developer/SDKs/MacOSX13.1.sdk/usr/include/c++/v1/algorithm (included 3389 times, avg 77 ms), included via:\n  341x: BKE_context.h BLI_string_ref.hh string \n  180x: DNA_mesh_types.h BLI_math_vector_types.hh array \n  125x: DNA_space_types.h DNA_node_types.h DNA_node_tree_interface_types.h BLI_function_ref.hh BLI_memory_utils.hh \n  ...\n\n188777 ms: /Developer/SDKs/MacOSX13.1.sdk/usr/include/c++/v1/string (included 3447 times, avg 54 ms), included via:\n  353x: BKE_context.h BLI_string_ref.hh \n  184x: DNA_mesh_types.h BLI_offset_indices.hh BLI_index_mask.hh BLI_linear_allocator.hh BLI_string_ref.hh \n  131x: DNA_node_types.h DNA_node_tree_interface_types.h BLI_span.hh \n  ...\n\n174792 ms: source/blender/makesdna/DNA_node_types.h (included 1653 times, avg 105 ms), included via:\n  316x: ED_screen.hh DNA_space_types.h \n  181x: DNA_space_types.h \n  173x: \u003cdirect include\u003e\n  ...\n```\n\nGranularity and amount of most expensive things (files, functions, templates, includes) that are reported can be controlled by having an\n`ClangBuildAnalyzer.ini` file in the working directory. Take a look at [`ClangBuildAnalyzer.ini`](/ClangBuildAnalyzer.ini) for an example.\n\n\n### Building it\n\n* Windows: Visual Studio 2019 solution at `projects/vs2019/ClangBuildAnalyzer.sln`.\n* Mac: Xcode 10.x project at `projects/xcode/ClangBuildAnalyzer.xcodeproj`.\n* Linux: Makefile for gcc (tested with 7.4), build with `make -f projects/make/Makefile`.\n* You can also use provided `CMakeLists.txt`, if you want to build using `CMake`.\n\n### Limitations\n\n* Does not capture anything related to linking or LTO right now.\n* May or may not scale to _huge_ builds (I haven't tried on something ginormous like a Chrome\n  build). However I have tried it on Unity editor and Blender builds and it worked fine.\n\n\n### License\n\nLicense for the Clang Build Analyzer itself is [Unlicense](https://unlicense.org/), i.e. public domain. However, the source code\nincludes several external library source files (all under `src/external`), each with their own license:\n\n* `cute_files.h` from [RandyGaul/cute_headers](https://github.com/RandyGaul/cute_headers): zlib or public domain,\n* `cwalk` from [likle/cwalk](https://github.com/likle/cwalk): MIT,\n* `enkiTS`, from [dougbinks/enkiTS](https://github.com/dougbinks/enkiTS): zlib, version 058150d2 (2024 Apr),\n* `flat_hash_map`, from [skarupke/flat_hash_map](https://github.com/skarupke/flat_hash_map): Boost 1.0,\n* `inih`, from [benhoyt/inih](https://github.com/benhoyt/inih): BSD 3 clause,\n* `llvm-Demangle`, part of [LLVM](https://llvm.org/): Apache-2.0 with LLVM-exception,\n* `simdjson` from [lemire/simdjson](https://github.com/lemire/simdjson): Apache-2.0, version 3.10.1 (2024 Aug),\n* `sokol_time.h` from [floooh/sokol](https://github.com/floooh/sokol): zlib/libpng,\n* `xxHash` from [Cyan4973/xxHash](https://github.com/Cyan4973/xxHash): BSD 2 clause, version 0.8.2 (2023 Jul).\n","funding_links":[],"categories":["Tools"],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Faras-p%2FClangBuildAnalyzer","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Faras-p%2FClangBuildAnalyzer","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Faras-p%2FClangBuildAnalyzer/lists"}