From 1f2614c60b663faa66a4cda4adeb14fff6efd1cb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?R=C3=A9mi=20Bernon?= Date: Tue, 25 Jan 2022 10:13:37 +0100 Subject: [PATCH] widl: Fix nested parameterized types C / short name output. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit We append type->name from each parameter when constructing the c_name of parameterized type. When the parameter is itself a parameterized type this field contains C++-like name, with template brackets. Instead this precomputes the names of parameterized types whenever they are used as a parameter. In this case the format is the same as the C name, except that __C is used as a namespace separator, instead of _C, and that there's no namespace or abi prefix included. Shorthands need to be applied too, altough they have to match the __C. Signed-off-by: RĂ©mi Bernon Signed-off-by: Alexandre Julliard --- tools/widl/typetree.c | 28 ++++++++++++++++++++-------- tools/widl/widltypes.h | 11 ++++++----- 2 files changed, 26 insertions(+), 13 deletions(-) diff --git a/tools/widl/typetree.c b/tools/widl/typetree.c index f45b6281b01..e1fab1e5525 100644 --- a/tools/widl/typetree.c +++ b/tools/widl/typetree.c @@ -53,6 +53,7 @@ type_t *make_type(enum type_type type) t->signature = NULL; t->qualified_name = NULL; t->impl_name = NULL; + t->param_name = NULL; t->short_name = NULL; memset(&t->details, 0, sizeof(t->details)); t->typestring_offset = 0; @@ -291,29 +292,36 @@ char *format_parameterized_type_name(type_t *type, typeref_list_t *params) } static char const *parameterized_type_shorthands[][2] = { + {"Windows__CFoundation__CCollections__C", "__F"}, {"Windows_CFoundation_CCollections_C", "__F"}, + {"Windows__CFoundation__C", "__F"}, {"Windows_CFoundation_C", "__F"}, }; -static char *format_parameterized_type_c_name(type_t *type, typeref_list_t *params, const char *prefix) +static char *format_parameterized_type_c_name(type_t *type, typeref_list_t *params, const char *prefix, const char *separator) { + const char *tmp, *ns_prefix = "__x_", *abi_prefix = NULL; size_t len = 0, pos = 0; - char *buf = NULL, *tmp; + char *buf = NULL; int i, count = params ? list_count(params) : 0; typeref_t *ref; - pos += append_namespaces(&buf, &len, pos, type->namespace, "__x_", "_C", "", use_abi_namespace ? "ABI" : NULL); + if (!strcmp(separator, "__C")) ns_prefix = "_C"; + else if (use_abi_namespace) abi_prefix = "ABI"; + + pos += append_namespaces(&buf, &len, pos, type->namespace, ns_prefix, separator, "", abi_prefix); pos += strappend(&buf, &len, pos, "%s%s_%d", prefix, type->name, count); if (params) LIST_FOR_EACH_ENTRY(ref, params, typeref_t, entry) { type = type_pointer_get_root_type(ref->type); - pos += append_namespaces(&buf, &len, pos, type->namespace, "_", "__C", type->name, NULL); + if ((tmp = type->param_name)) pos += strappend(&buf, &len, pos, "_%s", tmp); + else pos += append_namespaces(&buf, &len, pos, type->namespace, "_", "__C", type->name, NULL); } for (i = 0; i < ARRAY_SIZE(parameterized_type_shorthands); ++i) { if ((tmp = strstr(buf, parameterized_type_shorthands[i][0])) && - (tmp - buf) == strlen(use_abi_namespace ? "__x_ABI_C" : "__x_C")) + (tmp - buf) == strlen(ns_prefix) + (abi_prefix ? 5 : 0)) { tmp += strlen(parameterized_type_shorthands[i][0]); strcpy(buf, parameterized_type_shorthands[i][1]); @@ -358,7 +366,8 @@ static char *format_parameterized_type_short_name(type_t *type, typeref_list_t * if (params) LIST_FOR_EACH_ENTRY(ref, params, typeref_t, entry) { type = type_pointer_get_root_type(ref->type); - pos += strappend(&buf, &len, pos, "_%s", type->name); + if (type->short_name) pos += strappend(&buf, &len, pos, "_%s", type->short_name); + else pos += strappend(&buf, &len, pos, "_%s", type->name); } return buf; @@ -895,8 +904,10 @@ static void compute_delegate_iface_names(type_t *delegate, type_t *type, typeref type_t *iface = delegate->details.delegate.iface; iface->namespace = delegate->namespace; iface->name = strmake("I%s", delegate->name); - if (type) iface->c_name = format_parameterized_type_c_name(type, params, "I"); + if (type) iface->c_name = format_parameterized_type_c_name(type, params, "I", "_C"); else iface->c_name = format_namespace(delegate->namespace, "__x_", "_C", iface->name, use_abi_namespace ? "ABI" : NULL); + if (type) iface->param_name = format_parameterized_type_c_name(type, params, "I", "__C"); + else iface->param_name = format_namespace(delegate->namespace, "_", "__C", iface->name, NULL); iface->qualified_name = format_namespace(delegate->namespace, "", "::", iface->name, use_abi_namespace ? "ABI" : NULL); } @@ -1218,8 +1229,9 @@ type_t *type_parameterized_type_specialize_declare(type_t *type, typeref_list_t new_type->namespace = type->namespace; new_type->name = format_parameterized_type_name(type, params); reg_type(new_type, new_type->name, new_type->namespace, 0); - new_type->c_name = format_parameterized_type_c_name(type, params, ""); + new_type->c_name = format_parameterized_type_c_name(type, params, "", "_C"); new_type->short_name = format_parameterized_type_short_name(type, params, ""); + new_type->param_name = format_parameterized_type_c_name(type, params, "", "__C"); if (new_type->type_type == TYPE_DELEGATE) { diff --git a/tools/widl/widltypes.h b/tools/widl/widltypes.h index e345730731a..0d88e713433 100644 --- a/tools/widl/widltypes.h +++ b/tools/widl/widltypes.h @@ -483,7 +483,7 @@ enum type_type }; struct _type_t { - const char *name; + const char *name; /* C++ name with parameters in brackets */ struct namespace *namespace; enum type_type type_type; attr_list_t *attrs; @@ -504,11 +504,12 @@ struct _type_t { struct parameterized_details parameterized; struct delegate_details delegate; } details; - const char *c_name; + const char *c_name; /* mangled C name, with namespaces and parameters */ const char *signature; - const char *qualified_name; - const char *impl_name; - const char *short_name; + const char *qualified_name; /* C++ fully qualified name */ + const char *impl_name; /* C++ parameterized types impl base class name */ + const char *param_name; /* used to build c_name of a parameterized type, when used as a parameter */ + const char *short_name; /* widl specific short name */ unsigned int typestring_offset; unsigned int ptrdesc; /* used for complex structs */ int typelib_idx;