Anas Nashif | f026b47 | 2021-06-04 13:09:47 -0400 | [diff] [blame] | 1 | #!/usr/bin/env python3 |
| 2 | # Copyright (c) 2021 Intel Corporation |
| 3 | # |
| 4 | # SPDX-License-Identifier: Apache-2.0 |
| 5 | |
| 6 | # A script to diff between two ram or rom reports generated by |
| 7 | # size_report. When you call call the ram_report or rom_report targets you |
| 8 | # end up with a json file in the build directory that can be used as input |
| 9 | # for this script. |
| 10 | |
Nazar Kazakov | f483b1b | 2022-03-16 21:07:43 +0000 | [diff] [blame] | 11 | # The output shows which symbols increased and which decreased in size and |
Anas Nashif | f026b47 | 2021-06-04 13:09:47 -0400 | [diff] [blame] | 12 | # also tracked added/remove symbols as well. |
| 13 | |
| 14 | # Example: |
| 15 | # ./scripts/footprint/fpdiff.py ram1.json ram2.json |
| 16 | |
| 17 | from anytree.importer import DictImporter |
| 18 | from anytree import PreOrderIter |
| 19 | from anytree.search import find |
| 20 | |
Stephanos Ioannidis | 2ee02f9 | 2022-05-23 19:15:23 +0900 | [diff] [blame] | 21 | import colorama |
Anas Nashif | f026b47 | 2021-06-04 13:09:47 -0400 | [diff] [blame] | 22 | from colorama import Fore |
| 23 | import json |
| 24 | import argparse |
| 25 | |
| 26 | importer = DictImporter() |
| 27 | |
| 28 | def parse_args(): |
| 29 | parser = argparse.ArgumentParser( |
Jamie McCrae | ec70444 | 2023-01-04 16:08:36 +0000 | [diff] [blame] | 30 | description="Compare footprint sizes of two builds.", allow_abbrev=False) |
Anas Nashif | f026b47 | 2021-06-04 13:09:47 -0400 | [diff] [blame] | 31 | parser.add_argument("file1", help="First file") |
| 32 | parser.add_argument("file2", help="Second file") |
| 33 | |
| 34 | return parser.parse_args() |
| 35 | |
| 36 | def main(): |
Stephanos Ioannidis | 2ee02f9 | 2022-05-23 19:15:23 +0900 | [diff] [blame] | 37 | colorama.init() |
| 38 | |
Anas Nashif | f026b47 | 2021-06-04 13:09:47 -0400 | [diff] [blame] | 39 | args = parse_args() |
| 40 | |
| 41 | with open(args.file1, "r") as f: |
Anas Nashif | 88d4299 | 2022-05-04 13:43:51 -0400 | [diff] [blame] | 42 | data1 = json.load(f) |
Anas Nashif | f026b47 | 2021-06-04 13:09:47 -0400 | [diff] [blame] | 43 | |
| 44 | with open(args.file2, "r") as f: |
Anas Nashif | 88d4299 | 2022-05-04 13:43:51 -0400 | [diff] [blame] | 45 | data2 = json.load(f) |
Anas Nashif | f026b47 | 2021-06-04 13:09:47 -0400 | [diff] [blame] | 46 | |
Anas Nashif | 88d4299 | 2022-05-04 13:43:51 -0400 | [diff] [blame] | 47 | for idx, ch in enumerate(data1['symbols']['children']): |
| 48 | root1 = importer.import_(ch) |
| 49 | root2 = importer.import_(data2['symbols']['children'][idx]) |
| 50 | print(f"{root1.name}\n+++++++++++++++++++++") |
Anas Nashif | f026b47 | 2021-06-04 13:09:47 -0400 | [diff] [blame] | 51 | |
Anas Nashif | 88d4299 | 2022-05-04 13:43:51 -0400 | [diff] [blame] | 52 | for node in PreOrderIter(root1): |
| 53 | # pylint: disable=undefined-loop-variable |
| 54 | n = find(root2, lambda node2: node2.identifier == node.identifier) |
| 55 | if n: |
| 56 | if n.size != node.size: |
| 57 | diff = n.size - node.size |
| 58 | if diff == 0: |
| 59 | continue |
| 60 | if not n.children or not n.parent: |
| 61 | if diff < 0: |
| 62 | print(f"{n.identifier} -> {Fore.GREEN}{diff}{Fore.RESET}") |
| 63 | else: |
| 64 | print(f"{n.identifier} -> {Fore.RED}+{diff}{Fore.RESET}") |
Anas Nashif | f026b47 | 2021-06-04 13:09:47 -0400 | [diff] [blame] | 65 | |
Anas Nashif | 88d4299 | 2022-05-04 13:43:51 -0400 | [diff] [blame] | 66 | else: |
| 67 | if not node.children: |
| 68 | print(f"{node.identifier} ({Fore.GREEN}-{node.size}{Fore.RESET}) disappeared.") |
| 69 | |
| 70 | for node in PreOrderIter(root2): |
| 71 | n = find(root1, lambda node2: node2.identifier == node.identifier) |
| 72 | if not n: |
| 73 | if not node.children and node.size != 0: |
| 74 | print(f"{node.identifier} ({Fore.RED}+{node.size}{Fore.RESET}) is new.") |
Anas Nashif | f026b47 | 2021-06-04 13:09:47 -0400 | [diff] [blame] | 75 | |
| 76 | |
| 77 | if __name__ == "__main__": |
| 78 | main() |