4 ms·
How does this work? I want to wrap POSIX semaphores. You call sem_init, passing it the address of an int; later you call sem_destroy and pass it the same addres
by ridiculous_fish 4y ago
How does this work? I want to wrap POSIX semaphores. You call sem_init, passing it the address of an int; later you call sem_destroy and pass it the same address. So the location of the int must not change.
In C++ you would delete the move constructor:
struct sema {
int v;
void sema(sema &&) = delete;
};
In Rust you might try this, but it doesn't work:
struct Sema {
v: Pin<i32>,
}
there is no way to create a "Pin<i32>". The closest you can get is probably to malloc it:
struct Sema {
v: Pin<Box<i32>>
}
but now Pin is adding nothing at all (except perhaps a hint to the reader) and may be deleted. The real guarantee is provided by Box, not Pin.
It looks to me like Pin is created to support async, and outside of that use case is not very useful, and is a poor replacement for non-movable types.
- Ygg2 4y ago> there is no way to create a "Pin<i32>" Caveat, I haven't worked with Pin that much. Take this with a grain of salt. My understanding is - you really shouldn't put copyable stuff in Pin. Period. If you want something like that wrap i32 in new struct and declare it !Unpin. Since negative traits are unstable, you just write PhantomPinned marker struct NonPinI32 { v: i32, non_pin: PhantomPinned, }
- steveklabnik 4y agopin is purely a property of a pointer, so Pin<i32> doesn’t make sense. While you’re right that Box gives you a stable address, you can still move out of a Box, or swap something into the Box. Pin<Box<P>> prevents that.