Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Unusual shared_ptr use in copy_file #66

Closed
nyalloc opened this issue Jun 11, 2020 · 3 comments
Closed

Unusual shared_ptr use in copy_file #66

nyalloc opened this issue Jun 11, 2020 · 3 comments
Labels
enhancement New feature or request
Milestone

Comments

@nyalloc
Copy link

nyalloc commented Jun 11, 2020

The copy_file function uses shared_ptr as a RAII wrapper around close through a custom deleter.

std::shared_ptr<void> guard_in(nullptr, [in](void*) { ::close(in); });

std::shared_ptr<void> guard_out(nullptr, [out](void*) { ::close(out); });

It seems like this code is using shared_ptr as a mechanism for RAII. shared_ptr isn't necessarily free: it will likely allocate storage for the lamdas and their captures because it has to type erase the custom deleter internally. I find it confusing to see shared_ptr used this way. This is not really its intended use, so the intent of the code wasn't really clear on my first read.

I don't see why RAII is advantageous here: it would make sense if any of the functions called in copy_file could throw, because the destructor would ensure close is called. However, the function is noexcept. If anything throws in here, the application will be terminated anyway.

This is just something I noticed while I was digging around the source. I could submit a PR addressing these comments if you agree with them. Otherwise, I'd be really interested to hear why the code is written like this.

Cheers!

@gulrak
Copy link
Owner

gulrak commented Jun 11, 2020

You are right, this isn't the best place to use this pattern because of the noexcept. The reason it's in there is, that (as written in the readme under "Motivation") this library was not started in 2018 from scratch but I used a filesystem library I wrote in 2011 that much more loosely followed the boost::filesystem interface, when I tried to make my projects less third-party-depending.
It was part of a project to get deeper into C++11, and I used the "shared_ptr for RAII" pattern more often that time. The code was not noexcept at that time either, as I didn't have an error_code version at that time, so it used exceptions from inside the copy loop.

When reworking that code base into a std::filesystem api-conforming one, I simply didn't refactored that one out. And actually there was even a bug from that reworking, as originally the shared pointer order was swapped and and a a PR (#20) at least fixed that. Overall the code is not as homogeneous as I would wish, as it is from almost a decade of living code and style changes over the years. I hope to do some cleanup rounds over time, but I'm still quite happy considering the amount of work needed to complete the compatibility level I strived to achieve.

So yeah, it works, but I should clean that up. And a PR for that will be gladly integrated, as I'm currently quite busy at my job. In any way, thanks for looking through it! I'm always thankful for input to make this library a better piece of helpful software.

@gulrak gulrak added the enhancement New feature or request label Jun 11, 2020
@nyalloc
Copy link
Author

nyalloc commented Jun 11, 2020

Thanks for the explanation! I understand, libraries like this often have colourful histories. I'll gladly have a look into this and draft a PR when I have some free time.

@gulrak gulrak added this to the v1.3.4 milestone Aug 22, 2020
@gulrak
Copy link
Owner

gulrak commented Aug 30, 2020

Rework released with v1.3.4

@gulrak gulrak closed this as completed Aug 30, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

2 participants