Skip to content

Fix class template translations#195

Open
joaotgouveia wants to merge 3 commits into
Cpp2Rust:masterfrom
joaotgouveia:class-templates
Open

Fix class template translations#195
joaotgouveia wants to merge 3 commits into
Cpp2Rust:masterfrom
joaotgouveia:class-templates

Conversation

@joaotgouveia

Copy link
Copy Markdown
Contributor

Fixes how class templates are translated.

Class templates are currently monomorphized:

bool Converter::VisitClassTemplateDecl(clang::ClassTemplateDecl *decl) {
for (auto decl : decl->specializations()) {
VisitCXXRecordDecl(decl);
}
return false;
}

However, the name of each translated Rust struct was the plain C++ name, leading to collisions.

Additionally, the C++ name used in the translation rule inserted into Mapper was also the plain C++ name.
This name does not match how the type itself is printed, which led to internal cpp2rust assertion failures due to missing translation rules.

Comment thread tests/unit/class_templates.cpp Outdated

MyContainer<float> fmc;
assert(fmc.empty());
fmc.push_back('a');

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

1.0?

Comment thread cpp2rust/converter/mapper.cpp Outdated

std::string ToRustName(std::string name) {
size_t pos = 0;
std::string chars = "<>, ";

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe Mapper::ToString is a better place to do these replaces. We already have some similar replaces that we do to normalize the output

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ToString handles converting a given C++ construct to its corresponding string representation, whereas ToRustName is responsible for transforming the string representation of an arbitrary C++ construct into a valid Rust name. Given this distinction, wouldn't it be clearer to keep these two functions separate?

Additionally, this normalization is only required when we want to use the string representation of a given C++ construct as a Rust name. It is not required for the other uses of ToString, such as obtaining the string representation of a construct in order to look up or insert a translation rule.

Comment thread cpp2rust/converter/mapper.cpp Outdated
size_t pos = 0;
std::string chars = "<>, ";
while ((pos = name.find_first_of(chars, pos)) != std::string::npos) {
name.replace(pos, 1, 1, '_');

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

name[pos] = '_';

Comment thread cpp2rust/converter/mapper.cpp Outdated

std::string ToRustName(std::string name) {
size_t pos = 0;
std::string chars = "<>, ";

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

remove this var to avoid allocations (inline in find_first_of)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants