Changeset View
Changeset View
Standalone View
Standalone View
tools/c-constants-gen.py
1 | #!/usr/bin/python | 1 | #!/usr/bin/python | ||
---|---|---|---|---|---|
2 | 2 | | |||
3 | from sys import argv, stdout, stderr | 3 | from sys import argv, stdout, stderr | ||
4 | import xml.dom.minidom | 4 | import xml.dom.minidom | ||
5 | 5 | | |||
6 | from libtpcodegen import file_set_contents, u | ||||
6 | from libglibcodegen import NS_TP, get_docstring, \ | 7 | from libglibcodegen import NS_TP, get_docstring, \ | ||
7 | get_descendant_text, get_by_path | 8 | get_descendant_text, get_by_path | ||
8 | 9 | | |||
9 | class Generator(object): | 10 | class Generator(object): | ||
10 | def __init__(self, prefix, dom): | 11 | def __init__(self, prefix, dom, output_base): | ||
11 | self.prefix = prefix + '_' | 12 | self.prefix = prefix + '_' | ||
12 | self.spec = get_by_path(dom, "spec")[0] | 13 | self.spec = get_by_path(dom, "spec")[0] | ||
13 | 14 | | |||
15 | self.output_base = output_base | ||||
16 | self.__header = [] | ||||
17 | self.__docs = [] | ||||
18 | | ||||
14 | def __call__(self): | 19 | def __call__(self): | ||
15 | self.do_header() | 20 | self.do_header() | ||
16 | self.do_body() | 21 | self.do_body() | ||
17 | self.do_footer() | 22 | self.do_footer() | ||
18 | 23 | | |||
24 | file_set_contents(self.output_base + '.h', u('').join(self.__header).encode('utf-8')) | ||||
25 | file_set_contents(self.output_base + '-gtk-doc.h', u('').join(self.__docs).encode('utf-8')) | ||||
26 | | ||||
19 | def write(self, code): | 27 | def write(self, code): | ||
20 | stdout.write(code.encode('utf-8')) | 28 | self.__header.append(code) | ||
29 | | ||||
30 | def d(self, code): | ||||
31 | self.__docs.append(code) | ||||
21 | 32 | | |||
22 | # Header | 33 | # Header | ||
23 | def do_header(self): | 34 | def do_header(self): | ||
24 | self.write('/* Generated from ') | 35 | self.write('/* Generated from ') | ||
25 | self.write(get_descendant_text(get_by_path(self.spec, 'title'))) | 36 | self.write(get_descendant_text(get_by_path(self.spec, 'title'))) | ||
26 | version = get_by_path(self.spec, "version") | 37 | version = get_by_path(self.spec, "version") | ||
27 | if version: | 38 | if version: | ||
28 | self.write(', version ' + get_descendant_text(version)) | 39 | self.write(', version ' + get_descendant_text(version)) | ||
Show All 20 Lines | 57 | for elem in self.spec.getElementsByTagNameNS(NS_TP, '*'): | |||
49 | elif elem.localName == 'enum': | 60 | elif elem.localName == 'enum': | ||
50 | self.do_enum(elem) | 61 | self.do_enum(elem) | ||
51 | 62 | | |||
52 | def do_flags(self, flags): | 63 | def do_flags(self, flags): | ||
53 | name = flags.getAttribute('plural') or flags.getAttribute('name') | 64 | name = flags.getAttribute('plural') or flags.getAttribute('name') | ||
54 | value_prefix = flags.getAttribute('singular') or \ | 65 | value_prefix = flags.getAttribute('singular') or \ | ||
55 | flags.getAttribute('value-prefix') or \ | 66 | flags.getAttribute('value-prefix') or \ | ||
56 | flags.getAttribute('name') | 67 | flags.getAttribute('name') | ||
57 | self.write("""\ | 68 | self.d("""\ | ||
58 | /** | 69 | /** | ||
59 | * | 70 | * %s: | ||
60 | %s: | | |||
61 | """ % (self.prefix + name).replace('_', '')) | 71 | """ % (self.prefix + name).replace('_', '')) | ||
62 | for flag in get_by_path(flags, 'flag'): | 72 | for flag in get_by_path(flags, 'flag'): | ||
63 | self.do_gtkdoc(flag, value_prefix) | 73 | self.do_gtkdoc(flag, value_prefix) | ||
64 | self.write(' *\n') | 74 | self.d(' *\n') | ||
65 | docstrings = get_by_path(flags, 'docstring') | 75 | docstrings = get_by_path(flags, 'docstring') | ||
66 | if docstrings: | 76 | if docstrings: | ||
67 | self.write("""\ | 77 | self.d("""\ | ||
68 | * <![CDATA[%s]]> | 78 | * <![CDATA[%s]]> | ||
69 | * | 79 | * | ||
70 | """ % get_descendant_text(docstrings).replace('\n', ' ')) | 80 | """ % get_descendant_text(docstrings).replace('\n', ' ')) | ||
71 | self.write("""\ | 81 | self.d("""\ | ||
72 | * Bitfield/set of flags generated from the Telepathy specification. | 82 | * Bitfield/set of flags generated from the Telepathy specification. | ||
73 | */ | 83 | */ | ||
74 | typedef enum { | | |||
75 | """) | 84 | """) | ||
85 | | ||||
86 | self.write("typedef enum /*< flags >*/ {\n") | ||||
87 | | ||||
76 | for flag in get_by_path(flags, 'flag'): | 88 | for flag in get_by_path(flags, 'flag'): | ||
77 | self.do_val(flag, value_prefix) | 89 | self.do_val(flag, value_prefix) | ||
78 | self.write("""\ | 90 | self.write("""\ | ||
79 | } %s; | 91 | } %s; | ||
80 | 92 | | |||
81 | """ % (self.prefix + name).replace('_', '')) | 93 | """ % (self.prefix + name).replace('_', '')) | ||
82 | 94 | | |||
83 | def do_enum(self, enum): | 95 | def do_enum(self, enum): | ||
84 | name = enum.getAttribute('singular') or enum.getAttribute('name') | 96 | name = enum.getAttribute('singular') or enum.getAttribute('name') | ||
85 | value_prefix = enum.getAttribute('singular') or \ | 97 | value_prefix = enum.getAttribute('singular') or \ | ||
86 | enum.getAttribute('value-prefix') or \ | 98 | enum.getAttribute('value-prefix') or \ | ||
87 | enum.getAttribute('name') | 99 | enum.getAttribute('name') | ||
88 | name_plural = enum.getAttribute('plural') or \ | 100 | name_plural = enum.getAttribute('plural') or \ | ||
89 | enum.getAttribute('name') + 's' | 101 | enum.getAttribute('name') + 's' | ||
90 | self.write("""\ | 102 | self.d("""\ | ||
91 | /** | 103 | /** | ||
92 | * | 104 | * %s: | ||
93 | %s: | | |||
94 | """ % (self.prefix + name).replace('_', '')) | 105 | """ % (self.prefix + name).replace('_', '')) | ||
95 | vals = get_by_path(enum, 'enumvalue') | 106 | vals = get_by_path(enum, 'enumvalue') | ||
96 | for val in vals: | 107 | for val in vals: | ||
97 | self.do_gtkdoc(val, value_prefix) | 108 | self.do_gtkdoc(val, value_prefix) | ||
98 | self.write(' *\n') | 109 | self.d(' *\n') | ||
99 | docstrings = get_by_path(enum, 'docstring') | 110 | docstrings = get_by_path(enum, 'docstring') | ||
100 | if docstrings: | 111 | if docstrings: | ||
101 | self.write("""\ | 112 | self.d("""\ | ||
102 | * <![CDATA[%s]]> | 113 | * <![CDATA[%s]]> | ||
103 | * | 114 | * | ||
104 | """ % get_descendant_text(docstrings).replace('\n', ' ')) | 115 | """ % get_descendant_text(docstrings).replace('\n', ' ')) | ||
105 | self.write("""\ | 116 | self.d("""\ | ||
106 | * Bitfield/set of flags generated from the Telepathy specification. | 117 | * Bitfield/set of flags generated from the Telepathy specification. | ||
107 | */ | 118 | */ | ||
108 | typedef enum { | | |||
109 | """) | 119 | """) | ||
120 | | ||||
121 | self.write("typedef enum {\n") | ||||
122 | | ||||
110 | for val in vals: | 123 | for val in vals: | ||
111 | self.do_val(val, value_prefix) | 124 | self.do_val(val, value_prefix) | ||
112 | self.write("""\ | 125 | self.write("} %s;\n" % (self.prefix + name).replace('_', '')) | ||
113 | } %(mixed-name)s; | | |||
114 | 126 | | |||
127 | self.d("""\ | ||||
115 | /** | 128 | /** | ||
116 | * NUM_%(upper-plural)s: | 129 | * %(upper-prefix)sNUM_%(upper-plural)s: | ||
117 | * | 130 | * | ||
118 | * 1 higher than the highest valid value of #%(mixed-name)s. | 131 | * 1 higher than the highest valid value of #%(mixed-name)s. | ||
119 | */ | 132 | */ | ||
120 | #define NUM_%(upper-plural)s (%(last-val)s+1) | 133 | | ||
134 | /** | ||||
135 | * NUM_%(upper-prefix)s%(upper-plural)s: (skip) | ||||
136 | * | ||||
137 | * 1 higher than the highest valid value of #%(mixed-name)s. | ||||
138 | * In new code, use %(upper-prefix)sNUM_%(upper-plural)s instead. | ||||
139 | */ | ||||
140 | """ % {'mixed-name' : (self.prefix + name).replace('_', ''), | ||||
141 | 'upper-prefix' : self.prefix.upper(), | ||||
142 | 'upper-plural' : name_plural.upper(), | ||||
143 | 'last-val' : vals[-1].getAttribute('value')}) | ||||
144 | | ||||
145 | self.write("""\ | ||||
146 | #define %(upper-prefix)sNUM_%(upper-plural)s (%(last-val)s+1) | ||||
147 | #define NUM_%(upper-prefix)s%(upper-plural)s %(upper-prefix)sNUM_%(upper-plural)s | ||||
121 | 148 | | |||
122 | """ % {'mixed-name' : (self.prefix + name).replace('_', ''), | 149 | """ % {'mixed-name' : (self.prefix + name).replace('_', ''), | ||
123 | 'upper-plural' : (self.prefix + name_plural).upper(), | 150 | 'upper-prefix' : self.prefix.upper(), | ||
151 | 'upper-plural' : name_plural.upper(), | ||||
124 | 'last-val' : vals[-1].getAttribute('value')}) | 152 | 'last-val' : vals[-1].getAttribute('value')}) | ||
125 | 153 | | |||
126 | def do_val(self, val, value_prefix): | 154 | def do_val(self, val, value_prefix): | ||
127 | name = val.getAttribute('name') | 155 | name = val.getAttribute('name') | ||
128 | suffix = val.getAttribute('suffix') | 156 | suffix = val.getAttribute('suffix') | ||
129 | use_name = (self.prefix + value_prefix + '_' + \ | 157 | use_name = (self.prefix + value_prefix + '_' + \ | ||
130 | (suffix or name)).upper() | 158 | (suffix or name)).upper() | ||
131 | assert not (name and suffix) or name == suffix, \ | 159 | assert not (name and suffix) or name == suffix, \ | ||
132 | 'Flag/enumvalue name %s != suffix %s' % (name, suffix) | 160 | 'Flag/enumvalue name %s != suffix %s' % (name, suffix) | ||
133 | self.write(' %s = %s,\n' % (use_name, val.getAttribute('value'))) | 161 | self.write(' %s = %s,\n' % (use_name, val.getAttribute('value'))) | ||
134 | 162 | | |||
135 | def do_gtkdoc(self, node, value_prefix): | 163 | def do_gtkdoc(self, node, value_prefix): | ||
136 | self.write(' * @') | 164 | self.d(' * @') | ||
137 | self.write((self.prefix + value_prefix + '_' + | 165 | self.d((self.prefix + value_prefix + '_' + | ||
138 | node.getAttribute('suffix')).upper()) | 166 | node.getAttribute('suffix')).upper()) | ||
139 | self.write(': <![CDATA[') | 167 | self.d(': <![CDATA[') | ||
140 | docstring = get_by_path(node, 'docstring') | 168 | docstring = get_by_path(node, 'docstring') | ||
141 | self.write(get_descendant_text(docstring).replace('\n', ' ')) | 169 | self.d(get_descendant_text(docstring).replace('\n', ' ')) | ||
142 | self.write(']]>\n') | 170 | self.d(']]>\n') | ||
143 | 171 | | |||
144 | # Footer | 172 | # Footer | ||
145 | def do_footer(self): | 173 | def do_footer(self): | ||
146 | self.write(""" | 174 | self.write(""" | ||
147 | #ifdef __cplusplus | 175 | #ifdef __cplusplus | ||
148 | } | 176 | } | ||
149 | #endif | 177 | #endif | ||
150 | """) | 178 | """) | ||
151 | 179 | | |||
152 | if __name__ == '__main__': | 180 | if __name__ == '__main__': | ||
153 | argv = argv[1:] | 181 | argv = argv[1:] | ||
154 | Generator(argv[0], xml.dom.minidom.parse(argv[1]))() | 182 | Generator(argv[0], xml.dom.minidom.parse(argv[1]), argv[2])() |