''', file=self.stream)
class IndexRenderer:
    def __init__(self, output_dir):
        self.stream = open(os.path.join(output_dir, 'index.html'), 'w')
    def render_entry(self, r, odd):
        escaped_name = cgi.escape(r.DemangledFunctionName)
        print('''
'''.format(**locals()), file=self.stream)
    def render(self, all_remarks):
        print('''
| Source Location | Hotness | Function | Pass | 
''', file=self.stream)
        for i, remark in enumerate(all_remarks):
            self.render_entry(remark, i % 2)
        print('''
''', file=self.stream)
def _render_file(source_dir, output_dir, ctx, entry):
    global context
    context = ctx
    filename, remarks = entry
    SourceFileRenderer(source_dir, output_dir, filename).render(remarks)
def map_remarks(all_remarks):
    # Set up a map between function names and their source location for
    # function where inlining happened
    for remark in all_remarks.itervalues():
        if isinstance(remark, optrecord.Passed) and remark.Pass == "inline" and remark.Name == "Inlined":
            for arg in remark.Args:
                caller = arg.get('Caller')
                if caller:
                    context.caller_loc[caller] = arg['DebugLoc']
def generate_report(pmap, all_remarks, file_remarks, source_dir, output_dir, should_display_hotness):
    try:
        os.makedirs(output_dir)
    except OSError as e:
        if e.errno == errno.EEXIST and os.path.isdir(output_dir):
            pass
        else:
            raise
    _render_file_bound = functools.partial(_render_file, source_dir, output_dir, context)
    pmap(_render_file_bound, file_remarks.items())
    if should_display_hotness:
        sorted_remarks = sorted(all_remarks.itervalues(), key=lambda r: (r.Hotness, r.File, r.Line, r.Column, r.__dict__), reverse=True)
    else:
        sorted_remarks = sorted(all_remarks.itervalues(), key=lambda r: (r.File, r.Line, r.Column, r.__dict__))
    IndexRenderer(args.output_dir).render(sorted_remarks)
    shutil.copy(os.path.join(os.path.dirname(os.path.realpath(__file__)),
            "style.css"), output_dir)
if __name__ == '__main__':
    parser = argparse.ArgumentParser(description=desc)
    parser.add_argument('yaml_files', nargs='+')
    parser.add_argument('output_dir')
    parser.add_argument(
        '--jobs',
        '-j',
        default=cpu_count(),
        type=int,
        help='Max job count (defaults to current CPU count)')
    parser.add_argument(
        '-source-dir',
        '-s',
        default='',
        help='set source directory')
    args = parser.parse_args()
    if len(args.yaml_files) == 0:
        parser.print_help()
        sys.exit(1)
    if args.jobs == 1:
        pmap = map
    else:
        pool = Pool(processes=args.jobs)
        pmap = pool.map
    all_remarks, file_remarks, should_display_hotness = optrecord.gather_results(pmap, args.yaml_files)
    map_remarks(all_remarks)
    generate_report(pmap, all_remarks, file_remarks, args.source_dir, args.output_dir, should_display_hotness)