blob: f16b182219994a85eeef3b2f3701eb90b6b120a2 [file] [log] [blame]
Brad Bishopbf066a62016-10-19 08:09:44 -04001#!/usr/bin/env python
2
3import sys
4import os
5import re
6import argparse
7import yaml
Brad Bishopcfb3c892016-11-12 11:43:37 -05008import subprocess
Brad Bishop92665b22016-10-26 20:51:16 -05009from mako.template import Template
Brad Bishopbf066a62016-10-19 08:09:44 -040010
11valid_c_name_pattern = re.compile('[\W_]+')
Brad Bishopbf066a62016-10-19 08:09:44 -040012
13
Brad Bishop92665b22016-10-26 20:51:16 -050014def parse_event(e):
15 e['name'] = valid_c_name_pattern.sub('_', e['name']).lower()
16 if e.get('filter') is None:
17 e.setdefault('filter', {}).setdefault('type', 'none')
18 if e.get('action') is None:
19 e.setdefault('action', {}).setdefault('type', 'noop')
20 return e
Brad Bishopbf066a62016-10-19 08:09:44 -040021
Brad Bishopcfb3c892016-11-12 11:43:37 -050022
Brad Bishopbf066a62016-10-19 08:09:44 -040023if __name__ == '__main__':
Brad Bishop79d8f7a2016-11-09 22:40:57 -050024 script_dir = os.path.dirname(os.path.realpath(__file__))
25
Brad Bishopbf066a62016-10-19 08:09:44 -040026 parser = argparse.ArgumentParser(
27 description='Phosphor Inventory Manager (PIM) YAML '
28 'scanner and code generator.')
29 parser.add_argument(
Brad Bishop4d16b692016-11-12 11:45:35 -050030 '-o', '--output-dir', dest='outputdir',
31 default='.', help='Output directory.')
Brad Bishopbf066a62016-10-19 08:09:44 -040032 parser.add_argument(
33 '-d', '--dir', dest='inputdir',
Brad Bishopf30db4c2016-11-09 22:47:05 -050034 default=os.path.join(script_dir, 'example'),
Brad Bishop09fc2562016-10-21 22:58:08 -040035 help='Location of files to process.')
Brad Bishopbf066a62016-10-19 08:09:44 -040036
37 args = parser.parse_args()
38
Brad Bishop3904cf42016-11-12 12:00:03 -050039 # Aggregate all the event YAML in the events.d directory
Brad Bishopcfb3c892016-11-12 11:43:37 -050040 # into a single list of events.
Brad Bishop3904cf42016-11-12 12:00:03 -050041 events_dir = os.path.join(args.inputdir, 'events.d')
Brad Bishopbf066a62016-10-19 08:09:44 -040042 yaml_files = filter(
43 lambda x: x.endswith('.yaml'),
Brad Bishopbbf13bd2016-11-09 22:29:09 -050044 os.listdir(events_dir))
Brad Bishopbf066a62016-10-19 08:09:44 -040045
Brad Bishop92665b22016-10-26 20:51:16 -050046 events = []
47 for x in yaml_files:
Brad Bishopbbf13bd2016-11-09 22:29:09 -050048 with open(os.path.join(events_dir, x), 'r') as fd:
Brad Bishop92665b22016-10-26 20:51:16 -050049 for e in yaml.load(fd.read()).get('events', {}):
50 events.append(parse_event(e))
Brad Bishopbf066a62016-10-19 08:09:44 -040051
Brad Bishopcfb3c892016-11-12 11:43:37 -050052 # Import interfaces.yaml.
Brad Bishopbbf13bd2016-11-09 22:29:09 -050053 with open(os.path.join(args.inputdir, 'interfaces.yaml'), 'r') as fd:
Brad Bishop561a5652016-10-26 21:13:32 -050054 interfaces = yaml.load(fd.read())
55
Brad Bishopcfb3c892016-11-12 11:43:37 -050056 # Render the template with the provided events and interfaces.
57 template = os.path.join(script_dir, 'generated.mako.cpp')
58 t = Template(filename=template)
Brad Bishop4d16b692016-11-12 11:45:35 -050059 with open(os.path.join(args.outputdir, 'generated.cpp'), 'w') as fd:
Brad Bishop92665b22016-10-26 20:51:16 -050060 fd.write(
61 t.render(
Brad Bishop561a5652016-10-26 21:13:32 -050062 interfaces=interfaces,
Brad Bishop92665b22016-10-26 20:51:16 -050063 events=events))
64
Brad Bishopcfb3c892016-11-12 11:43:37 -050065 # Invoke sdbus++ to generate any extra interface bindings for
66 # extra interfaces that aren't defined externally.
67 yaml_files = []
68 extra_ifaces_dir = os.path.join(args.inputdir, 'interfaces')
69 if os.path.exists(extra_ifaces_dir):
70 for directory, _, files in os.walk(extra_ifaces_dir):
71 if not files:
72 continue
73
74 yaml_files += map(
75 lambda f: os.path.relpath(
76 os.path.join(directory, f),
77 extra_ifaces_dir),
78 filter(lambda f: f.endswith('.interface.yaml'), files))
79
80 genfiles = {
81 'server-cpp': lambda x: '%s.cpp' % (
82 x.replace(os.sep, '.')),
83 'server-header': lambda x: os.path.join(
84 os.path.join(
85 *x.split('.')), 'server.hpp')
86 }
87
88 for i in yaml_files:
89 iface = i.replace('.interface.yaml', '').replace(os.sep, '.')
90 for process, f in genfiles.iteritems():
91
92 dest = os.path.join(args.outputdir, f(iface))
93 parent = os.path.dirname(dest)
94 if parent and not os.path.exists(parent):
95 os.makedirs(parent)
96
97 with open(dest, 'w') as fd:
98 subprocess.call([
99 'sdbus++',
100 '-r',
101 extra_ifaces_dir,
102 'interface',
103 process,
104 iface],
105 stdout=fd)
Brad Bishopbf066a62016-10-19 08:09:44 -0400106
107# vim: tabstop=8 expandtab shiftwidth=4 softtabstop=4