s.interface_blocks.clear();
r_any_resolved = false;
s.content.visit(*this);
- for(VariableDeclaration *v: redeclared_builtins)
- v->source = GENERATED_SOURCE;
+ for(Statement *b: redeclared_builtins)
+ b->source = GENERATED_SOURCE;
NodeRemover().apply(s, nodes_to_remove);
return r_any_resolved;
}
void VariableResolver::visit(VariableDeclaration &var)
{
TraversingVisitor::visit(var);
- VariableDeclaration *&ptr = current_block->variables[var.name];
- if(!ptr)
- ptr = &var;
- else if(!current_block->parent && ptr->interface==var.interface && ptr->type==var.type)
+
+ auto i = current_block->variables.find(var.name);
+ VariableDeclaration *existing = 0;
+ InterfaceBlock *block = 0;
+ if(i!=current_block->variables.end())
+ existing = i->second;
+ else if(!current_block->parent)
{
- if(ptr->source==BUILTIN_SOURCE)
- {
- redeclared_builtins.push_back(ptr);
+ const map<string, InterfaceBlock *> &blocks = stage->interface_blocks;
+ for(auto j=blocks.begin(); j!=blocks.end(); ++j)
+ if(j->second->instance_name.empty() && j->second->struct_declaration)
+ {
+ map<string, VariableDeclaration *> &block_vars = j->second->struct_declaration->members.variables;
+ i = block_vars.find(var.name);
+ if(i!=block_vars.end())
+ {
+ existing = i->second;
+ block = j->second;
+ break;
+ }
+ }
+ }
+ if(!existing)
+ current_block->variables.insert(make_pair(var.name, &var));
+ else if(!current_block->parent && (block ? block->interface : existing->interface)==var.interface && existing->type==var.type && existing->array==var.array)
+ {
+ if(existing->source==BUILTIN_SOURCE)
+ {
if(var.layout)
{
- if(ptr->layout)
- merge_layouts(*ptr->layout, *var.layout);
+ if(existing->layout)
+ merge_layouts(*existing->layout, *var.layout);
else
- ptr->layout = var.layout;
+ existing->layout = var.layout;
}
if(var.array_size)
- ptr->array_size = var.array_size;
+ existing->array_size = var.array_size;
+
+ redeclared_builtins.push_back(existing);
+ if(block)
+ {
+ redeclared_builtins.push_back(block);
+ for(const auto &kvp: block->struct_declaration->members.variables)
+ redeclared_builtins.push_back(kvp.second);
+ }
nodes_to_remove.insert(&var);
r_any_resolved = true;
}
- else if(ptr->array && !ptr->array_size && !var.layout && !var.init_expression)
+ else if(existing->array && !existing->array_size && !var.layout && !var.init_expression)
{
- ptr->array_size = var.array_size;
+ existing->array_size = var.array_size;
nodes_to_remove.insert(&var);
r_any_resolved = true;
}