1'''
2XML parser.  One function for each top-level element in the schema.
3
4Most functions just declare a new object and add it to the module.
5For typedefs, eventcopies, xidtypes, and other aliases though,
6we do not create a new type object, we just record the existing one under a new name.
7'''
8
9from os.path import join
10from xml.etree.cElementTree import parse
11
12from xcbgen.xtypes import *
13
14def import_(node, module, namespace):
15    '''
16    For imports, we load the file, create a new namespace object,
17    execute recursively, then record the import (for header files, etc.)
18    '''
19    # To avoid circular import error
20    from xcbgen import state
21    module.import_level = module.import_level + 1
22    new_file = join(namespace.dir, '%s.xml' % node.text)
23    new_root = parse(new_file).getroot()
24    new_namespace = state.Namespace(new_file)
25    execute(module, new_namespace)
26    module.import_level = module.import_level - 1
27    if not module.has_import(node.text):
28        module.add_import(node.text, new_namespace)
29
30def typedef(node, module, namespace):
31    id = node.get('newname')
32    name = namespace.prefix + (id,)
33    type = module.get_type(node.get('oldname'))
34    module.add_type(id, namespace.ns, name, type)
35
36def xidtype(node, module, namespace):
37    id = node.get('name')
38    name = namespace.prefix + (id,)
39    type = module.get_type('CARD32')
40    module.add_type(id, namespace.ns, name, type)
41
42def xidunion(node, module, namespace):
43    id = node.get('name')
44    name = namespace.prefix + (id,)
45    type = module.get_type('CARD32')
46    module.add_type(id, namespace.ns, name, type)
47
48def enum(node, module, namespace):
49    id = node.get('name')
50    name = namespace.prefix + (id,)
51    type = Enum(name, node)
52    module.add_type(id, namespace.ns, name, type)
53
54def struct(node, module, namespace):
55    id = node.get('name')
56    name = namespace.prefix + (id,)
57    type = Struct(name, node)
58    module.add_type(id, namespace.ns, name, type)
59
60def union(node, module, namespace):
61    id = node.get('name')
62    name = namespace.prefix + (id,)
63    type = Union(name, node)
64    module.add_type(id, namespace.ns, name, type)
65
66def request(node, module, namespace):
67    id = node.get('name')
68    name = namespace.prefix + (id,)
69    type = Request(name, node)
70    module.add_request(id, name, type)
71
72def event(node, module, namespace):
73    id = node.get('name')
74    name = namespace.prefix + (id,)
75    event = Event(name, node)
76    event.add_opcode(node.get('number'), name, True)
77    module.add_event(id, name, event)
78
79def eventcopy(node, module, namespace):
80    id = node.get('name')
81    name = namespace.prefix + (id,)
82    event = module.get_event(node.get('ref'))
83    event.add_opcode(node.get('number'), name, False)
84    module.add_event(id, name, event)
85
86def error(node, module, namespace):
87    id = node.get('name')
88    name = namespace.prefix + (id,)
89    error = Error(name, node)
90    error.add_opcode(node.get('number'), name, True)
91    module.add_error(id, name, error)
92
93def errorcopy(node, module, namespace):
94    id = node.get('name')
95    name = namespace.prefix + (id,)
96    error = module.get_error(node.get('ref'))
97    error.add_opcode(node.get('number'), name, False)
98    module.add_error(id, name, error)
99
100funcs = {'import' : import_,
101         'typedef' : typedef,
102         'xidtype' : xidtype,
103         'xidunion' : xidunion,
104         'enum' : enum,
105         'struct' : struct,
106         'union' : union,
107         'request' : request,
108         'event' : event,
109         'eventcopy' : eventcopy,
110         'error' : error,
111         'errorcopy' : errorcopy}
112
113def execute(module, namespace):
114    for elt in list(namespace.root):
115        funcs[elt.tag](elt, module, namespace)
116