widl: Do not write type definitions for types defined in an imported header.

midl does not, and this would result in redefinition errors.

An equivalent (and arguably a bit more declarative) way to do this would be to
keep track in the parser whether a type or typedef statement is actually a
definition or not, and record that information in the statement_t. However, this
would require passing additional information alongside the type_t from each
relevant bison rule, which would thrash a lot of code.
This commit is contained in:
Elizabeth Figura 2024-03-25 18:37:42 -05:00 committed by Alexandre Julliard
parent 1db2eaf0b3
commit 93d50fd9de
3 changed files with 6 additions and 3 deletions

View file

@ -1359,7 +1359,7 @@ type:
typedef: m_attributes tTYPEDEF m_attributes decl_spec declarator_list typedef: m_attributes tTYPEDEF m_attributes decl_spec declarator_list
{ $1 = append_attribs($1, $3); { $1 = append_attribs($1, $3);
reg_typedefs( @$, $4, $5, check_typedef_attrs( $1 ) ); reg_typedefs( @$, $4, $5, check_typedef_attrs( $1 ) );
$$ = make_statement_typedef($5, $4->type->defined); $$ = make_statement_typedef($5, $4->type->defined && !$4->type->defined_in_import);
} }
; ;
@ -1719,7 +1719,7 @@ static var_t *declare_var(attr_list_t *attrs, decl_spec_t *decl_spec, declarator
v->declspec.type = decl->type; v->declspec.type = decl->type;
v->declspec.qualifier = decl->qualifier; v->declspec.qualifier = decl->qualifier;
v->attrs = attrs; v->attrs = attrs;
v->is_defined = type->defined; v->is_defined = type->defined && !type->defined_in_import;
if (is_attr(type->attrs, ATTR_CALLCONV) && !is_func(type)) if (is_attr(type->attrs, ATTR_CALLCONV) && !is_func(type))
error_loc("calling convention applied to non-function type\n"); error_loc("calling convention applied to non-function type\n");
@ -2833,7 +2833,7 @@ static statement_t *make_statement_type_decl(type_t *type)
{ {
statement_t *stmt = make_statement(STMT_TYPE); statement_t *stmt = make_statement(STMT_TYPE);
stmt->u.type = type; stmt->u.type = type;
stmt->is_defined = type->defined; stmt->is_defined = type->defined && !type->defined_in_import;
return stmt; return stmt;
} }

View file

@ -536,6 +536,7 @@ static void define_type(type_t *type, const struct location *where)
error_loc("type %s already defined at %s:%d\n", type->name, type->where.input_name, type->where.first_line ); error_loc("type %s already defined at %s:%d\n", type->name, type->where.input_name, type->where.first_line );
type->defined = TRUE; type->defined = TRUE;
type->defined_in_import = parse_only;
type->where = *where; type->where = *where;
} }
@ -935,6 +936,7 @@ type_t *type_delegate_define(type_t *delegate, attr_list_t *attrs,
iface->details.iface->disp_inherit = NULL; iface->details.iface->disp_inherit = NULL;
iface->details.iface->async_iface = NULL; iface->details.iface->async_iface = NULL;
iface->details.iface->requires = NULL; iface->details.iface->requires = NULL;
define_type(iface, where);
iface->defined = TRUE; iface->defined = TRUE;
compute_method_indexes(iface); compute_method_indexes(iface);

View file

@ -523,6 +523,7 @@ struct _type_t {
struct location where; struct location where;
unsigned int ignore : 1; unsigned int ignore : 1;
unsigned int defined : 1; unsigned int defined : 1;
unsigned int defined_in_import : 1;
unsigned int written : 1; unsigned int written : 1;
unsigned int user_types_registered : 1; unsigned int user_types_registered : 1;
unsigned int tfswrite : 1; /* if the type needs to be written to the TFS */ unsigned int tfswrite : 1; /* if the type needs to be written to the TFS */