Module: wine Branch: master Commit: f8684cf953c5aae31e0b2858ab839e702b7cff20 URL: https://source.winehq.org/git/wine.git/?a=commit;h=f8684cf953c5aae31e0b2858a...
Author: Rémi Bernon rbernon@codeweavers.com Date: Fri Feb 5 10:11:00 2021 +0100
widl: Factor and cleanup interface type declaration and definition.
Signed-off-by: Rémi Bernon rbernon@codeweavers.com Signed-off-by: Jacek Caban jacek@codeweavers.com Signed-off-by: Alexandre Julliard julliard@winehq.org
---
tools/widl/parser.y | 34 ++++++++++------------------------ tools/widl/typetree.c | 19 ++++++++++++++++++- tools/widl/typetree.h | 4 +++- 3 files changed, 31 insertions(+), 26 deletions(-)
diff --git a/tools/widl/parser.y b/tools/widl/parser.y index 1505e3e88a0..44716deb5b6 100644 --- a/tools/widl/parser.y +++ b/tools/widl/parser.y @@ -87,7 +87,6 @@ static void push_lookup_namespace(const char *name); static void check_arg_attrs(const var_t *arg); static void check_statements(const statement_list_t *stmts, int is_inside_library); static void check_all_user_types(const statement_list_t *stmts); -static attr_list_t *check_iface_attrs(const char *name, attr_list_t *attrs); static attr_list_t *check_function_attrs(const char *name, attr_list_t *attrs); static attr_list_t *check_typedef_attrs(attr_list_t *attrs); static attr_list_t *check_enum_attrs(attr_list_t *attrs); @@ -281,7 +280,6 @@ static typelib_t *current_typelib; %type <expr> m_expr expr expr_const expr_int_const array m_bitfield %type <expr_list> m_exprs /* exprs expr_list */ expr_list_int_const %type <expr> contract_req -%type <type> interfacehdr %type <stgclass> storage_cls_spec %type <type_qualifier> type_qualifier m_type_qual_list %type <function_specifier> function_specifier @@ -971,31 +969,20 @@ inherit: { $$ = NULL; } | ':' qualified_type { $$ = $2; } ;
-interface: tINTERFACE aIDENTIFIER { $$ = get_type(TYPE_INTERFACE, $2, current_namespace, 0); } - | tINTERFACE aKNOWNTYPE { $$ = get_type(TYPE_INTERFACE, $2, current_namespace, 0); } +interface: + tINTERFACE aIDENTIFIER { $$ = type_interface_declare($2, current_namespace); } + | tINTERFACE aKNOWNTYPE { $$ = type_interface_declare($2, current_namespace); } ;
-interfacehdr: attributes interface { $$ = $2; - check_def($2); - $2->attrs = check_iface_attrs($2->name, $1); - $2->defined = TRUE; - } - ; - -interfacedef: interfacehdr inherit - '{' int_statements '}' semicolon_opt { $$ = $1; - if($$ == $2) - error_loc("Interface can't inherit from itself\n"); - type_interface_define($$, $2, $4); +interfacedef: attributes interface inherit + '{' int_statements '}' semicolon_opt { $$ = type_interface_define($2, $1, $3, $5); check_async_uuid($$); } /* MIDL is able to import the definition of a base class from inside the * definition of a derived class, I'll try to support it with this rule */ - | interfacehdr ':' aIDENTIFIER + | attributes interface ':' aIDENTIFIER '{' import int_statements '}' - semicolon_opt { $$ = $1; - type_interface_define($$, find_type_or_error($3), $6); - } + semicolon_opt { $$ = type_interface_define($2, $1, find_type_or_error($4), $7); } | dispinterfacedef semicolon_opt { $$ = $1; } ;
@@ -2340,7 +2327,7 @@ const char *get_attr_display_name(enum attr_type type) return allowed_attr[type].display_name; }
-static attr_list_t *check_iface_attrs(const char *name, attr_list_t *attrs) +attr_list_t *check_interface_attrs(const char *name, attr_list_t *attrs) { const attr_t *attr; if (!attrs) return attrs; @@ -2978,8 +2965,7 @@ static void check_async_uuid(type_t *iface) if (!inherit) error_loc("async_uuid applied to an interface with incompatible parent\n");
- async_iface = get_type(TYPE_INTERFACE, strmake("Async%s", iface->name), iface->namespace, 0); - async_iface->attrs = map_attrs(iface->attrs, async_iface_attrs); + async_iface = type_interface_declare(strmake("Async%s", iface->name), iface->namespace);
STATEMENTS_FOR_EACH_FUNC( stmt, type_iface_get_stmts(iface) ) { @@ -3010,7 +2996,7 @@ static void check_async_uuid(type_t *iface) stmts = append_statement(stmts, make_statement_declaration(finish_func)); }
- type_interface_define(async_iface, inherit, stmts); + type_interface_define(async_iface, map_attrs(iface->attrs, async_iface_attrs), inherit, stmts); iface->details.iface->async_iface = async_iface->details.iface->async_iface = async_iface; }
diff --git a/tools/widl/typetree.c b/tools/widl/typetree.c index 825348ddef4..84be75fa3b7 100644 --- a/tools/widl/typetree.c +++ b/tools/widl/typetree.c @@ -442,8 +442,24 @@ static unsigned int compute_method_indexes(type_t *iface) return idx; }
-void type_interface_define(type_t *iface, type_t *inherit, statement_list_t *stmts) +type_t *type_interface_declare(char *name, struct namespace *namespace) { + type_t *type = get_type(TYPE_INTERFACE, name, namespace, 0); + if (type_get_type_detect_alias(type) != TYPE_INTERFACE) + error_loc("interface %s previously not declared an interface at %s:%d\n", + type->name, type->loc_info.input_name, type->loc_info.line_number); + return type; +} + +type_t *type_interface_define(type_t *iface, attr_list_t *attrs, type_t *inherit, statement_list_t *stmts) +{ + if (iface->defined) + error_loc("interface %s already defined at %s:%d\n", + iface->name, iface->loc_info.input_name, iface->loc_info.line_number); + if (iface == inherit) + error_loc("interface %s can't inherit from itself\n", + iface->name); + iface->attrs = check_interface_attrs(iface->name, attrs); iface->details.iface = xmalloc(sizeof(*iface->details.iface)); iface->details.iface->disp_props = NULL; iface->details.iface->disp_methods = NULL; @@ -453,6 +469,7 @@ void type_interface_define(type_t *iface, type_t *inherit, statement_list_t *stm iface->details.iface->async_iface = NULL; iface->defined = TRUE; compute_method_indexes(iface); + return iface; }
void type_dispinterface_define(type_t *iface, var_list_t *props, var_list_t *methods) diff --git a/tools/widl/typetree.h b/tools/widl/typetree.h index 8a8e1c529ac..7b67f3b996a 100644 --- a/tools/widl/typetree.h +++ b/tools/widl/typetree.h @@ -30,6 +30,7 @@ enum name_type { };
attr_list_t *check_coclass_attrs(const char *name, attr_list_t *attrs); +attr_list_t *check_interface_attrs(const char *name, attr_list_t *attrs); attr_list_t *check_runtimeclass_attrs(const char *name, attr_list_t *attrs);
type_t *type_new_function(var_list_t *args); @@ -48,7 +49,8 @@ type_t *type_new_nonencapsulated_union(const char *name, int defined, var_list_t type_t *type_new_encapsulated_union(char *name, var_t *switch_field, var_t *union_field, var_list_t *cases); type_t *type_new_bitfield(type_t *field_type, const expr_t *bits); type_t *type_runtimeclass_declare(char *name, struct namespace *namespace); -void type_interface_define(type_t *iface, type_t *inherit, statement_list_t *stmts); +type_t *type_interface_declare(char *name, struct namespace *namespace); +type_t *type_interface_define(type_t *iface, attr_list_t *attrs, type_t *inherit, statement_list_t *stmts); void type_dispinterface_define(type_t *iface, var_list_t *props, var_list_t *methods); void type_dispinterface_define_from_iface(type_t *dispiface, type_t *iface); void type_module_define(type_t *module, statement_list_t *stmts);