Skip to content

Improve concat_str C implementation#1350

Open
Timmmm wants to merge 1 commit intorems-project:sail2from
Timmmm:user/timh/str_cat_improvement
Open

Improve concat_str C implementation#1350
Timmmm wants to merge 1 commit intorems-project:sail2from
Timmmm:user/timh/str_cat_improvement

Conversation

@Timmmm
Copy link
Copy Markdown
Contributor

@Timmmm Timmmm commented Jun 12, 2025

This is more optimal in some cases (especially appending to a string).

It's very fiddly code though and I haven't tested it, so feel free to ignore this!

This is more optimal in some cases (especially appending to a string).

It's very fiddly code though and I haven't tested it, so feel free to ignore this!
@github-actions
Copy link
Copy Markdown

Test Results

   13 files     28 suites   0s ⏱️
  882 tests   882 ✅ 0 💤 0 ❌
4 091 runs  4 091 ✅ 0 💤 0 ❌

Results for commit 638d4e6.

Comment thread lib/sail.c
Comment on lines +224 to +230
if (str2_is_output) {
// Must memmove within stro because str2 has been invalidated
// and the source and destination may overlap.
memmove(*stro + in1_len, *stro, in2_len + 1);
} else {
in2 = (sail_string)str2;
// str2 is valid and a different string to stro so we can just copy.
memcpy(*stro + in1_len, str2, in2_len + 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.

memmove already does this kind of check so doing it here doesn't really add any efficiency. memcpy might even be an alias - I'd just unconditionally call memmove and keep the comment that they might overlap so we can't use memcpy

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.

Yep, but I made the mistake of unconditionally using memmove(*stro + in1_len, str2, in2_len + 1); in an earlier version and that was incorrect because the realloc may have freed str2. So the primary reason for the if() here is whether to copy from *stro or str2.

This is a perfect example of why Rust exists!

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.

That's a fair point I didn't see you were changing the source pointer.

@Alasdair
Copy link
Copy Markdown
Collaborator

Alasdair commented Jul 1, 2025

I think we have a test case that is hitting this case, and they are all run with UBSan and address sanitiser in CI, so I'm pretty sure this is safe, and repeatedly appending is our most common use-case.

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