1#!/usr/bin/env python3 2# coding: utf-8 3# 4# © 2021 Qualcomm Innovation Center, Inc. All rights reserved. 5# 6# SPDX-License-Identifier: BSD-3-Clause 7 8""" 9Simple script to parse the compile_commands to extract generated source and 10header files, to pass to cscope or other source indexing tools. 11""" 12 13import json 14import sys 15import os 16import re 17 18build_dir = 'build' 19commands_file = 'compile_commands.json' 20compile_commands = [] 21 22conf_default_weight = 60 23build_preferences = {} 24 25files = set() 26incdirs = set() 27 28include_regex = re.compile('(-iquote|-I) (\\w+[-\\{:s}\\w]+)'.format(os.sep)) 29imacros_regex = re.compile('(-imacros) (\\w+[-\\{:s}\\w.]+)'.format(os.sep)) 30 31for dir, dir_dirs, dir_files in os.walk('config/featureset'): 32 regex = re.compile('^# indexer-weight: (\\d+)') 33 for file in dir_files: 34 file_base = os.path.splitext(file)[0] 35 if file.endswith('.conf'): 36 build_preferences[file_base] = conf_default_weight 37 infile = os.path.join(dir, file) 38 with open(infile, 'r') as f: 39 for i, line in enumerate(f): 40 weights = regex.findall(line) 41 if weights: 42 build_preferences[file_base] = int(weights[0]) 43 44for dir, dir_dirs, dir_files in os.walk(build_dir): 45 if commands_file in dir_files: 46 x = os.stat(dir) 47 time = max(x.st_atime, x.st_mtime, x.st_ctime) 48 compile_commands.append((time, os.path.join(dir, commands_file))) 49 50if not compile_commands: 51 print('no build found!', file=sys.stderr) 52 exit(1) 53 54newest = 0.0 55 56for time, f in compile_commands: 57 x = os.stat(f) 58 time = max(x.st_atime, x.st_mtime, x.st_ctime, time) 59 for p in build_preferences.keys(): 60 if p in f: 61 # Boost these to preference them 62 time += build_preferences[p] 63 64 if time > newest: 65 newest = time 66 infile = f 67 68if len(compile_commands) > 1: 69 print('warning: multiple builds found, using: {:s}'.format( 70 infile), file=sys.stderr) 71 72try: 73 with open(infile, 'r') as f: 74 compile = json.loads(f.read()) 75 76 for s in compile: 77 if s['file'].startswith(build_dir): 78 files.add(s['file']) 79 cmd = s['command'] 80 for t, dir in include_regex.findall(cmd): 81 if dir.startswith(build_dir): 82 incdirs.add(dir) 83 for t, f in imacros_regex.findall(cmd): 84 files.add(f) 85except FileNotFoundError: 86 exit(1) 87 88for dir in incdirs: 89 try: 90 for f in os.listdir(dir): 91 filename = os.path.join(dir, f) 92 if filename.endswith('.h'): 93 files.add(filename) 94 except OSError: 95 pass 96 97for f in files: 98 print(f) 99