Commit 5b2f63ca authored by Robert Bradshaw's avatar Robert Bradshaw

C++ templating fixes.

parent bd9e529d
...@@ -477,6 +477,19 @@ class CArrayDeclaratorNode(CDeclaratorNode): ...@@ -477,6 +477,19 @@ class CArrayDeclaratorNode(CDeclaratorNode):
child_attrs = ["base", "dimension"] child_attrs = ["base", "dimension"]
def analyse(self, base_type, env, nonempty = 0): def analyse(self, base_type, env, nonempty = 0):
if base_type.is_cpp_class:
from ExprNodes import TupleNode
if isinstance(self.dimension, TupleNode):
args = self.dimension.args
else:
args = self.dimension,
values = [v.analyse_as_type(env) for v in args]
if None in values:
ix = values.index(None)
error(args[ix].pos, "Template parameter not a type.")
return error_type
base_type = base_type.specialize_here(self.pos, values)
return self.base.analyse(base_type, env, nonempty = nonempty)
if self.dimension: if self.dimension:
self.dimension.analyse_const_expression(env) self.dimension.analyse_const_expression(env)
if not self.dimension.type.is_int: if not self.dimension.type.is_int:
......
...@@ -1832,6 +1832,7 @@ class CppClassType(CType): ...@@ -1832,6 +1832,7 @@ class CppClassType(CType):
self.operators = [] self.operators = []
self.templates = templates self.templates = templates
self.template_type = template_type self.template_type = template_type
self.specializations = {}
def specialize_here(self, pos, template_values = None): def specialize_here(self, pos, template_values = None):
if self.templates is None: if self.templates is None:
...@@ -1844,10 +1845,14 @@ class CppClassType(CType): ...@@ -1844,10 +1845,14 @@ class CppClassType(CType):
return self.specialize(dict(zip(self.templates, template_values))) return self.specialize(dict(zip(self.templates, template_values)))
def specialize(self, values): def specialize(self, values):
# TODO(danilo): Cache for efficiency. key = tuple(values.items())
if key in self.specializations:
return self.specializations[key]
template_values = [t.specialize(values) for t in self.templates] template_values = [t.specialize(values) for t in self.templates]
return CppClassType(self.name, self.scope.specialize(values), self.cname, self.base_classes, specialized = self.specializations[key] = \
template_values, template_type=self) CppClassType(self.name, None, self.cname, self.base_classes, template_values, template_type=self)
specialized.scope = self.scope.specialize(values)
return specialized
def declaration_code(self, entity_code, for_display = 0, dll_linkage = None, pyrex = 0): def declaration_code(self, entity_code, for_display = 0, dll_linkage = None, pyrex = 0):
if self.templates: if self.templates:
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment