Skip to content

cstr16: add method to get the underlying bytes #788

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

Merged
merged 1 commit into from
May 5, 2023

Conversation

phip1611
Copy link
Member

@phip1611 phip1611 commented May 3, 2023

This fixes #787 by adding to_bytes_with_nul and to_bytes. The operations can also be called on CString16, as CString16 implements Deref<CStr16>.

Checklist

  • Sensible git history (for example, squash "typo" or "fix" commits). See the Rewriting History guide for help.
  • Update the changelog (if necessary)

impl Borrow<[u8]> for CStr16 {
fn borrow(&self) -> &[u8] {
self.to_bytes_with_nul()
}
Copy link
Member

Choose a reason for hiding this comment

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

I think it would be better to leave out the AsRef/Borrow impls, as it would not be as clear when reading the code as an explicit call to to_bytes_with_nul.

Copy link
Member Author

Choose a reason for hiding this comment

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

I'd much rather drop self.to_bytes() and rename self.to_bytes_with_nul() to self.to_bytes(). Then we can keep AsRef and Borrow. What do you think?

Copy link
Member

Choose a reason for hiding this comment

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

Yeah that sounds reasonable. Also, I didn't think of this before, but it should probably be as_bytes instead of to_bytes (per the conversion naming guidelines).

For Borrow and AsRef, do you have an example of how they'd get used in practice? Like <CStr16 as AsRef<[u8]>>::as_ref(string) is pretty verbose so I assume a user would usually prefer to write string.as_bytes(). But perhaps there's some generic code where the former would be more usable? An example would help me clear up my doubts since I always get a bit confused with those two very-similar-seeming traits.

Copy link
Member Author

@phip1611 phip1611 May 4, 2023

Choose a reason for hiding this comment

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

Sure. For example FileSystem::write() consumes content: impl AsRef<[u8]> as second parameter. This is equivalent to the standard lib's implementation.

Hence, you can just write a CStr16 to a file.

I only implemented both, AsRef and Borrow, as the standard library also does this for a lot of types (for example for std::path::Path). In my past years I've come accross a lot of code that used AsRef-types as parameters but Borrow only once or twice - Probably good to have both, tho.

Copy link
Member Author

@phip1611 phip1611 May 4, 2023

Choose a reason for hiding this comment

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

Update Hm, now I'm confused.. https://doc.rust-lang.org/core/ffi/struct.CStr.html provides to_bytes() and to_bytes_with_nul() methods, but those method implementations are cheap (other than the naming convention implies).

But I do not see a strong reason why we should be consistent with https://doc.rust-lang.org/core/ffi/struct.CStr.html .. but..on the other hand.. we can also stay consistent with std::ffi::CStr and provide to_bytes(), to_bytes_until_nul(), and drop AsRef and Borrow, as it might be confusing then.

Copy link
Member

Choose a reason for hiding this comment

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

Interesting. I would guess the reason is this:

Note: This method is currently implemented as a constant-time cast, but it is planned to alter its definition in the future to perform the length calculation whenever this method is called.

Several CStr methods make note that the implementation of the type may change in the future to make it more FFI friendly. Not sure how likely that is to ever actually happen.

I'm realizing I don't have a very strong opinion here :)

How about: just provide the as_bytes method (so no separate with/without null methods), and also include the AsRef and Borrow impls?

Copy link
Member Author

Choose a reason for hiding this comment

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

Done

@phip1611 phip1611 force-pushed the cstr16-as-bytes branch 3 times, most recently from 3d28228 to e0059b7 Compare May 5, 2023 13:48
@phip1611 phip1611 requested a review from nicholasbishop May 5, 2023 13:49
@phip1611 phip1611 merged commit ed34335 into rust-osdev:main May 5, 2023
@phip1611 phip1611 deleted the cstr16-as-bytes branch May 5, 2023 16:20
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.

as_bytes for CString16/CStr16
2 participants