1*36ac495dSmrg#! /usr/bin/python2 2*36ac495dSmrgimport os.path 3*36ac495dSmrgimport sys 4*36ac495dSmrgimport shlex 5*36ac495dSmrgimport re 6*36ac495dSmrg 7*36ac495dSmrgfrom headerutils import * 8*36ac495dSmrg 9*36ac495dSmrg 10*36ac495dSmrgtabstop = 2 11*36ac495dSmrgpadding = " " 12*36ac495dSmrgseen = { } 13*36ac495dSmrgoutput = list() 14*36ac495dSmrgsummary = list() 15*36ac495dSmrgsawcore = False 16*36ac495dSmrg 17*36ac495dSmrg# list of headers to emphasize 18*36ac495dSmrghighlight = list () 19*36ac495dSmrg 20*36ac495dSmrgbld_dir = "" 21*36ac495dSmrg# search path for headers 22*36ac495dSmrgincl_dirs = ["../include", "../libcpp/include", "common", "c-family", "c", "cp", "config" ] 23*36ac495dSmrg# extra search paths to look in *after* the directory the source file is in. 24*36ac495dSmrg 25*36ac495dSmrg# append (1) to the end of the first line which includes INC in list INC. 26*36ac495dSmrgdef append_1 (output, inc): 27*36ac495dSmrg for n,t in enumerate (output): 28*36ac495dSmrg idx = t.find(inc) 29*36ac495dSmrg if idx != -1: 30*36ac495dSmrg eos = idx + len (inc) 31*36ac495dSmrg t = t[:eos] + " (1)" + t[eos+1:] 32*36ac495dSmrg output[n] = t 33*36ac495dSmrg return 34*36ac495dSmrg 35*36ac495dSmrg# These headers show up as duplicates in rtl.h due to conditional code arund the includes 36*36ac495dSmrgrtl_core = [ "machmode.h" , "signop.h" , "wide-int.h" , "double-int.h" , "real.h" , "fixed-value.h" , "statistics.h" , "vec.h" , "hash-table.h" , "hash-set.h" , "input.h" , "is-a.h" ] 37*36ac495dSmrg 38*36ac495dSmrgdef find_include_data (inc): 39*36ac495dSmrg global sawcore 40*36ac495dSmrg for x in incl_dirs: 41*36ac495dSmrg nm = x+"/"+inc 42*36ac495dSmrg if os.path.exists (nm): 43*36ac495dSmrg info = find_unique_include_list (nm) 44*36ac495dSmrg # rtl.h mimics coretypes for GENERATOR FILES, remove if coretypes.h seen. 45*36ac495dSmrg if inc == "coretypes.h": 46*36ac495dSmrg sawcore = True 47*36ac495dSmrg elif inc == "rtl.h" and sawcore: 48*36ac495dSmrg for i in rtl_core: 49*36ac495dSmrg if i in info: 50*36ac495dSmrg info.remove (i) 51*36ac495dSmrg return info 52*36ac495dSmrg return list() 53*36ac495dSmrg 54*36ac495dSmrgdef process_include (inc, indent): 55*36ac495dSmrg if inc[-2:] != ".h": 56*36ac495dSmrg return 57*36ac495dSmrg bname = os.path.basename (inc) 58*36ac495dSmrg if bname in highlight: 59*36ac495dSmrg arrow = " <<-------" 60*36ac495dSmrg if bname not in summary: 61*36ac495dSmrg summary.append (bname) 62*36ac495dSmrg else: 63*36ac495dSmrg arrow = "" 64*36ac495dSmrg if seen.get(inc) == None: 65*36ac495dSmrg seen[inc] = 1 66*36ac495dSmrg output.append (padding[:indent*tabstop] + bname + arrow) 67*36ac495dSmrg info = find_include_data (inc) 68*36ac495dSmrg for y in info: 69*36ac495dSmrg process_include (y, indent+1) 70*36ac495dSmrg else: 71*36ac495dSmrg seen[inc] += 1 72*36ac495dSmrg if (seen[inc] == 2): 73*36ac495dSmrg append_1(output, inc) 74*36ac495dSmrg output.append (padding[:indent*tabstop] + bname + " ("+str(seen[inc])+")" + arrow) 75*36ac495dSmrg 76*36ac495dSmrg 77*36ac495dSmrg 78*36ac495dSmrgextradir = list() 79*36ac495dSmrgusage = False 80*36ac495dSmrgsrc = list() 81*36ac495dSmrg 82*36ac495dSmrgfor x in sys.argv[1:]: 83*36ac495dSmrg if x[0:2] == "-i": 84*36ac495dSmrg bld = x[2:] 85*36ac495dSmrg extradir.append (bld) 86*36ac495dSmrg elif x[0:2] == "-s": 87*36ac495dSmrg highlight.append (os.path.basename (x[2:])) 88*36ac495dSmrg elif x[0:2] == "-h": 89*36ac495dSmrg usage = True 90*36ac495dSmrg else: 91*36ac495dSmrg src.append (x) 92*36ac495dSmrg 93*36ac495dSmrgif len(src) != 1: 94*36ac495dSmrg usage = True 95*36ac495dSmrgelif not os.path.exists (src[0]): 96*36ac495dSmrg print src[0] + ": Requested source file does not exist.\n" 97*36ac495dSmrg usage = True 98*36ac495dSmrg 99*36ac495dSmrgif usage: 100*36ac495dSmrg print "show-headers [-idir] [-sfilen] file1 " 101*36ac495dSmrg print " " 102*36ac495dSmrg print " Show a hierarchical visual format how many times each header file" 103*36ac495dSmrg print " is included in a source file. Should be run from the source directory" 104*36ac495dSmrg print " files from find-include-depends" 105*36ac495dSmrg print " -s : search for a header, and point it out." 106*36ac495dSmrg print " -i : Specifies additonal directories to search for includes." 107*36ac495dSmrg sys.exit(0) 108*36ac495dSmrg 109*36ac495dSmrg 110*36ac495dSmrg 111*36ac495dSmrgif extradir: 112*36ac495dSmrg incl_dirs = extradir + incl_dirs; 113*36ac495dSmrg 114*36ac495dSmrgblddir = find_gcc_bld_dir ("../..") 115*36ac495dSmrg 116*36ac495dSmrgif blddir: 117*36ac495dSmrg print "Using build directory: " + blddir 118*36ac495dSmrg incl_dirs.insert (0, blddir) 119*36ac495dSmrgelse: 120*36ac495dSmrg print "Could not find a build directory, better results if you specify one with -i" 121*36ac495dSmrg 122*36ac495dSmrg# search path is now ".", blddir, extradirs_from_-i, built_in_incl_dirs 123*36ac495dSmrgincl_dirs.insert (0, ".") 124*36ac495dSmrg 125*36ac495dSmrg# if source is in a subdirectory, prepend the subdirectory to the search list 126*36ac495dSmrgx = src[0] 127*36ac495dSmrgsrcpath = os.path.dirname(x) 128*36ac495dSmrgif srcpath: 129*36ac495dSmrg incl_dirs.insert (0, srcpath) 130*36ac495dSmrg 131*36ac495dSmrgoutput = list() 132*36ac495dSmrgsawcore = False 133*36ac495dSmrg 134*36ac495dSmrgdata = open (x).read().splitlines() 135*36ac495dSmrgfor line in data: 136*36ac495dSmrg d = find_pound_include (line, True, True) 137*36ac495dSmrg if d and d[-2:] == ".h": 138*36ac495dSmrg process_include (d, 1) 139*36ac495dSmrg 140*36ac495dSmrgprint "\n" + x 141*36ac495dSmrgfor line in output: 142*36ac495dSmrg print line 143*36ac495dSmrg 144*36ac495dSmrgif highlight: 145*36ac495dSmrg print " " 146*36ac495dSmrg for h in summary: 147*36ac495dSmrg print h + " is included by source file." 148*36ac495dSmrg for h in highlight: 149*36ac495dSmrg if h not in summary: 150*36ac495dSmrg print h + " is not included by source file." 151*36ac495dSmrg 152